1*819833afSPeter Tyser /* 2*819833afSPeter Tyser * Copyright (C) 2004-2007 Freescale Semiconductor, Inc. 3*819833afSPeter Tyser * TsiChung Liew (Tsi-Chung.Liew@freescale.com) 4*819833afSPeter Tyser * 5*819833afSPeter Tyser * See file CREDITS for list of people who contributed to this 6*819833afSPeter Tyser * project. 7*819833afSPeter Tyser * 8*819833afSPeter Tyser * This program is free software; you can redistribute it and/or 9*819833afSPeter Tyser * modify it under the terms of the GNU General Public License as 10*819833afSPeter Tyser * published by the Free Software Foundation; either version 2 of 11*819833afSPeter Tyser * the License, or (at your option) any later version. 12*819833afSPeter Tyser * 13*819833afSPeter Tyser * This program is distributed in the hope that it will be useful, 14*819833afSPeter Tyser * but WITHOUT ANY WARRANTY; without even the implied warranty of 15*819833afSPeter Tyser * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16*819833afSPeter Tyser * GNU General Public License for more details. 17*819833afSPeter Tyser * 18*819833afSPeter Tyser * You should have received a copy of the GNU General Public License 19*819833afSPeter Tyser * along with this program; if not, write to the Free Software 20*819833afSPeter Tyser * Foundation, Inc., 59 Temple Place, Suite 330, Boston, 21*819833afSPeter Tyser * MA 02111-1307 USA 22*819833afSPeter Tyser */ 23*819833afSPeter Tyser 24*819833afSPeter Tyser #ifndef _M68K_BYTEORDER_H 25*819833afSPeter Tyser #define _M68K_BYTEORDER_H 26*819833afSPeter Tyser 27*819833afSPeter Tyser #include <asm/types.h> 28*819833afSPeter Tyser 29*819833afSPeter Tyser #ifdef __GNUC__ 30*819833afSPeter Tyser #define __sw16(x) \ 31*819833afSPeter Tyser ((__u16)( \ 32*819833afSPeter Tyser (((__u16)(x) & (__u16)0x00ffU) << 8) | \ 33*819833afSPeter Tyser (((__u16)(x) & (__u16)0xff00U) >> 8) )) 34*819833afSPeter Tyser #define __sw32(x) \ 35*819833afSPeter Tyser ((__u32)( \ 36*819833afSPeter Tyser (((__u32)(x)) << 24) | \ 37*819833afSPeter Tyser (((__u32)(x) & (__u32)0x0000ff00UL) << 8) | \ 38*819833afSPeter Tyser (((__u32)(x) & (__u32)0x00ff0000UL) >> 8) | \ 39*819833afSPeter Tyser (((__u32)(x)) >> 24) )) 40*819833afSPeter Tyser 41*819833afSPeter Tyser extern __inline__ unsigned ld_le16(const volatile unsigned short *addr) 42*819833afSPeter Tyser { 43*819833afSPeter Tyser unsigned result = *addr; 44*819833afSPeter Tyser return __sw16(result); 45*819833afSPeter Tyser } 46*819833afSPeter Tyser 47*819833afSPeter Tyser extern __inline__ void st_le16(volatile unsigned short *addr, 48*819833afSPeter Tyser const unsigned val) 49*819833afSPeter Tyser { 50*819833afSPeter Tyser *addr = __sw16(val); 51*819833afSPeter Tyser } 52*819833afSPeter Tyser 53*819833afSPeter Tyser extern __inline__ unsigned ld_le32(const volatile unsigned *addr) 54*819833afSPeter Tyser { 55*819833afSPeter Tyser unsigned result = *addr; 56*819833afSPeter Tyser return __sw32(result); 57*819833afSPeter Tyser } 58*819833afSPeter Tyser 59*819833afSPeter Tyser extern __inline__ void st_le32(volatile unsigned *addr, const unsigned val) 60*819833afSPeter Tyser { 61*819833afSPeter Tyser *addr = __sw32(val); 62*819833afSPeter Tyser } 63*819833afSPeter Tyser 64*819833afSPeter Tyser #if 0 65*819833afSPeter Tyser /* alas, egcs sounds like it has a bug in this code that doesn't use the 66*819833afSPeter Tyser inline asm correctly, and can cause file corruption. Until I hear that 67*819833afSPeter Tyser it's fixed, I can live without the extra speed. I hope. */ 68*819833afSPeter Tyser #if !(__GNUC__ >= 2 && __GNUC_MINOR__ >= 90) 69*819833afSPeter Tyser #if 0 70*819833afSPeter Tyser # define __arch_swab16(x) ld_le16(&x) 71*819833afSPeter Tyser # define __arch_swab32(x) ld_le32(&x) 72*819833afSPeter Tyser #else 73*819833afSPeter Tyser static __inline__ __attribute__ ((const)) 74*819833afSPeter Tyser __u16 ___arch__swab16(__u16 value) 75*819833afSPeter Tyser { 76*819833afSPeter Tyser return __sw16(value); 77*819833afSPeter Tyser } 78*819833afSPeter Tyser 79*819833afSPeter Tyser static __inline__ __attribute__ ((const)) 80*819833afSPeter Tyser __u32 ___arch__swab32(__u32 value) 81*819833afSPeter Tyser { 82*819833afSPeter Tyser return __sw32(value); 83*819833afSPeter Tyser } 84*819833afSPeter Tyser 85*819833afSPeter Tyser #define __arch__swab32(x) ___arch__swab32(x) 86*819833afSPeter Tyser #define __arch__swab16(x) ___arch__swab16(x) 87*819833afSPeter Tyser #endif /* 0 */ 88*819833afSPeter Tyser 89*819833afSPeter Tyser #endif 90*819833afSPeter Tyser 91*819833afSPeter Tyser /* The same, but returns converted value from the location pointer by addr. */ 92*819833afSPeter Tyser #define __arch__swab16p(addr) ld_le16(addr) 93*819833afSPeter Tyser #define __arch__swab32p(addr) ld_le32(addr) 94*819833afSPeter Tyser 95*819833afSPeter Tyser /* The same, but do the conversion in situ, ie. put the value back to addr. */ 96*819833afSPeter Tyser #define __arch__swab16s(addr) st_le16(addr,*addr) 97*819833afSPeter Tyser #define __arch__swab32s(addr) st_le32(addr,*addr) 98*819833afSPeter Tyser #endif 99*819833afSPeter Tyser 100*819833afSPeter Tyser #endif /* __GNUC__ */ 101*819833afSPeter Tyser 102*819833afSPeter Tyser #if defined(__GNUC__) && !defined(__STRICT_ANSI__) 103*819833afSPeter Tyser #define __BYTEORDER_HAS_U64__ 104*819833afSPeter Tyser #endif 105*819833afSPeter Tyser #include <linux/byteorder/big_endian.h> 106*819833afSPeter Tyser 107*819833afSPeter Tyser #endif /* _M68K_BYTEORDER_H */ 108