diff options
| author | Richard Weinberger <richard@nod.at> | 2013-10-07 08:14:38 -0400 |
|---|---|---|
| committer | Richard Weinberger <richard@sigma-star.at> | 2014-08-06 07:02:16 -0400 |
| commit | 9c53c7ec14a5738ae3117d7d71b7abf630526c9f (patch) | |
| tree | 7b917fe8581274648e949eaea2686b2dc29676e7 /arch/microblaze | |
| parent | 0d97500d393012690f3579056629bea0369e6554 (diff) | |
microblaze: Use get_signal() signal_setup_done()
Use the more generic functions get_signal() signal_setup_done()
for signal delivery.
Signed-off-by: Richard Weinberger <richard@nod.at>
Diffstat (limited to 'arch/microblaze')
| -rw-r--r-- | arch/microblaze/kernel/signal.c | 48 |
1 files changed, 17 insertions, 31 deletions
diff --git a/arch/microblaze/kernel/signal.c b/arch/microblaze/kernel/signal.c index 49a07a4d76d0..83137e868e19 100644 --- a/arch/microblaze/kernel/signal.c +++ b/arch/microblaze/kernel/signal.c | |||
| @@ -156,11 +156,11 @@ get_sigframe(struct k_sigaction *ka, struct pt_regs *regs, size_t frame_size) | |||
| 156 | return (void __user *)((sp - frame_size) & -8UL); | 156 | return (void __user *)((sp - frame_size) & -8UL); |
| 157 | } | 157 | } |
| 158 | 158 | ||
| 159 | static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, | 159 | static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, |
| 160 | sigset_t *set, struct pt_regs *regs) | 160 | struct pt_regs *regs) |
| 161 | { | 161 | { |
| 162 | struct rt_sigframe __user *frame; | 162 | struct rt_sigframe __user *frame; |
| 163 | int err = 0; | 163 | int err = 0, sig = ksig->sig; |
| 164 | int signal; | 164 | int signal; |
| 165 | unsigned long address = 0; | 165 | unsigned long address = 0; |
| 166 | #ifdef CONFIG_MMU | 166 | #ifdef CONFIG_MMU |
| @@ -168,10 +168,10 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, | |||
| 168 | pte_t *ptep; | 168 | pte_t *ptep; |
| 169 | #endif | 169 | #endif |
| 170 | 170 | ||
| 171 | frame = get_sigframe(ka, regs, sizeof(*frame)); | 171 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame)); |
| 172 | 172 | ||
| 173 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 173 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) |
| 174 | goto give_sigsegv; | 174 | return -EFAULT; |
| 175 | 175 | ||
| 176 | signal = current_thread_info()->exec_domain | 176 | signal = current_thread_info()->exec_domain |
| 177 | && current_thread_info()->exec_domain->signal_invmap | 177 | && current_thread_info()->exec_domain->signal_invmap |
| @@ -179,8 +179,8 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, | |||
| 179 | ? current_thread_info()->exec_domain->signal_invmap[sig] | 179 | ? current_thread_info()->exec_domain->signal_invmap[sig] |
| 180 | : sig; | 180 | : sig; |
| 181 | 181 | ||
| 182 | if (info) | 182 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) |
| 183 | err |= copy_siginfo_to_user(&frame->info, info); | 183 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); |
| 184 | 184 | ||
| 185 | /* Create the ucontext. */ | 185 | /* Create the ucontext. */ |
| 186 | err |= __put_user(0, &frame->uc.uc_flags); | 186 | err |= __put_user(0, &frame->uc.uc_flags); |
| @@ -227,7 +227,7 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, | |||
| 227 | flush_dcache_range(address, address + 8); | 227 | flush_dcache_range(address, address + 8); |
| 228 | #endif | 228 | #endif |
| 229 | if (err) | 229 | if (err) |
| 230 | goto give_sigsegv; | 230 | return -EFAULT; |
| 231 | 231 | ||
| 232 | /* Set up registers for signal handler */ | 232 | /* Set up registers for signal handler */ |
| 233 | regs->r1 = (unsigned long) frame; | 233 | regs->r1 = (unsigned long) frame; |
| @@ -237,7 +237,7 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, | |||
| 237 | regs->r6 = (unsigned long) &frame->info; /* arg 1: siginfo */ | 237 | regs->r6 = (unsigned long) &frame->info; /* arg 1: siginfo */ |
| 238 | regs->r7 = (unsigned long) &frame->uc; /* arg2: ucontext */ | 238 | regs->r7 = (unsigned long) &frame->uc; /* arg2: ucontext */ |
| 239 | /* Offset to handle microblaze rtid r14, 0 */ | 239 | /* Offset to handle microblaze rtid r14, 0 */ |
| 240 | regs->pc = (unsigned long)ka->sa.sa_handler; | 240 | regs->pc = (unsigned long)ksig->ka.sa.sa_handler; |
| 241 | 241 | ||
| 242 | set_fs(USER_DS); | 242 | set_fs(USER_DS); |
| 243 | 243 | ||
| @@ -247,10 +247,6 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, | |||
| 247 | #endif | 247 | #endif |
| 248 | 248 | ||
| 249 | return 0; | 249 | return 0; |
| 250 | |||
| 251 | give_sigsegv: | ||
| 252 | force_sigsegv(sig, current); | ||
| 253 | return -EFAULT; | ||
| 254 | } | 250 | } |
| 255 | 251 | ||
| 256 | /* Handle restarting system calls */ | 252 | /* Handle restarting system calls */ |
| @@ -283,23 +279,15 @@ do_restart: | |||
| 283 | */ | 279 | */ |
| 284 | 280 | ||
| 285 | static void | 281 | static void |
| 286 | handle_signal(unsigned long sig, struct k_sigaction *ka, | 282 | handle_signal(struct ksignal *ksig, struct pt_regs *regs) |
| 287 | siginfo_t *info, struct pt_regs *regs) | ||
| 288 | { | 283 | { |
| 289 | sigset_t *oldset = sigmask_to_save(); | 284 | sigset_t *oldset = sigmask_to_save(); |
| 290 | int ret; | 285 | int ret; |
| 291 | 286 | ||
| 292 | /* Set up the stack frame */ | 287 | /* Set up the stack frame */ |
| 293 | if (ka->sa.sa_flags & SA_SIGINFO) | 288 | ret = setup_rt_frame(ksig, oldset, regs); |
| 294 | ret = setup_rt_frame(sig, ka, info, oldset, regs); | ||
| 295 | else | ||
| 296 | ret = setup_rt_frame(sig, ka, NULL, oldset, regs); | ||
| 297 | 289 | ||
| 298 | if (ret) | 290 | signal_setup_done(ret, ksig, test_thread_flag(TIF_SINGLESTEP)); |
| 299 | return; | ||
| 300 | |||
| 301 | signal_delivered(sig, info, ka, regs, | ||
| 302 | test_thread_flag(TIF_SINGLESTEP)); | ||
| 303 | } | 291 | } |
| 304 | 292 | ||
| 305 | /* | 293 | /* |
| @@ -313,21 +301,19 @@ handle_signal(unsigned long sig, struct k_sigaction *ka, | |||
| 313 | */ | 301 | */ |
| 314 | static void do_signal(struct pt_regs *regs, int in_syscall) | 302 | static void do_signal(struct pt_regs *regs, int in_syscall) |
| 315 | { | 303 | { |
| 316 | siginfo_t info; | 304 | struct ksignal ksig; |
| 317 | int signr; | 305 | |
| 318 | struct k_sigaction ka; | ||
| 319 | #ifdef DEBUG_SIG | 306 | #ifdef DEBUG_SIG |
| 320 | pr_info("do signal: %p %d\n", regs, in_syscall); | 307 | pr_info("do signal: %p %d\n", regs, in_syscall); |
| 321 | pr_info("do signal2: %lx %lx %ld [%lx]\n", regs->pc, regs->r1, | 308 | pr_info("do signal2: %lx %lx %ld [%lx]\n", regs->pc, regs->r1, |
| 322 | regs->r12, current_thread_info()->flags); | 309 | regs->r12, current_thread_info()->flags); |
| 323 | #endif | 310 | #endif |
| 324 | 311 | ||
| 325 | signr = get_signal_to_deliver(&info, &ka, regs, NULL); | 312 | if (get_signal(&ksig)) { |
| 326 | if (signr > 0) { | ||
| 327 | /* Whee! Actually deliver the signal. */ | 313 | /* Whee! Actually deliver the signal. */ |
| 328 | if (in_syscall) | 314 | if (in_syscall) |
| 329 | handle_restart(regs, &ka, 1); | 315 | handle_restart(regs, &ksig.ka, 1); |
| 330 | handle_signal(signr, &ka, &info, regs); | 316 | handle_signal(&ksig, regs); |
| 331 | return; | 317 | return; |
| 332 | } | 318 | } |
| 333 | 319 | ||
