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

nios2: rework trap handler

Redefine trap handler as below:

0 N/A reserved for system calls
1 SIGUSR1 user-defined signal 1
2 SIGUSR2 user-defined signal 2
3 SIGILL illegal instruction
4..29 reserved (but implemented to raise SIGILL instead of being undefined)
30 SIGTRAP KGDB
31 SIGTRAP trace/breakpoint trap

Signed-off-by: Ley Foon Tan <lftan@altera.com>

+69 -36
+42 -29
arch/nios2/kernel/entry.S
··· 92 92 93 93 trap_table: 94 94 .word handle_system_call /* 0 */ 95 - .word instruction_trap /* 1 */ 96 - .word instruction_trap /* 2 */ 97 - .word instruction_trap /* 3 */ 98 - .word instruction_trap /* 4 */ 99 - .word instruction_trap /* 5 */ 100 - .word instruction_trap /* 6 */ 101 - .word instruction_trap /* 7 */ 102 - .word instruction_trap /* 8 */ 103 - .word instruction_trap /* 9 */ 104 - .word instruction_trap /* 10 */ 105 - .word instruction_trap /* 11 */ 106 - .word instruction_trap /* 12 */ 107 - .word instruction_trap /* 13 */ 108 - .word instruction_trap /* 14 */ 109 - .word instruction_trap /* 15 */ 110 - .word instruction_trap /* 16 */ 111 - .word instruction_trap /* 17 */ 112 - .word instruction_trap /* 18 */ 113 - .word instruction_trap /* 19 */ 114 - .word instruction_trap /* 20 */ 115 - .word instruction_trap /* 21 */ 116 - .word instruction_trap /* 22 */ 117 - .word instruction_trap /* 23 */ 118 - .word instruction_trap /* 24 */ 119 - .word instruction_trap /* 25 */ 120 - .word instruction_trap /* 26 */ 121 - .word instruction_trap /* 27 */ 122 - .word instruction_trap /* 28 */ 123 - .word instruction_trap /* 29 */ 95 + .word handle_trap_1 /* 1 */ 96 + .word handle_trap_2 /* 2 */ 97 + .word handle_trap_3 /* 3 */ 98 + .word handle_trap_reserved /* 4 */ 99 + .word handle_trap_reserved /* 5 */ 100 + .word handle_trap_reserved /* 6 */ 101 + .word handle_trap_reserved /* 7 */ 102 + .word handle_trap_reserved /* 8 */ 103 + .word handle_trap_reserved /* 9 */ 104 + .word handle_trap_reserved /* 10 */ 105 + .word handle_trap_reserved /* 11 */ 106 + .word handle_trap_reserved /* 12 */ 107 + .word handle_trap_reserved /* 13 */ 108 + .word handle_trap_reserved /* 14 */ 109 + .word handle_trap_reserved /* 15 */ 110 + .word handle_trap_reserved /* 16 */ 111 + .word handle_trap_reserved /* 17 */ 112 + .word handle_trap_reserved /* 18 */ 113 + .word handle_trap_reserved /* 19 */ 114 + .word handle_trap_reserved /* 20 */ 115 + .word handle_trap_reserved /* 21 */ 116 + .word handle_trap_reserved /* 22 */ 117 + .word handle_trap_reserved /* 23 */ 118 + .word handle_trap_reserved /* 24 */ 119 + .word handle_trap_reserved /* 25 */ 120 + .word handle_trap_reserved /* 26 */ 121 + .word handle_trap_reserved /* 27 */ 122 + .word handle_trap_reserved /* 28 */ 123 + .word handle_trap_reserved /* 29 */ 124 124 #ifdef CONFIG_KGDB 125 125 .word handle_kgdb_breakpoint /* 30 KGDB breakpoint */ 126 126 #else ··· 454 454 call kgdb_breakpoint_c 455 455 br ret_from_exception 456 456 #endif 457 + 458 + handle_trap_1: 459 + call handle_trap_1_c 460 + br ret_from_exception 461 + 462 + handle_trap_2: 463 + call handle_trap_2_c 464 + br ret_from_exception 465 + 466 + handle_trap_3: 467 + handle_trap_reserved: 468 + call handle_trap_3_c 469 + br ret_from_exception 457 470 458 471 /* 459 472 * Beware - when entering resume, prev (the current task) is
+27 -7
arch/nios2/kernel/traps.c
··· 23 23 24 24 static DEFINE_SPINLOCK(die_lock); 25 25 26 + static void _send_sig(int signo, int code, unsigned long addr) 27 + { 28 + siginfo_t info; 29 + 30 + info.si_signo = signo; 31 + info.si_errno = 0; 32 + info.si_code = code; 33 + info.si_addr = (void __user *) addr; 34 + force_sig_info(signo, &info, current); 35 + } 36 + 26 37 void die(const char *str, struct pt_regs *regs, long err) 27 38 { 28 39 console_verbose(); ··· 50 39 51 40 void _exception(int signo, struct pt_regs *regs, int code, unsigned long addr) 52 41 { 53 - siginfo_t info; 54 - 55 42 if (!user_mode(regs)) 56 43 die("Exception in kernel mode", regs, signo); 57 44 58 - info.si_signo = signo; 59 - info.si_errno = 0; 60 - info.si_code = code; 61 - info.si_addr = (void __user *) addr; 62 - force_sig_info(signo, &info, current); 45 + _send_sig(signo, code, addr); 63 46 } 64 47 65 48 /* ··· 187 182 show_regs(regs); 188 183 189 184 pr_emerg("opcode: 0x%08lx\n", *(unsigned long *)(regs->ea)); 185 + } 186 + 187 + asmlinkage void handle_trap_1_c(struct pt_regs *fp) 188 + { 189 + _send_sig(SIGUSR1, 0, fp->ea); 190 + } 191 + 192 + asmlinkage void handle_trap_2_c(struct pt_regs *fp) 193 + { 194 + _send_sig(SIGUSR2, 0, fp->ea); 195 + } 196 + 197 + asmlinkage void handle_trap_3_c(struct pt_regs *fp) 198 + { 199 + _send_sig(SIGILL, ILL_ILLTRP, fp->ea); 190 200 }