Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

MIPS: Add DWARF unwinding to assembly

This will allow kdump dumps to work correclty with MIPS and
future DWARF unwinding of the stack to give accurate tracebacks.

Signed-off-by: Corey Minyard <cminyard@mvista.com>
Cc: linux-mips@linux-mips.org
Cc: linux-kernel@vger.kernel.org
Patchwork: https://patchwork.linux-mips.org/patch/16990/
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>

authored by

Corey Minyard and committed by
Ralf Baechle
866b6a89 9fef6868

+151 -117
+4
arch/mips/Makefile
··· 299 299 bootvars-y += ADDR_BITS=64 300 300 endif 301 301 302 + # This is required to get dwarf unwinding tables into .debug_frame 303 + # instead of .eh_frame so we don't discard them. 304 + KBUILD_CFLAGS += -fno-asynchronous-unwind-tables 305 + 302 306 LDFLAGS += -m $(ld-emul) 303 307 304 308 ifdef CONFIG_MIPS
+3
arch/mips/include/asm/asm.h
··· 55 55 .type symbol, @function; \ 56 56 .ent symbol, 0; \ 57 57 symbol: .frame sp, 0, ra; \ 58 + .cfi_startproc; \ 58 59 .insn 59 60 60 61 /* ··· 67 66 .type symbol, @function; \ 68 67 .ent symbol, 0; \ 69 68 symbol: .frame sp, framesize, rpc; \ 69 + .cfi_startproc; \ 70 70 .insn 71 71 72 72 /* 73 73 * END - mark end of function 74 74 */ 75 75 #define END(function) \ 76 + .cfi_endproc; \ 76 77 .end function; \ 77 78 .size function, .-function 78 79
+132 -99
arch/mips/include/asm/stackframe.h
··· 19 19 #include <asm/asm-offsets.h> 20 20 #include <asm/thread_info.h> 21 21 22 + /* Make the addition of cfi info a little easier. */ 23 + .macro cfi_rel_offset reg offset=0 docfi=0 24 + .if \docfi 25 + .cfi_rel_offset \reg, \offset 26 + .endif 27 + .endm 28 + 29 + .macro cfi_st reg offset=0 docfi=0 30 + LONG_S \reg, \offset(sp) 31 + cfi_rel_offset \reg, \offset, \docfi 32 + .endm 33 + 34 + .macro cfi_restore reg offset=0 docfi=0 35 + .if \docfi 36 + .cfi_restore \reg 37 + .endif 38 + .endm 39 + 40 + .macro cfi_ld reg offset=0 docfi=0 41 + LONG_L \reg, \offset(sp) 42 + cfi_restore \reg \offset \docfi 43 + .endm 44 + 22 45 #if defined(CONFIG_CPU_R3000) || defined(CONFIG_CPU_TX39XX) 23 46 #define STATMASK 0x3f 24 47 #else 25 48 #define STATMASK 0x1f 26 49 #endif 27 50 28 - .macro SAVE_AT 51 + .macro SAVE_AT docfi=0 29 52 .set push 30 53 .set noat 31 - LONG_S $1, PT_R1(sp) 54 + cfi_st $1, PT_R1, \docfi 32 55 .set pop 33 56 .endm 34 57 35 - .macro SAVE_TEMP 58 + .macro SAVE_TEMP docfi=0 36 59 #ifdef CONFIG_CPU_HAS_SMARTMIPS 37 60 mflhxu v1 38 61 LONG_S v1, PT_LO(sp) ··· 67 44 mfhi v1 68 45 #endif 69 46 #ifdef CONFIG_32BIT 70 - LONG_S $8, PT_R8(sp) 71 - LONG_S $9, PT_R9(sp) 47 + cfi_st $8, PT_R8, \docfi 48 + cfi_st $9, PT_R9, \docfi 72 49 #endif 73 - LONG_S $10, PT_R10(sp) 74 - LONG_S $11, PT_R11(sp) 75 - LONG_S $12, PT_R12(sp) 50 + cfi_st $10, PT_R10, \docfi 51 + cfi_st $11, PT_R11, \docfi 52 + cfi_st $12, PT_R12, \docfi 76 53 #if !defined(CONFIG_CPU_HAS_SMARTMIPS) && !defined(CONFIG_CPU_MIPSR6) 77 54 LONG_S v1, PT_HI(sp) 78 55 mflo v1 79 56 #endif 80 - LONG_S $13, PT_R13(sp) 81 - LONG_S $14, PT_R14(sp) 82 - LONG_S $15, PT_R15(sp) 83 - LONG_S $24, PT_R24(sp) 57 + cfi_st $13, PT_R13, \docfi 58 + cfi_st $14, PT_R14, \docfi 59 + cfi_st $15, PT_R15, \docfi 60 + cfi_st $24, PT_R24, \docfi 84 61 #if !defined(CONFIG_CPU_HAS_SMARTMIPS) && !defined(CONFIG_CPU_MIPSR6) 85 62 LONG_S v1, PT_LO(sp) 86 63 #endif ··· 94 71 #endif 95 72 .endm 96 73 97 - .macro SAVE_STATIC 98 - LONG_S $16, PT_R16(sp) 99 - LONG_S $17, PT_R17(sp) 100 - LONG_S $18, PT_R18(sp) 101 - LONG_S $19, PT_R19(sp) 102 - LONG_S $20, PT_R20(sp) 103 - LONG_S $21, PT_R21(sp) 104 - LONG_S $22, PT_R22(sp) 105 - LONG_S $23, PT_R23(sp) 106 - LONG_S $30, PT_R30(sp) 74 + .macro SAVE_STATIC docfi=0 75 + cfi_st $16, PT_R16, \docfi 76 + cfi_st $17, PT_R17, \docfi 77 + cfi_st $18, PT_R18, \docfi 78 + cfi_st $19, PT_R19, \docfi 79 + cfi_st $20, PT_R20, \docfi 80 + cfi_st $21, PT_R21, \docfi 81 + cfi_st $22, PT_R22, \docfi 82 + cfi_st $23, PT_R23, \docfi 83 + cfi_st $30, PT_R30, \docfi 107 84 .endm 108 85 109 86 /* ··· 191 168 .endm 192 169 #endif 193 170 194 - .macro SAVE_SOME 171 + .macro SAVE_SOME docfi=0 195 172 .set push 196 173 .set noat 197 174 .set reorder ··· 226 203 #endif 227 204 .set reorder 228 205 move k0, sp 206 + .if \docfi 207 + .cfi_register sp, k0 208 + .endif 229 209 /* Called from user mode, new stack. */ 230 - get_saved_sp 210 + get_saved_sp docfi=\docfi tosp=1 231 211 8: 232 212 #ifdef CONFIG_CPU_DADDI_WORKAROUNDS 233 213 .set at=k1 ··· 239 213 #ifdef CONFIG_CPU_DADDI_WORKAROUNDS 240 214 .set noat 241 215 #endif 242 - LONG_S k0, PT_R29(sp) 243 - LONG_S $3, PT_R3(sp) 216 + .if \docfi 217 + .cfi_def_cfa sp,0 218 + .endif 219 + cfi_st k0, PT_R29, \docfi 220 + cfi_rel_offset sp, PT_R29, \docfi 221 + cfi_st v1, PT_R3, \docfi 244 222 /* 245 223 * You might think that you don't need to save $0, 246 224 * but the FPU emulator and gdb remote debug stub ··· 252 222 */ 253 223 LONG_S $0, PT_R0(sp) 254 224 mfc0 v1, CP0_STATUS 255 - LONG_S $2, PT_R2(sp) 225 + cfi_st v0, PT_R2, \docfi 256 226 LONG_S v1, PT_STATUS(sp) 257 - LONG_S $4, PT_R4(sp) 227 + cfi_st $4, PT_R4, \docfi 258 228 mfc0 v1, CP0_CAUSE 259 - LONG_S $5, PT_R5(sp) 229 + cfi_st $5, PT_R5, \docfi 260 230 LONG_S v1, PT_CAUSE(sp) 261 - LONG_S $6, PT_R6(sp) 262 - LONG_S ra, PT_R31(sp) 231 + cfi_st $6, PT_R6, \docfi 232 + cfi_st ra, PT_R31, \docfi 263 233 MFC0 ra, CP0_EPC 264 - LONG_S $7, PT_R7(sp) 234 + cfi_st $7, PT_R7, \docfi 265 235 #ifdef CONFIG_64BIT 266 - LONG_S $8, PT_R8(sp) 267 - LONG_S $9, PT_R9(sp) 236 + cfi_st $8, PT_R8, \docfi 237 + cfi_st $9, PT_R9, \docfi 268 238 #endif 269 239 LONG_S ra, PT_EPC(sp) 270 - LONG_S $25, PT_R25(sp) 271 - LONG_S $28, PT_R28(sp) 240 + .if \docfi 241 + .cfi_rel_offset ra, PT_EPC 242 + .endif 243 + cfi_st $25, PT_R25, \docfi 244 + cfi_st $28, PT_R28, \docfi 272 245 273 246 /* Set thread_info if we're coming from user mode */ 274 247 mfc0 k0, CP0_STATUS ··· 288 255 .set pop 289 256 .endm 290 257 291 - .macro SAVE_ALL 292 - SAVE_SOME 293 - SAVE_AT 294 - SAVE_TEMP 295 - SAVE_STATIC 258 + .macro SAVE_ALL docfi=0 259 + SAVE_SOME \docfi 260 + SAVE_AT \docfi 261 + SAVE_TEMP \docfi 262 + SAVE_STATIC \docfi 296 263 .endm 297 264 298 - .macro RESTORE_AT 265 + .macro RESTORE_AT docfi=0 299 266 .set push 300 267 .set noat 301 - LONG_L $1, PT_R1(sp) 268 + cfi_ld $1, PT_R1, \docfi 302 269 .set pop 303 270 .endm 304 271 305 - .macro RESTORE_TEMP 272 + .macro RESTORE_TEMP docfi=0 306 273 #ifdef CONFIG_CPU_CAVIUM_OCTEON 307 274 /* Restore the Octeon multiplier state */ 308 275 jal octeon_mult_restore ··· 321 288 mthi $24 322 289 #endif 323 290 #ifdef CONFIG_32BIT 324 - LONG_L $8, PT_R8(sp) 325 - LONG_L $9, PT_R9(sp) 291 + cfi_ld $8, PT_R8, \docfi 292 + cfi_ld $9, PT_R9, \docfi 326 293 #endif 327 - LONG_L $10, PT_R10(sp) 328 - LONG_L $11, PT_R11(sp) 329 - LONG_L $12, PT_R12(sp) 330 - LONG_L $13, PT_R13(sp) 331 - LONG_L $14, PT_R14(sp) 332 - LONG_L $15, PT_R15(sp) 333 - LONG_L $24, PT_R24(sp) 294 + cfi_ld $10, PT_R10, \docfi 295 + cfi_ld $11, PT_R11, \docfi 296 + cfi_ld $12, PT_R12, \docfi 297 + cfi_ld $13, PT_R13, \docfi 298 + cfi_ld $14, PT_R14, \docfi 299 + cfi_ld $15, PT_R15, \docfi 300 + cfi_ld $24, PT_R24, \docfi 334 301 .endm 335 302 336 - .macro RESTORE_STATIC 337 - LONG_L $16, PT_R16(sp) 338 - LONG_L $17, PT_R17(sp) 339 - LONG_L $18, PT_R18(sp) 340 - LONG_L $19, PT_R19(sp) 341 - LONG_L $20, PT_R20(sp) 342 - LONG_L $21, PT_R21(sp) 343 - LONG_L $22, PT_R22(sp) 344 - LONG_L $23, PT_R23(sp) 345 - LONG_L $30, PT_R30(sp) 303 + .macro RESTORE_STATIC docfi=0 304 + cfi_ld $16, PT_R16, \docfi 305 + cfi_ld $17, PT_R17, \docfi 306 + cfi_ld $18, PT_R18, \docfi 307 + cfi_ld $19, PT_R19, \docfi 308 + cfi_ld $20, PT_R20, \docfi 309 + cfi_ld $21, PT_R21, \docfi 310 + cfi_ld $22, PT_R22, \docfi 311 + cfi_ld $23, PT_R23, \docfi 312 + cfi_ld $30, PT_R30, \docfi 313 + .endm 314 + 315 + .macro RESTORE_SP docfi=0 316 + cfi_ld sp, PT_R29, \docfi 346 317 .endm 347 318 348 319 #if defined(CONFIG_CPU_R3000) || defined(CONFIG_CPU_TX39XX) 349 320 350 - .macro RESTORE_SOME 321 + .macro RESTORE_SOME docfi=0 351 322 .set push 352 323 .set reorder 353 324 .set noat ··· 366 329 and v0, v1 367 330 or v0, a0 368 331 mtc0 v0, CP0_STATUS 369 - LONG_L $31, PT_R31(sp) 370 - LONG_L $28, PT_R28(sp) 371 - LONG_L $25, PT_R25(sp) 372 - LONG_L $7, PT_R7(sp) 373 - LONG_L $6, PT_R6(sp) 374 - LONG_L $5, PT_R5(sp) 375 - LONG_L $4, PT_R4(sp) 376 - LONG_L $3, PT_R3(sp) 377 - LONG_L $2, PT_R2(sp) 332 + cfi_ld $31, PT_R31, \docfi 333 + cfi_ld $28, PT_R28, \docfi 334 + cfi_ld $25, PT_R25, \docfi 335 + cfi_ld $7, PT_R7, \docfi 336 + cfi_ld $6, PT_R6, \docfi 337 + cfi_ld $5, PT_R5, \docfi 338 + cfi_ld $4, PT_R4, \docfi 339 + cfi_ld $3, PT_R3, \docfi 340 + cfi_ld $2, PT_R2, \docfi 378 341 .set pop 379 342 .endm 380 343 381 - .macro RESTORE_SP_AND_RET 344 + .macro RESTORE_SP_AND_RET docfi=0 382 345 .set push 383 346 .set noreorder 384 347 LONG_L k0, PT_EPC(sp) 385 - LONG_L sp, PT_R29(sp) 348 + RESTORE_SP \docfi 386 349 jr k0 387 350 rfe 388 351 .set pop 389 352 .endm 390 353 391 354 #else 392 - .macro RESTORE_SOME 355 + .macro RESTORE_SOME docfi=0 393 356 .set push 394 357 .set reorder 395 358 .set noat ··· 406 369 mtc0 v0, CP0_STATUS 407 370 LONG_L v1, PT_EPC(sp) 408 371 MTC0 v1, CP0_EPC 409 - LONG_L $31, PT_R31(sp) 410 - LONG_L $28, PT_R28(sp) 411 - LONG_L $25, PT_R25(sp) 372 + cfi_ld $31, PT_R31, \docfi 373 + cfi_ld $28, PT_R28, \docfi 374 + cfi_ld $25, PT_R25, \docfi 412 375 #ifdef CONFIG_64BIT 413 - LONG_L $8, PT_R8(sp) 414 - LONG_L $9, PT_R9(sp) 376 + cfi_ld $8, PT_R8, \docfi 377 + cfi_ld $9, PT_R9, \docfi 415 378 #endif 416 - LONG_L $7, PT_R7(sp) 417 - LONG_L $6, PT_R6(sp) 418 - LONG_L $5, PT_R5(sp) 419 - LONG_L $4, PT_R4(sp) 420 - LONG_L $3, PT_R3(sp) 421 - LONG_L $2, PT_R2(sp) 379 + cfi_ld $7, PT_R7, \docfi 380 + cfi_ld $6, PT_R6, \docfi 381 + cfi_ld $5, PT_R5, \docfi 382 + cfi_ld $4, PT_R4, \docfi 383 + cfi_ld $3, PT_R3, \docfi 384 + cfi_ld $2, PT_R2, \docfi 422 385 .set pop 423 386 .endm 424 387 425 - .macro RESTORE_SP_AND_RET 426 - LONG_L sp, PT_R29(sp) 388 + .macro RESTORE_SP_AND_RET docfi=0 389 + RESTORE_SP \docfi 427 390 #ifdef CONFIG_CPU_MIPSR6 428 391 eretnc 429 392 #else ··· 435 398 436 399 #endif 437 400 438 - .macro RESTORE_SP 439 - LONG_L sp, PT_R29(sp) 440 - .endm 441 - 442 - .macro RESTORE_ALL 443 - RESTORE_TEMP 444 - RESTORE_STATIC 445 - RESTORE_AT 446 - RESTORE_SOME 447 - RESTORE_SP 401 + .macro RESTORE_ALL docfi=0 402 + RESTORE_TEMP \docfi 403 + RESTORE_STATIC \docfi 404 + RESTORE_AT \docfi 405 + RESTORE_SOME \docfi 406 + RESTORE_SP \docfi 448 407 .endm 449 408 450 409 /*
+8 -5
arch/mips/kernel/genex.S
··· 150 150 .align 5 151 151 BUILD_ROLLBACK_PROLOGUE handle_int 152 152 NESTED(handle_int, PT_SIZE, sp) 153 + .cfi_signal_frame 153 154 #ifdef CONFIG_TRACE_IRQFLAGS 154 155 /* 155 156 * Check to see if the interrupted code has just disabled ··· 182 181 1: 183 182 .set pop 184 183 #endif 185 - SAVE_ALL 184 + SAVE_ALL docfi=1 186 185 CLI 187 186 TRACE_IRQS_OFF 188 187 ··· 270 269 */ 271 270 BUILD_ROLLBACK_PROLOGUE except_vec_vi 272 271 NESTED(except_vec_vi, 0, sp) 273 - SAVE_SOME 274 - SAVE_AT 272 + SAVE_SOME docfi=1 273 + SAVE_AT docfi=1 275 274 .set push 276 275 .set noreorder 277 276 PTR_LA v1, except_vec_vi_handler ··· 397 396 __FINIT 398 397 399 398 NESTED(nmi_handler, PT_SIZE, sp) 399 + .cfi_signal_frame 400 400 .set push 401 401 .set noat 402 402 /* ··· 480 478 .macro __BUILD_HANDLER exception handler clear verbose ext 481 479 .align 5 482 480 NESTED(handle_\exception, PT_SIZE, sp) 481 + .cfi_signal_frame 483 482 .set noat 484 483 SAVE_ALL 485 484 FEXPORT(handle_\exception\ext) ··· 488 485 .set at 489 486 __BUILD_\verbose \exception 490 487 move a0, sp 491 - PTR_LA ra, ret_from_exception 492 - j do_\handler 488 + jal do_\handler 489 + j ret_from_exception 493 490 END(handle_\exception) 494 491 .endm 495 492
+4 -3
arch/mips/mm/tlbex-fault.S
··· 12 12 13 13 .macro tlb_do_page_fault, write 14 14 NESTED(tlb_do_page_fault_\write, PT_SIZE, sp) 15 - SAVE_ALL 15 + .cfi_signal_frame 16 + SAVE_ALL docfi=1 16 17 MFC0 a2, CP0_BADVADDR 17 18 KMODE 18 19 move a0, sp 19 20 REG_S a2, PT_BVADDR(sp) 20 21 li a1, \write 21 - PTR_LA ra, ret_from_exception 22 - j do_page_fault 22 + jal do_page_fault 23 + j ret_from_exception 23 24 END(tlb_do_page_fault_\write) 24 25 .endm 25 26
-10
arch/mips/vdso/sigreturn.S
··· 19 19 .cfi_sections .debug_frame 20 20 21 21 LEAF(__vdso_rt_sigreturn) 22 - .cfi_startproc 23 - .frame sp, 0, ra 24 - .mask 0x00000000, 0 25 - .fmask 0x00000000, 0 26 22 .cfi_signal_frame 27 23 28 24 li v0, __NR_rt_sigreturn 29 25 syscall 30 26 31 - .cfi_endproc 32 27 END(__vdso_rt_sigreturn) 33 28 34 29 #if _MIPS_SIM == _MIPS_SIM_ABI32 35 30 36 31 LEAF(__vdso_sigreturn) 37 - .cfi_startproc 38 - .frame sp, 0, ra 39 - .mask 0x00000000, 0 40 - .fmask 0x00000000, 0 41 32 .cfi_signal_frame 42 33 43 34 li v0, __NR_sigreturn 44 35 syscall 45 36 46 - .cfi_endproc 47 37 END(__vdso_sigreturn) 48 38 49 39 #endif