查看: 340|回复: 1

网狐棋牌(五) TCPSocketEnging分析(3)

[复制链接]

8

主题

37

帖子

224

积分

vip会员

Rank: 1

积分
224
发表于 2020-3-27 16:17:20 | 显示全部楼层 |阅读模式
具体的看看接受代码:
// 接收完成函数
bool CServerSocketItem::OnRecvCompleted(COverLappedRecv * pOverLappedRecv, DWORD dwThancferred)
{
     // 效验数据
    ASSERT(m_bRecvIng== true);

     // 设置变量
    m_bRecvIng= false;
    m_dwRecvTickCount=GetTickCount();

     // 判断关闭
     if (m_hSocket==INVALID_SOCKET)
    {
        CloseSocket(m_wRountID);
         return  true;
    }

     // 接收数据
     int iRetCode=recv(m_hSocket,( char *)m_cbRecvBuf+m_wRecvSize, sizeof(m_cbRecvBuf)-m_wRecvSize,0);
     if (iRetCode<=0)
    {
        CloseSocket(m_wRountID);
         return  true;
    }

     // 接收完成
    m_wRecvSize+=iRetCode;
    BYTE cbBuffer[SOCKET_BUFFER];
    CMD_Head * pHead=(CMD_Head *)m_cbRecvBuf;

     // 处理数据
     try
    {
         while (m_wRecvSize>= sizeof(CMD_Head))
        {
             // 效验数据
            WORD wPacketSize=pHead->CmdInfo.wDataSize;
             if (wPacketSize>SOCKET_BUFFER)  throw TEXT("数据包超长");
             if (wPacketSize< sizeof(CMD_Head))  throw TEXT("数据包非法");
             if (pHead->CmdInfo.cbMessageVer!=SOCKET_VER)  throw TEXT("数据包版本错误");
             if (m_wRecvSize<wPacketSize)  break;

             // 提取数据
            CopyMemory(cbBuffer,m_cbRecvBuf,wPacketSize);
            WORD wRealySize=CrevasseBuffer(cbBuffer,wPacketSize);
            ASSERT(wRealySize>= sizeof(CMD_Head));
            m_dwRecvPacketCount++;

             // 解释数据
            WORD wDataSize=wRealySize- sizeof(CMD_Head);
             void * pDataBuffer=cbBuffer+ sizeof(CMD_Head);
            CMD_Command Command=((CMD_Head *)cbBuffer)->CommandInfo;

             // 内核命令
             if (Command.wMainCmdID==MDM_KN_COMMAND)
            {
                 switch (Command.wSubCmdID)
                {
                 case SUB_KN_DETECT_SOCKET:     // 网络检测
                    {
                         break;
                    }
                 default:  throw TEXT("非法命令码");
                }
            }
             else
            {
                 // 消息处理
                m_pIServerSocketItemSink->OnSocketReadEvent(Command,pDataBuffer,wDataSize, this);            
            }

             // 删除缓存数据
            m_wRecvSize-=wPacketSize;
            MoveMemory(m_cbRecvBuf,m_cbRecvBuf+wPacketSize,m_wRecvSize);
        }
    }
     catch ( 网狐棋牌(五) TCPSocketEnging分析(3))
    {
        CloseSocket(m_wRountID);
         return  false;
    }

     return RecvData();
}


这是还是有分包算法的,总的来说接受流程如下:
直接使用recv把数据接受到SocketItem的缓冲区中,当长度大于CMD_HEAD之后,进入处理阶段,处理head数据各种判断,然后将数据扔出去,再调整缓冲区,,,

简单的说:
Send完全不考虑同步问题,不管一个劲的网队列投递Send请求,,,这边处理队列也是直接Send完事,完全不考虑上一次是否send成功,,,
Recv更是莫名其妙的使用完成端口绕一圈还回到recv直接接受了,,,

回复

使用道具 举报

*滑块验证:
您需要登录后才可以回帖 登录 | enginedx注册

本版积分规则

 
 



邮件留言:


 
返回顶部