diff options
Diffstat (limited to 'arch/powerpc/include/asm/io.h')
| -rw-r--r-- | arch/powerpc/include/asm/io.h | 85 | 
1 files changed, 66 insertions, 19 deletions
diff --git a/arch/powerpc/include/asm/io.h b/arch/powerpc/include/asm/io.h index 5a64757dc0d..97d3869991c 100644 --- a/arch/powerpc/include/asm/io.h +++ b/arch/powerpc/include/asm/io.h @@ -21,7 +21,7 @@ extern struct pci_dev *isa_bridge_pcidev;  /*   * has legacy ISA devices ?   */ -#define arch_has_dev_port()	(isa_bridge_pcidev != NULL) +#define arch_has_dev_port()	(isa_bridge_pcidev != NULL || isa_io_special)  #endif  #include <linux/device.h> @@ -113,7 +113,7 @@ extern bool isa_io_special;  /* gcc 4.0 and older doesn't have 'Z' constraint */  #if __GNUC__ < 4 || (__GNUC__ == 4 && __GNUC_MINOR__ == 0) -#define DEF_MMIO_IN_LE(name, size, insn)				\ +#define DEF_MMIO_IN_X(name, size, insn)				\  static inline u##size name(const volatile u##size __iomem *addr)	\  {									\  	u##size ret;							\ @@ -122,7 +122,7 @@ static inline u##size name(const volatile u##size __iomem *addr)	\  	return ret;							\  } -#define DEF_MMIO_OUT_LE(name, size, insn) 				\ +#define DEF_MMIO_OUT_X(name, size, insn)				\  static inline void name(volatile u##size __iomem *addr, u##size val)	\  {									\  	__asm__ __volatile__("sync;"#insn" %1,0,%2"			\ @@ -130,7 +130,7 @@ static inline void name(volatile u##size __iomem *addr, u##size val)	\  	IO_SET_SYNC_FLAG();						\  }  #else /* newer gcc */ -#define DEF_MMIO_IN_LE(name, size, insn)				\ +#define DEF_MMIO_IN_X(name, size, insn)				\  static inline u##size name(const volatile u##size __iomem *addr)	\  {									\  	u##size ret;							\ @@ -139,7 +139,7 @@ static inline u##size name(const volatile u##size __iomem *addr)	\  	return ret;							\  } -#define DEF_MMIO_OUT_LE(name, size, insn) 				\ +#define DEF_MMIO_OUT_X(name, size, insn)				\  static inline void name(volatile u##size __iomem *addr, u##size val)	\  {									\  	__asm__ __volatile__("sync;"#insn" %1,%y0"			\ @@ -148,7 +148,7 @@ static inline void name(volatile u##size __iomem *addr, u##size val)	\  }  #endif -#define DEF_MMIO_IN_BE(name, size, insn)				\ +#define DEF_MMIO_IN_D(name, size, insn)				\  static inline u##size name(const volatile u##size __iomem *addr)	\  {									\  	u##size ret;							\ @@ -157,7 +157,7 @@ static inline u##size name(const volatile u##size __iomem *addr)	\  	return ret;							\  } -#define DEF_MMIO_OUT_BE(name, size, insn)				\ +#define DEF_MMIO_OUT_D(name, size, insn)				\  static inline void name(volatile u##size __iomem *addr, u##size val)	\  {									\  	__asm__ __volatile__("sync;"#insn"%U0%X0 %1,%0"			\ @@ -165,22 +165,53 @@ static inline void name(volatile u##size __iomem *addr, u##size val)	\  	IO_SET_SYNC_FLAG();						\  } +DEF_MMIO_IN_D(in_8,     8, lbz); +DEF_MMIO_OUT_D(out_8,   8, stb); -DEF_MMIO_IN_BE(in_8,     8, lbz); -DEF_MMIO_IN_BE(in_be16, 16, lhz); -DEF_MMIO_IN_BE(in_be32, 32, lwz); -DEF_MMIO_IN_LE(in_le16, 16, lhbrx); -DEF_MMIO_IN_LE(in_le32, 32, lwbrx); +#ifdef __BIG_ENDIAN__ +DEF_MMIO_IN_D(in_be16, 16, lhz); +DEF_MMIO_IN_D(in_be32, 32, lwz); +DEF_MMIO_IN_X(in_le16, 16, lhbrx); +DEF_MMIO_IN_X(in_le32, 32, lwbrx); -DEF_MMIO_OUT_BE(out_8,     8, stb); -DEF_MMIO_OUT_BE(out_be16, 16, sth); -DEF_MMIO_OUT_BE(out_be32, 32, stw); -DEF_MMIO_OUT_LE(out_le16, 16, sthbrx); -DEF_MMIO_OUT_LE(out_le32, 32, stwbrx); +DEF_MMIO_OUT_D(out_be16, 16, sth); +DEF_MMIO_OUT_D(out_be32, 32, stw); +DEF_MMIO_OUT_X(out_le16, 16, sthbrx); +DEF_MMIO_OUT_X(out_le32, 32, stwbrx); +#else +DEF_MMIO_IN_X(in_be16, 16, lhbrx); +DEF_MMIO_IN_X(in_be32, 32, lwbrx); +DEF_MMIO_IN_D(in_le16, 16, lhz); +DEF_MMIO_IN_D(in_le32, 32, lwz); + +DEF_MMIO_OUT_X(out_be16, 16, sthbrx); +DEF_MMIO_OUT_X(out_be32, 32, stwbrx); +DEF_MMIO_OUT_D(out_le16, 16, sth); +DEF_MMIO_OUT_D(out_le32, 32, stw); + +#endif /* __BIG_ENDIAN */ + +/* + * Cache inhibitied accessors for use in real mode, you don't want to use these + * unless you know what you're doing. + * + * NB. These use the cpu byte ordering. + */ +DEF_MMIO_OUT_X(out_rm8,   8, stbcix); +DEF_MMIO_OUT_X(out_rm16, 16, sthcix); +DEF_MMIO_OUT_X(out_rm32, 32, stwcix); +DEF_MMIO_IN_X(in_rm8,   8, lbzcix); +DEF_MMIO_IN_X(in_rm16, 16, lhzcix); +DEF_MMIO_IN_X(in_rm32, 32, lwzcix);  #ifdef __powerpc64__ -DEF_MMIO_OUT_BE(out_be64, 64, std); -DEF_MMIO_IN_BE(in_be64, 64, ld); + +DEF_MMIO_OUT_X(out_rm64, 64, stdcix); +DEF_MMIO_IN_X(in_rm64, 64, ldcix); + +#ifdef __BIG_ENDIAN__ +DEF_MMIO_OUT_D(out_be64, 64, std); +DEF_MMIO_IN_D(in_be64, 64, ld);  /* There is no asm instructions for 64 bits reverse loads and stores */  static inline u64 in_le64(const volatile u64 __iomem *addr) @@ -192,6 +223,22 @@ static inline void out_le64(volatile u64 __iomem *addr, u64 val)  {  	out_be64(addr, swab64(val));  } +#else +DEF_MMIO_OUT_D(out_le64, 64, std); +DEF_MMIO_IN_D(in_le64, 64, ld); + +/* There is no asm instructions for 64 bits reverse loads and stores */ +static inline u64 in_be64(const volatile u64 __iomem *addr) +{ +	return swab64(in_le64(addr)); +} + +static inline void out_be64(volatile u64 __iomem *addr, u64 val) +{ +	out_le64(addr, swab64(val)); +} + +#endif  #endif /* __powerpc64__ */  /*  | 
