最简单的TCP网络封包解包

本文介绍了TCP网络封包解包的原理和必要性,包括封包结构、包头和数据域。通过实例展示了服务器如何发送数据包,客户端如何接收并解包,以及处理粘包、半包问题。此外,提供了服务器和客户端的C++实现代码。
摘要由CSDN通过智能技术生成
TCP为什么需要进行封包解包?
        TCP采用字节流的方式,即以字节为单位传输字节序列。那么,我们recv到的就是一串毫无规则的字节流。如果要让这无规则的字节流有规则,那么,就需要我们去定义一个规则。那便是所谓的“封包规则”。

封包结构是怎么样的?
        封包就像是信,信是由:信封、信内容。两部分组成。而网络封包也是由两部分组成:包头、数据。包头域是定长的,数据域是不定长的。包头必然包含两个信息:操作码、包长度。包头可能还包含别的信息,这个呢就要视乎情况去定了。操作码是该网络数据包的标识符,这就和UI里面的事件ID什么的差不多。其中,操作码有的只有一级,有的则有两级甚至多级操作码,这个的设计也要看情况去了,不过,这些底层的东西,定好了,基本就不能动了,就像房子都砌起来了,再去动地基,那就欧也了。
以下是网络数据包的伪代码:
struct NetPacket
{
包头;
数据;
};
以下是包头的伪代码:
struct NetPacketHeader
{
操作码;
包长度;
};

收包中存在的一个问题(粘包,半包)
        在现实的网络情况中,网络传输往往是不可靠的,因此会有丢包之类的情况发生,对此,TCP相应的有一个重传的机制。对于接收者来说,它接收到的数据流中的数据有可能不是完整的数据包,或是只有一部分,或是粘着别的数据包,因此,接收者还需要对接收到的数据流的数据进行分包。

服务器客户端逻辑描述
        服务等待一个客户端的连接,客户端连接上了以后,服务器向客户端发送5个数据包,客户端接收服务器端的数据并解包然后做相应的逻辑处理。

需要注意的事项
1.服务器客户端是阻塞的,而不是非阻塞的套接字,这是为了简单;
2.当客户端收到了5个数据包之后,就主动和服务器断开连接,这个是硬代码;
3.阻塞套接字其实没有必要这样处理数据包,主要应用在非阻塞的套接字上;
4.此段代码只支持POD数据,不支持变长的情况;
5.各平台下字节对齐方式不一样,如Windows下默认字节对齐为4,这是此方式需要注意的。


服务器CPP代码:
None.gif
None.gif#include "stdafx.h"
None.gif#include "TCPServer.h"
None.gif
None.gifTCPServer::TCPServer()
None.gif: mServerSocket(INVALID_SOCKET)
ExpandedBlockStart.gif {
InBlock.gif     //  创建套接字
InBlock.gif
    mServerSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_IP);
InBlock.gif     if (mServerSocket == INVALID_SOCKET)
ExpandedSubBlockStart.gif    {
InBlock.gif        std::cout << "创建套接字失败!" << std::endl;
InBlock.gif         return;
ExpandedSubBlockEnd.gif    }
InBlock.gif
InBlock.gif     //  填充服务器的IP和端口号
InBlock.gif
    mServerAddr.sin_family        = AF_INET;
InBlock.gif    mServerAddr.sin_addr.s_addr    = INADDR_ANY;
InBlock.gif    mServerAddr.sin_port        = htons((u_short)SERVER_PORT);
InBlock.gif
InBlock.gif     //  绑定IP和端口
InBlock.gif
     if ( ::bind(mServerSocket, (sockaddr*)&mServerAddr,  sizeof(mServerAddr)) == SOCKET_ERROR)
ExpandedSubBlockStart.gif    {
InBlock.gif        std::cout << "绑定IP和端口失败!" << std::endl;
InBlock.gif         return;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值