r108: merged files
[ctsim.git] / libctsupport / byteorder.cpp
1 #if HAVE_CONFIG_H
2 #include "config.h"
3 #endif
4
5 #if HAVE_UNISTD_H
6 #include <unistd.h>
7 #endif
8
9 #include "kstddef.h"
10 #include "byteorder.h"
11
12 inline void
13 SwapBytes2 (void* buffer)
14 {
15   unsigned char* p = static_cast<unsigned char*>(buffer);
16   unsigned char temp = p[0];
17   p[0] = p[1];
18   p[1] = temp;
19 }
20
21 // 0<->3  1<->2 = 0123 -> 3210
22 inline void
23 SwapBytes4 (void* buffer)
24 {
25   unsigned char* p = static_cast<unsigned char*>(buffer);
26   unsigned char temp = p[0];
27   p[0] = p[3];
28   p[3] = temp;
29   temp = p[1];
30   p[1] = p[2];
31   p[2] = temp;
32 }
33
34 // 0<->7 1<->6 2<->5 3<->4 = 01234567 -> 76543210
35 inline void
36 SwapBytes8 (void* buffer)
37 {
38   unsigned char* p = static_cast<unsigned char*>(buffer);
39   unsigned char temp = p[0];
40   p[0] = p[7];
41   p[7] = temp;
42   temp = p[1];
43   p[1] = p[6];
44   p[6] = temp;
45   temp = p[2];
46   p[2] = p[5];
47   p[5] = temp;
48   temp = p[3];
49   p[3] = p[4];
50   p[4] = temp;
51 }
52
53 void 
54 ConvertNetworkOrder (void* buffer, size_t bytes)
55 {
56 #if ! defined (WORDS_BIGENDIAN)
57     if (bytes < 2)
58         return;
59
60     char* start = static_cast<char*>(buffer);
61     char* end = start + bytes - 1;   // last byte
62     size_t nSwap = bytes / 2;
63     
64     while (nSwap-- > 0) {
65         unsigned char c = *start;
66         *start++ = *end;
67         *end-- = c;
68     }
69 #endif    
70 }
71
72 void 
73 ConvertReverseNetworkOrder (void* buffer, size_t bytes)
74 {
75 #if defined (WORDS_BIGENDIAN)
76     if (bytes < 2)
77         return;
78
79     char* start = static_cast<char*>(buffer);
80     char* end = start + bytes - 1;  // last byte 
81     size_t nSwap = bytes / 2;
82     
83     while (nSwap-- > 0) {
84         unsigned char c = *start;
85         *start++ = *end;
86         *end-- = c;
87     }
88 #endif    
89 }
90
91 bool
92 write_nint16 (kuint16 const *n_in, int fd)
93 {
94     kuint16 n = *n_in;
95
96 #ifndef WORDS_BIGENDIAN
97     SwapBytes2 (&n);
98 #endif
99
100     if (write (fd, &n, 2) != 2)
101         return false;
102     else
103         return true;
104 }
105
106 bool 
107 read_nint16 (kuint16 *n_out, int fd)
108 {
109     if (read (fd, n_out, 2) != 2)
110       return false;
111
112 #ifndef WORDS_BIGENDIAN
113     SwapBytes2 (n_out);
114 #endif
115     
116     return true;
117 }
118
119 bool 
120 write_nint32 (kuint32 const *n_in, int fd)
121 {
122     kuint32 n = *n_in;
123
124 #ifndef WORDS_BIGENDIAN
125     SwapBytes4(&n);
126 #endif
127
128     if (write (fd, &n, 4) != 4)
129       return false;
130     else
131       return true;
132 }
133
134 bool 
135 read_nint32 (kuint32 *n_out, int fd)
136 {
137   if (read (fd, n_out, 4) != 4)
138     return false;
139
140 #ifndef WORDS_BIGENDIAN
141   SwapBytes4 (n_out);
142 #endif
143
144     return true;
145 }
146
147 bool 
148 write_nfloat32 (kfloat32 const *f_in, int fd)
149 {
150   kfloat32 f = *f_in;
151
152 #ifndef WORDS_BIGENDIAN
153   SwapBytes4 (&f);
154 #endif
155
156   if (write (fd, &f, 4) != 4)
157     return false;
158   else
159     return true;
160 }
161
162 bool 
163 read_nfloat32 (kfloat32 *f_out, int fd)
164 {
165   if (read (fd, f_out, 4) != 4)
166     return false;
167
168 #ifndef WORDS_BIGENDIAN
169   SwapBytes4(f_out);
170 #endif
171
172   return true;
173 }
174
175 bool 
176 write_nfloat64 (kfloat64 const *f_in, int fd)
177 {
178   kfloat64 f = *f_in;
179
180 #ifndef WORDS_BIGENDIAN
181   SwapBytes8 (&f);
182 #endif
183
184   if (write (fd, &f, 8) != 8)
185     return false;
186   else
187     return true;
188 }
189
190 bool 
191 read_nfloat64 (kfloat64 *f_out, int fd)
192 {
193   if (read (fd, f_out, 8) != 8)
194     return false;
195
196 #ifndef WORDS_BIGENDIAN
197   SwapBytes8 (f_out);
198 #endif
199     
200   return true;
201 }
202
203
204
205 onetorderstream& onetorderstream::writeInt16 (kuint16 n) {
206 #ifndef WORDS_BIGENDIAN
207   SwapBytes2 (&n);
208 #endif
209   write (&n, 2);
210   return (*this);
211 }
212
213 inetorderstream& inetorderstream::readInt16 (kuint16& n) {
214   read (&n, 2);
215 #ifndef WORDS_BIGENDIAN
216   SwapBytes2 (&n);
217 #endif
218   return (*this);
219 }
220
221 onetorderstream& onetorderstream::writeInt32 (kuint32 n) {
222 #ifndef WORDS_BIGENDIAN
223   SwapBytes4(&n);
224 #endif
225   write (&n, 4);
226   return (*this);
227 }
228
229 inetorderstream& inetorderstream::readInt32 (kuint32& n) {
230   read (&n, 4);
231 #ifndef WORDS_BIGENDIAN
232   SwapBytes4 (&n);
233 #endif
234   return (*this);
235 }
236
237 onetorderstream& onetorderstream::writeFloat32 (kfloat32 n) {
238 #ifndef WORDS_BIGENDIAN
239   SwapBytes4 (&n);
240 #endif
241   write (&n, 4);
242   return (*this);
243 }
244
245 inetorderstream& inetorderstream::readFloat32 (kfloat32& n) {
246   read (&n, 4);
247 #ifndef WORDS_BIGENDIAN
248   SwapBytes4 (&n);
249 #endif
250   return (*this);
251 }
252
253 onetorderstream& onetorderstream::writeFloat64 (kfloat64 n) {
254 #ifndef WORDS_BIGENDIAN
255   SwapBytes8 (&n);
256 #endif
257   write (&n, 8);
258   return (*this);
259 }
260
261 inetorderstream& inetorderstream::readFloat64 (kfloat64& n) {
262   read (&n, 8);
263 #ifndef WORDS_BIGENDIAN
264   SwapBytes8 (&n);
265 #endif
266   return (*this);
267 }
268
269
270
271 void
272 write_rnint16 (kuint16 n, ostream& ostr)
273 {
274 #ifdef WORDS_BIGENDIAN
275   SwapBytes2 (&n);
276 #endif
277   ostr.write (&n, 2);
278 }
279
280 void
281 read_rnint16 (kuint16& n, istream& istr)
282 {
283   istr.read (&n, 2);
284 #ifdef WORDS_BIGENDIAN
285   SwapBytes2 (&n);
286 #endif
287 }
288
289 void
290 write_rnint32 (kuint32 n, ostream& ostr)
291 {
292 #ifdef WORDS_BIGENDIAN
293   SwapBytes4(&n);
294 #endif
295   ostr.write (&n, 4);
296 }
297
298 void
299 read_rnint32 (kuint32& n, istream istr)
300 {
301   istr.read (&n, 4);
302 #ifdef WORDS_BIGENDIAN
303   SwapBytes4 (&n);
304 #endif
305 }
306
307 void
308 write_rnfloat32 (kfloat32 n, ostream ostr)
309 {
310 #ifdef WORDS_BIGENDIAN
311   SwapBytes4 (&n);
312 #endif
313   ostr.write (&n, 4);
314 }
315
316 void
317 read_rnfloat32 (kfloat32& n, istream istr)
318 {
319   istr.read (&n, 4);
320 #ifdef WORDS_BIGENDIAN
321   SwapBytes4 (&n);
322 #endif
323 }
324
325 void
326 write_rnfloat64 (kfloat64 n, ostream ostr)
327 {
328 #ifdef WORDS_BIGENDIAN
329   SwapBytes8 (&n);
330 #endif
331   ostr.write (&n, 8);
332 }
333
334 void
335 read_rnfloat64 (kfloat64& n, istream istr)
336 {
337   istr.read (&n, 8);
338 #ifdef WORDS_BIGENDIAN
339   SwapBytes8 (&n);
340 #endif
341 }
342