xref: /redis-3.2.3/src/endianconv.c (revision 8febcffd)
1 /* endinconv.c -- Endian conversions utilities.
2  *
3  * This functions are never called directly, but always using the macros
4  * defined into endianconv.h, this way we define everything is a non-operation
5  * if the arch is already little endian.
6  *
7  * Redis tries to encode everything as little endian (but a few things that need
8  * to be backward compatible are still in big endian) because most of the
9  * production environments are little endian, and we have a lot of conversions
10  * in a few places because ziplists, intsets, zipmaps, need to be endian-neutral
11  * even in memory, since they are serialied on RDB files directly with a single
12  * write(2) without other additional steps.
13  *
14  * ----------------------------------------------------------------------------
15  *
16  * Copyright (c) 2011-2012, Salvatore Sanfilippo <antirez at gmail dot com>
17  * All rights reserved.
18  *
19  * Redistribution and use in source and binary forms, with or without
20  * modification, are permitted provided that the following conditions are met:
21  *
22  *   * Redistributions of source code must retain the above copyright notice,
23  *     this list of conditions and the following disclaimer.
24  *   * Redistributions in binary form must reproduce the above copyright
25  *     notice, this list of conditions and the following disclaimer in the
26  *     documentation and/or other materials provided with the distribution.
27  *   * Neither the name of Redis nor the names of its contributors may be used
28  *     to endorse or promote products derived from this software without
29  *     specific prior written permission.
30  *
31  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
32  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
33  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
34  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
35  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
36  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
37  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
38  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
39  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
40  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41  * POSSIBILITY OF SUCH DAMAGE.
42  */
43 
44 
45 #include <stdint.h>
46 
47 /* Toggle the 16 bit unsigned integer pointed by *p from little endian to
48  * big endian */
memrev16(void * p)49 void memrev16(void *p) {
50     unsigned char *x = p, t;
51 
52     t = x[0];
53     x[0] = x[1];
54     x[1] = t;
55 }
56 
57 /* Toggle the 32 bit unsigned integer pointed by *p from little endian to
58  * big endian */
memrev32(void * p)59 void memrev32(void *p) {
60     unsigned char *x = p, t;
61 
62     t = x[0];
63     x[0] = x[3];
64     x[3] = t;
65     t = x[1];
66     x[1] = x[2];
67     x[2] = t;
68 }
69 
70 /* Toggle the 64 bit unsigned integer pointed by *p from little endian to
71  * big endian */
memrev64(void * p)72 void memrev64(void *p) {
73     unsigned char *x = p, t;
74 
75     t = x[0];
76     x[0] = x[7];
77     x[7] = t;
78     t = x[1];
79     x[1] = x[6];
80     x[6] = t;
81     t = x[2];
82     x[2] = x[5];
83     x[5] = t;
84     t = x[3];
85     x[3] = x[4];
86     x[4] = t;
87 }
88 
intrev16(uint16_t v)89 uint16_t intrev16(uint16_t v) {
90     memrev16(&v);
91     return v;
92 }
93 
intrev32(uint32_t v)94 uint32_t intrev32(uint32_t v) {
95     memrev32(&v);
96     return v;
97 }
98 
intrev64(uint64_t v)99 uint64_t intrev64(uint64_t v) {
100     memrev64(&v);
101     return v;
102 }
103 
104 #ifdef REDIS_TEST
105 #include <stdio.h>
106 
107 #define UNUSED(x) (void)(x)
endianconvTest(int argc,char * argv[])108 int endianconvTest(int argc, char *argv[]) {
109     char buf[32];
110 
111     UNUSED(argc);
112     UNUSED(argv);
113 
114     sprintf(buf,"ciaoroma");
115     memrev16(buf);
116     printf("%s\n", buf);
117 
118     sprintf(buf,"ciaoroma");
119     memrev32(buf);
120     printf("%s\n", buf);
121 
122     sprintf(buf,"ciaoroma");
123     memrev64(buf);
124     printf("%s\n", buf);
125 
126     return 0;
127 }
128 #endif
129