Line data Source code
1 : /* +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 : University of Illinois Open Source License 3 : Copyright 2003 Theoretical and Computational Biophysics Group, 4 : All rights reserved. 5 : 6 : Developed by: Theoretical and Computational Biophysics Group 7 : University of Illinois at Urbana-Champaign 8 : http://www.ks.uiuc.edu/ 9 : 10 : Permission is hereby granted, free of charge, to any person obtaining a copy of 11 : this software and associated documentation files (the Software), to deal with 12 : the Software without restriction, including without limitation the rights to 13 : use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies 14 : of the Software, and to permit persons to whom the Software is furnished to 15 : do so, subject to the following conditions: 16 : 17 : Redistributions of source code must retain the above copyright notice, 18 : this list of conditions and the following disclaimers. 19 : 20 : Redistributions in binary form must reproduce the above copyright notice, 21 : this list of conditions and the following disclaimers in the documentation 22 : and/or other materials provided with the distribution. 23 : 24 : Neither the names of Theoretical and Computational Biophysics Group, 25 : University of Illinois at Urbana-Champaign, nor the names of its contributors 26 : may be used to endorse or promote products derived from this Software without 27 : specific prior written permission. 28 : 29 : THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 30 : IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 31 : FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 32 : THE CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR 33 : OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 34 : ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 35 : OTHER DEALINGS WITH THE SOFTWARE. 36 : +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */ 37 : #ifndef __PLUMED_molfile_endianswap_h 38 : #define __PLUMED_molfile_endianswap_h 39 : namespace PLMD{ 40 : namespace molfile{ 41 : /*************************************************************************** 42 : *cr 43 : *cr (C) Copyright 1995-2016 The Board of Trustees of the 44 : *cr University of Illinois 45 : *cr All Rights Reserved 46 : *cr 47 : ***************************************************************************/ 48 : /*************************************************************************** 49 : * RCS INFORMATION: 50 : * 51 : * $RCSfile: endianswap.h,v $ 52 : * $Author: johns $ $Locker: $ $State: Exp $ 53 : * $Revision: 1.7 $ $Date: 2016/11/28 05:01:53 $ 54 : * 55 : *************************************************************************** 56 : * DESCRIPTION: 57 : * Byte swapping routines used in various plugins 58 : * There are two versions of each routine, one that's safe to use in 59 : * all cases (but is slow) and one that is only safe to use on memory 60 : * addresses that are aligned to the word size that's being byte-swapped 61 : * but are much much much faster. Use the aligned versions of these 62 : * routines whenever possible. The 'ndata' length count parameters and 63 : * internal loops should be safe to use on huge memory arrays on 64-bit 64 : * machines. 65 : * 66 : ***************************************************************************/ 67 : 68 : #ifndef ENDIAN_SWAP_H 69 : #define ENDIAN_SWAP_H 70 : 71 : /* works on unaligned 2-byte quantities */ 72 : static void swap2_unaligned(void *v, long ndata) { 73 : long i; 74 : char * dataptr = (char *) v; 75 : char tmp; 76 : 77 : for (i = 0; i < ndata-1; i += 2) { 78 : tmp = dataptr[i]; 79 : dataptr[i] = dataptr[i+1]; 80 : dataptr[i+1] = tmp; 81 : } 82 : } 83 : 84 : 85 : /* works on unaligned 4-byte quantities */ 86 0 : static void swap4_unaligned(void *v, long ndata) { 87 : long i; 88 : char *dataptr; 89 : char tmp; 90 : 91 : dataptr = (char *) v; 92 0 : for (i=0; i<ndata; i++) { 93 0 : tmp = dataptr[0]; 94 0 : dataptr[0] = dataptr[3]; 95 0 : dataptr[3] = tmp; 96 0 : tmp = dataptr[1]; 97 0 : dataptr[1] = dataptr[2]; 98 0 : dataptr[2] = tmp; 99 0 : dataptr += 4; 100 : } 101 0 : } 102 : 103 : 104 : /* works on unaligned 8-byte quantities */ 105 0 : static void swap8_unaligned(void *v, long ndata) { 106 : char *data = (char *) v; 107 : long i; 108 : char byteArray[8]; 109 : char *bytePointer; 110 : 111 0 : for (i=0; i<ndata; i++) { 112 0 : bytePointer = data + (i<<3); 113 0 : byteArray[0] = *bytePointer; 114 0 : byteArray[1] = *(bytePointer+1); 115 0 : byteArray[2] = *(bytePointer+2); 116 0 : byteArray[3] = *(bytePointer+3); 117 0 : byteArray[4] = *(bytePointer+4); 118 0 : byteArray[5] = *(bytePointer+5); 119 0 : byteArray[6] = *(bytePointer+6); 120 0 : byteArray[7] = *(bytePointer+7); 121 : 122 0 : *bytePointer = byteArray[7]; 123 0 : *(bytePointer+1) = byteArray[6]; 124 0 : *(bytePointer+2) = byteArray[5]; 125 0 : *(bytePointer+3) = byteArray[4]; 126 0 : *(bytePointer+4) = byteArray[3]; 127 0 : *(bytePointer+5) = byteArray[2]; 128 0 : *(bytePointer+6) = byteArray[1]; 129 0 : *(bytePointer+7) = byteArray[0]; 130 : } 131 0 : } 132 : 133 : 134 : /* Only works with aligned 2-byte quantities, will cause a bus error */ 135 : /* on some platforms if used on unaligned data. */ 136 : static void swap2_aligned(void *v, long ndata) { 137 : short *data = (short *) v; 138 : long i; 139 : short *N; 140 : 141 : for (i=0; i<ndata; i++) { 142 : N = data + i; 143 : *N=(((*N>>8)&0xff) | ((*N&0xff)<<8)); 144 : } 145 : } 146 : 147 : 148 : /* Only works with aligned 4-byte quantities, will cause a bus error */ 149 : /* on some platforms if used on unaligned data. */ 150 1461240 : static void swap4_aligned(void *v, long ndata) { 151 : int *data = (int *) v; 152 : long i; 153 : int *N; 154 2922480 : for (i=0; i<ndata; i++) { 155 1461240 : N = data + i; 156 1461240 : *N=(((*N>>24)&0xff) | ((*N&0xff)<<24) | 157 1461240 : ((*N>>8)&0xff00) | ((*N&0xff00)<<8)); 158 : } 159 1461240 : } 160 : 161 : 162 : /* Only works with aligned 8-byte quantities, will cause a bus error */ 163 : /* on some platforms if used on unaligned data. */ 164 0 : static void swap8_aligned(void *v, long ndata) { 165 : /* Use int* internally to prevent bugs caused by some compilers */ 166 : /* and hardware that would potentially load data into an FP reg */ 167 : /* and hose everything, such as the old "jmemcpy()" bug in NAMD */ 168 : int *data = (int *) v; 169 : long i; 170 : int *N; 171 : int t0, t1; 172 : 173 0 : for (i=0; i<ndata; i++) { 174 0 : N = data + (i<<1); 175 0 : t0 = N[0]; 176 0 : t0=(((t0>>24)&0xff) | ((t0&0xff)<<24) | 177 0 : ((t0>>8)&0xff00) | ((t0&0xff00)<<8)); 178 : 179 0 : t1 = N[1]; 180 0 : t1=(((t1>>24)&0xff) | ((t1&0xff)<<24) | 181 0 : ((t1>>8)&0xff00) | ((t1&0xff00)<<8)); 182 : 183 0 : N[0] = t1; 184 0 : N[1] = t0; 185 : } 186 0 : } 187 : 188 : #if 0 189 : /* Other implementations that might be faster in some cases */ 190 : 191 : /* swaps the endianism of an eight byte word. */ 192 : void mdio_swap8(double *i) { 193 : char c; 194 : char *n; 195 : n = (char *) i; 196 : c = n[0]; 197 : n[0] = n[7]; 198 : n[7] = c; 199 : c = n[1]; 200 : n[1] = n[6]; 201 : n[6] = c; 202 : c = n[2]; 203 : n[2] = n[5]; 204 : n[5] = c; 205 : c = n[3]; 206 : n[3] = n[4]; 207 : n[4] = c; 208 : } 209 : 210 : #endif 211 : 212 : #endif 213 : } 214 : } 215 : #endif