首页
社区
课程
招聘
[求助]完成端口的问题,请高手指点啊,谢谢
发表于: 2006-12-15 18:31 4387

[求助]完成端口的问题,请高手指点啊,谢谢

2006-12-15 18:31
4387
大侠门,为什么我的这个完成端口的服务端和客户端在连接的时候
服务段就一直向客户端发送消息,不停止,我简直没能力和实力解决,请大家帮帮我啊
谢谢
整个线程的函数处理如下:
DWORD WINAPI ServerWorkerThread(LPVOID CompletionPortID)
{
    HANDLE                    CompletionPort = (HANDLE)CompletionPortID;
    DWORD                         BytesTransferred;
        LPPER_HANDLE_DATA         pPerHandleData;
        LPPER_IO_OPERATION_DATA   pPerIoOperationData;
        DWORD                     flags;
        DWORD                     RecvBytes;
        DWORD                     SendBytes;

        while (TRUE)
        {
                bool Ret = GetQueuedCompletionStatus(CompletionPort, &BytesTransferred, (LPDWORD)&pPerHandleData, (LPOVERLAPPED *)&pPerIoOperationData, INFINITE);
                //退出信号到达,退出线程
                if (BytesTransferred==-1 && pPerIoOperationData==NULL)
                {
                        return 1L;
                }
                //客户机已经断开连接或者连接出现错误
                if ( BytesTransferred==0 && (pPerIoOperationData->_type == RECV_POSTED || pPerIoOperationData->_type == SEND_POSTED) )
                {
                        // 从Vector中删除客户端连接SOCKET
                    EnterCriticalSection(&cs);
                        for (it=SocketVector.begin(); it<SocketVector.end(); it++)
                        {
                                if ( (*it)._socket == pPerHandleData->_socket )
                                {
                                        SocketVector.erase(it);
                                        break;
                                }
                        }
                    LeaveCriticalSection(&cs);
                        // 关闭套接口
                        closesocket(pPerHandleData->_socket);
                        GlobalFree(pPerHandleData);
                        GlobalFree(pPerIoOperationData);
                        continue;
                }

                //发送完成,置空缓冲区,释放缓冲区
                if(pPerIoOperationData->_type == SEND_POSTED)
                {
                        memset(pPerIoOperationData, 0, sizeof(PER_IO_OPERATION_DATA));
                        GlobalFree(pPerIoOperationData);
                        BytesTransferred = 0;
                }

        //为读操作完成,处理数据
                if (pPerIoOperationData->_type == RECV_POSTED)
                {
                       
                        //处理数据//////////////////////////////////////////////////////////////////////                       
                        ZeroMemory(&(pPerIoOperationData->_overlapped), sizeof(OVERLAPPED));
                        pPerIoOperationData->_wsabuf.buf  =  pPerIoOperationData->buff;
                        pPerIoOperationData->_wsabuf.len  =  BUFFER_SIZE;
                        pPerIoOperationData->_type        =  SEND_POSTED;
                        EnterCriticalSection(&cs);  
                        for (it=SocketVector.begin(); it<SocketVector.end(); it++)
                        {
                                if (WSASend((*it)._socket, &(pPerIoOperationData->_wsabuf), 1, &SendBytes, 0, &(pPerIoOperationData->_overlapped), NULL) == SOCKET_ERROR)
                                 {
                                        if (WSAGetLastError() != ERROR_IO_PENDING)
                                        {
                                           printf("WSASend() failed with error %d\n", WSAGetLastError());
                                           return 0;
                                        }
                                 }
                        }
                        LeaveCriticalSection(&cs);               
                }
               

                // 将源数据置空
                memset(pPerIoOperationData->buff, 0, BUFFER_SIZE);
                BytesTransferred = 0;
                //重置IO操作数据
                ZeroMemory(&(pPerIoOperationData->_overlapped), sizeof(OVERLAPPED));
                pPerIoOperationData->_wsabuf.buf = pPerIoOperationData->buff;
                pPerIoOperationData->_wsabuf.len = BUFFER_SIZE;  
        pPerIoOperationData->_type       = RECV_POSTED;
                //提交另一个Recv请求
                WSARecv(pPerHandleData->_socket, &(pPerIoOperationData->_wsabuf), 1, &RecvBytes, &flags, &(pPerIoOperationData->_overlapped), NULL);
        }
        return 0;
}
代码如下:
谢谢大家的指点

[招生]科锐逆向工程师培训(2024年11月15日实地,远程教学同时开班, 第51期)

上传的附件:
收藏
免费 0
支持
分享
最新回复 (3)
雪    币: 235
活跃值: (100)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
2
我修正的部分代码

DWORD WINAPI ServerWorkerThread(LPVOID CompletionPortID)
{
        HANDLE                    CompletionPort = (HANDLE)CompletionPortID;
        DWORD                         BytesTransferred;
        LPPER_HANDLE_DATA         pPerHandleData;
        LPPER_IO_OPERATION_DATA   pPerIoOperationData;
        DWORD                     flags;
        DWORD                     RecvBytes;
        DWORD                     SendBytes;

        while (TRUE)
        {
                bool Ret = GetQueuedCompletionStatus(CompletionPort, &BytesTransferred, (LPDWORD)&pPerHandleData, (LPOVERLAPPED *)&pPerIoOperationData, INFINITE);
                //退出信号到达,退出线程
                if (BytesTransferred==-1 && pPerIoOperationData==NULL)
                {
                        return 1L;
                }
                //客户机已经断开连接或者连接出现错误
                if ( BytesTransferred==0 && (pPerIoOperationData->_type == RECV_POSTED || pPerIoOperationData->_type == SEND_POSTED) )
                {
                        // 从Vector中删除客户端连接SOCKET
                        EnterCriticalSection(&cs);
                        for (it=SocketVector.begin(); it<SocketVector.end(); it++)
                        {
                                if ( (*it)._socket == pPerHandleData->_socket )
                                {
                                        SocketVector.erase(it);
                                        break;
                                }
                        }
                        LeaveCriticalSection(&cs);
                        // 关闭套接口
                        closesocket(pPerHandleData->_socket);
                        GlobalFree(pPerHandleData);
                        GlobalFree(pPerIoOperationData);
                        continue;
                }

                switch(pPerIoOperationData->_type)
                {
                case RECV_POSTED:
                        {
                                //申请新的内存空间
                                PER_IO_OPERATION_DATA *SendIOData = (PER_IO_OPERATION_DATA *)GlobalAlloc(GPTR,sizeof(PER_IO_OPERATION_DATA));

                                SendIOData->_type = SEND_POSTED;
                                CopyMemory(SendIOData->buff,pPerIoOperationData->buff,BytesTransferred);
                                SendIOData->_wsabuf.buf = SendIOData->buff;
                                SendIOData->_wsabuf.len = BytesTransferred;

                                WSASend(pPerHandleData->_socket, &SendIOData->_wsabuf, 1, &SendBytes, 0, &SendIOData->_overlapped, NULL);
                                //////////////////////////////////////////////////////////////////////////////////

                                //重置重叠结构,为再次接收数据做准备
                                ZeroMemory(&(pPerIoOperationData->_overlapped), sizeof(OVERLAPPED));

                                pPerIoOperationData->_wsabuf.buf = pPerIoOperationData->buff;
                                pPerIoOperationData->_wsabuf.len = BUFFER_SIZE;  
                                pPerIoOperationData->_type       = RECV_POSTED;

                                flags = 0;
                                //提交另一个Recv请求
                                WSARecv(pPerHandleData->_socket, &(pPerIoOperationData->_wsabuf), 1, &RecvBytes, &flags, &(pPerIoOperationData->_overlapped), NULL);
                        }
                        break;
                case SEND_POSTED:
                        {
                                memset(pPerIoOperationData, 0, sizeof(PER_IO_OPERATION_DATA));
                                GlobalFree(pPerIoOperationData);
                                BytesTransferred = 0;
                        }
                        break;
                }
        }
        return 0;
}
2006-12-15 19:06
0
雪    币: 236
活跃值: (26)
能力值: ( LV8,RANK:130 )
在线值:
发帖
回帖
粉丝
3
就不是这个问题
这样改了还是有错的
2006-12-15 19:23
0
雪    币: 235
活跃值: (100)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
4
当我没改。。
2006-12-15 19:49
0
游客
登录 | 注册 方可回帖
返回
//