xref: /haiku/src/kits/app/MessageUtils.cpp (revision fe88ae51ec00581a9c6e41f99de8a7f3b0f5a9d5)
1 /*
2  * Copyright 2001-2005, Haiku.
3  * Distributed under the terms of the MIT License.
4  *
5  * Authors:
6  *		Erik Jaesler (erik@cgsoftware.com)
7  */
8 
9 /**	Extra messaging utility functions */
10 
11 #include <string.h>
12 #include <ByteOrder.h>
13 
14 #include <MessageUtils.h>
15 
16 namespace BPrivate {
17 
18 uint32
CalculateChecksum(const uint8 * buffer,int32 size)19 CalculateChecksum(const uint8 *buffer, int32 size)
20 {
21 	uint32 sum = 0;
22 	uint32 temp = 0;
23 
24 	while (size > 3) {
25 		sum += B_BENDIAN_TO_HOST_INT32(*(int32 *)buffer);
26 		buffer += 4;
27 		size -= 4;
28 	}
29 
30 	while (size > 0) {
31 		temp = (temp << 8) + *buffer++;
32 		size -= 1;
33 	}
34 
35 	return sum + temp;
36 }
37 
38 
39 /* entry_ref support functions */
40 status_t
entry_ref_flatten(char * buffer,size_t * size,const entry_ref * ref)41 entry_ref_flatten(char *buffer, size_t *size, const entry_ref *ref)
42 {
43 	if (*size < sizeof(ref->device) + sizeof(ref->directory))
44 		return B_BUFFER_OVERFLOW;
45 
46 	memcpy((void *)buffer, (const void *)&ref->device, sizeof(ref->device));
47 	buffer += sizeof(ref->device);
48 	memcpy((void *)buffer, (const void *)&ref->directory, sizeof(ref->directory));
49 	buffer += sizeof(ref->directory);
50 	*size -= sizeof(ref->device) + sizeof(ref->directory);
51 
52 	size_t nameLength = 0;
53 	if (ref->name) {
54 		nameLength = strlen(ref->name) + 1;
55 		if (*size < nameLength)
56 			return B_BUFFER_OVERFLOW;
57 
58 		memcpy((void *)buffer, (const void *)ref->name, nameLength);
59 	}
60 
61 	*size = sizeof(ref->device) + sizeof(ref->directory) + nameLength;
62 
63 	return B_OK;
64 }
65 
66 
67 status_t
entry_ref_unflatten(entry_ref * ref,const char * buffer,size_t size)68 entry_ref_unflatten(entry_ref *ref, const char *buffer, size_t size)
69 {
70 	if (size < sizeof(ref->device) + sizeof(ref->directory)) {
71 		*ref = entry_ref();
72 		return B_BAD_VALUE;
73 	}
74 
75 	memcpy((void *)&ref->device, (const void *)buffer, sizeof(ref->device));
76 	buffer += sizeof(ref->device);
77 	memcpy((void *)&ref->directory, (const void *)buffer,
78 		sizeof(ref->directory));
79 	buffer += sizeof(ref->directory);
80 
81 	if (ref->device != ~(dev_t)0 && size > sizeof(ref->device)
82 			+ sizeof(ref->directory)) {
83 		ref->set_name(buffer);
84 		if (ref->name == NULL) {
85 			*ref = entry_ref();
86 			return B_NO_MEMORY;
87 		}
88 	} else
89 		ref->set_name(NULL);
90 
91 	return B_OK;
92 }
93 
94 
95 status_t
entry_ref_swap(char * buffer,size_t size)96 entry_ref_swap(char *buffer, size_t size)
97 {
98 	if (size < sizeof(dev_t) + sizeof(ino_t))
99 		return B_BAD_VALUE;
100 
101 	dev_t *dev = (dev_t *)buffer;
102 	*dev = B_SWAP_INT32(*dev);
103 	buffer += sizeof(dev_t);
104 
105 	ino_t *ino = (ino_t *)buffer;
106 	*ino = B_SWAP_INT64(*ino);
107 
108 	return B_OK;
109 }
110 
111 
112 /* node_ref support functions */
113 status_t
node_ref_flatten(char * buffer,size_t * size,const node_ref * ref)114 node_ref_flatten(char *buffer, size_t *size, const node_ref *ref)
115 {
116 	if (*size < sizeof(dev_t) + sizeof(ino_t))
117 		return B_BUFFER_OVERFLOW;
118 
119 	memcpy((void *)buffer, (const void *)&ref->device, sizeof(ref->device));
120 	buffer += sizeof(ref->device);
121 	memcpy((void *)buffer, (const void *)&ref->node, sizeof(ref->node));
122 	buffer += sizeof(ref->node);
123 
124 	return B_OK;
125 }
126 
127 
128 status_t
node_ref_unflatten(node_ref * ref,const char * buffer,size_t size)129 node_ref_unflatten(node_ref *ref, const char *buffer, size_t size)
130 {
131 	if (size < sizeof(dev_t) + sizeof(ino_t)) {
132 		*ref = node_ref();
133 		return B_BAD_VALUE;
134 	}
135 
136 	memcpy((void *)&ref->device, (const void *)buffer, sizeof(dev_t));
137 	buffer += sizeof(dev_t);
138 	memcpy((void *)&ref->node, (const void *)buffer, sizeof(ino_t));
139 	buffer += sizeof(ino_t);
140 
141 	return B_OK;
142 }
143 
144 
145 status_t
node_ref_swap(char * buffer,size_t size)146 node_ref_swap(char *buffer, size_t size)
147 {
148 	if (size < sizeof(dev_t) + sizeof(ino_t))
149 		return B_BAD_VALUE;
150 
151 	dev_t *dev = (dev_t *)buffer;
152 	*dev = B_SWAP_INT32(*dev);
153 	buffer += sizeof(dev_t);
154 
155 	ino_t *ino = (ino_t *)buffer;
156 	*ino = B_SWAP_INT64(*ino);
157 
158 	return B_OK;
159 }
160 
161 } // namespace BPrivate
162