diff options
author | Eric W. Biederman <ebiederm@xmission.com> | 2018-04-15 21:14:10 -0400 |
---|---|---|
committer | Eric W. Biederman <ebiederm@xmission.com> | 2018-04-25 11:44:05 -0400 |
commit | 75bfb9a1c89ae1f28cd09f7ae0d236ebde9b97ec (patch) | |
tree | 10bf007bd8672c57cd06c890ff1d81078f5b1c7e | |
parent | c046e2c693c770153acb568e56c0c41cce9c91e2 (diff) |
signal/openrisc: Use force_sig_fault where appropriate
Filling in struct siginfo before calling force_sig_info a tedious and
error prone process, where once in a great while the wrong fields
are filled out, and siginfo has been inconsistently cleared.
Simplify this process by using the helper force_sig_fault. Which
takes as a parameters all of the information it needs, ensures
all of the fiddly bits of filling in struct siginfo are done properly
and then calls force_sig_info.
In short about a 5 line reduction in code for every time force_sig_info
is called, which makes the calling function clearer.
Cc: Jonas Bonn <jonas@southpole.se>
Cc: Stefan Kristiansson <stefan.kristiansson@saunalahti.fi>
Cc: Stafford Horne <shorne@gmail.com>
Cc: openrisc@lists.librecores.org
Signed-off-by: "Eric W. Biederman" <ebiederm@xmission.com>
-rw-r--r-- | arch/openrisc/kernel/traps.c | 33 | ||||
-rw-r--r-- | arch/openrisc/mm/fault.c | 19 |
2 files changed, 9 insertions, 43 deletions
diff --git a/arch/openrisc/kernel/traps.c b/arch/openrisc/kernel/traps.c index 1610b1d65a11..fac246e6f37a 100644 --- a/arch/openrisc/kernel/traps.c +++ b/arch/openrisc/kernel/traps.c | |||
@@ -250,28 +250,16 @@ void __init trap_init(void) | |||
250 | 250 | ||
251 | asmlinkage void do_trap(struct pt_regs *regs, unsigned long address) | 251 | asmlinkage void do_trap(struct pt_regs *regs, unsigned long address) |
252 | { | 252 | { |
253 | siginfo_t info; | 253 | force_sig_fault(SIGTRAP, TRAP_TRACE, (void __user *)address, current); |
254 | clear_siginfo(&info); | ||
255 | info.si_signo = SIGTRAP; | ||
256 | info.si_code = TRAP_TRACE; | ||
257 | info.si_addr = (void *)address; | ||
258 | force_sig_info(SIGTRAP, &info, current); | ||
259 | 254 | ||
260 | regs->pc += 4; | 255 | regs->pc += 4; |
261 | } | 256 | } |
262 | 257 | ||
263 | asmlinkage void do_unaligned_access(struct pt_regs *regs, unsigned long address) | 258 | asmlinkage void do_unaligned_access(struct pt_regs *regs, unsigned long address) |
264 | { | 259 | { |
265 | siginfo_t info; | ||
266 | |||
267 | if (user_mode(regs)) { | 260 | if (user_mode(regs)) { |
268 | /* Send a SIGBUS */ | 261 | /* Send a SIGBUS */ |
269 | clear_siginfo(&info); | 262 | force_sig_fault(SIGBUS, BUS_ADRALN, (void __user *)address, current); |
270 | info.si_signo = SIGBUS; | ||
271 | info.si_errno = 0; | ||
272 | info.si_code = BUS_ADRALN; | ||
273 | info.si_addr = (void __user *)address; | ||
274 | force_sig_info(SIGBUS, &info, current); | ||
275 | } else { | 263 | } else { |
276 | printk("KERNEL: Unaligned Access 0x%.8lx\n", address); | 264 | printk("KERNEL: Unaligned Access 0x%.8lx\n", address); |
277 | show_registers(regs); | 265 | show_registers(regs); |
@@ -282,16 +270,9 @@ asmlinkage void do_unaligned_access(struct pt_regs *regs, unsigned long address) | |||
282 | 270 | ||
283 | asmlinkage void do_bus_fault(struct pt_regs *regs, unsigned long address) | 271 | asmlinkage void do_bus_fault(struct pt_regs *regs, unsigned long address) |
284 | { | 272 | { |
285 | siginfo_t info; | ||
286 | |||
287 | if (user_mode(regs)) { | 273 | if (user_mode(regs)) { |
288 | /* Send a SIGBUS */ | 274 | /* Send a SIGBUS */ |
289 | clear_siginfo(&info); | 275 | force_sig_fault(SIGBUS, BUS_ADRERR, (void __user *)address, current); |
290 | info.si_signo = SIGBUS; | ||
291 | info.si_errno = 0; | ||
292 | info.si_code = BUS_ADRERR; | ||
293 | info.si_addr = (void *)address; | ||
294 | force_sig_info(SIGBUS, &info, current); | ||
295 | } else { /* Kernel mode */ | 276 | } else { /* Kernel mode */ |
296 | printk("KERNEL: Bus error (SIGBUS) 0x%.8lx\n", address); | 277 | printk("KERNEL: Bus error (SIGBUS) 0x%.8lx\n", address); |
297 | show_registers(regs); | 278 | show_registers(regs); |
@@ -466,7 +447,6 @@ static inline void simulate_swa(struct pt_regs *regs, unsigned long address, | |||
466 | asmlinkage void do_illegal_instruction(struct pt_regs *regs, | 447 | asmlinkage void do_illegal_instruction(struct pt_regs *regs, |
467 | unsigned long address) | 448 | unsigned long address) |
468 | { | 449 | { |
469 | siginfo_t info; | ||
470 | unsigned int op; | 450 | unsigned int op; |
471 | unsigned int insn = *((unsigned int *)address); | 451 | unsigned int insn = *((unsigned int *)address); |
472 | 452 | ||
@@ -487,12 +467,7 @@ asmlinkage void do_illegal_instruction(struct pt_regs *regs, | |||
487 | 467 | ||
488 | if (user_mode(regs)) { | 468 | if (user_mode(regs)) { |
489 | /* Send a SIGILL */ | 469 | /* Send a SIGILL */ |
490 | clear_siginfo(&info); | 470 | force_sig_fault(SIGILL, ILL_ILLOPC, (void __user *)address, current); |
491 | info.si_signo = SIGILL; | ||
492 | info.si_errno = 0; | ||
493 | info.si_code = ILL_ILLOPC; | ||
494 | info.si_addr = (void *)address; | ||
495 | force_sig_info(SIGBUS, &info, current); | ||
496 | } else { /* Kernel mode */ | 471 | } else { /* Kernel mode */ |
497 | printk("KERNEL: Illegal instruction (SIGILL) 0x%.8lx\n", | 472 | printk("KERNEL: Illegal instruction (SIGILL) 0x%.8lx\n", |
498 | address); | 473 | address); |
diff --git a/arch/openrisc/mm/fault.c b/arch/openrisc/mm/fault.c index 68be33e4ae17..9f011d16cc46 100644 --- a/arch/openrisc/mm/fault.c +++ b/arch/openrisc/mm/fault.c | |||
@@ -52,11 +52,10 @@ asmlinkage void do_page_fault(struct pt_regs *regs, unsigned long address, | |||
52 | struct task_struct *tsk; | 52 | struct task_struct *tsk; |
53 | struct mm_struct *mm; | 53 | struct mm_struct *mm; |
54 | struct vm_area_struct *vma; | 54 | struct vm_area_struct *vma; |
55 | siginfo_t info; | 55 | int si_code; |
56 | int fault; | 56 | int fault; |
57 | unsigned int flags = FAULT_FLAG_ALLOW_RETRY | FAULT_FLAG_KILLABLE; | 57 | unsigned int flags = FAULT_FLAG_ALLOW_RETRY | FAULT_FLAG_KILLABLE; |
58 | 58 | ||
59 | clear_siginfo(&info); | ||
60 | tsk = current; | 59 | tsk = current; |
61 | 60 | ||
62 | /* | 61 | /* |
@@ -98,7 +97,7 @@ asmlinkage void do_page_fault(struct pt_regs *regs, unsigned long address, | |||
98 | } | 97 | } |
99 | 98 | ||
100 | mm = tsk->mm; | 99 | mm = tsk->mm; |
101 | info.si_code = SEGV_MAPERR; | 100 | si_code = SEGV_MAPERR; |
102 | 101 | ||
103 | /* | 102 | /* |
104 | * If we're in an interrupt or have no user | 103 | * If we're in an interrupt or have no user |
@@ -140,7 +139,7 @@ retry: | |||
140 | */ | 139 | */ |
141 | 140 | ||
142 | good_area: | 141 | good_area: |
143 | info.si_code = SEGV_ACCERR; | 142 | si_code = SEGV_ACCERR; |
144 | 143 | ||
145 | /* first do some preliminary protection checks */ | 144 | /* first do some preliminary protection checks */ |
146 | 145 | ||
@@ -214,11 +213,7 @@ bad_area_nosemaphore: | |||
214 | /* User mode accesses just cause a SIGSEGV */ | 213 | /* User mode accesses just cause a SIGSEGV */ |
215 | 214 | ||
216 | if (user_mode(regs)) { | 215 | if (user_mode(regs)) { |
217 | info.si_signo = SIGSEGV; | 216 | force_sig_fault(SIGSEGV, si_code, (void __user *)address, tsk); |
218 | info.si_errno = 0; | ||
219 | /* info.si_code has been set above */ | ||
220 | info.si_addr = (void *)address; | ||
221 | force_sig_info(SIGSEGV, &info, tsk); | ||
222 | return; | 217 | return; |
223 | } | 218 | } |
224 | 219 | ||
@@ -283,11 +278,7 @@ do_sigbus: | |||
283 | * Send a sigbus, regardless of whether we were in kernel | 278 | * Send a sigbus, regardless of whether we were in kernel |
284 | * or user mode. | 279 | * or user mode. |
285 | */ | 280 | */ |
286 | info.si_signo = SIGBUS; | 281 | force_sig_fault(SIGBUS, BUS_ADRERR, (void __user *)address, tsk); |
287 | info.si_errno = 0; | ||
288 | info.si_code = BUS_ADRERR; | ||
289 | info.si_addr = (void *)address; | ||
290 | force_sig_info(SIGBUS, &info, tsk); | ||
291 | 282 | ||
292 | /* Kernel mode? Handle exceptions or die */ | 283 | /* Kernel mode? Handle exceptions or die */ |
293 | if (!user_mode(regs)) | 284 | if (!user_mode(regs)) |