source: osgVisual/trunk/src/cluster/enet/packet.c @ 350

Last change on this file since 350 was 65, checked in by Torben Dannhauer, 14 years ago

new cluster implementation added: ENet
ENet is a reliable UDP implementation with quite simple usage and high performance for transmission with small or medium size packet.

File size: 3.7 KB
Line 
1/**
2 @file  packet.c
3 @brief ENet packet management functions
4*/
5#include <string.h>
6#define ENET_BUILDING_LIB 1
7#include "enet/enet.h"
8
9/** @defgroup Packet ENet packet functions
10    @{
11*/
12
13/** Creates a packet that may be sent to a peer.
14    @param dataContents initial contents of the packet's data; the packet's data will remain uninitialized if dataContents is NULL.
15    @param dataLength   size of the data allocated for this packet
16    @param flags        flags for this packet as described for the ENetPacket structure.
17    @returns the packet on success, NULL on failure
18*/
19ENetPacket *
20enet_packet_create (const void * data, size_t dataLength, enet_uint32 flags)
21{
22    ENetPacket * packet = (ENetPacket *) enet_malloc (sizeof (ENetPacket));
23    if (packet == NULL)
24      return NULL;
25
26    if (flags & ENET_PACKET_FLAG_NO_ALLOCATE)
27      packet -> data = (enet_uint8 *) data;
28    else
29    {
30       packet -> data = (enet_uint8 *) enet_malloc (dataLength);
31       if (packet -> data == NULL)
32       {
33          enet_free (packet);
34          return NULL;
35       }
36
37       if (data != NULL)
38         memcpy (packet -> data, data, dataLength);
39    }
40
41    packet -> referenceCount = 0;
42    packet -> flags = flags;
43    packet -> dataLength = dataLength;
44    packet -> freeCallback = NULL;
45
46    return packet;
47}
48
49/** Destroys the packet and deallocates its data.
50    @param packet packet to be destroyed
51*/
52void
53enet_packet_destroy (ENetPacket * packet)
54{
55    if (packet -> freeCallback != NULL)
56      (* packet -> freeCallback) (packet);
57    if (! (packet -> flags & ENET_PACKET_FLAG_NO_ALLOCATE))
58      enet_free (packet -> data);
59    enet_free (packet);
60}
61
62/** Attempts to resize the data in the packet to length specified in the
63    dataLength parameter
64    @param packet packet to resize
65    @param dataLength new size for the packet data
66    @returns 0 on success, < 0 on failure
67*/
68int
69enet_packet_resize (ENetPacket * packet, size_t dataLength)
70{
71    enet_uint8 * newData;
72   
73    if (dataLength <= packet -> dataLength || (packet -> flags & ENET_PACKET_FLAG_NO_ALLOCATE))
74    {
75       packet -> dataLength = dataLength;
76
77       return 0;
78    }
79
80    newData = (enet_uint8 *) enet_malloc (dataLength);
81    if (newData == NULL)
82      return -1;
83
84    memcpy (newData, packet -> data, packet -> dataLength);
85    enet_free (packet -> data);
86   
87    packet -> data = newData;
88    packet -> dataLength = dataLength;
89
90    return 0;
91}
92
93static int initializedCRC32 = 0;
94static enet_uint32 crcTable [256];
95
96static enet_uint32
97reflect_crc (int val, int bits)
98{
99    int result = 0, bit;
100
101    for (bit = 0; bit < bits; bit ++)
102    {
103        if(val & 1) result |= 1 << (bits - 1 - bit); 
104        val >>= 1;
105    }
106
107    return result;
108}
109
110static void 
111initialize_crc32 ()
112{
113    int byte;
114
115    for (byte = 0; byte < 256; ++ byte)
116    {
117        enet_uint32 crc = reflect_crc (byte, 8) << 24;
118        int offset;
119
120        for(offset = 0; offset < 8; ++ offset)
121        {
122            if (crc & 0x80000000)
123                crc = (crc << 1) ^ 0x04c11db7;
124            else
125                crc <<= 1;
126        }
127
128        crcTable [byte] = reflect_crc (crc, 32);
129    }
130
131    initializedCRC32 = 1;
132}
133   
134enet_uint32
135enet_crc32 (const ENetBuffer * buffers, size_t bufferCount)
136{
137    enet_uint32 crc = 0xFFFFFFFF;
138   
139    if (! initializedCRC32) initialize_crc32 ();
140
141    while (bufferCount -- > 0)
142    {
143        const enet_uint8 * data = (const enet_uint8 *) buffers -> data,
144                         * dataEnd = & data [buffers -> dataLength];
145
146        while (data < dataEnd)
147        {
148            crc = (crc >> 8) ^ crcTable [(crc & 0xFF) ^ *data++];       
149        }
150
151        ++ buffers;
152    }
153
154    return ENET_HOST_TO_NET_32 (~ crc);
155}
156
157/** @} */
Note: See TracBrowser for help on using the repository browser.