[PARISC] Further updates to timer_interrupt()
[linux-2.6] / arch / parisc / kernel / signal.c
1 /*
2  *  linux/arch/parisc/kernel/signal.c: Architecture-specific signal
3  *  handling support.
4  *
5  *  Copyright (C) 2000 David Huggins-Daines <dhd@debian.org>
6  *  Copyright (C) 2000 Linuxcare, Inc.
7  *
8  *  Based on the ia64, i386, and alpha versions.
9  *
10  *  Like the IA-64, we are a recent enough port (we are *starting*
11  *  with glibc2.2) that we do not need to support the old non-realtime
12  *  Linux signals.  Therefore we don't.  HP/UX signals will go in
13  *  arch/parisc/hpux/signal.c when we figure out how to do them.
14  */
15
16 #include <linux/sched.h>
17 #include <linux/mm.h>
18 #include <linux/smp.h>
19 #include <linux/smp_lock.h>
20 #include <linux/kernel.h>
21 #include <linux/signal.h>
22 #include <linux/errno.h>
23 #include <linux/wait.h>
24 #include <linux/ptrace.h>
25 #include <linux/unistd.h>
26 #include <linux/stddef.h>
27 #include <linux/compat.h>
28 #include <linux/elf.h>
29 #include <asm/ucontext.h>
30 #include <asm/rt_sigframe.h>
31 #include <asm/uaccess.h>
32 #include <asm/pgalloc.h>
33 #include <asm/cacheflush.h>
34 #include <asm/asm-offsets.h>
35
36 #ifdef CONFIG_COMPAT
37 #include <linux/compat.h>
38 #include "signal32.h"
39 #endif
40
41 #define DEBUG_SIG 0 
42 #define DEBUG_SIG_LEVEL 2
43
44 #if DEBUG_SIG
45 #define DBG(LEVEL, ...) \
46         ((DEBUG_SIG_LEVEL >= LEVEL) \
47         ? printk(__VA_ARGS__) : (void) 0)
48 #else
49 #define DBG(LEVEL, ...)
50 #endif
51         
52
53 #define _BLOCKABLE (~(sigmask(SIGKILL) | sigmask(SIGSTOP)))
54
55 /* gcc will complain if a pointer is cast to an integer of different
56  * size.  If you really need to do this (and we do for an ELF32 user
57  * application in an ELF64 kernel) then you have to do a cast to an
58  * integer of the same size first.  The A() macro accomplishes
59  * this. */
60 #define A(__x)  ((unsigned long)(__x))
61
62 int do_signal(sigset_t *oldset, struct pt_regs *regs, int in_syscall);
63
64 /*
65  * Atomically swap in the new signal mask, and wait for a signal.
66  */
67 #ifdef __LP64__
68 #include "sys32.h"
69 #endif
70
71 asmlinkage int
72 sys_rt_sigsuspend(sigset_t __user *unewset, size_t sigsetsize, struct pt_regs *regs)
73 {
74         sigset_t saveset, newset;
75 #ifdef __LP64__
76         compat_sigset_t newset32;
77
78         if (is_compat_task()) {
79                 /* XXX: Don't preclude handling different sized sigset_t's.  */
80                 if (sigsetsize != sizeof(compat_sigset_t))
81                         return -EINVAL;
82                 if (copy_from_user(&newset32, (compat_sigset_t __user *)unewset, sizeof(newset32)))
83                         return -EFAULT;
84                 sigset_32to64(&newset,&newset32);
85                 
86         } else 
87 #endif
88         {
89                 /* XXX: Don't preclude handling different sized sigset_t's.  */
90                 if (sigsetsize != sizeof(sigset_t))
91                         return -EINVAL;
92         
93                 if (copy_from_user(&newset, unewset, sizeof(newset)))
94                         return -EFAULT;
95         }
96
97         sigdelsetmask(&newset, ~_BLOCKABLE);
98
99         spin_lock_irq(&current->sighand->siglock);
100         saveset = current->blocked;
101         current->blocked = newset;
102         recalc_sigpending();
103         spin_unlock_irq(&current->sighand->siglock);
104
105         regs->gr[28] = -EINTR;
106         while (1) {
107                 current->state = TASK_INTERRUPTIBLE;
108                 schedule();
109                 if (do_signal(&saveset, regs, 1))
110                         return -EINTR;
111         }
112 }
113
114 /*
115  * Do a signal return - restore sigcontext.
116  */
117
118 /* Trampoline for calling rt_sigreturn() */
119 #define INSN_LDI_R25_0   0x34190000 /* ldi  0,%r25 (in_syscall=0) */
120 #define INSN_LDI_R25_1   0x34190002 /* ldi  1,%r25 (in_syscall=1) */
121 #define INSN_LDI_R20     0x3414015a /* ldi  __NR_rt_sigreturn,%r20 */
122 #define INSN_BLE_SR2_R0  0xe4008200 /* be,l 0x100(%sr2,%r0),%sr0,%r31 */
123 #define INSN_NOP         0x08000240 /* nop */
124 /* For debugging */
125 #define INSN_DIE_HORRIBLY 0x68000ccc /* stw %r0,0x666(%sr0,%r0) */
126
127 static long
128 restore_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs)
129 {
130         long err = 0;
131
132         err |= __copy_from_user(regs->gr, sc->sc_gr, sizeof(regs->gr));
133         err |= __copy_from_user(regs->fr, sc->sc_fr, sizeof(regs->fr));
134         err |= __copy_from_user(regs->iaoq, sc->sc_iaoq, sizeof(regs->iaoq));
135         err |= __copy_from_user(regs->iasq, sc->sc_iasq, sizeof(regs->iasq));
136         err |= __get_user(regs->sar, &sc->sc_sar);
137         DBG(2,"restore_sigcontext: iaoq is 0x%#lx / 0x%#lx\n", 
138                         regs->iaoq[0],regs->iaoq[1]);
139         DBG(2,"restore_sigcontext: r28 is %ld\n", regs->gr[28]);
140         return err;
141 }
142
143 void
144 sys_rt_sigreturn(struct pt_regs *regs, int in_syscall)
145 {
146         struct rt_sigframe __user *frame;
147         struct siginfo si;
148         sigset_t set;
149         unsigned long usp = (regs->gr[30] & ~(0x01UL));
150         unsigned long sigframe_size = PARISC_RT_SIGFRAME_SIZE;
151 #ifdef __LP64__
152         compat_sigset_t compat_set;
153         struct compat_rt_sigframe __user * compat_frame;
154         
155         if (is_compat_task())
156                 sigframe_size = PARISC_RT_SIGFRAME_SIZE32;
157 #endif
158
159
160         /* Unwind the user stack to get the rt_sigframe structure. */
161         frame = (struct rt_sigframe __user *)
162                 (usp - sigframe_size);
163         DBG(2,"sys_rt_sigreturn: frame is %p\n", frame);
164
165 #ifdef __LP64__
166         compat_frame = (struct compat_rt_sigframe __user *)frame;
167         
168         if (is_compat_task()) {
169                 DBG(2,"sys_rt_sigreturn: ELF32 process.\n");
170                 if (__copy_from_user(&compat_set, &compat_frame->uc.uc_sigmask, sizeof(compat_set)))
171                         goto give_sigsegv;
172                 sigset_32to64(&set,&compat_set);
173         } else
174 #endif
175         {
176                 if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set)))
177                         goto give_sigsegv;
178         }
179                 
180         sigdelsetmask(&set, ~_BLOCKABLE);
181         spin_lock_irq(&current->sighand->siglock);
182         current->blocked = set;
183         recalc_sigpending();
184         spin_unlock_irq(&current->sighand->siglock);
185
186         /* Good thing we saved the old gr[30], eh? */
187 #ifdef __LP64__
188         if (is_compat_task()) {
189                 DBG(1,"sys_rt_sigreturn: compat_frame->uc.uc_mcontext 0x%p\n",
190                                 &compat_frame->uc.uc_mcontext);
191 // FIXME: Load upper half from register file
192                 if (restore_sigcontext32(&compat_frame->uc.uc_mcontext, 
193                                         &compat_frame->regs, regs))
194                         goto give_sigsegv;
195                 DBG(1,"sys_rt_sigreturn: usp %#08lx stack 0x%p\n", 
196                                 usp, &compat_frame->uc.uc_stack);
197                 if (do_sigaltstack32(&compat_frame->uc.uc_stack, NULL, usp) == -EFAULT)
198                         goto give_sigsegv;
199         } else
200 #endif
201         {
202                 DBG(1,"sys_rt_sigreturn: frame->uc.uc_mcontext 0x%p\n",
203                                 &frame->uc.uc_mcontext);
204                 if (restore_sigcontext(&frame->uc.uc_mcontext, regs))
205                         goto give_sigsegv;
206                 DBG(1,"sys_rt_sigreturn: usp %#08lx stack 0x%p\n", 
207                                 usp, &frame->uc.uc_stack);
208                 if (do_sigaltstack(&frame->uc.uc_stack, NULL, usp) == -EFAULT)
209                         goto give_sigsegv;
210         }
211                 
212
213
214         /* If we are on the syscall path IAOQ will not be restored, and
215          * if we are on the interrupt path we must not corrupt gr31.
216          */
217         if (in_syscall)
218                 regs->gr[31] = regs->iaoq[0];
219 #if DEBUG_SIG
220         DBG(1,"sys_rt_sigreturn: returning to %#lx, DUMPING REGS:\n", regs->iaoq[0]);
221         show_regs(regs);
222 #endif
223         return;
224
225 give_sigsegv:
226         DBG(1,"sys_rt_sigreturn: Sending SIGSEGV\n");
227         si.si_signo = SIGSEGV;
228         si.si_errno = 0;
229         si.si_code = SI_KERNEL;
230         si.si_pid = current->pid;
231         si.si_uid = current->uid;
232         si.si_addr = &frame->uc;
233         force_sig_info(SIGSEGV, &si, current);
234         return;
235 }
236
237 /*
238  * Set up a signal frame.
239  */
240
241 static inline void __user *
242 get_sigframe(struct k_sigaction *ka, unsigned long sp, size_t frame_size)
243 {
244         /*FIXME: ELF32 vs. ELF64 has different frame_size, but since we
245           don't use the parameter it doesn't matter */
246
247         DBG(1,"get_sigframe: ka = %#lx, sp = %#lx, frame_size = %#lx\n",
248                         (unsigned long)ka, sp, frame_size);
249         
250         if ((ka->sa.sa_flags & SA_ONSTACK) != 0 && ! sas_ss_flags(sp))
251                 sp = current->sas_ss_sp; /* Stacks grow up! */
252
253         DBG(1,"get_sigframe: Returning sp = %#lx\n", (unsigned long)sp);
254         return (void __user *) sp; /* Stacks grow up.  Fun. */
255 }
256
257 static long
258 setup_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs, int in_syscall)
259                  
260 {
261         unsigned long flags = 0;
262         long err = 0;
263
264         if (on_sig_stack((unsigned long) sc))
265                 flags |= PARISC_SC_FLAG_ONSTACK;
266         if (in_syscall) {
267                 flags |= PARISC_SC_FLAG_IN_SYSCALL;
268                 /* regs->iaoq is undefined in the syscall return path */
269                 err |= __put_user(regs->gr[31], &sc->sc_iaoq[0]);
270                 err |= __put_user(regs->gr[31]+4, &sc->sc_iaoq[1]);
271                 err |= __put_user(regs->sr[3], &sc->sc_iasq[0]);
272                 err |= __put_user(regs->sr[3], &sc->sc_iasq[1]);
273                 DBG(1,"setup_sigcontext: iaoq %#lx / %#lx (in syscall)\n",
274                         regs->gr[31], regs->gr[31]+4);
275         } else {
276                 err |= __copy_to_user(sc->sc_iaoq, regs->iaoq, sizeof(regs->iaoq));
277                 err |= __copy_to_user(sc->sc_iasq, regs->iasq, sizeof(regs->iasq));
278                 DBG(1,"setup_sigcontext: iaoq %#lx / %#lx (not in syscall)\n", 
279                         regs->iaoq[0], regs->iaoq[1]);
280         }
281
282         err |= __put_user(flags, &sc->sc_flags);
283         err |= __copy_to_user(sc->sc_gr, regs->gr, sizeof(regs->gr));
284         err |= __copy_to_user(sc->sc_fr, regs->fr, sizeof(regs->fr));
285         err |= __put_user(regs->sar, &sc->sc_sar);
286         DBG(1,"setup_sigcontext: r28 is %ld\n", regs->gr[28]);
287
288         return err;
289 }
290
291 static long
292 setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
293                sigset_t *set, struct pt_regs *regs, int in_syscall)
294 {
295         struct rt_sigframe __user *frame;
296         unsigned long rp, usp;
297         unsigned long haddr, sigframe_size;
298         int err = 0;
299 #ifdef __LP64__
300         compat_int_t compat_val;
301         struct compat_rt_sigframe __user * compat_frame;
302         compat_sigset_t compat_set;
303 #endif
304         
305         usp = (regs->gr[30] & ~(0x01UL));
306         /*FIXME: frame_size parameter is unused, remove it. */
307         frame = get_sigframe(ka, usp, sizeof(*frame));
308
309         DBG(1,"SETUP_RT_FRAME: START\n");
310         DBG(1,"setup_rt_frame: frame %p info %p\n", frame, info);
311
312         
313 #ifdef __LP64__
314
315         compat_frame = (struct compat_rt_sigframe __user *)frame;
316         
317         if (is_compat_task()) {
318                 DBG(1,"setup_rt_frame: frame->info = 0x%p\n", &compat_frame->info);
319                 err |= copy_siginfo_to_user32(&compat_frame->info, info);
320                 DBG(1,"SETUP_RT_FRAME: 1\n");
321                 compat_val = (compat_int_t)current->sas_ss_sp;
322                 err |= __put_user(compat_val, &compat_frame->uc.uc_stack.ss_sp);
323                 DBG(1,"SETUP_RT_FRAME: 2\n");
324                 compat_val = (compat_int_t)current->sas_ss_size;
325                 err |= __put_user(compat_val, &compat_frame->uc.uc_stack.ss_size);
326                 DBG(1,"SETUP_RT_FRAME: 3\n");
327                 compat_val = sas_ss_flags(regs->gr[30]);                
328                 err |= __put_user(compat_val, &compat_frame->uc.uc_stack.ss_flags);             
329                 DBG(1,"setup_rt_frame: frame->uc = 0x%p\n", &compat_frame->uc);
330                 DBG(1,"setup_rt_frame: frame->uc.uc_mcontext = 0x%p\n", &compat_frame->uc.uc_mcontext);
331                 err |= setup_sigcontext32(&compat_frame->uc.uc_mcontext, 
332                                         &compat_frame->regs, regs, in_syscall);
333                 sigset_64to32(&compat_set,set);
334                 err |= __copy_to_user(&compat_frame->uc.uc_sigmask, &compat_set, sizeof(compat_set));
335         } else
336 #endif
337         {       
338                 DBG(1,"setup_rt_frame: frame->info = 0x%p\n", &frame->info);
339                 err |= copy_siginfo_to_user(&frame->info, info);
340                 err |= __put_user(current->sas_ss_sp, &frame->uc.uc_stack.ss_sp);
341                 err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size);
342                 err |= __put_user(sas_ss_flags(regs->gr[30]),
343                                   &frame->uc.uc_stack.ss_flags);
344                 DBG(1,"setup_rt_frame: frame->uc = 0x%p\n", &frame->uc);
345                 DBG(1,"setup_rt_frame: frame->uc.uc_mcontext = 0x%p\n", &frame->uc.uc_mcontext);
346                 err |= setup_sigcontext(&frame->uc.uc_mcontext, regs, in_syscall);
347                 /* FIXME: Should probably be converted aswell for the compat case */
348                 err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
349         }
350         
351         if (err)
352                 goto give_sigsegv;
353
354         /* Set up to return from userspace.  If provided, use a stub
355            already in userspace. The first words of tramp are used to
356            save the previous sigrestartblock trampoline that might be
357            on the stack. We start the sigreturn trampoline at 
358            SIGRESTARTBLOCK_TRAMP+X. */
359         err |= __put_user(in_syscall ? INSN_LDI_R25_1 : INSN_LDI_R25_0,
360                         &frame->tramp[SIGRESTARTBLOCK_TRAMP+0]);
361         err |= __put_user(INSN_LDI_R20, 
362                         &frame->tramp[SIGRESTARTBLOCK_TRAMP+1]);
363         err |= __put_user(INSN_BLE_SR2_R0, 
364                         &frame->tramp[SIGRESTARTBLOCK_TRAMP+2]);
365         err |= __put_user(INSN_NOP, &frame->tramp[SIGRESTARTBLOCK_TRAMP+3]);
366
367 #if DEBUG_SIG
368         /* Assert that we're flushing in the correct space... */
369         {
370                 int sid;
371                 asm ("mfsp %%sr3,%0" : "=r" (sid));
372                 DBG(1,"setup_rt_frame: Flushing 64 bytes at space %#x offset %p\n",
373                        sid, frame->tramp);
374         }
375 #endif
376
377         flush_user_dcache_range((unsigned long) &frame->tramp[0],
378                            (unsigned long) &frame->tramp[TRAMP_SIZE]);
379         flush_user_icache_range((unsigned long) &frame->tramp[0],
380                            (unsigned long) &frame->tramp[TRAMP_SIZE]);
381
382         /* TRAMP Words 0-4, Lenght 5 = SIGRESTARTBLOCK_TRAMP
383          * TRAMP Words 5-9, Length 4 = SIGRETURN_TRAMP
384          * So the SIGRETURN_TRAMP is at the end of SIGRESTARTBLOCK_TRAMP
385          */
386         rp = (unsigned long) &frame->tramp[SIGRESTARTBLOCK_TRAMP];
387
388         if (err)
389                 goto give_sigsegv;
390
391         haddr = A(ka->sa.sa_handler);
392         /* The sa_handler may be a pointer to a function descriptor */
393 #ifdef __LP64__
394         if (is_compat_task()) {
395 #endif
396                 if (haddr & PA_PLABEL_FDESC) {
397                         Elf32_Fdesc fdesc;
398                         Elf32_Fdesc __user *ufdesc = (Elf32_Fdesc __user *)A(haddr & ~3);
399
400                         err = __copy_from_user(&fdesc, ufdesc, sizeof(fdesc));
401
402                         if (err)
403                                 goto give_sigsegv;
404
405                         haddr = fdesc.addr;
406                         regs->gr[19] = fdesc.gp;
407                 }
408 #ifdef __LP64__
409         } else {
410                 Elf64_Fdesc fdesc;
411                 Elf64_Fdesc __user *ufdesc = (Elf64_Fdesc __user *)A(haddr & ~3);
412                 
413                 err = __copy_from_user(&fdesc, ufdesc, sizeof(fdesc));
414                 
415                 if (err)
416                         goto give_sigsegv;
417                 
418                 haddr = fdesc.addr;
419                 regs->gr[19] = fdesc.gp;
420                 DBG(1,"setup_rt_frame: 64 bit signal, exe=%#lx, r19=%#lx, in_syscall=%d\n",
421                      haddr, regs->gr[19], in_syscall);
422         }
423 #endif
424
425         /* The syscall return path will create IAOQ values from r31.
426          */
427         sigframe_size = PARISC_RT_SIGFRAME_SIZE;
428 #ifdef __LP64__
429         if (is_compat_task())
430                 sigframe_size = PARISC_RT_SIGFRAME_SIZE32;
431 #endif
432         if (in_syscall) {
433                 regs->gr[31] = haddr;
434 #ifdef __LP64__
435                 if (!test_thread_flag(TIF_32BIT))
436                         sigframe_size |= 1;
437 #endif
438         } else {
439                 unsigned long psw = USER_PSW;
440 #ifdef __LP64__
441                 if (!test_thread_flag(TIF_32BIT))
442                         psw |= PSW_W;
443 #endif
444
445                 /* If we are singlestepping, arrange a trap to be delivered
446                    when we return to userspace. Note the semantics -- we
447                    should trap before the first insn in the handler is
448                    executed. Ref:
449                         http://sources.redhat.com/ml/gdb/2004-11/msg00245.html
450                  */
451                 if (pa_psw(current)->r) {
452                         pa_psw(current)->r = 0;
453                         psw |= PSW_R;
454                         mtctl(-1, 0);
455                 }
456
457                 regs->gr[0] = psw;
458                 regs->iaoq[0] = haddr | 3;
459                 regs->iaoq[1] = regs->iaoq[0] + 4;
460         }
461
462         regs->gr[2]  = rp;                /* userland return pointer */
463         regs->gr[26] = sig;               /* signal number */
464         
465 #ifdef __LP64__
466         if (is_compat_task()) {
467                 regs->gr[25] = A(&compat_frame->info); /* siginfo pointer */
468                 regs->gr[24] = A(&compat_frame->uc);   /* ucontext pointer */
469         } else
470 #endif
471         {               
472                 regs->gr[25] = A(&frame->info); /* siginfo pointer */
473                 regs->gr[24] = A(&frame->uc);   /* ucontext pointer */
474         }
475         
476         DBG(1,"setup_rt_frame: making sigreturn frame: %#lx + %#lx = %#lx\n",
477                regs->gr[30], sigframe_size,
478                regs->gr[30] + sigframe_size);
479         /* Raise the user stack pointer to make a proper call frame. */
480         regs->gr[30] = (A(frame) + sigframe_size);
481
482
483         DBG(1,"setup_rt_frame: sig deliver (%s,%d) frame=0x%p sp=%#lx iaoq=%#lx/%#lx rp=%#lx\n",
484                current->comm, current->pid, frame, regs->gr[30],
485                regs->iaoq[0], regs->iaoq[1], rp);
486
487         return 1;
488
489 give_sigsegv:
490         DBG(1,"setup_rt_frame: sending SIGSEGV\n");
491         force_sigsegv(sig, current);
492         return 0;
493 }
494
495 /*
496  * OK, we're invoking a handler.
497  */     
498
499 static long
500 handle_signal(unsigned long sig, siginfo_t *info, struct k_sigaction *ka,
501                 sigset_t *oldset, struct pt_regs *regs, int in_syscall)
502 {
503         DBG(1,"handle_signal: sig=%ld, ka=%p, info=%p, oldset=%p, regs=%p\n",
504                sig, ka, info, oldset, regs);
505         
506         /* Set up the stack frame */
507         if (!setup_rt_frame(sig, ka, info, oldset, regs, in_syscall))
508                 return 0;
509
510         spin_lock_irq(&current->sighand->siglock);
511         sigorsets(&current->blocked,&current->blocked,&ka->sa.sa_mask);
512         if (!(ka->sa.sa_flags & SA_NODEFER))
513                 sigaddset(&current->blocked,sig);
514         recalc_sigpending();
515         spin_unlock_irq(&current->sighand->siglock);
516         return 1;
517 }
518
519 /*
520  * Note that 'init' is a special process: it doesn't get signals it doesn't
521  * want to handle. Thus you cannot kill init even with a SIGKILL even by
522  * mistake.
523  *
524  * We need to be able to restore the syscall arguments (r21-r26) to
525  * restart syscalls.  Thus, the syscall path should save them in the
526  * pt_regs structure (it's okay to do so since they are caller-save
527  * registers).  As noted below, the syscall number gets restored for
528  * us due to the magic of delayed branching.
529  */
530
531 asmlinkage int
532 do_signal(sigset_t *oldset, struct pt_regs *regs, int in_syscall)
533 {
534         siginfo_t info;
535         struct k_sigaction ka;
536         int signr;
537
538         DBG(1,"\ndo_signal: oldset=0x%p, regs=0x%p, sr7 %#lx, in_syscall=%d\n",
539                oldset, regs, regs->sr[7], in_syscall);
540
541         /* Everyone else checks to see if they are in kernel mode at
542            this point and exits if that's the case.  I'm not sure why
543            we would be called in that case, but for some reason we
544            are. */
545
546         if (!oldset)
547                 oldset = &current->blocked;
548
549         DBG(1,"do_signal: oldset %08lx / %08lx\n", 
550                 oldset->sig[0], oldset->sig[1]);
551
552
553         /* May need to force signal if handle_signal failed to deliver */
554         while (1) {
555           
556                 signr = get_signal_to_deliver(&info, &ka, regs, NULL);
557                 DBG(3,"do_signal: signr = %d, regs->gr[28] = %ld\n", signr, regs->gr[28]); 
558         
559                 if (signr <= 0)
560                   break;
561                 
562                 /* Restart a system call if necessary. */
563                 if (in_syscall) {
564                         /* Check the return code */
565                         switch (regs->gr[28]) {
566                         case -ERESTART_RESTARTBLOCK:
567                                 current_thread_info()->restart_block.fn = do_no_restart_syscall;
568                         case -ERESTARTNOHAND:
569                                 DBG(1,"ERESTARTNOHAND: returning -EINTR\n");
570                                 regs->gr[28] = -EINTR;
571                                 break;
572
573                         case -ERESTARTSYS:
574                                 if (!(ka.sa.sa_flags & SA_RESTART)) {
575                                         DBG(1,"ERESTARTSYS: putting -EINTR\n");
576                                         regs->gr[28] = -EINTR;
577                                         break;
578                                 }
579                         /* fallthrough */
580                         case -ERESTARTNOINTR:
581                                 /* A syscall is just a branch, so all
582                                    we have to do is fiddle the return pointer. */
583                                 regs->gr[31] -= 8; /* delayed branching */
584                                 /* Preserve original r28. */
585                                 regs->gr[28] = regs->orig_r28;
586                                 break;
587                         }
588                 }
589                 /* Whee!  Actually deliver the signal.  If the
590                    delivery failed, we need to continue to iterate in
591                    this loop so we can deliver the SIGSEGV... */
592                 if (handle_signal(signr, &info, &ka, oldset, regs, in_syscall)) {
593                         DBG(1,KERN_DEBUG "do_signal: Exit (success), regs->gr[28] = %ld\n",
594                                 regs->gr[28]);
595                         return 1;
596                 }
597         }
598         /* end of while(1) looping forever if we can't force a signal */
599
600         /* Did we come from a system call? */
601         if (in_syscall) {
602                 /* Restart the system call - no handlers present */
603                 if (regs->gr[28] == -ERESTART_RESTARTBLOCK) {
604                         unsigned int *usp = (unsigned int *)regs->gr[30];
605
606                         /* Setup a trampoline to restart the syscall
607                          * with __NR_restart_syscall
608                          *
609                          *  0: <return address (orig r31)>
610                          *  4: <2nd half for 64-bit>
611                          *  8: ldw 0(%sp), %r31
612                          * 12: be 0x100(%sr2, %r0)
613                          * 16: ldi __NR_restart_syscall, %r20
614                          */
615 #ifndef __LP64__
616                         put_user(regs->gr[31], &usp[0]);
617                         put_user(0x0fc0109f, &usp[2]);
618 #else
619                         put_user(regs->gr[31] >> 32, &usp[0]);
620                         put_user(regs->gr[31] & 0xffffffff, &usp[1]);
621                         put_user(0x0fc010df, &usp[2]);
622 #endif
623                         put_user(0xe0008200, &usp[3]);
624                         put_user(0x34140000, &usp[4]);
625
626                         /* Stack is 64-byte aligned, and we only need
627                          * to flush 1 cache line.
628                          * Flushing one cacheline is cheap.
629                          * "sync" on bigger (> 4 way) boxes is not.
630                          */
631                         asm("fdc %%r0(%%sr3, %0)\n"
632                             "sync\n"
633                             "fic %%r0(%%sr3, %0)\n"
634                             "sync\n"
635                             : : "r"(regs->gr[30]));
636
637                         regs->gr[31] = regs->gr[30] + 8;
638                         /* Preserve original r28. */
639                         regs->gr[28] = regs->orig_r28;
640                 } else if (regs->gr[28] == -ERESTARTNOHAND ||
641                            regs->gr[28] == -ERESTARTSYS ||
642                            regs->gr[28] == -ERESTARTNOINTR) {
643                         /* Hooray for delayed branching.  We don't
644                            have to restore %r20 (the system call
645                            number) because it gets loaded in the delay
646                            slot of the branch external instruction. */
647                         regs->gr[31] -= 8;
648                         /* Preserve original r28. */
649                         regs->gr[28] = regs->orig_r28;
650                 }
651         }
652         
653         DBG(1,"do_signal: Exit (not delivered), regs->gr[28] = %ld\n", 
654                 regs->gr[28]);
655
656         return 0;
657 }