aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRobin Murphy <robin.murphy@arm.com>2016-04-26 06:38:20 -0400
committerWill Deacon <will.deacon@arm.com>2016-05-03 13:23:02 -0400
commite511267bc25e18926826e7cccdf7872bcbb4776a (patch)
treeae8d3be2bee8b89cfaa309a88ebd229f76b5f95c
parentf0cfffc48cac516e37711786227f6808491913a5 (diff)
io-64-nonatomic: Add relaxed accessor variants
Whilst commit 9439eb3ab9d1 ("asm-generic: io: implement relaxed accessor macros as conditional wrappers") makes the *_relaxed forms of I/O accessors universally available to drivers, in cases where writeq() is implemented via the io-64-nonatomic helpers, writeq_relaxed() will end up falling back to writel() regardless of whether writel_relaxed() is available (identically for s/write/read/). Add corresponding relaxed forms of the nonatomic helpers to delegate to the equivalent 32-bit accessors as appropriate. We also need to fix io.h to avoid defining default relaxed variants if the basic accessors themselves don't exist. CC: Christoph Hellwig <hch@lst.de> CC: Darren Hart <dvhart@linux.intel.com> CC: Hitoshi Mitake <mitake.hitoshi@lab.ntt.co.jp> Acked-by: Arnd Bergmann <arnd@arndb.de> Signed-off-by: Robin Murphy <robin.murphy@arm.com> Signed-off-by: Will Deacon <will.deacon@arm.com>
-rw-r--r--include/asm-generic/io.h4
-rw-r--r--include/linux/io-64-nonatomic-hi-lo.h25
-rw-r--r--include/linux/io-64-nonatomic-lo-hi.h25
3 files changed, 52 insertions, 2 deletions
diff --git a/include/asm-generic/io.h b/include/asm-generic/io.h
index eed3bbe88c8a..002b81f6f2bc 100644
--- a/include/asm-generic/io.h
+++ b/include/asm-generic/io.h
@@ -191,7 +191,7 @@ static inline void writeq(u64 value, volatile void __iomem *addr)
191#define readl_relaxed readl 191#define readl_relaxed readl
192#endif 192#endif
193 193
194#ifndef readq_relaxed 194#if defined(readq) && !defined(readq_relaxed)
195#define readq_relaxed readq 195#define readq_relaxed readq
196#endif 196#endif
197 197
@@ -207,7 +207,7 @@ static inline void writeq(u64 value, volatile void __iomem *addr)
207#define writel_relaxed writel 207#define writel_relaxed writel
208#endif 208#endif
209 209
210#ifndef writeq_relaxed 210#if defined(writeq) && !defined(writeq_relaxed)
211#define writeq_relaxed writeq 211#define writeq_relaxed writeq
212#endif 212#endif
213 213
diff --git a/include/linux/io-64-nonatomic-hi-lo.h b/include/linux/io-64-nonatomic-hi-lo.h
index 11d7e840d913..defcc4644ce3 100644
--- a/include/linux/io-64-nonatomic-hi-lo.h
+++ b/include/linux/io-64-nonatomic-hi-lo.h
@@ -21,6 +21,23 @@ static inline void hi_lo_writeq(__u64 val, volatile void __iomem *addr)
21 writel(val, addr); 21 writel(val, addr);
22} 22}
23 23
24static inline __u64 hi_lo_readq_relaxed(const volatile void __iomem *addr)
25{
26 const volatile u32 __iomem *p = addr;
27 u32 low, high;
28
29 high = readl_relaxed(p + 1);
30 low = readl_relaxed(p);
31
32 return low + ((u64)high << 32);
33}
34
35static inline void hi_lo_writeq_relaxed(__u64 val, volatile void __iomem *addr)
36{
37 writel_relaxed(val >> 32, addr + 4);
38 writel_relaxed(val, addr);
39}
40
24#ifndef readq 41#ifndef readq
25#define readq hi_lo_readq 42#define readq hi_lo_readq
26#endif 43#endif
@@ -29,4 +46,12 @@ static inline void hi_lo_writeq(__u64 val, volatile void __iomem *addr)
29#define writeq hi_lo_writeq 46#define writeq hi_lo_writeq
30#endif 47#endif
31 48
49#ifndef readq_relaxed
50#define readq_relaxed hi_lo_readq_relaxed
51#endif
52
53#ifndef writeq_relaxed
54#define writeq_relaxed hi_lo_writeq_relaxed
55#endif
56
32#endif /* _LINUX_IO_64_NONATOMIC_HI_LO_H_ */ 57#endif /* _LINUX_IO_64_NONATOMIC_HI_LO_H_ */
diff --git a/include/linux/io-64-nonatomic-lo-hi.h b/include/linux/io-64-nonatomic-lo-hi.h
index 1a4315f97360..084461a4e5ab 100644
--- a/include/linux/io-64-nonatomic-lo-hi.h
+++ b/include/linux/io-64-nonatomic-lo-hi.h
@@ -21,6 +21,23 @@ static inline void lo_hi_writeq(__u64 val, volatile void __iomem *addr)
21 writel(val >> 32, addr + 4); 21 writel(val >> 32, addr + 4);
22} 22}
23 23
24static inline __u64 lo_hi_readq_relaxed(const volatile void __iomem *addr)
25{
26 const volatile u32 __iomem *p = addr;
27 u32 low, high;
28
29 low = readl_relaxed(p);
30 high = readl_relaxed(p + 1);
31
32 return low + ((u64)high << 32);
33}
34
35static inline void lo_hi_writeq_relaxed(__u64 val, volatile void __iomem *addr)
36{
37 writel_relaxed(val, addr);
38 writel_relaxed(val >> 32, addr + 4);
39}
40
24#ifndef readq 41#ifndef readq
25#define readq lo_hi_readq 42#define readq lo_hi_readq
26#endif 43#endif
@@ -29,4 +46,12 @@ static inline void lo_hi_writeq(__u64 val, volatile void __iomem *addr)
29#define writeq lo_hi_writeq 46#define writeq lo_hi_writeq
30#endif 47#endif
31 48
49#ifndef readq_relaxed
50#define readq_relaxed lo_hi_readq_relaxed
51#endif
52
53#ifndef writeq_relaxed
54#define writeq_relaxed lo_hi_writeq_relaxed
55#endif
56
32#endif /* _LINUX_IO_64_NONATOMIC_LO_HI_H_ */ 57#endif /* _LINUX_IO_64_NONATOMIC_LO_HI_H_ */