Skip to content

Commit 1036b89

Browse files
linuswRussell King (Oracle)
authored andcommitted
ARM: 9385/2: mm: Type-annotate all cache assembly routines
Tag all references to assembly functions with SYM_TYPED_FUNC_START() and SYM_FUNC_END() so they also become CFI-safe. When we add SYM_TYPED_FUNC_START() to assembly calls, a function prototype signature will be emitted into the object file at (pc-4) at the call site, so that the KCFI runtime check can compare this to the expected call. Example: 8011ae38: a540670c .word 0xa540670c 8011ae3c <v7_flush_icache_all>: 8011ae3c: e3a00000 mov r0, #0 8011ae40: ee070f11 mcr 15, 0, r0, cr7, cr1, {0} 8011ae44: e12fff1e bx lr This means no "fallthrough" code can enter a SYM_TYPED_FUNC_START() call from above it: there will be a function prototype signature there, so those are consistently converted to a branch or ret lr depending on context. Tested-by: Kees Cook <[email protected]> Reviewed-by: Sami Tolvanen <[email protected]> Signed-off-by: Linus Walleij <[email protected]> Signed-off-by: Russell King (Oracle) <[email protected]>
1 parent 6b0ef27 commit 1036b89

22 files changed

+544
-373
lines changed

arch/arm/mm/cache-fa.S

Lines changed: 24 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
*/
1313
#include <linux/linkage.h>
1414
#include <linux/init.h>
15+
#include <linux/cfi_types.h>
1516
#include <asm/assembler.h>
1617
#include <asm/page.h>
1718

@@ -39,26 +40,28 @@
3940
*
4041
* Unconditionally clean and invalidate the entire icache.
4142
*/
42-
ENTRY(fa_flush_icache_all)
43+
SYM_TYPED_FUNC_START(fa_flush_icache_all)
4344
mov r0, #0
4445
mcr p15, 0, r0, c7, c5, 0 @ invalidate I cache
4546
ret lr
46-
ENDPROC(fa_flush_icache_all)
47+
SYM_FUNC_END(fa_flush_icache_all)
4748

4849
/*
4950
* flush_user_cache_all()
5051
*
5152
* Clean and invalidate all cache entries in a particular address
5253
* space.
5354
*/
54-
ENTRY(fa_flush_user_cache_all)
55-
/* FALLTHROUGH */
55+
SYM_TYPED_FUNC_START(fa_flush_user_cache_all)
56+
b fa_flush_kern_cache_all
57+
SYM_FUNC_END(fa_flush_user_cache_all)
58+
5659
/*
5760
* flush_kern_cache_all()
5861
*
5962
* Clean and invalidate the entire cache.
6063
*/
61-
ENTRY(fa_flush_kern_cache_all)
64+
SYM_TYPED_FUNC_START(fa_flush_kern_cache_all)
6265
mov ip, #0
6366
mov r2, #VM_EXEC
6467
__flush_whole_cache:
@@ -69,6 +72,7 @@ __flush_whole_cache:
6972
mcrne p15, 0, ip, c7, c10, 4 @ drain write buffer
7073
mcrne p15, 0, ip, c7, c5, 4 @ prefetch flush
7174
ret lr
75+
SYM_FUNC_END(fa_flush_kern_cache_all)
7276

7377
/*
7478
* flush_user_cache_range(start, end, flags)
@@ -80,7 +84,7 @@ __flush_whole_cache:
8084
* - end - end address (exclusive, page aligned)
8185
* - flags - vma_area_struct flags describing address space
8286
*/
83-
ENTRY(fa_flush_user_cache_range)
87+
SYM_TYPED_FUNC_START(fa_flush_user_cache_range)
8488
mov ip, #0
8589
sub r3, r1, r0 @ calculate total size
8690
cmp r3, #CACHE_DLIMIT @ total size >= limit?
@@ -97,6 +101,7 @@ ENTRY(fa_flush_user_cache_range)
97101
mcrne p15, 0, ip, c7, c10, 4 @ data write barrier
98102
mcrne p15, 0, ip, c7, c5, 4 @ prefetch flush
99103
ret lr
104+
SYM_FUNC_END(fa_flush_user_cache_range)
100105

101106
/*
102107
* coherent_kern_range(start, end)
@@ -108,8 +113,9 @@ ENTRY(fa_flush_user_cache_range)
108113
* - start - virtual start address
109114
* - end - virtual end address
110115
*/
111-
ENTRY(fa_coherent_kern_range)
112-
/* fall through */
116+
SYM_TYPED_FUNC_START(fa_coherent_kern_range)
117+
b fa_coherent_user_range
118+
SYM_FUNC_END(fa_coherent_kern_range)
113119

114120
/*
115121
* coherent_user_range(start, end)
@@ -121,7 +127,7 @@ ENTRY(fa_coherent_kern_range)
121127
* - start - virtual start address
122128
* - end - virtual end address
123129
*/
124-
ENTRY(fa_coherent_user_range)
130+
SYM_TYPED_FUNC_START(fa_coherent_user_range)
125131
bic r0, r0, #CACHE_DLINESIZE - 1
126132
1: mcr p15, 0, r0, c7, c14, 1 @ clean and invalidate D entry
127133
mcr p15, 0, r0, c7, c5, 1 @ invalidate I entry
@@ -133,6 +139,7 @@ ENTRY(fa_coherent_user_range)
133139
mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
134140
mcr p15, 0, r0, c7, c5, 4 @ prefetch flush
135141
ret lr
142+
SYM_FUNC_END(fa_coherent_user_range)
136143

137144
/*
138145
* flush_kern_dcache_area(void *addr, size_t size)
@@ -143,7 +150,7 @@ ENTRY(fa_coherent_user_range)
143150
* - addr - kernel address
144151
* - size - size of region
145152
*/
146-
ENTRY(fa_flush_kern_dcache_area)
153+
SYM_TYPED_FUNC_START(fa_flush_kern_dcache_area)
147154
add r1, r0, r1
148155
1: mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D line
149156
add r0, r0, #CACHE_DLINESIZE
@@ -153,6 +160,7 @@ ENTRY(fa_flush_kern_dcache_area)
153160
mcr p15, 0, r0, c7, c5, 0 @ invalidate I cache
154161
mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
155162
ret lr
163+
SYM_FUNC_END(fa_flush_kern_dcache_area)
156164

157165
/*
158166
* dma_inv_range(start, end)
@@ -203,7 +211,7 @@ fa_dma_clean_range:
203211
* - start - virtual start address of region
204212
* - end - virtual end address of region
205213
*/
206-
ENTRY(fa_dma_flush_range)
214+
SYM_TYPED_FUNC_START(fa_dma_flush_range)
207215
bic r0, r0, #CACHE_DLINESIZE - 1
208216
1: mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D entry
209217
add r0, r0, #CACHE_DLINESIZE
@@ -212,30 +220,31 @@ ENTRY(fa_dma_flush_range)
212220
mov r0, #0
213221
mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
214222
ret lr
223+
SYM_FUNC_END(fa_dma_flush_range)
215224

216225
/*
217226
* dma_map_area(start, size, dir)
218227
* - start - kernel virtual start address
219228
* - size - size of region
220229
* - dir - DMA direction
221230
*/
222-
ENTRY(fa_dma_map_area)
231+
SYM_TYPED_FUNC_START(fa_dma_map_area)
223232
add r1, r1, r0
224233
cmp r2, #DMA_TO_DEVICE
225234
beq fa_dma_clean_range
226235
bcs fa_dma_inv_range
227236
b fa_dma_flush_range
228-
ENDPROC(fa_dma_map_area)
237+
SYM_FUNC_END(fa_dma_map_area)
229238

230239
/*
231240
* dma_unmap_area(start, size, dir)
232241
* - start - kernel virtual start address
233242
* - size - size of region
234243
* - dir - DMA direction
235244
*/
236-
ENTRY(fa_dma_unmap_area)
245+
SYM_TYPED_FUNC_START(fa_dma_unmap_area)
237246
ret lr
238-
ENDPROC(fa_dma_unmap_area)
247+
SYM_FUNC_END(fa_dma_unmap_area)
239248

240249
.globl fa_flush_kern_cache_louis
241250
.equ fa_flush_kern_cache_louis, fa_flush_kern_cache_all

arch/arm/mm/cache-nop.S

Lines changed: 30 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,47 +1,56 @@
11
/* SPDX-License-Identifier: GPL-2.0-only */
22
#include <linux/linkage.h>
33
#include <linux/init.h>
4+
#include <linux/cfi_types.h>
45
#include <asm/assembler.h>
56

67
#include "proc-macros.S"
78

8-
ENTRY(nop_flush_icache_all)
9+
SYM_TYPED_FUNC_START(nop_flush_icache_all)
910
ret lr
10-
ENDPROC(nop_flush_icache_all)
11+
SYM_FUNC_END(nop_flush_icache_all)
1112

12-
.globl nop_flush_kern_cache_all
13-
.equ nop_flush_kern_cache_all, nop_flush_icache_all
13+
SYM_TYPED_FUNC_START(nop_flush_kern_cache_all)
14+
ret lr
15+
SYM_FUNC_END(nop_flush_kern_cache_all)
1416

1517
.globl nop_flush_kern_cache_louis
1618
.equ nop_flush_kern_cache_louis, nop_flush_icache_all
1719

18-
.globl nop_flush_user_cache_all
19-
.equ nop_flush_user_cache_all, nop_flush_icache_all
20+
SYM_TYPED_FUNC_START(nop_flush_user_cache_all)
21+
ret lr
22+
SYM_FUNC_END(nop_flush_user_cache_all)
2023

21-
.globl nop_flush_user_cache_range
22-
.equ nop_flush_user_cache_range, nop_flush_icache_all
24+
SYM_TYPED_FUNC_START(nop_flush_user_cache_range)
25+
ret lr
26+
SYM_FUNC_END(nop_flush_user_cache_range)
2327

24-
.globl nop_coherent_kern_range
25-
.equ nop_coherent_kern_range, nop_flush_icache_all
28+
SYM_TYPED_FUNC_START(nop_coherent_kern_range)
29+
ret lr
30+
SYM_FUNC_END(nop_coherent_kern_range)
2631

27-
ENTRY(nop_coherent_user_range)
32+
SYM_TYPED_FUNC_START(nop_coherent_user_range)
2833
mov r0, 0
2934
ret lr
30-
ENDPROC(nop_coherent_user_range)
31-
32-
.globl nop_flush_kern_dcache_area
33-
.equ nop_flush_kern_dcache_area, nop_flush_icache_all
35+
SYM_FUNC_END(nop_coherent_user_range)
3436

35-
.globl nop_dma_flush_range
36-
.equ nop_dma_flush_range, nop_flush_icache_all
37+
SYM_TYPED_FUNC_START(nop_flush_kern_dcache_area)
38+
ret lr
39+
SYM_FUNC_END(nop_flush_kern_dcache_area)
3740

38-
.globl nop_dma_map_area
39-
.equ nop_dma_map_area, nop_flush_icache_all
41+
SYM_TYPED_FUNC_START(nop_dma_flush_range)
42+
ret lr
43+
SYM_FUNC_END(nop_dma_flush_range)
4044

41-
.globl nop_dma_unmap_area
42-
.equ nop_dma_unmap_area, nop_flush_icache_all
45+
SYM_TYPED_FUNC_START(nop_dma_map_area)
46+
ret lr
47+
SYM_FUNC_END(nop_dma_map_area)
4348

4449
__INITDATA
4550

4651
@ define struct cpu_cache_fns (see <asm/cacheflush.h> and proc-macros.S)
4752
define_cache_functions nop
53+
54+
SYM_TYPED_FUNC_START(nop_dma_unmap_area)
55+
ret lr
56+
SYM_FUNC_END(nop_dma_unmap_area)

arch/arm/mm/cache-v4.S

Lines changed: 28 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
*/
77
#include <linux/linkage.h>
88
#include <linux/init.h>
9+
#include <linux/cfi_types.h>
910
#include <asm/assembler.h>
1011
#include <asm/page.h>
1112
#include "proc-macros.S"
@@ -15,9 +16,9 @@
1516
*
1617
* Unconditionally clean and invalidate the entire icache.
1718
*/
18-
ENTRY(v4_flush_icache_all)
19+
SYM_TYPED_FUNC_START(v4_flush_icache_all)
1920
ret lr
20-
ENDPROC(v4_flush_icache_all)
21+
SYM_FUNC_END(v4_flush_icache_all)
2122

2223
/*
2324
* flush_user_cache_all()
@@ -27,21 +28,24 @@ ENDPROC(v4_flush_icache_all)
2728
*
2829
* - mm - mm_struct describing address space
2930
*/
30-
ENTRY(v4_flush_user_cache_all)
31-
/* FALLTHROUGH */
31+
SYM_TYPED_FUNC_START(v4_flush_user_cache_all)
32+
b v4_flush_kern_cache_all
33+
SYM_FUNC_END(v4_flush_user_cache_all)
34+
3235
/*
3336
* flush_kern_cache_all()
3437
*
3538
* Clean and invalidate the entire cache.
3639
*/
37-
ENTRY(v4_flush_kern_cache_all)
40+
SYM_TYPED_FUNC_START(v4_flush_kern_cache_all)
3841
#ifdef CONFIG_CPU_CP15
3942
mov r0, #0
4043
mcr p15, 0, r0, c7, c7, 0 @ flush ID cache
4144
ret lr
4245
#else
43-
/* FALLTHROUGH */
46+
ret lr
4447
#endif
48+
SYM_FUNC_END(v4_flush_kern_cache_all)
4549

4650
/*
4751
* flush_user_cache_range(start, end, flags)
@@ -53,14 +57,15 @@ ENTRY(v4_flush_kern_cache_all)
5357
* - end - end address (exclusive, may not be aligned)
5458
* - flags - vma_area_struct flags describing address space
5559
*/
56-
ENTRY(v4_flush_user_cache_range)
60+
SYM_TYPED_FUNC_START(v4_flush_user_cache_range)
5761
#ifdef CONFIG_CPU_CP15
5862
mov ip, #0
5963
mcr p15, 0, ip, c7, c7, 0 @ flush ID cache
6064
ret lr
6165
#else
62-
/* FALLTHROUGH */
66+
ret lr
6367
#endif
68+
SYM_FUNC_END(v4_flush_user_cache_range)
6469

6570
/*
6671
* coherent_kern_range(start, end)
@@ -72,8 +77,9 @@ ENTRY(v4_flush_user_cache_range)
7277
* - start - virtual start address
7378
* - end - virtual end address
7479
*/
75-
ENTRY(v4_coherent_kern_range)
76-
/* FALLTHROUGH */
80+
SYM_TYPED_FUNC_START(v4_coherent_kern_range)
81+
ret lr
82+
SYM_FUNC_END(v4_coherent_kern_range)
7783

7884
/*
7985
* coherent_user_range(start, end)
@@ -85,9 +91,10 @@ ENTRY(v4_coherent_kern_range)
8591
* - start - virtual start address
8692
* - end - virtual end address
8793
*/
88-
ENTRY(v4_coherent_user_range)
94+
SYM_TYPED_FUNC_START(v4_coherent_user_range)
8995
mov r0, #0
9096
ret lr
97+
SYM_FUNC_END(v4_coherent_user_range)
9198

9299
/*
93100
* flush_kern_dcache_area(void *addr, size_t size)
@@ -98,8 +105,9 @@ ENTRY(v4_coherent_user_range)
98105
* - addr - kernel address
99106
* - size - region size
100107
*/
101-
ENTRY(v4_flush_kern_dcache_area)
102-
/* FALLTHROUGH */
108+
SYM_TYPED_FUNC_START(v4_flush_kern_dcache_area)
109+
b v4_dma_flush_range
110+
SYM_FUNC_END(v4_flush_kern_dcache_area)
103111

104112
/*
105113
* dma_flush_range(start, end)
@@ -109,34 +117,35 @@ ENTRY(v4_flush_kern_dcache_area)
109117
* - start - virtual start address
110118
* - end - virtual end address
111119
*/
112-
ENTRY(v4_dma_flush_range)
120+
SYM_TYPED_FUNC_START(v4_dma_flush_range)
113121
#ifdef CONFIG_CPU_CP15
114122
mov r0, #0
115123
mcr p15, 0, r0, c7, c7, 0 @ flush ID cache
116124
#endif
117125
ret lr
126+
SYM_FUNC_END(v4_dma_flush_range)
118127

119128
/*
120129
* dma_unmap_area(start, size, dir)
121130
* - start - kernel virtual start address
122131
* - size - size of region
123132
* - dir - DMA direction
124133
*/
125-
ENTRY(v4_dma_unmap_area)
134+
SYM_TYPED_FUNC_START(v4_dma_unmap_area)
126135
teq r2, #DMA_TO_DEVICE
127136
bne v4_dma_flush_range
128-
/* FALLTHROUGH */
137+
ret lr
138+
SYM_FUNC_END(v4_dma_unmap_area)
129139

130140
/*
131141
* dma_map_area(start, size, dir)
132142
* - start - kernel virtual start address
133143
* - size - size of region
134144
* - dir - DMA direction
135145
*/
136-
ENTRY(v4_dma_map_area)
146+
SYM_TYPED_FUNC_START(v4_dma_map_area)
137147
ret lr
138-
ENDPROC(v4_dma_unmap_area)
139-
ENDPROC(v4_dma_map_area)
148+
SYM_FUNC_END(v4_dma_map_area)
140149

141150
.globl v4_flush_kern_cache_louis
142151
.equ v4_flush_kern_cache_louis, v4_flush_kern_cache_all

0 commit comments

Comments
 (0)