1 /* SPDX-License-Identifier: GPL-2.0-only */
2 /*
3  *  linux/arch/arm/lib/backtrace-clang.S
4  *
5  *  Copyright (C) 2019 Nathan Huckleberry
6  *
7  */
8 #include <linux/kern_levels.h>
9 #include <linux/linkage.h>
10 #include <asm/assembler.h>
11 		.text
12 
13 /* fp is 0 or stack frame */
14 
15 #define frame	r4
16 #define sv_fp	r5
17 #define sv_pc	r6
18 #define mask	r7
19 #define sv_lr	r8
20 #define loglvl	r9
21 
22 ENTRY(c_backtrace)
23 
24 #if !defined(CONFIG_FRAME_POINTER) || !defined(CONFIG_PRINTK)
25 		ret	lr
26 ENDPROC(c_backtrace)
27 #else
28 
29 
30 /*
31  * Clang does not store pc or sp in function prologues so we don't know exactly
32  * where the function starts.
33  *
34  * We can treat the current frame's lr as the saved pc and the preceding
35  * frame's lr as the current frame's lr, but we can't trace the most recent
36  * call.  Inserting a false stack frame allows us to reference the function
37  * called last in the stacktrace.
38  *
39  * If the call instruction was a bl we can look at the callers branch
40  * instruction to calculate the saved pc.  We can recover the pc in most cases,
41  * but in cases such as calling function pointers we cannot. In this case,
42  * default to using the lr. This will be some address in the function, but will
43  * not be the function start.
44  *
45  * Unfortunately due to the stack frame layout we can't dump r0 - r3, but these
46  * are less frequently saved.
47  *
48  * Stack frame layout:
49  * 		<larger addresses>
50  * 		saved lr
51  * 	frame=> saved fp
52  * 		optionally saved caller registers (r4 - r10)
53  * 		optionally saved arguments (r0 - r3)
54  * 		<top of stack frame>
55  * 		<smaller addresses>
56  *
57  * Functions start with the following code sequence:
58  * corrected pc =>  stmfd sp!, {..., fp, lr}
59  *		add fp, sp, #x
60  *		stmfd sp!, {r0 - r3} (optional)
61  *
62  *
63  *
64  *
65  *
66  *
67  * The diagram below shows an example stack setup for dump_stack.
68  *
69  * The frame for c_backtrace has pointers to the code of dump_stack. This is
70  * why the frame of c_backtrace is used to for the pc calculation of
71  * dump_stack. This is why we must move back a frame to print dump_stack.
72  *
73  * The stored locals for dump_stack are in dump_stack's frame. This means that
74  * to fully print dump_stack's frame we need both the frame for dump_stack (for
75  * locals) and the frame that was called by dump_stack (for pc).
76  *
77  * To print locals we must know where the function start is. If we read the
78  * function prologue opcodes we can determine which variables are stored in the
79  * stack frame.
80  *
81  * To find the function start of dump_stack we can look at the stored LR of
82  * show_stack. It points at the instruction directly after the bl dump_stack.
83  * We can then read the offset from the bl opcode to determine where the branch
84  * takes us.  The address calculated must be the start of dump_stack.
85  *
86  * c_backtrace frame           dump_stack:
87  * {[LR]    }  ============|   ...
88  * {[FP]    }  =======|    |   bl c_backtrace
89  *                    |    |=> ...
90  * {[R4-R10]}         |
91  * {[R0-R3] }         |        show_stack:
92  * dump_stack frame   |        ...
93  * {[LR]    } =============|   bl dump_stack
94  * {[FP]    } <=======|    |=> ...
95  * {[R4-R10]}
96  * {[R0-R3] }
97  */
98 
99 		stmfd	sp!, {r4 - r9, fp, lr}	@ Save an extra register
100 						@ to ensure 8 byte alignment
101 		movs	frame, r0		@ if frame pointer is zero
102 		beq	no_frame		@ we have no stack frames
103 		mov	loglvl, r2
104 		tst	r1, #0x10		@ 26 or 32-bit mode?
105 		moveq	mask, #0xfc000003
106 		movne	mask, #0		@ mask for 32-bit
107 
108 /*
109  * Switches the current frame to be the frame for dump_stack.
110  */
111 		add	frame, sp, #24		@ switch to false frame
112 for_each_frame:	tst	frame, mask		@ Check for address exceptions
113 		bne	no_frame
114 
115 /*
116  * sv_fp is the stack frame with the locals for the current considered
117  * function.
118  *
119  * sv_pc is the saved lr frame the frame above. This is a pointer to a code
120  * address within the current considered function, but it is not the function
121  * start. This value gets updated to be the function start later if it is
122  * possible.
123  */
124 1001:		ldr	sv_pc, [frame, #4]	@ get saved 'pc'
125 1002:		ldr	sv_fp, [frame, #0]	@ get saved fp
126 
127 		teq	sv_fp, mask		@ make sure next frame exists
128 		beq	no_frame
129 
130 /*
131  * sv_lr is the lr from the function that called the current function. This is
132  * a pointer to a code address in the current function's caller.  sv_lr-4 is
133  * the instruction used to call the current function.
134  *
135  * This sv_lr can be used to calculate the function start if the function was
136  * called using a bl instruction. If the function start can be recovered sv_pc
137  * is overwritten with the function start.
138  *
139  * If the current function was called using a function pointer we cannot
140  * recover the function start and instead continue with sv_pc as an arbitrary
141  * value within the current function. If this is the case we cannot print
142  * registers for the current function, but the stacktrace is still printed
143  * properly.
144  */
145 1003:		ldr	sv_lr, [sv_fp, #4]	@ get saved lr from next frame
146 
147 		ldr	r0, [sv_lr, #-4]	@ get call instruction
148 		ldr	r3, .Lopcode+4
149 		and	r2, r3, r0		@ is this a bl call
150 		teq	r2, r3
151 		bne	finished_setup		@ give up if it's not
152 		and	r0, #0xffffff		@ get call offset 24-bit int
153 		lsl	r0, r0, #8		@ sign extend offset
154 		asr	r0, r0, #8
155 		ldr	sv_pc, [sv_fp, #4]	@ get lr address
156 		add	sv_pc, sv_pc, #-4	@ get call instruction address
157 		add	sv_pc, sv_pc, #8	@ take care of prefetch
158 		add	sv_pc, sv_pc, r0, lsl #2@ find function start
159 
160 finished_setup:
161 
162 		bic	sv_pc, sv_pc, mask	@ mask PC/LR for the mode
163 
164 /*
165  * Print the function (sv_pc) and where it was called from (sv_lr).
166  */
167 1004:		mov	r0, sv_pc
168 
169 		mov	r1, sv_lr
170 		mov	r2, frame
171 		bic	r1, r1, mask		@ mask PC/LR for the mode
172 		mov	r3, loglvl
173 		bl	dump_backtrace_entry
174 
175 /*
176  * Test if the function start is a stmfd instruction to determine which
177  * registers were stored in the function prologue.
178  *
179  * If we could not recover the sv_pc because we were called through a function
180  * pointer the comparison will fail and no registers will print. Unwinding will
181  * continue as if there had been no registers stored in this frame.
182  */
183 1005:		ldr	r1, [sv_pc, #0]		@ if stmfd sp!, {..., fp, lr}
184 		ldr	r3, .Lopcode		@ instruction exists,
185 		teq	r3, r1, lsr #11
186 		ldr	r0, [frame]		@ locals are stored in
187 						@ the preceding frame
188 		subeq	r0, r0, #4
189 		mov	r2, loglvl
190 		bleq	dump_backtrace_stm	@ dump saved registers
191 
192 /*
193  * If we are out of frames or if the next frame is invalid.
194  */
195 		teq	sv_fp, #0		@ zero saved fp means
196 		beq	no_frame		@ no further frames
197 
198 		cmp	sv_fp, frame		@ next frame must be
199 		mov	frame, sv_fp		@ above the current frame
200 		bhi	for_each_frame
201 
202 1006:		adr	r0, .Lbad
203 		mov	r1, loglvl
204 		mov	r2, frame
205 		bl	printk
206 no_frame:	ldmfd	sp!, {r4 - r9, fp, pc}
207 ENDPROC(c_backtrace)
208 		.pushsection __ex_table,"a"
209 		.align	3
210 		.long	1001b, 1006b
211 		.long	1002b, 1006b
212 		.long	1003b, 1006b
213 		.long	1004b, 1006b
214 		.long   1005b, 1006b
215 		.popsection
216 
217 .Lbad:		.asciz	"%sBacktrace aborted due to bad frame pointer <%p>\n"
218 		.align
219 .Lopcode:	.word	0xe92d4800 >> 11	@ stmfd sp!, {... fp, lr}
220 		.word	0x0b000000		@ bl if these bits are set
221 
222 #endif
223