0001
0002 #ifndef _ASM_S390_PCI_IO_H
0003 #define _ASM_S390_PCI_IO_H
0004
0005 #ifdef CONFIG_PCI
0006
0007 #include <linux/kernel.h>
0008 #include <linux/slab.h>
0009 #include <asm/pci_insn.h>
0010
0011
0012 #define ZPCI_MAX_READ_SIZE 8
0013 #define ZPCI_MAX_WRITE_SIZE 128
0014
0015
0016 #define ZPCI_IOMAP_SHIFT 48
0017 #define ZPCI_IOMAP_ADDR_SHIFT 62
0018 #define ZPCI_IOMAP_ADDR_BASE (1UL << ZPCI_IOMAP_ADDR_SHIFT)
0019 #define ZPCI_IOMAP_ADDR_OFF_MASK ((1UL << ZPCI_IOMAP_SHIFT) - 1)
0020 #define ZPCI_IOMAP_MAX_ENTRIES \
0021 (1UL << (ZPCI_IOMAP_ADDR_SHIFT - ZPCI_IOMAP_SHIFT))
0022 #define ZPCI_IOMAP_ADDR_IDX_MASK \
0023 ((ZPCI_IOMAP_ADDR_BASE - 1) & ~ZPCI_IOMAP_ADDR_OFF_MASK)
0024
0025 struct zpci_iomap_entry {
0026 u32 fh;
0027 u8 bar;
0028 u16 count;
0029 };
0030
0031 extern struct zpci_iomap_entry *zpci_iomap_start;
0032
0033 #define ZPCI_ADDR(idx) (ZPCI_IOMAP_ADDR_BASE | ((u64) idx << ZPCI_IOMAP_SHIFT))
0034 #define ZPCI_IDX(addr) \
0035 (((__force u64) addr & ZPCI_IOMAP_ADDR_IDX_MASK) >> ZPCI_IOMAP_SHIFT)
0036 #define ZPCI_OFFSET(addr) \
0037 ((__force u64) addr & ZPCI_IOMAP_ADDR_OFF_MASK)
0038
0039 #define ZPCI_CREATE_REQ(handle, space, len) \
0040 ((u64) handle << 32 | space << 16 | len)
0041
0042 #define zpci_read(LENGTH, RETTYPE) \
0043 static inline RETTYPE zpci_read_##RETTYPE(const volatile void __iomem *addr) \
0044 { \
0045 u64 data; \
0046 int rc; \
0047 \
0048 rc = zpci_load(&data, addr, LENGTH); \
0049 if (rc) \
0050 data = -1ULL; \
0051 return (RETTYPE) data; \
0052 }
0053
0054 #define zpci_write(LENGTH, VALTYPE) \
0055 static inline void zpci_write_##VALTYPE(VALTYPE val, \
0056 const volatile void __iomem *addr) \
0057 { \
0058 u64 data = (VALTYPE) val; \
0059 \
0060 zpci_store(addr, data, LENGTH); \
0061 }
0062
0063 zpci_read(8, u64)
0064 zpci_read(4, u32)
0065 zpci_read(2, u16)
0066 zpci_read(1, u8)
0067 zpci_write(8, u64)
0068 zpci_write(4, u32)
0069 zpci_write(2, u16)
0070 zpci_write(1, u8)
0071
0072 static inline int zpci_write_single(volatile void __iomem *dst, const void *src,
0073 unsigned long len)
0074 {
0075 u64 val;
0076
0077 switch (len) {
0078 case 1:
0079 val = (u64) *((u8 *) src);
0080 break;
0081 case 2:
0082 val = (u64) *((u16 *) src);
0083 break;
0084 case 4:
0085 val = (u64) *((u32 *) src);
0086 break;
0087 case 8:
0088 val = (u64) *((u64 *) src);
0089 break;
0090 default:
0091 val = 0;
0092 break;
0093 }
0094 return zpci_store(dst, val, len);
0095 }
0096
0097 static inline int zpci_read_single(void *dst, const volatile void __iomem *src,
0098 unsigned long len)
0099 {
0100 u64 data;
0101 int cc;
0102
0103 cc = zpci_load(&data, src, len);
0104 if (cc)
0105 goto out;
0106
0107 switch (len) {
0108 case 1:
0109 *((u8 *) dst) = (u8) data;
0110 break;
0111 case 2:
0112 *((u16 *) dst) = (u16) data;
0113 break;
0114 case 4:
0115 *((u32 *) dst) = (u32) data;
0116 break;
0117 case 8:
0118 *((u64 *) dst) = (u64) data;
0119 break;
0120 }
0121 out:
0122 return cc;
0123 }
0124
0125 int zpci_write_block(volatile void __iomem *dst, const void *src,
0126 unsigned long len);
0127
0128 static inline u8 zpci_get_max_write_size(u64 src, u64 dst, int len, int max)
0129 {
0130 int count = len > max ? max : len, size = 1;
0131
0132 while (!(src & 0x1) && !(dst & 0x1) && ((size << 1) <= count)) {
0133 dst = dst >> 1;
0134 src = src >> 1;
0135 size = size << 1;
0136 }
0137 return size;
0138 }
0139
0140 static inline int zpci_memcpy_fromio(void *dst,
0141 const volatile void __iomem *src,
0142 unsigned long n)
0143 {
0144 int size, rc = 0;
0145
0146 while (n > 0) {
0147 size = zpci_get_max_write_size((u64 __force) src,
0148 (u64) dst, n,
0149 ZPCI_MAX_READ_SIZE);
0150 rc = zpci_read_single(dst, src, size);
0151 if (rc)
0152 break;
0153 src += size;
0154 dst += size;
0155 n -= size;
0156 }
0157 return rc;
0158 }
0159
0160 static inline int zpci_memcpy_toio(volatile void __iomem *dst,
0161 const void *src, unsigned long n)
0162 {
0163 int size, rc = 0;
0164
0165 if (!src)
0166 return -EINVAL;
0167
0168 while (n > 0) {
0169 size = zpci_get_max_write_size((u64 __force) dst,
0170 (u64) src, n,
0171 ZPCI_MAX_WRITE_SIZE);
0172 if (size > 8)
0173 rc = zpci_write_block(dst, src, size);
0174 else
0175 rc = zpci_write_single(dst, src, size);
0176 if (rc)
0177 break;
0178 src += size;
0179 dst += size;
0180 n -= size;
0181 }
0182 return rc;
0183 }
0184
0185 static inline int zpci_memset_io(volatile void __iomem *dst,
0186 unsigned char val, size_t count)
0187 {
0188 u8 *src = kmalloc(count, GFP_KERNEL);
0189 int rc;
0190
0191 if (src == NULL)
0192 return -ENOMEM;
0193 memset(src, val, count);
0194
0195 rc = zpci_memcpy_toio(dst, src, count);
0196 kfree(src);
0197 return rc;
0198 }
0199
0200 #endif
0201
0202 #endif