$search
00001 /* 00002 Aseba - an event-based framework for distributed robot control 00003 Copyright (C) 2007--2012: 00004 Stephane Magnenat <stephane at magnenat dot net> 00005 (http://stephane.magnenat.net) 00006 and other contributors, see authors.txt for details 00007 00008 This program is free software: you can redistribute it and/or modify 00009 it under the terms of the GNU Lesser General Public License as published 00010 by the Free Software Foundation, version 3 of the License. 00011 00012 This program is distributed in the hope that it will be useful, 00013 but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 GNU Lesser General Public License for more details. 00016 00017 You should have received a copy of the GNU Lesser General Public License 00018 along with this program. If not, see <http://www.gnu.org/licenses/>. 00019 */ 00020 00021 #ifndef ASEBA_ENDIAN 00022 #define ASEBA_ENDIAN 00023 00024 namespace Aseba 00025 { 00028 00030 00031 struct ByteSwapper 00032 { 00035 template<size_t size> 00036 static inline void swapp(void *data) 00037 { 00038 uint8 temp[size]; 00039 for (size_t i = 0; i < size; ++i) 00040 temp[i] = reinterpret_cast<uint8*>(data); 00041 for (size_t i = 0; i < size; ++i) 00042 reinterpret_cast<uint8*>(data)[i] = temp[size-1-i]; 00043 } 00044 00047 template<typename T> 00048 static void swap(T& v) 00049 { 00050 swapp<sizeof(T)>(&v); 00051 } 00052 00057 template<typename T> 00058 static T swap(const T& v) 00059 { 00060 T temp(v); 00061 swapp<sizeof(T)>(&temp); 00062 return temp; 00063 } 00064 }; 00066 template<> inline void ByteSwapper::swapp<1>(void * /*data*/) 00067 { 00068 } 00070 template<> inline void ByteSwapper::swapp<2>(void *data) 00071 { 00072 const uint16 a=*reinterpret_cast<uint16*>(data); 00073 *reinterpret_cast<uint16*>(data)= 00074 ((a&0x00ff)<< 8)| 00075 ((a>> 8)&0x00ff); 00076 } 00078 template<> inline void ByteSwapper::swapp<4>(void *data) 00079 { 00080 const uint32 a=*reinterpret_cast<uint32*>(data); 00081 *reinterpret_cast<uint32*>(data)= 00082 ((a&0x000000ff)<<24)| 00083 ((a&0x0000ff00)<< 8)| 00084 ((a>> 8)&0x0000ff00)| 00085 ((a>>24)&0x000000ff); 00086 } 00088 template<> inline void ByteSwapper::swapp<8>(void *data) 00089 { 00090 const uint64 a=*reinterpret_cast<uint64*>(data); 00091 *reinterpret_cast<uint64*>(data)= 00092 ((a&0x00000000000000ffLL)<<56)| 00093 ((a&0x000000000000ff00LL)<<40)| 00094 ((a&0x0000000000ff0000LL)<<24)| 00095 ((a&0x00000000ff000000LL)<< 8)| 00096 ((a>> 8)&0x00000000ff000000LL)| 00097 ((a>>24)&0x0000000000ff0000LL)| 00098 ((a>>40)&0x000000000000ff00LL)| 00099 ((a>>56)&0x00000000000000ffLL); 00100 } 00101 00102 #ifdef __BIG_ENDIAN__ 00103 00104 template<typename T> 00105 T swapEndianCopy(const T& v) { return ByteSwapper::swap<T>(v); } 00106 template<typename T> 00107 void swapEndian(T& v) { ByteSwapper::swap<T>(v); } 00108 00109 #else 00110 00111 template<typename T> 00112 T swapEndianCopy(const T& v) { return v; } 00113 template<typename T> 00114 void swapEndian(T& v) { /* do nothing */ } 00115 00116 #endif 00117 00119 } 00120 00121 #endif // ASEBA_ENDIAN