[手游新项目历程]第9天-webSocket 包头:字符串129,二进制130

打包解包函数分享

int WebsocketProtocol::tryDeframeIncomingPacket( PushFramework::DataBuffer& buffer, PushFramework::IncomingPacket*& pPacket, int& serviceId, unsigned int& nExtractedBytes, ConnectionContext* pContext )
{
    if (buffer.GetDataSize() == 0)
        return Protocol::eIncompletePacket;

	WebsocketConnectionContext* pCxt = (WebsocketConnectionContext*) pContext;

	if (pCxt->GetStage() == WebsocketConnectionContext::HandshakeStage)
	{
		WebsocketHandshakeMessage* pMessage = new WebsocketHandshakeMessage(buffer.GetBuffer(), buffer.GetDataSize());
		serviceId = 0;
		nExtractedBytes = buffer.GetDataSize();
		pPacket = pMessage;
		return Protocol::Success;
	}

	//In the other cases, we should expect a data message : 
    int nMinExpectedSize = 6;
    if (buffer.GetDataSize() < nMinExpectedSize)
        return Protocol::eIncompletePacket;

    BYTE payloadFlags = buffer.getAt(0);
	if( (payloadFlags >> 7) == 0 )
	{
		return Protocol::eUndefinedFailure;
	}
	
	/*
    if (payloadFlags != 129)
        return Protocol::eUndefinedFailure;
	*/

    BYTE basicSize = buffer.getAt(1) & 0x7F;
    unsigned __int64 payloadSize;
    int masksOffset;

    if (basicSize <= 125)
    {
        payloadSize = basicSize;
        masksOffset = 2;
    }
    else if (basicSize == 126)
    {
        nMinExpectedSize += 2;
        if (buffer.GetDataSize() < nMinExpectedSize)
            return Protocol::eIncompletePacket;
        payloadSize = ntohs( *(u_short*) (buffer.GetBuffer() + 2) );
        masksOffset = 4;
    }
    else if (basicSize == 127)
    {
        nMinExpectedSize += 8;
        if (buffer.GetDataSize() < nMinExpectedSize)
            return Protocol::eIncompletePacket;
        payloadSize = ntohl( *(u_long*) (buffer.GetBuffer() + 2) );
        masksOffset = 10;
    }
    else
        return Protocol::eUndefinedFailure;

    nMinExpectedSize += payloadSize;
    if (buffer.GetDataSize() < nMinExpectedSize)
        return Protocol::eIncompletePacket;

	BYTE Len = 4;	//掩码的长度
    BYTE masks[4];
    memcpy(masks, buffer.GetBuffer() + masksOffset, 4);
	
    char* payload = new char[payloadSize + 1];
    memcpy(payload, buffer.GetBuffer() + masksOffset + Len, payloadSize);
	
    for (unsigned __int64 i = 0; i < payloadSize; i++) {
        payload[i] = (payload[i] ^ masks[i%4]);
    }

	payload[payloadSize] = '';

	WebsocketDataMessage* pMessage = new WebsocketDataMessage(payload);
	serviceId = 1;
	nExtractedBytes = nMinExpectedSize;
	pPacket = pMessage;

	delete payload;
	return Protocol::Success;
}

int WebsocketProtocol::frameOutgoingPacket( PushFramework::OutgoingPacket& packet, PushFramework::DataBuffer& buffer, unsigned int& nWrittenBytes, unsigned int size)
{
	WebsocketMessage& message = (WebsocketMessage&) packet;

	if (message.GetType() == WebsocketMessage::Handshake)
	{
		WebsocketHandshakeMessage& handshake = (WebsocketHandshakeMessage&) message;

        string strRaw = handshake.Serialize();
        if(strRaw.size() > buffer.getRemainingSize())
            return Protocol::eInsufficientBuffer;

        buffer.Append((char*)strRaw.c_str(), strRaw.size());
        nWrittenBytes = strRaw.size();
        return Protocol::Success;
	}

	if (message.GetType() == WebsocketMessage::DataMessage)
	{
		WebsocketDataMessage& dataMessage = (WebsocketDataMessage&) message;
        string strData = dataMessage.GetEncodedData();
		
		Stream stream;		//二进制写入
		int nSize = strData.size();
		if(size != 0)
		{
			nSize = size;
		}
		unsigned __int64 payloadSize = nSize;
		/*
		int expectedSize = payloadSize + 1; //统计包的长度
		if(payloadSize <= 125  && payloadSize <= 65535 )
			expectedSize += 1;
		else if(payloadSize > 125  && payloadSize <= 65535)
			expectedSize += 3;
		else
			expectedSize += 9;
		if (expectedSize > buffer.getRemainingSize())
			return Protocol::eInsufficientBuffer;
		*/
		//create the flags byte
		unsigned char payloadFlags = 130;//包头:字符串129,二进制130
		if(size == 0)
		{
			payloadFlags = 129;
		}
		if(size == 0)
		{
			buffer.WriteByte(payloadFlags);
		}
		else
		{
			stream.Write(payloadFlags);
		}
		int expectedSize = 1;			//统计包的长度

		//create the length byte
		if (payloadSize <= 125)
		{
			unsigned char basicSize = payloadSize;
			if(size == 0)
			{
				buffer.WriteByte(basicSize);
			}
			else
			{
				stream.Write(basicSize);
			}
			expectedSize += 1;
		}
		else if (/*payloadSize > 125 &&*/ payloadSize <= 65535)//by byfei 2017/02/20
		{
			unsigned char basicSize = 126;
			unsigned char len[2];
			len[0] = ( payloadSize >> 8 ) & 255;
			len[1] = ( payloadSize ) & 255;
			if(size == 0)
			{
				buffer.WriteByte(basicSize);
				buffer.WriteByte(len[0]);
				buffer.WriteByte(len[1]);
			}
			else
			{
				stream.Write(basicSize);
				stream.Write(len[0]);
				stream.Write(len[1]);
			}
			expectedSize += 3;
		}
		else
		{
			unsigned char basicSize = 127;
			char len[8];
			len[0] = ( payloadSize >> 56 ) & 255;
			len[1] = ( payloadSize >> 48  ) & 255;
			len[2] = ( payloadSize >> 40 ) & 255;
			len[3] = ( payloadSize >> 32  ) & 255;
			len[4] = ( payloadSize >> 24 ) & 255;
			len[5] = ( payloadSize >> 16  ) & 255;
			len[6] = ( payloadSize >> 8 ) & 255;
			len[7] = ( payloadSize ) & 255;
			if(size == 0)
			{
				buffer.WriteByte(basicSize);
				buffer.Append(len, 8);
			}
			else
			{
				stream.Write(basicSize);
				stream.WriteBuffer(len, 8);
			}
			expectedSize += 9;
		}
        //buffer.Append((char*)strData.c_str(), size);
		if(size != 0)
		{
			buffer.Append(stream.getBuf(), expectedSize);
			buffer.Append(dataMessage.getStream().getBuf(),nSize);
		}
		else
		{
			buffer.Append((char*)strData.c_str(), nSize);
		}
		expectedSize = payloadSize + expectedSize; //统计包的长度
        nWrittenBytes = expectedSize;
        return Protocol::Success;
	}
	
	return Protocol::eUndefinedFailure;
}

Google protobuf使用中的小陷阱  点击打开链接

Google Protocol Buffers浅析 点击打开链接

原文地址:https://www.cnblogs.com/byfei/p/14104299.html