IOCP 投递recv 请求失败

mc_ran 2014-02-10 09:42:10
我目前在写一个服务器,有个客户端列表,客户端连接上服务器之后首先发送验证消息,如果验证成功在界面上现实某个客户端在线,现在出现这么个情况,我的服务端 开启之后,程序能够登陆,但是在程序不关闭的情况下,重启服务,当客户端再次连接之后,投递recv请求时候出现错误,错误代码 10057. 这个大概是什么原因??
...全文
169 5 打赏 收藏 转发到动态 举报
写回复
用AI写文章
5 条回复
切换为时间正序
请发表友善的回复…
发表回复
mc_ran 2014-02-11
  • 打赏
  • 举报
回复
别这么冷清撒
mc_ran 2014-02-11
  • 打赏
  • 举报
回复
来人啊。。。
mc_ran 2014-02-11
  • 打赏
  • 举报
回复
引用 2 楼 VisualEleven 的回复:
10057: A request to send or receive data was disallowed because the socket is not connected and (when sending on a datagram socket using a sendto call) no address was supplied. 你的SOCKET有效?是accept返回的有效的SOCKET句柄吗?
应该是吧,客户端的验证信息都已经发过来了,而且已经验证成功了... 代码如下:

bool CSocketServer::DoAccept(lpREQUEST_CONTEXT lpAcceptContext)
{
	SOCKADDR_IN * pClientAddr = NULL;
	SOCKADDR_IN * pLocalAddr  = NULL;

	int nSockAddrLen = sizeof(SOCKADDR_IN);
	m_lpfnGetAcceptExSockAddrs		//acceptex 之友 用来获取 客户端发送回来的第一组数据、本地地址信息,客户端地址信息
		(
		lpAcceptContext->wsaBuffer.buf,
		lpAcceptContext->wsaBuffer.len -( (nSockAddrLen + 16) * 2) ,
		nSockAddrLen  + 16 , 
		nSockAddrLen  + 16 , 
		(LPSOCKADDR*)&pLocalAddr  ,
		&nSockAddrLen , 
		(LPSOCKADDR*)&pClientAddr , 
		&nSockAddrLen
		);
	
	string   ip     = inet_ntoa(pClientAddr->sin_addr);
	int      port   = ntohs(pClientAddr->sin_port);
	SOCKET   sock   = GetAcceptContextSocket(lpAcceptContext);   //获取之前投递Accept请求时插入的socket
	APP_TYPE type	= GetClientType(lpAcceptContext->wsaBuffer.buf);

	if(  APP_NULL == type
		|| !IsLoginCmd(lpAcceptContext->wsaBuffer.buf))	 //如果验证失败
	{

		m_ploger->formatMsg("验证失败,断开连接:%s:%d.",ip.c_str(),port);

		RELEASE_SOCKET(sock);
	}
	else
	{
		lpSOCKET_CONTEXT pSocketContext = GetClientSockContext(type , ip.c_str());

		if(!pSocketContext)
		{
		    m_ploger->formatMsg("不存在该客户端,端类型:%s 地址:%s.",GetAppTypeName(type).c_str(),ip.c_str());
			RELEASE_SOCKET(sock);

		}
		else
		{
			pSocketContext->sock = sock;
			pSocketContext->ip   = ip;
			pSocketContext->port = port;
			pSocketContext->type = type;

			setsockopt(sock,
				SOL_SOCKET,
				SO_UPDATE_ACCEPT_CONTEXT,
				(char*)&m_plisenContext->sock,
				sizeof(m_plisenContext->sock)
				);

			CreateIoCompletionPort((HANDLE)sock,m_hIOCompletionPort,(DWORD)pSocketContext,0);

			SetClientOnline(pSocketContext);
			 
			m_ploger->formatMsg("客户端 类型:%s 地址:%s:%d 登陆成功.",GetAppTypeName(type).c_str(),
				ip.c_str(),port);

			 
			lpREQUEST_CONTEXT pRecvContext = pSocketContext->GetNewContext(REQUEST_RECV);

			if(!PostRecv(pSocketContext,pRecvContext))   //如果客户端投递recv请求失败,断开连接,并设置客户端离线
				SetClientUnline(pSocketContext);
		 
		}
		
	}
	return PostAccept(lpAcceptContext);
}

bool CSocketServer::PostRecv(lpSOCKET_CONTEXT pSockContext,lpREQUEST_CONTEXT lpRecvContext)
{
	lpRecvContext->ZeroBuffer();
	OVERLAPPED * pOverlapped = &lpRecvContext->overlapped;
	WSABUF     * pWsaBuffer	 = &lpRecvContext->wsaBuffer;

	DWORD dwFlags = 0;
	DWORD dwBytes = 0;

	int nBytesRecv = WSARecv( 
		pSockContext->sock,
		pWsaBuffer,
		1,
		&dwBytes,
		&dwFlags,
		pOverlapped,
		NULL
		);

	// 如果返回值错误,并且错误的代码并非是Pending的话,那就说明这个重叠请求失败了
	if ((SOCKET_ERROR == nBytesRecv) && (WSA_IO_PENDING != WSAGetLastError()))
	{
		m_ploger->formatMsg("客户端投递Recv请求失败 类型:%s 地址:%s,Socket错误代码:%d",
			GetAppTypeName(pSockContext->type).c_str(),pSockContext->ip.c_str(),WSAGetLastError());

		SetClientUnline(pSockContext);
		return false;
	}

	return true;
}
Eleven 2014-02-10
  • 打赏
  • 举报
回复
10057: A request to send or receive data was disallowed because the socket is not connected and (when sending on a datagram socket using a sendto call) no address was supplied. 你的SOCKET有效?是accept返回的有效的SOCKET句柄吗?
mc_ran 2014-02-10
  • 打赏
  • 举报
回复
....没人???

18,356

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 网络编程
c++c语言开发语言 技术论坛(原bbs)
社区管理员
  • 网络编程
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧