]> Git Repo - qemu.git/blob - linux-user/signal.c
linux-user: Minimum Sig Handler Stack Size for PPC64 ELF V2
[qemu.git] / linux-user / signal.c
1 /*
2  *  Emulation of Linux signals
3  *
4  *  Copyright (c) 2003 Fabrice Bellard
5  *
6  *  This program is free software; you can redistribute it and/or modify
7  *  it under the terms of the GNU General Public License as published by
8  *  the Free Software Foundation; either version 2 of the License, or
9  *  (at your option) any later version.
10  *
11  *  This program is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *  GNU General Public License for more details.
15  *
16  *  You should have received a copy of the GNU General Public License
17  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
18  */
19 #include <stdlib.h>
20 #include <stdio.h>
21 #include <string.h>
22 #include <stdarg.h>
23 #include <unistd.h>
24 #include <errno.h>
25 #include <assert.h>
26 #include <sys/ucontext.h>
27 #include <sys/resource.h>
28
29 #include "qemu.h"
30 #include "qemu-common.h"
31 #include "target_signal.h"
32
33 //#define DEBUG_SIGNAL
34
35 static struct target_sigaltstack target_sigaltstack_used = {
36     .ss_sp = 0,
37     .ss_size = 0,
38     .ss_flags = TARGET_SS_DISABLE,
39 };
40
41 static struct target_sigaction sigact_table[TARGET_NSIG];
42
43 static void host_signal_handler(int host_signum, siginfo_t *info,
44                                 void *puc);
45
46 static uint8_t host_to_target_signal_table[_NSIG] = {
47     [SIGHUP] = TARGET_SIGHUP,
48     [SIGINT] = TARGET_SIGINT,
49     [SIGQUIT] = TARGET_SIGQUIT,
50     [SIGILL] = TARGET_SIGILL,
51     [SIGTRAP] = TARGET_SIGTRAP,
52     [SIGABRT] = TARGET_SIGABRT,
53 /*    [SIGIOT] = TARGET_SIGIOT,*/
54     [SIGBUS] = TARGET_SIGBUS,
55     [SIGFPE] = TARGET_SIGFPE,
56     [SIGKILL] = TARGET_SIGKILL,
57     [SIGUSR1] = TARGET_SIGUSR1,
58     [SIGSEGV] = TARGET_SIGSEGV,
59     [SIGUSR2] = TARGET_SIGUSR2,
60     [SIGPIPE] = TARGET_SIGPIPE,
61     [SIGALRM] = TARGET_SIGALRM,
62     [SIGTERM] = TARGET_SIGTERM,
63 #ifdef SIGSTKFLT
64     [SIGSTKFLT] = TARGET_SIGSTKFLT,
65 #endif
66     [SIGCHLD] = TARGET_SIGCHLD,
67     [SIGCONT] = TARGET_SIGCONT,
68     [SIGSTOP] = TARGET_SIGSTOP,
69     [SIGTSTP] = TARGET_SIGTSTP,
70     [SIGTTIN] = TARGET_SIGTTIN,
71     [SIGTTOU] = TARGET_SIGTTOU,
72     [SIGURG] = TARGET_SIGURG,
73     [SIGXCPU] = TARGET_SIGXCPU,
74     [SIGXFSZ] = TARGET_SIGXFSZ,
75     [SIGVTALRM] = TARGET_SIGVTALRM,
76     [SIGPROF] = TARGET_SIGPROF,
77     [SIGWINCH] = TARGET_SIGWINCH,
78     [SIGIO] = TARGET_SIGIO,
79     [SIGPWR] = TARGET_SIGPWR,
80     [SIGSYS] = TARGET_SIGSYS,
81     /* next signals stay the same */
82     /* Nasty hack: Reverse SIGRTMIN and SIGRTMAX to avoid overlap with
83        host libpthread signals.  This assumes no one actually uses SIGRTMAX :-/
84        To fix this properly we need to do manual signal delivery multiplexed
85        over a single host signal.  */
86     [__SIGRTMIN] = __SIGRTMAX,
87     [__SIGRTMAX] = __SIGRTMIN,
88 };
89 static uint8_t target_to_host_signal_table[_NSIG];
90
91 static inline int on_sig_stack(unsigned long sp)
92 {
93     return (sp - target_sigaltstack_used.ss_sp
94             < target_sigaltstack_used.ss_size);
95 }
96
97 static inline int sas_ss_flags(unsigned long sp)
98 {
99     return (target_sigaltstack_used.ss_size == 0 ? SS_DISABLE
100             : on_sig_stack(sp) ? SS_ONSTACK : 0);
101 }
102
103 int host_to_target_signal(int sig)
104 {
105     if (sig < 0 || sig >= _NSIG)
106         return sig;
107     return host_to_target_signal_table[sig];
108 }
109
110 int target_to_host_signal(int sig)
111 {
112     if (sig < 0 || sig >= _NSIG)
113         return sig;
114     return target_to_host_signal_table[sig];
115 }
116
117 static inline void target_sigemptyset(target_sigset_t *set)
118 {
119     memset(set, 0, sizeof(*set));
120 }
121
122 static inline void target_sigaddset(target_sigset_t *set, int signum)
123 {
124     signum--;
125     abi_ulong mask = (abi_ulong)1 << (signum % TARGET_NSIG_BPW);
126     set->sig[signum / TARGET_NSIG_BPW] |= mask;
127 }
128
129 static inline int target_sigismember(const target_sigset_t *set, int signum)
130 {
131     signum--;
132     abi_ulong mask = (abi_ulong)1 << (signum % TARGET_NSIG_BPW);
133     return ((set->sig[signum / TARGET_NSIG_BPW] & mask) != 0);
134 }
135
136 static void host_to_target_sigset_internal(target_sigset_t *d,
137                                            const sigset_t *s)
138 {
139     int i;
140     target_sigemptyset(d);
141     for (i = 1; i <= TARGET_NSIG; i++) {
142         if (sigismember(s, i)) {
143             target_sigaddset(d, host_to_target_signal(i));
144         }
145     }
146 }
147
148 void host_to_target_sigset(target_sigset_t *d, const sigset_t *s)
149 {
150     target_sigset_t d1;
151     int i;
152
153     host_to_target_sigset_internal(&d1, s);
154     for(i = 0;i < TARGET_NSIG_WORDS; i++)
155         d->sig[i] = tswapal(d1.sig[i]);
156 }
157
158 static void target_to_host_sigset_internal(sigset_t *d,
159                                            const target_sigset_t *s)
160 {
161     int i;
162     sigemptyset(d);
163     for (i = 1; i <= TARGET_NSIG; i++) {
164         if (target_sigismember(s, i)) {
165             sigaddset(d, target_to_host_signal(i));
166         }
167      }
168 }
169
170 void target_to_host_sigset(sigset_t *d, const target_sigset_t *s)
171 {
172     target_sigset_t s1;
173     int i;
174
175     for(i = 0;i < TARGET_NSIG_WORDS; i++)
176         s1.sig[i] = tswapal(s->sig[i]);
177     target_to_host_sigset_internal(d, &s1);
178 }
179
180 void host_to_target_old_sigset(abi_ulong *old_sigset,
181                                const sigset_t *sigset)
182 {
183     target_sigset_t d;
184     host_to_target_sigset(&d, sigset);
185     *old_sigset = d.sig[0];
186 }
187
188 void target_to_host_old_sigset(sigset_t *sigset,
189                                const abi_ulong *old_sigset)
190 {
191     target_sigset_t d;
192     int i;
193
194     d.sig[0] = *old_sigset;
195     for(i = 1;i < TARGET_NSIG_WORDS; i++)
196         d.sig[i] = 0;
197     target_to_host_sigset(sigset, &d);
198 }
199
200 /* Wrapper for sigprocmask function
201  * Emulates a sigprocmask in a safe way for the guest. Note that set and oldset
202  * are host signal set, not guest ones. This wraps the sigprocmask host calls
203  * that should be protected (calls originated from guest)
204  */
205 int do_sigprocmask(int how, const sigset_t *set, sigset_t *oldset)
206 {
207     int ret;
208     sigset_t val;
209     sigset_t *temp = NULL;
210     CPUState *cpu = thread_cpu;
211     TaskState *ts = (TaskState *)cpu->opaque;
212     bool segv_was_blocked = ts->sigsegv_blocked;
213
214     if (set) {
215         bool has_sigsegv = sigismember(set, SIGSEGV);
216         val = *set;
217         temp = &val;
218
219         sigdelset(temp, SIGSEGV);
220
221         switch (how) {
222         case SIG_BLOCK:
223             if (has_sigsegv) {
224                 ts->sigsegv_blocked = true;
225             }
226             break;
227         case SIG_UNBLOCK:
228             if (has_sigsegv) {
229                 ts->sigsegv_blocked = false;
230             }
231             break;
232         case SIG_SETMASK:
233             ts->sigsegv_blocked = has_sigsegv;
234             break;
235         default:
236             g_assert_not_reached();
237         }
238     }
239
240     ret = sigprocmask(how, temp, oldset);
241
242     if (oldset && segv_was_blocked) {
243         sigaddset(oldset, SIGSEGV);
244     }
245
246     return ret;
247 }
248
249 /* siginfo conversion */
250
251 static inline void host_to_target_siginfo_noswap(target_siginfo_t *tinfo,
252                                                  const siginfo_t *info)
253 {
254     int sig = host_to_target_signal(info->si_signo);
255     tinfo->si_signo = sig;
256     tinfo->si_errno = 0;
257     tinfo->si_code = info->si_code;
258
259     if (sig == TARGET_SIGILL || sig == TARGET_SIGFPE || sig == TARGET_SIGSEGV
260         || sig == TARGET_SIGBUS || sig == TARGET_SIGTRAP) {
261         /* Should never come here, but who knows. The information for
262            the target is irrelevant.  */
263         tinfo->_sifields._sigfault._addr = 0;
264     } else if (sig == TARGET_SIGIO) {
265         tinfo->_sifields._sigpoll._band = info->si_band;
266         tinfo->_sifields._sigpoll._fd = info->si_fd;
267     } else if (sig == TARGET_SIGCHLD) {
268         tinfo->_sifields._sigchld._pid = info->si_pid;
269         tinfo->_sifields._sigchld._uid = info->si_uid;
270         tinfo->_sifields._sigchld._status
271             = host_to_target_waitstatus(info->si_status);
272         tinfo->_sifields._sigchld._utime = info->si_utime;
273         tinfo->_sifields._sigchld._stime = info->si_stime;
274     } else if (sig >= TARGET_SIGRTMIN) {
275         tinfo->_sifields._rt._pid = info->si_pid;
276         tinfo->_sifields._rt._uid = info->si_uid;
277         /* XXX: potential problem if 64 bit */
278         tinfo->_sifields._rt._sigval.sival_ptr
279             = (abi_ulong)(unsigned long)info->si_value.sival_ptr;
280     }
281 }
282
283 static void tswap_siginfo(target_siginfo_t *tinfo,
284                           const target_siginfo_t *info)
285 {
286     int sig = info->si_signo;
287     tinfo->si_signo = tswap32(sig);
288     tinfo->si_errno = tswap32(info->si_errno);
289     tinfo->si_code = tswap32(info->si_code);
290
291     if (sig == TARGET_SIGILL || sig == TARGET_SIGFPE || sig == TARGET_SIGSEGV
292         || sig == TARGET_SIGBUS || sig == TARGET_SIGTRAP) {
293         tinfo->_sifields._sigfault._addr
294             = tswapal(info->_sifields._sigfault._addr);
295     } else if (sig == TARGET_SIGIO) {
296         tinfo->_sifields._sigpoll._band
297             = tswap32(info->_sifields._sigpoll._band);
298         tinfo->_sifields._sigpoll._fd = tswap32(info->_sifields._sigpoll._fd);
299     } else if (sig == TARGET_SIGCHLD) {
300         tinfo->_sifields._sigchld._pid
301             = tswap32(info->_sifields._sigchld._pid);
302         tinfo->_sifields._sigchld._uid
303             = tswap32(info->_sifields._sigchld._uid);
304         tinfo->_sifields._sigchld._status
305             = tswap32(info->_sifields._sigchld._status);
306         tinfo->_sifields._sigchld._utime
307             = tswapal(info->_sifields._sigchld._utime);
308         tinfo->_sifields._sigchld._stime
309             = tswapal(info->_sifields._sigchld._stime);
310     } else if (sig >= TARGET_SIGRTMIN) {
311         tinfo->_sifields._rt._pid = tswap32(info->_sifields._rt._pid);
312         tinfo->_sifields._rt._uid = tswap32(info->_sifields._rt._uid);
313         tinfo->_sifields._rt._sigval.sival_ptr
314             = tswapal(info->_sifields._rt._sigval.sival_ptr);
315     }
316 }
317
318
319 void host_to_target_siginfo(target_siginfo_t *tinfo, const siginfo_t *info)
320 {
321     host_to_target_siginfo_noswap(tinfo, info);
322     tswap_siginfo(tinfo, tinfo);
323 }
324
325 /* XXX: we support only POSIX RT signals are used. */
326 /* XXX: find a solution for 64 bit (additional malloced data is needed) */
327 void target_to_host_siginfo(siginfo_t *info, const target_siginfo_t *tinfo)
328 {
329     info->si_signo = tswap32(tinfo->si_signo);
330     info->si_errno = tswap32(tinfo->si_errno);
331     info->si_code = tswap32(tinfo->si_code);
332     info->si_pid = tswap32(tinfo->_sifields._rt._pid);
333     info->si_uid = tswap32(tinfo->_sifields._rt._uid);
334     info->si_value.sival_ptr =
335             (void *)(long)tswapal(tinfo->_sifields._rt._sigval.sival_ptr);
336 }
337
338 static int fatal_signal (int sig)
339 {
340     switch (sig) {
341     case TARGET_SIGCHLD:
342     case TARGET_SIGURG:
343     case TARGET_SIGWINCH:
344         /* Ignored by default.  */
345         return 0;
346     case TARGET_SIGCONT:
347     case TARGET_SIGSTOP:
348     case TARGET_SIGTSTP:
349     case TARGET_SIGTTIN:
350     case TARGET_SIGTTOU:
351         /* Job control signals.  */
352         return 0;
353     default:
354         return 1;
355     }
356 }
357
358 /* returns 1 if given signal should dump core if not handled */
359 static int core_dump_signal(int sig)
360 {
361     switch (sig) {
362     case TARGET_SIGABRT:
363     case TARGET_SIGFPE:
364     case TARGET_SIGILL:
365     case TARGET_SIGQUIT:
366     case TARGET_SIGSEGV:
367     case TARGET_SIGTRAP:
368     case TARGET_SIGBUS:
369         return (1);
370     default:
371         return (0);
372     }
373 }
374
375 void signal_init(void)
376 {
377     struct sigaction act;
378     struct sigaction oact;
379     int i, j;
380     int host_sig;
381
382     /* generate signal conversion tables */
383     for(i = 1; i < _NSIG; i++) {
384         if (host_to_target_signal_table[i] == 0)
385             host_to_target_signal_table[i] = i;
386     }
387     for(i = 1; i < _NSIG; i++) {
388         j = host_to_target_signal_table[i];
389         target_to_host_signal_table[j] = i;
390     }
391
392     /* set all host signal handlers. ALL signals are blocked during
393        the handlers to serialize them. */
394     memset(sigact_table, 0, sizeof(sigact_table));
395
396     sigfillset(&act.sa_mask);
397     act.sa_flags = SA_SIGINFO;
398     act.sa_sigaction = host_signal_handler;
399     for(i = 1; i <= TARGET_NSIG; i++) {
400         host_sig = target_to_host_signal(i);
401         sigaction(host_sig, NULL, &oact);
402         if (oact.sa_sigaction == (void *)SIG_IGN) {
403             sigact_table[i - 1]._sa_handler = TARGET_SIG_IGN;
404         } else if (oact.sa_sigaction == (void *)SIG_DFL) {
405             sigact_table[i - 1]._sa_handler = TARGET_SIG_DFL;
406         }
407         /* If there's already a handler installed then something has
408            gone horribly wrong, so don't even try to handle that case.  */
409         /* Install some handlers for our own use.  We need at least
410            SIGSEGV and SIGBUS, to detect exceptions.  We can not just
411            trap all signals because it affects syscall interrupt
412            behavior.  But do trap all default-fatal signals.  */
413         if (fatal_signal (i))
414             sigaction(host_sig, &act, NULL);
415     }
416 }
417
418 /* signal queue handling */
419
420 static inline struct sigqueue *alloc_sigqueue(CPUArchState *env)
421 {
422     CPUState *cpu = ENV_GET_CPU(env);
423     TaskState *ts = cpu->opaque;
424     struct sigqueue *q = ts->first_free;
425     if (!q)
426         return NULL;
427     ts->first_free = q->next;
428     return q;
429 }
430
431 static inline void free_sigqueue(CPUArchState *env, struct sigqueue *q)
432 {
433     CPUState *cpu = ENV_GET_CPU(env);
434     TaskState *ts = cpu->opaque;
435
436     q->next = ts->first_free;
437     ts->first_free = q;
438 }
439
440 /* abort execution with signal */
441 static void QEMU_NORETURN force_sig(int target_sig)
442 {
443     CPUState *cpu = thread_cpu;
444     CPUArchState *env = cpu->env_ptr;
445     TaskState *ts = (TaskState *)cpu->opaque;
446     int host_sig, core_dumped = 0;
447     struct sigaction act;
448     host_sig = target_to_host_signal(target_sig);
449     gdb_signalled(env, target_sig);
450
451     /* dump core if supported by target binary format */
452     if (core_dump_signal(target_sig) && (ts->bprm->core_dump != NULL)) {
453         stop_all_tasks();
454         core_dumped =
455             ((*ts->bprm->core_dump)(target_sig, env) == 0);
456     }
457     if (core_dumped) {
458         /* we already dumped the core of target process, we don't want
459          * a coredump of qemu itself */
460         struct rlimit nodump;
461         getrlimit(RLIMIT_CORE, &nodump);
462         nodump.rlim_cur=0;
463         setrlimit(RLIMIT_CORE, &nodump);
464         (void) fprintf(stderr, "qemu: uncaught target signal %d (%s) - %s\n",
465             target_sig, strsignal(host_sig), "core dumped" );
466     }
467
468     /* The proper exit code for dying from an uncaught signal is
469      * -<signal>.  The kernel doesn't allow exit() or _exit() to pass
470      * a negative value.  To get the proper exit code we need to
471      * actually die from an uncaught signal.  Here the default signal
472      * handler is installed, we send ourself a signal and we wait for
473      * it to arrive. */
474     sigfillset(&act.sa_mask);
475     act.sa_handler = SIG_DFL;
476     act.sa_flags = 0;
477     sigaction(host_sig, &act, NULL);
478
479     /* For some reason raise(host_sig) doesn't send the signal when
480      * statically linked on x86-64. */
481     kill(getpid(), host_sig);
482
483     /* Make sure the signal isn't masked (just reuse the mask inside
484     of act) */
485     sigdelset(&act.sa_mask, host_sig);
486     sigsuspend(&act.sa_mask);
487
488     /* unreachable */
489     abort();
490 }
491
492 /* queue a signal so that it will be send to the virtual CPU as soon
493    as possible */
494 int queue_signal(CPUArchState *env, int sig, target_siginfo_t *info)
495 {
496     CPUState *cpu = ENV_GET_CPU(env);
497     TaskState *ts = cpu->opaque;
498     struct emulated_sigtable *k;
499     struct sigqueue *q, **pq;
500     abi_ulong handler;
501     int queue;
502
503 #if defined(DEBUG_SIGNAL)
504     fprintf(stderr, "queue_signal: sig=%d\n",
505             sig);
506 #endif
507     k = &ts->sigtab[sig - 1];
508     queue = gdb_queuesig ();
509     handler = sigact_table[sig - 1]._sa_handler;
510
511     if (ts->sigsegv_blocked && sig == TARGET_SIGSEGV) {
512         /* Guest has blocked SIGSEGV but we got one anyway. Assume this
513          * is a forced SIGSEGV (ie one the kernel handles via force_sig_info
514          * because it got a real MMU fault). A blocked SIGSEGV in that
515          * situation is treated as if using the default handler. This is
516          * not correct if some other process has randomly sent us a SIGSEGV
517          * via kill(), but that is not easy to distinguish at this point,
518          * so we assume it doesn't happen.
519          */
520         handler = TARGET_SIG_DFL;
521     }
522
523     if (!queue && handler == TARGET_SIG_DFL) {
524         if (sig == TARGET_SIGTSTP || sig == TARGET_SIGTTIN || sig == TARGET_SIGTTOU) {
525             kill(getpid(),SIGSTOP);
526             return 0;
527         } else
528         /* default handler : ignore some signal. The other are fatal */
529         if (sig != TARGET_SIGCHLD &&
530             sig != TARGET_SIGURG &&
531             sig != TARGET_SIGWINCH &&
532             sig != TARGET_SIGCONT) {
533             force_sig(sig);
534         } else {
535             return 0; /* indicate ignored */
536         }
537     } else if (!queue && handler == TARGET_SIG_IGN) {
538         /* ignore signal */
539         return 0;
540     } else if (!queue && handler == TARGET_SIG_ERR) {
541         force_sig(sig);
542     } else {
543         pq = &k->first;
544         if (sig < TARGET_SIGRTMIN) {
545             /* if non real time signal, we queue exactly one signal */
546             if (!k->pending)
547                 q = &k->info;
548             else
549                 return 0;
550         } else {
551             if (!k->pending) {
552                 /* first signal */
553                 q = &k->info;
554             } else {
555                 q = alloc_sigqueue(env);
556                 if (!q)
557                     return -EAGAIN;
558                 while (*pq != NULL)
559                     pq = &(*pq)->next;
560             }
561         }
562         *pq = q;
563         q->info = *info;
564         q->next = NULL;
565         k->pending = 1;
566         /* signal that a new signal is pending */
567         ts->signal_pending = 1;
568         return 1; /* indicates that the signal was queued */
569     }
570 }
571
572 static void host_signal_handler(int host_signum, siginfo_t *info,
573                                 void *puc)
574 {
575     CPUArchState *env = thread_cpu->env_ptr;
576     int sig;
577     target_siginfo_t tinfo;
578
579     /* the CPU emulator uses some host signals to detect exceptions,
580        we forward to it some signals */
581     if ((host_signum == SIGSEGV || host_signum == SIGBUS)
582         && info->si_code > 0) {
583         if (cpu_signal_handler(host_signum, info, puc))
584             return;
585     }
586
587     /* get target signal number */
588     sig = host_to_target_signal(host_signum);
589     if (sig < 1 || sig > TARGET_NSIG)
590         return;
591 #if defined(DEBUG_SIGNAL)
592     fprintf(stderr, "qemu: got signal %d\n", sig);
593 #endif
594     host_to_target_siginfo_noswap(&tinfo, info);
595     if (queue_signal(env, sig, &tinfo) == 1) {
596         /* interrupt the virtual CPU as soon as possible */
597         cpu_exit(thread_cpu);
598     }
599 }
600
601 /* do_sigaltstack() returns target values and errnos. */
602 /* compare linux/kernel/signal.c:do_sigaltstack() */
603 abi_long do_sigaltstack(abi_ulong uss_addr, abi_ulong uoss_addr, abi_ulong sp)
604 {
605     int ret;
606     struct target_sigaltstack oss;
607
608     /* XXX: test errors */
609     if(uoss_addr)
610     {
611         __put_user(target_sigaltstack_used.ss_sp, &oss.ss_sp);
612         __put_user(target_sigaltstack_used.ss_size, &oss.ss_size);
613         __put_user(sas_ss_flags(sp), &oss.ss_flags);
614     }
615
616     if(uss_addr)
617     {
618         struct target_sigaltstack *uss;
619         struct target_sigaltstack ss;
620         size_t minstacksize = TARGET_MINSIGSTKSZ;
621
622 #if defined(TARGET_PPC64)
623         /* ELF V2 for PPC64 has a 4K minimum stack size for signal handlers */
624         struct image_info *image = ((TaskState *)thread_cpu->opaque)->info;
625         if (get_ppc64_abi(image) > 1) {
626             minstacksize = 4096;
627         }
628 #endif
629
630         ret = -TARGET_EFAULT;
631         if (!lock_user_struct(VERIFY_READ, uss, uss_addr, 1)) {
632             goto out;
633         }
634         __get_user(ss.ss_sp, &uss->ss_sp);
635         __get_user(ss.ss_size, &uss->ss_size);
636         __get_user(ss.ss_flags, &uss->ss_flags);
637         unlock_user_struct(uss, uss_addr, 0);
638
639         ret = -TARGET_EPERM;
640         if (on_sig_stack(sp))
641             goto out;
642
643         ret = -TARGET_EINVAL;
644         if (ss.ss_flags != TARGET_SS_DISABLE
645             && ss.ss_flags != TARGET_SS_ONSTACK
646             && ss.ss_flags != 0)
647             goto out;
648
649         if (ss.ss_flags == TARGET_SS_DISABLE) {
650             ss.ss_size = 0;
651             ss.ss_sp = 0;
652         } else {
653             ret = -TARGET_ENOMEM;
654             if (ss.ss_size < minstacksize) {
655                 goto out;
656             }
657         }
658
659         target_sigaltstack_used.ss_sp = ss.ss_sp;
660         target_sigaltstack_used.ss_size = ss.ss_size;
661     }
662
663     if (uoss_addr) {
664         ret = -TARGET_EFAULT;
665         if (copy_to_user(uoss_addr, &oss, sizeof(oss)))
666             goto out;
667     }
668
669     ret = 0;
670 out:
671     return ret;
672 }
673
674 /* do_sigaction() return host values and errnos */
675 int do_sigaction(int sig, const struct target_sigaction *act,
676                  struct target_sigaction *oact)
677 {
678     struct target_sigaction *k;
679     struct sigaction act1;
680     int host_sig;
681     int ret = 0;
682
683     if (sig < 1 || sig > TARGET_NSIG || sig == TARGET_SIGKILL || sig == TARGET_SIGSTOP)
684         return -EINVAL;
685     k = &sigact_table[sig - 1];
686 #if defined(DEBUG_SIGNAL)
687     fprintf(stderr, "sigaction sig=%d act=0x%p, oact=0x%p\n",
688             sig, act, oact);
689 #endif
690     if (oact) {
691         __put_user(k->_sa_handler, &oact->_sa_handler);
692         __put_user(k->sa_flags, &oact->sa_flags);
693 #if !defined(TARGET_MIPS)
694         __put_user(k->sa_restorer, &oact->sa_restorer);
695 #endif
696         /* Not swapped.  */
697         oact->sa_mask = k->sa_mask;
698     }
699     if (act) {
700         /* FIXME: This is not threadsafe.  */
701         __get_user(k->_sa_handler, &act->_sa_handler);
702         __get_user(k->sa_flags, &act->sa_flags);
703 #if !defined(TARGET_MIPS)
704         __get_user(k->sa_restorer, &act->sa_restorer);
705 #endif
706         /* To be swapped in target_to_host_sigset.  */
707         k->sa_mask = act->sa_mask;
708
709         /* we update the host linux signal state */
710         host_sig = target_to_host_signal(sig);
711         if (host_sig != SIGSEGV && host_sig != SIGBUS) {
712             sigfillset(&act1.sa_mask);
713             act1.sa_flags = SA_SIGINFO;
714             if (k->sa_flags & TARGET_SA_RESTART)
715                 act1.sa_flags |= SA_RESTART;
716             /* NOTE: it is important to update the host kernel signal
717                ignore state to avoid getting unexpected interrupted
718                syscalls */
719             if (k->_sa_handler == TARGET_SIG_IGN) {
720                 act1.sa_sigaction = (void *)SIG_IGN;
721             } else if (k->_sa_handler == TARGET_SIG_DFL) {
722                 if (fatal_signal (sig))
723                     act1.sa_sigaction = host_signal_handler;
724                 else
725                     act1.sa_sigaction = (void *)SIG_DFL;
726             } else {
727                 act1.sa_sigaction = host_signal_handler;
728             }
729             ret = sigaction(host_sig, &act1, NULL);
730         }
731     }
732     return ret;
733 }
734
735 static inline void copy_siginfo_to_user(target_siginfo_t *tinfo,
736                                        const target_siginfo_t *info)
737 {
738     tswap_siginfo(tinfo, info);
739 }
740
741 static inline int current_exec_domain_sig(int sig)
742 {
743     return /* current->exec_domain && current->exec_domain->signal_invmap
744               && sig < 32 ? current->exec_domain->signal_invmap[sig] : */ sig;
745 }
746
747 #if defined(TARGET_I386) && TARGET_ABI_BITS == 32
748
749 /* from the Linux kernel */
750
751 struct target_fpreg {
752         uint16_t significand[4];
753         uint16_t exponent;
754 };
755
756 struct target_fpxreg {
757         uint16_t significand[4];
758         uint16_t exponent;
759         uint16_t padding[3];
760 };
761
762 struct target_xmmreg {
763         abi_ulong element[4];
764 };
765
766 struct target_fpstate {
767         /* Regular FPU environment */
768         abi_ulong       cw;
769         abi_ulong       sw;
770         abi_ulong       tag;
771         abi_ulong       ipoff;
772         abi_ulong       cssel;
773         abi_ulong       dataoff;
774         abi_ulong       datasel;
775         struct target_fpreg     _st[8];
776         uint16_t        status;
777         uint16_t        magic;          /* 0xffff = regular FPU data only */
778
779         /* FXSR FPU environment */
780         abi_ulong       _fxsr_env[6];   /* FXSR FPU env is ignored */
781         abi_ulong       mxcsr;
782         abi_ulong       reserved;
783         struct target_fpxreg    _fxsr_st[8];    /* FXSR FPU reg data is ignored */
784         struct target_xmmreg    _xmm[8];
785         abi_ulong       padding[56];
786 };
787
788 #define X86_FXSR_MAGIC          0x0000
789
790 struct target_sigcontext {
791         uint16_t gs, __gsh;
792         uint16_t fs, __fsh;
793         uint16_t es, __esh;
794         uint16_t ds, __dsh;
795         abi_ulong edi;
796         abi_ulong esi;
797         abi_ulong ebp;
798         abi_ulong esp;
799         abi_ulong ebx;
800         abi_ulong edx;
801         abi_ulong ecx;
802         abi_ulong eax;
803         abi_ulong trapno;
804         abi_ulong err;
805         abi_ulong eip;
806         uint16_t cs, __csh;
807         abi_ulong eflags;
808         abi_ulong esp_at_signal;
809         uint16_t ss, __ssh;
810         abi_ulong fpstate; /* pointer */
811         abi_ulong oldmask;
812         abi_ulong cr2;
813 };
814
815 struct target_ucontext {
816         abi_ulong         tuc_flags;
817         abi_ulong         tuc_link;
818         target_stack_t    tuc_stack;
819         struct target_sigcontext tuc_mcontext;
820         target_sigset_t   tuc_sigmask;  /* mask last for extensibility */
821 };
822
823 struct sigframe
824 {
825     abi_ulong pretcode;
826     int sig;
827     struct target_sigcontext sc;
828     struct target_fpstate fpstate;
829     abi_ulong extramask[TARGET_NSIG_WORDS-1];
830     char retcode[8];
831 };
832
833 struct rt_sigframe
834 {
835     abi_ulong pretcode;
836     int sig;
837     abi_ulong pinfo;
838     abi_ulong puc;
839     struct target_siginfo info;
840     struct target_ucontext uc;
841     struct target_fpstate fpstate;
842     char retcode[8];
843 };
844
845 /*
846  * Set up a signal frame.
847  */
848
849 /* XXX: save x87 state */
850 static void setup_sigcontext(struct target_sigcontext *sc,
851         struct target_fpstate *fpstate, CPUX86State *env, abi_ulong mask,
852         abi_ulong fpstate_addr)
853 {
854     CPUState *cs = CPU(x86_env_get_cpu(env));
855     uint16_t magic;
856
857         /* already locked in setup_frame() */
858     __put_user(env->segs[R_GS].selector, (unsigned int *)&sc->gs);
859     __put_user(env->segs[R_FS].selector, (unsigned int *)&sc->fs);
860     __put_user(env->segs[R_ES].selector, (unsigned int *)&sc->es);
861     __put_user(env->segs[R_DS].selector, (unsigned int *)&sc->ds);
862     __put_user(env->regs[R_EDI], &sc->edi);
863     __put_user(env->regs[R_ESI], &sc->esi);
864     __put_user(env->regs[R_EBP], &sc->ebp);
865     __put_user(env->regs[R_ESP], &sc->esp);
866     __put_user(env->regs[R_EBX], &sc->ebx);
867     __put_user(env->regs[R_EDX], &sc->edx);
868     __put_user(env->regs[R_ECX], &sc->ecx);
869     __put_user(env->regs[R_EAX], &sc->eax);
870     __put_user(cs->exception_index, &sc->trapno);
871     __put_user(env->error_code, &sc->err);
872     __put_user(env->eip, &sc->eip);
873     __put_user(env->segs[R_CS].selector, (unsigned int *)&sc->cs);
874     __put_user(env->eflags, &sc->eflags);
875     __put_user(env->regs[R_ESP], &sc->esp_at_signal);
876     __put_user(env->segs[R_SS].selector, (unsigned int *)&sc->ss);
877
878         cpu_x86_fsave(env, fpstate_addr, 1);
879         fpstate->status = fpstate->sw;
880         magic = 0xffff;
881     __put_user(magic, &fpstate->magic);
882     __put_user(fpstate_addr, &sc->fpstate);
883
884         /* non-iBCS2 extensions.. */
885     __put_user(mask, &sc->oldmask);
886     __put_user(env->cr[2], &sc->cr2);
887 }
888
889 /*
890  * Determine which stack to use..
891  */
892
893 static inline abi_ulong
894 get_sigframe(struct target_sigaction *ka, CPUX86State *env, size_t frame_size)
895 {
896         unsigned long esp;
897
898         /* Default to using normal stack */
899         esp = env->regs[R_ESP];
900         /* This is the X/Open sanctioned signal stack switching.  */
901         if (ka->sa_flags & TARGET_SA_ONSTACK) {
902             if (sas_ss_flags(esp) == 0)
903                 esp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
904         }
905
906         /* This is the legacy signal stack switching. */
907         else
908         if ((env->segs[R_SS].selector & 0xffff) != __USER_DS &&
909             !(ka->sa_flags & TARGET_SA_RESTORER) &&
910             ka->sa_restorer) {
911             esp = (unsigned long) ka->sa_restorer;
912         }
913         return (esp - frame_size) & -8ul;
914 }
915
916 /* compare linux/arch/i386/kernel/signal.c:setup_frame() */
917 static void setup_frame(int sig, struct target_sigaction *ka,
918                         target_sigset_t *set, CPUX86State *env)
919 {
920         abi_ulong frame_addr;
921         struct sigframe *frame;
922         int i;
923
924         frame_addr = get_sigframe(ka, env, sizeof(*frame));
925
926         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
927                 goto give_sigsegv;
928
929     __put_user(current_exec_domain_sig(sig),
930                &frame->sig);
931
932         setup_sigcontext(&frame->sc, &frame->fpstate, env, set->sig[0],
933                          frame_addr + offsetof(struct sigframe, fpstate));
934
935     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
936         __put_user(set->sig[i], &frame->extramask[i - 1]);
937     }
938
939         /* Set up to return from userspace.  If provided, use a stub
940            already in userspace.  */
941         if (ka->sa_flags & TARGET_SA_RESTORER) {
942         __put_user(ka->sa_restorer, &frame->pretcode);
943         } else {
944                 uint16_t val16;
945                 abi_ulong retcode_addr;
946                 retcode_addr = frame_addr + offsetof(struct sigframe, retcode);
947         __put_user(retcode_addr, &frame->pretcode);
948                 /* This is popl %eax ; movl $,%eax ; int $0x80 */
949                 val16 = 0xb858;
950         __put_user(val16, (uint16_t *)(frame->retcode+0));
951         __put_user(TARGET_NR_sigreturn, (int *)(frame->retcode+2));
952                 val16 = 0x80cd;
953         __put_user(val16, (uint16_t *)(frame->retcode+6));
954         }
955
956
957         /* Set up registers for signal handler */
958         env->regs[R_ESP] = frame_addr;
959         env->eip = ka->_sa_handler;
960
961         cpu_x86_load_seg(env, R_DS, __USER_DS);
962         cpu_x86_load_seg(env, R_ES, __USER_DS);
963         cpu_x86_load_seg(env, R_SS, __USER_DS);
964         cpu_x86_load_seg(env, R_CS, __USER_CS);
965         env->eflags &= ~TF_MASK;
966
967         unlock_user_struct(frame, frame_addr, 1);
968
969         return;
970
971 give_sigsegv:
972         if (sig == TARGET_SIGSEGV)
973                 ka->_sa_handler = TARGET_SIG_DFL;
974         force_sig(TARGET_SIGSEGV /* , current */);
975 }
976
977 /* compare linux/arch/i386/kernel/signal.c:setup_rt_frame() */
978 static void setup_rt_frame(int sig, struct target_sigaction *ka,
979                            target_siginfo_t *info,
980                            target_sigset_t *set, CPUX86State *env)
981 {
982         abi_ulong frame_addr, addr;
983         struct rt_sigframe *frame;
984         int i;
985
986         frame_addr = get_sigframe(ka, env, sizeof(*frame));
987
988         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
989                 goto give_sigsegv;
990
991     __put_user(current_exec_domain_sig(sig), &frame->sig);
992         addr = frame_addr + offsetof(struct rt_sigframe, info);
993     __put_user(addr, &frame->pinfo);
994         addr = frame_addr + offsetof(struct rt_sigframe, uc);
995     __put_user(addr, &frame->puc);
996         copy_siginfo_to_user(&frame->info, info);
997
998         /* Create the ucontext.  */
999     __put_user(0, &frame->uc.tuc_flags);
1000     __put_user(0, &frame->uc.tuc_link);
1001     __put_user(target_sigaltstack_used.ss_sp, &frame->uc.tuc_stack.ss_sp);
1002     __put_user(sas_ss_flags(get_sp_from_cpustate(env)),
1003                &frame->uc.tuc_stack.ss_flags);
1004     __put_user(target_sigaltstack_used.ss_size,
1005                &frame->uc.tuc_stack.ss_size);
1006     setup_sigcontext(&frame->uc.tuc_mcontext, &frame->fpstate, env,
1007             set->sig[0], frame_addr + offsetof(struct rt_sigframe, fpstate));
1008
1009     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
1010         __put_user(set->sig[i], &frame->uc.tuc_sigmask.sig[i]);
1011     }
1012
1013         /* Set up to return from userspace.  If provided, use a stub
1014            already in userspace.  */
1015         if (ka->sa_flags & TARGET_SA_RESTORER) {
1016         __put_user(ka->sa_restorer, &frame->pretcode);
1017         } else {
1018                 uint16_t val16;
1019                 addr = frame_addr + offsetof(struct rt_sigframe, retcode);
1020         __put_user(addr, &frame->pretcode);
1021                 /* This is movl $,%eax ; int $0x80 */
1022         __put_user(0xb8, (char *)(frame->retcode+0));
1023         __put_user(TARGET_NR_rt_sigreturn, (int *)(frame->retcode+1));
1024                 val16 = 0x80cd;
1025         __put_user(val16, (uint16_t *)(frame->retcode+5));
1026         }
1027
1028         /* Set up registers for signal handler */
1029         env->regs[R_ESP] = frame_addr;
1030         env->eip = ka->_sa_handler;
1031
1032         cpu_x86_load_seg(env, R_DS, __USER_DS);
1033         cpu_x86_load_seg(env, R_ES, __USER_DS);
1034         cpu_x86_load_seg(env, R_SS, __USER_DS);
1035         cpu_x86_load_seg(env, R_CS, __USER_CS);
1036         env->eflags &= ~TF_MASK;
1037
1038         unlock_user_struct(frame, frame_addr, 1);
1039
1040         return;
1041
1042 give_sigsegv:
1043         if (sig == TARGET_SIGSEGV)
1044                 ka->_sa_handler = TARGET_SIG_DFL;
1045         force_sig(TARGET_SIGSEGV /* , current */);
1046 }
1047
1048 static int
1049 restore_sigcontext(CPUX86State *env, struct target_sigcontext *sc, int *peax)
1050 {
1051         unsigned int err = 0;
1052         abi_ulong fpstate_addr;
1053         unsigned int tmpflags;
1054
1055         cpu_x86_load_seg(env, R_GS, tswap16(sc->gs));
1056         cpu_x86_load_seg(env, R_FS, tswap16(sc->fs));
1057         cpu_x86_load_seg(env, R_ES, tswap16(sc->es));
1058         cpu_x86_load_seg(env, R_DS, tswap16(sc->ds));
1059
1060         env->regs[R_EDI] = tswapl(sc->edi);
1061         env->regs[R_ESI] = tswapl(sc->esi);
1062         env->regs[R_EBP] = tswapl(sc->ebp);
1063         env->regs[R_ESP] = tswapl(sc->esp);
1064         env->regs[R_EBX] = tswapl(sc->ebx);
1065         env->regs[R_EDX] = tswapl(sc->edx);
1066         env->regs[R_ECX] = tswapl(sc->ecx);
1067         env->eip = tswapl(sc->eip);
1068
1069         cpu_x86_load_seg(env, R_CS, lduw_p(&sc->cs) | 3);
1070         cpu_x86_load_seg(env, R_SS, lduw_p(&sc->ss) | 3);
1071
1072         tmpflags = tswapl(sc->eflags);
1073         env->eflags = (env->eflags & ~0x40DD5) | (tmpflags & 0x40DD5);
1074         //              regs->orig_eax = -1;            /* disable syscall checks */
1075
1076         fpstate_addr = tswapl(sc->fpstate);
1077         if (fpstate_addr != 0) {
1078                 if (!access_ok(VERIFY_READ, fpstate_addr, 
1079                                sizeof(struct target_fpstate)))
1080                         goto badframe;
1081                 cpu_x86_frstor(env, fpstate_addr, 1);
1082         }
1083
1084         *peax = tswapl(sc->eax);
1085         return err;
1086 badframe:
1087         return 1;
1088 }
1089
1090 long do_sigreturn(CPUX86State *env)
1091 {
1092     struct sigframe *frame;
1093     abi_ulong frame_addr = env->regs[R_ESP] - 8;
1094     target_sigset_t target_set;
1095     sigset_t set;
1096     int eax, i;
1097
1098 #if defined(DEBUG_SIGNAL)
1099     fprintf(stderr, "do_sigreturn\n");
1100 #endif
1101     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
1102         goto badframe;
1103     /* set blocked signals */
1104     __get_user(target_set.sig[0], &frame->sc.oldmask);
1105     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
1106         __get_user(target_set.sig[i], &frame->extramask[i - 1]);
1107     }
1108
1109     target_to_host_sigset_internal(&set, &target_set);
1110     do_sigprocmask(SIG_SETMASK, &set, NULL);
1111
1112     /* restore registers */
1113     if (restore_sigcontext(env, &frame->sc, &eax))
1114         goto badframe;
1115     unlock_user_struct(frame, frame_addr, 0);
1116     return eax;
1117
1118 badframe:
1119     unlock_user_struct(frame, frame_addr, 0);
1120     force_sig(TARGET_SIGSEGV);
1121     return 0;
1122 }
1123
1124 long do_rt_sigreturn(CPUX86State *env)
1125 {
1126         abi_ulong frame_addr;
1127         struct rt_sigframe *frame;
1128         sigset_t set;
1129         int eax;
1130
1131         frame_addr = env->regs[R_ESP] - 4;
1132         if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
1133                 goto badframe;
1134         target_to_host_sigset(&set, &frame->uc.tuc_sigmask);
1135         do_sigprocmask(SIG_SETMASK, &set, NULL);
1136
1137         if (restore_sigcontext(env, &frame->uc.tuc_mcontext, &eax))
1138                 goto badframe;
1139
1140         if (do_sigaltstack(frame_addr + offsetof(struct rt_sigframe, uc.tuc_stack), 0, 
1141                            get_sp_from_cpustate(env)) == -EFAULT)
1142                 goto badframe;
1143
1144         unlock_user_struct(frame, frame_addr, 0);
1145         return eax;
1146
1147 badframe:
1148         unlock_user_struct(frame, frame_addr, 0);
1149         force_sig(TARGET_SIGSEGV);
1150         return 0;
1151 }
1152
1153 #elif defined(TARGET_AARCH64)
1154
1155 struct target_sigcontext {
1156     uint64_t fault_address;
1157     /* AArch64 registers */
1158     uint64_t regs[31];
1159     uint64_t sp;
1160     uint64_t pc;
1161     uint64_t pstate;
1162     /* 4K reserved for FP/SIMD state and future expansion */
1163     char __reserved[4096] __attribute__((__aligned__(16)));
1164 };
1165
1166 struct target_ucontext {
1167     abi_ulong tuc_flags;
1168     abi_ulong tuc_link;
1169     target_stack_t tuc_stack;
1170     target_sigset_t tuc_sigmask;
1171     /* glibc uses a 1024-bit sigset_t */
1172     char __unused[1024 / 8 - sizeof(target_sigset_t)];
1173     /* last for future expansion */
1174     struct target_sigcontext tuc_mcontext;
1175 };
1176
1177 /*
1178  * Header to be used at the beginning of structures extending the user
1179  * context. Such structures must be placed after the rt_sigframe on the stack
1180  * and be 16-byte aligned. The last structure must be a dummy one with the
1181  * magic and size set to 0.
1182  */
1183 struct target_aarch64_ctx {
1184     uint32_t magic;
1185     uint32_t size;
1186 };
1187
1188 #define TARGET_FPSIMD_MAGIC 0x46508001
1189
1190 struct target_fpsimd_context {
1191     struct target_aarch64_ctx head;
1192     uint32_t fpsr;
1193     uint32_t fpcr;
1194     uint64_t vregs[32 * 2]; /* really uint128_t vregs[32] */
1195 };
1196
1197 /*
1198  * Auxiliary context saved in the sigcontext.__reserved array. Not exported to
1199  * user space as it will change with the addition of new context. User space
1200  * should check the magic/size information.
1201  */
1202 struct target_aux_context {
1203     struct target_fpsimd_context fpsimd;
1204     /* additional context to be added before "end" */
1205     struct target_aarch64_ctx end;
1206 };
1207
1208 struct target_rt_sigframe {
1209     struct target_siginfo info;
1210     struct target_ucontext uc;
1211     uint64_t fp;
1212     uint64_t lr;
1213     uint32_t tramp[2];
1214 };
1215
1216 static int target_setup_sigframe(struct target_rt_sigframe *sf,
1217                                  CPUARMState *env, target_sigset_t *set)
1218 {
1219     int i;
1220     struct target_aux_context *aux =
1221         (struct target_aux_context *)sf->uc.tuc_mcontext.__reserved;
1222
1223     /* set up the stack frame for unwinding */
1224     __put_user(env->xregs[29], &sf->fp);
1225     __put_user(env->xregs[30], &sf->lr);
1226
1227     for (i = 0; i < 31; i++) {
1228         __put_user(env->xregs[i], &sf->uc.tuc_mcontext.regs[i]);
1229     }
1230     __put_user(env->xregs[31], &sf->uc.tuc_mcontext.sp);
1231     __put_user(env->pc, &sf->uc.tuc_mcontext.pc);
1232     __put_user(pstate_read(env), &sf->uc.tuc_mcontext.pstate);
1233
1234     __put_user(env->exception.vaddress, &sf->uc.tuc_mcontext.fault_address);
1235
1236     for (i = 0; i < TARGET_NSIG_WORDS; i++) {
1237         __put_user(set->sig[i], &sf->uc.tuc_sigmask.sig[i]);
1238     }
1239
1240     for (i = 0; i < 32; i++) {
1241 #ifdef TARGET_WORDS_BIGENDIAN
1242         __put_user(env->vfp.regs[i * 2], &aux->fpsimd.vregs[i * 2 + 1]);
1243         __put_user(env->vfp.regs[i * 2 + 1], &aux->fpsimd.vregs[i * 2]);
1244 #else
1245         __put_user(env->vfp.regs[i * 2], &aux->fpsimd.vregs[i * 2]);
1246         __put_user(env->vfp.regs[i * 2 + 1], &aux->fpsimd.vregs[i * 2 + 1]);
1247 #endif
1248     }
1249     __put_user(vfp_get_fpsr(env), &aux->fpsimd.fpsr);
1250     __put_user(vfp_get_fpcr(env), &aux->fpsimd.fpcr);
1251     __put_user(TARGET_FPSIMD_MAGIC, &aux->fpsimd.head.magic);
1252     __put_user(sizeof(struct target_fpsimd_context),
1253             &aux->fpsimd.head.size);
1254
1255     /* set the "end" magic */
1256     __put_user(0, &aux->end.magic);
1257     __put_user(0, &aux->end.size);
1258
1259     return 0;
1260 }
1261
1262 static int target_restore_sigframe(CPUARMState *env,
1263                                    struct target_rt_sigframe *sf)
1264 {
1265     sigset_t set;
1266     int i;
1267     struct target_aux_context *aux =
1268         (struct target_aux_context *)sf->uc.tuc_mcontext.__reserved;
1269     uint32_t magic, size, fpsr, fpcr;
1270     uint64_t pstate;
1271
1272     target_to_host_sigset(&set, &sf->uc.tuc_sigmask);
1273     do_sigprocmask(SIG_SETMASK, &set, NULL);
1274
1275     for (i = 0; i < 31; i++) {
1276         __get_user(env->xregs[i], &sf->uc.tuc_mcontext.regs[i]);
1277     }
1278
1279     __get_user(env->xregs[31], &sf->uc.tuc_mcontext.sp);
1280     __get_user(env->pc, &sf->uc.tuc_mcontext.pc);
1281     __get_user(pstate, &sf->uc.tuc_mcontext.pstate);
1282     pstate_write(env, pstate);
1283
1284     __get_user(magic, &aux->fpsimd.head.magic);
1285     __get_user(size, &aux->fpsimd.head.size);
1286
1287     if (magic != TARGET_FPSIMD_MAGIC
1288         || size != sizeof(struct target_fpsimd_context)) {
1289         return 1;
1290     }
1291
1292     for (i = 0; i < 32; i++) {
1293 #ifdef TARGET_WORDS_BIGENDIAN
1294         __get_user(env->vfp.regs[i * 2], &aux->fpsimd.vregs[i * 2 + 1]);
1295         __get_user(env->vfp.regs[i * 2 + 1], &aux->fpsimd.vregs[i * 2]);
1296 #else
1297         __get_user(env->vfp.regs[i * 2], &aux->fpsimd.vregs[i * 2]);
1298         __get_user(env->vfp.regs[i * 2 + 1], &aux->fpsimd.vregs[i * 2 + 1]);
1299 #endif
1300     }
1301     __get_user(fpsr, &aux->fpsimd.fpsr);
1302     vfp_set_fpsr(env, fpsr);
1303     __get_user(fpcr, &aux->fpsimd.fpcr);
1304     vfp_set_fpcr(env, fpcr);
1305
1306     return 0;
1307 }
1308
1309 static abi_ulong get_sigframe(struct target_sigaction *ka, CPUARMState *env)
1310 {
1311     abi_ulong sp;
1312
1313     sp = env->xregs[31];
1314
1315     /*
1316      * This is the X/Open sanctioned signal stack switching.
1317      */
1318     if ((ka->sa_flags & TARGET_SA_ONSTACK) && !sas_ss_flags(sp)) {
1319         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
1320     }
1321
1322     sp = (sp - sizeof(struct target_rt_sigframe)) & ~15;
1323
1324     return sp;
1325 }
1326
1327 static void target_setup_frame(int usig, struct target_sigaction *ka,
1328                                target_siginfo_t *info, target_sigset_t *set,
1329                                CPUARMState *env)
1330 {
1331     struct target_rt_sigframe *frame;
1332     abi_ulong frame_addr, return_addr;
1333
1334     frame_addr = get_sigframe(ka, env);
1335     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0)) {
1336         goto give_sigsegv;
1337     }
1338
1339     __put_user(0, &frame->uc.tuc_flags);
1340     __put_user(0, &frame->uc.tuc_link);
1341
1342     __put_user(target_sigaltstack_used.ss_sp,
1343                       &frame->uc.tuc_stack.ss_sp);
1344     __put_user(sas_ss_flags(env->xregs[31]),
1345                       &frame->uc.tuc_stack.ss_flags);
1346     __put_user(target_sigaltstack_used.ss_size,
1347                       &frame->uc.tuc_stack.ss_size);
1348     target_setup_sigframe(frame, env, set);
1349     if (ka->sa_flags & TARGET_SA_RESTORER) {
1350         return_addr = ka->sa_restorer;
1351     } else {
1352         /* mov x8,#__NR_rt_sigreturn; svc #0 */
1353         __put_user(0xd2801168, &frame->tramp[0]);
1354         __put_user(0xd4000001, &frame->tramp[1]);
1355         return_addr = frame_addr + offsetof(struct target_rt_sigframe, tramp);
1356     }
1357     env->xregs[0] = usig;
1358     env->xregs[31] = frame_addr;
1359     env->xregs[29] = env->xregs[31] + offsetof(struct target_rt_sigframe, fp);
1360     env->pc = ka->_sa_handler;
1361     env->xregs[30] = return_addr;
1362     if (info) {
1363         copy_siginfo_to_user(&frame->info, info);
1364         env->xregs[1] = frame_addr + offsetof(struct target_rt_sigframe, info);
1365         env->xregs[2] = frame_addr + offsetof(struct target_rt_sigframe, uc);
1366     }
1367
1368     unlock_user_struct(frame, frame_addr, 1);
1369     return;
1370
1371  give_sigsegv:
1372     unlock_user_struct(frame, frame_addr, 1);
1373     force_sig(TARGET_SIGSEGV);
1374 }
1375
1376 static void setup_rt_frame(int sig, struct target_sigaction *ka,
1377                            target_siginfo_t *info, target_sigset_t *set,
1378                            CPUARMState *env)
1379 {
1380     target_setup_frame(sig, ka, info, set, env);
1381 }
1382
1383 static void setup_frame(int sig, struct target_sigaction *ka,
1384                         target_sigset_t *set, CPUARMState *env)
1385 {
1386     target_setup_frame(sig, ka, 0, set, env);
1387 }
1388
1389 long do_rt_sigreturn(CPUARMState *env)
1390 {
1391     struct target_rt_sigframe *frame = NULL;
1392     abi_ulong frame_addr = env->xregs[31];
1393
1394     if (frame_addr & 15) {
1395         goto badframe;
1396     }
1397
1398     if  (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1)) {
1399         goto badframe;
1400     }
1401
1402     if (target_restore_sigframe(env, frame)) {
1403         goto badframe;
1404     }
1405
1406     if (do_sigaltstack(frame_addr +
1407             offsetof(struct target_rt_sigframe, uc.tuc_stack),
1408             0, get_sp_from_cpustate(env)) == -EFAULT) {
1409         goto badframe;
1410     }
1411
1412     unlock_user_struct(frame, frame_addr, 0);
1413     return env->xregs[0];
1414
1415  badframe:
1416     unlock_user_struct(frame, frame_addr, 0);
1417     force_sig(TARGET_SIGSEGV);
1418     return 0;
1419 }
1420
1421 long do_sigreturn(CPUARMState *env)
1422 {
1423     return do_rt_sigreturn(env);
1424 }
1425
1426 #elif defined(TARGET_ARM)
1427
1428 struct target_sigcontext {
1429         abi_ulong trap_no;
1430         abi_ulong error_code;
1431         abi_ulong oldmask;
1432         abi_ulong arm_r0;
1433         abi_ulong arm_r1;
1434         abi_ulong arm_r2;
1435         abi_ulong arm_r3;
1436         abi_ulong arm_r4;
1437         abi_ulong arm_r5;
1438         abi_ulong arm_r6;
1439         abi_ulong arm_r7;
1440         abi_ulong arm_r8;
1441         abi_ulong arm_r9;
1442         abi_ulong arm_r10;
1443         abi_ulong arm_fp;
1444         abi_ulong arm_ip;
1445         abi_ulong arm_sp;
1446         abi_ulong arm_lr;
1447         abi_ulong arm_pc;
1448         abi_ulong arm_cpsr;
1449         abi_ulong fault_address;
1450 };
1451
1452 struct target_ucontext_v1 {
1453     abi_ulong tuc_flags;
1454     abi_ulong tuc_link;
1455     target_stack_t tuc_stack;
1456     struct target_sigcontext tuc_mcontext;
1457     target_sigset_t  tuc_sigmask;       /* mask last for extensibility */
1458 };
1459
1460 struct target_ucontext_v2 {
1461     abi_ulong tuc_flags;
1462     abi_ulong tuc_link;
1463     target_stack_t tuc_stack;
1464     struct target_sigcontext tuc_mcontext;
1465     target_sigset_t  tuc_sigmask;       /* mask last for extensibility */
1466     char __unused[128 - sizeof(target_sigset_t)];
1467     abi_ulong tuc_regspace[128] __attribute__((__aligned__(8)));
1468 };
1469
1470 struct target_user_vfp {
1471     uint64_t fpregs[32];
1472     abi_ulong fpscr;
1473 };
1474
1475 struct target_user_vfp_exc {
1476     abi_ulong fpexc;
1477     abi_ulong fpinst;
1478     abi_ulong fpinst2;
1479 };
1480
1481 struct target_vfp_sigframe {
1482     abi_ulong magic;
1483     abi_ulong size;
1484     struct target_user_vfp ufp;
1485     struct target_user_vfp_exc ufp_exc;
1486 } __attribute__((__aligned__(8)));
1487
1488 struct target_iwmmxt_sigframe {
1489     abi_ulong magic;
1490     abi_ulong size;
1491     uint64_t regs[16];
1492     /* Note that not all the coprocessor control registers are stored here */
1493     uint32_t wcssf;
1494     uint32_t wcasf;
1495     uint32_t wcgr0;
1496     uint32_t wcgr1;
1497     uint32_t wcgr2;
1498     uint32_t wcgr3;
1499 } __attribute__((__aligned__(8)));
1500
1501 #define TARGET_VFP_MAGIC 0x56465001
1502 #define TARGET_IWMMXT_MAGIC 0x12ef842a
1503
1504 struct sigframe_v1
1505 {
1506     struct target_sigcontext sc;
1507     abi_ulong extramask[TARGET_NSIG_WORDS-1];
1508     abi_ulong retcode;
1509 };
1510
1511 struct sigframe_v2
1512 {
1513     struct target_ucontext_v2 uc;
1514     abi_ulong retcode;
1515 };
1516
1517 struct rt_sigframe_v1
1518 {
1519     abi_ulong pinfo;
1520     abi_ulong puc;
1521     struct target_siginfo info;
1522     struct target_ucontext_v1 uc;
1523     abi_ulong retcode;
1524 };
1525
1526 struct rt_sigframe_v2
1527 {
1528     struct target_siginfo info;
1529     struct target_ucontext_v2 uc;
1530     abi_ulong retcode;
1531 };
1532
1533 #define TARGET_CONFIG_CPU_32 1
1534
1535 /*
1536  * For ARM syscalls, we encode the syscall number into the instruction.
1537  */
1538 #define SWI_SYS_SIGRETURN       (0xef000000|(TARGET_NR_sigreturn + ARM_SYSCALL_BASE))
1539 #define SWI_SYS_RT_SIGRETURN    (0xef000000|(TARGET_NR_rt_sigreturn + ARM_SYSCALL_BASE))
1540
1541 /*
1542  * For Thumb syscalls, we pass the syscall number via r7.  We therefore
1543  * need two 16-bit instructions.
1544  */
1545 #define SWI_THUMB_SIGRETURN     (0xdf00 << 16 | 0x2700 | (TARGET_NR_sigreturn))
1546 #define SWI_THUMB_RT_SIGRETURN  (0xdf00 << 16 | 0x2700 | (TARGET_NR_rt_sigreturn))
1547
1548 static const abi_ulong retcodes[4] = {
1549         SWI_SYS_SIGRETURN,      SWI_THUMB_SIGRETURN,
1550         SWI_SYS_RT_SIGRETURN,   SWI_THUMB_RT_SIGRETURN
1551 };
1552
1553
1554 static inline int valid_user_regs(CPUARMState *regs)
1555 {
1556     return 1;
1557 }
1558
1559 static void
1560 setup_sigcontext(struct target_sigcontext *sc, /*struct _fpstate *fpstate,*/
1561                  CPUARMState *env, abi_ulong mask)
1562 {
1563         __put_user(env->regs[0], &sc->arm_r0);
1564         __put_user(env->regs[1], &sc->arm_r1);
1565         __put_user(env->regs[2], &sc->arm_r2);
1566         __put_user(env->regs[3], &sc->arm_r3);
1567         __put_user(env->regs[4], &sc->arm_r4);
1568         __put_user(env->regs[5], &sc->arm_r5);
1569         __put_user(env->regs[6], &sc->arm_r6);
1570         __put_user(env->regs[7], &sc->arm_r7);
1571         __put_user(env->regs[8], &sc->arm_r8);
1572         __put_user(env->regs[9], &sc->arm_r9);
1573         __put_user(env->regs[10], &sc->arm_r10);
1574         __put_user(env->regs[11], &sc->arm_fp);
1575         __put_user(env->regs[12], &sc->arm_ip);
1576         __put_user(env->regs[13], &sc->arm_sp);
1577         __put_user(env->regs[14], &sc->arm_lr);
1578         __put_user(env->regs[15], &sc->arm_pc);
1579 #ifdef TARGET_CONFIG_CPU_32
1580         __put_user(cpsr_read(env), &sc->arm_cpsr);
1581 #endif
1582
1583         __put_user(/* current->thread.trap_no */ 0, &sc->trap_no);
1584         __put_user(/* current->thread.error_code */ 0, &sc->error_code);
1585         __put_user(/* current->thread.address */ 0, &sc->fault_address);
1586         __put_user(mask, &sc->oldmask);
1587 }
1588
1589 static inline abi_ulong
1590 get_sigframe(struct target_sigaction *ka, CPUARMState *regs, int framesize)
1591 {
1592         unsigned long sp = regs->regs[13];
1593
1594         /*
1595          * This is the X/Open sanctioned signal stack switching.
1596          */
1597         if ((ka->sa_flags & TARGET_SA_ONSTACK) && !sas_ss_flags(sp))
1598             sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
1599         /*
1600          * ATPCS B01 mandates 8-byte alignment
1601          */
1602         return (sp - framesize) & ~7;
1603 }
1604
1605 static void
1606 setup_return(CPUARMState *env, struct target_sigaction *ka,
1607              abi_ulong *rc, abi_ulong frame_addr, int usig, abi_ulong rc_addr)
1608 {
1609         abi_ulong handler = ka->_sa_handler;
1610         abi_ulong retcode;
1611         int thumb = handler & 1;
1612         uint32_t cpsr = cpsr_read(env);
1613
1614         cpsr &= ~CPSR_IT;
1615         if (thumb) {
1616                 cpsr |= CPSR_T;
1617         } else {
1618                 cpsr &= ~CPSR_T;
1619         }
1620
1621         if (ka->sa_flags & TARGET_SA_RESTORER) {
1622                 retcode = ka->sa_restorer;
1623         } else {
1624                 unsigned int idx = thumb;
1625
1626                 if (ka->sa_flags & TARGET_SA_SIGINFO)
1627                         idx += 2;
1628
1629         __put_user(retcodes[idx], rc);
1630
1631                 retcode = rc_addr + thumb;
1632         }
1633
1634         env->regs[0] = usig;
1635         env->regs[13] = frame_addr;
1636         env->regs[14] = retcode;
1637         env->regs[15] = handler & (thumb ? ~1 : ~3);
1638         cpsr_write(env, cpsr, 0xffffffff);
1639 }
1640
1641 static abi_ulong *setup_sigframe_v2_vfp(abi_ulong *regspace, CPUARMState *env)
1642 {
1643     int i;
1644     struct target_vfp_sigframe *vfpframe;
1645     vfpframe = (struct target_vfp_sigframe *)regspace;
1646     __put_user(TARGET_VFP_MAGIC, &vfpframe->magic);
1647     __put_user(sizeof(*vfpframe), &vfpframe->size);
1648     for (i = 0; i < 32; i++) {
1649         __put_user(float64_val(env->vfp.regs[i]), &vfpframe->ufp.fpregs[i]);
1650     }
1651     __put_user(vfp_get_fpscr(env), &vfpframe->ufp.fpscr);
1652     __put_user(env->vfp.xregs[ARM_VFP_FPEXC], &vfpframe->ufp_exc.fpexc);
1653     __put_user(env->vfp.xregs[ARM_VFP_FPINST], &vfpframe->ufp_exc.fpinst);
1654     __put_user(env->vfp.xregs[ARM_VFP_FPINST2], &vfpframe->ufp_exc.fpinst2);
1655     return (abi_ulong*)(vfpframe+1);
1656 }
1657
1658 static abi_ulong *setup_sigframe_v2_iwmmxt(abi_ulong *regspace,
1659                                            CPUARMState *env)
1660 {
1661     int i;
1662     struct target_iwmmxt_sigframe *iwmmxtframe;
1663     iwmmxtframe = (struct target_iwmmxt_sigframe *)regspace;
1664     __put_user(TARGET_IWMMXT_MAGIC, &iwmmxtframe->magic);
1665     __put_user(sizeof(*iwmmxtframe), &iwmmxtframe->size);
1666     for (i = 0; i < 16; i++) {
1667         __put_user(env->iwmmxt.regs[i], &iwmmxtframe->regs[i]);
1668     }
1669     __put_user(env->vfp.xregs[ARM_IWMMXT_wCSSF], &iwmmxtframe->wcssf);
1670     __put_user(env->vfp.xregs[ARM_IWMMXT_wCASF], &iwmmxtframe->wcssf);
1671     __put_user(env->vfp.xregs[ARM_IWMMXT_wCGR0], &iwmmxtframe->wcgr0);
1672     __put_user(env->vfp.xregs[ARM_IWMMXT_wCGR1], &iwmmxtframe->wcgr1);
1673     __put_user(env->vfp.xregs[ARM_IWMMXT_wCGR2], &iwmmxtframe->wcgr2);
1674     __put_user(env->vfp.xregs[ARM_IWMMXT_wCGR3], &iwmmxtframe->wcgr3);
1675     return (abi_ulong*)(iwmmxtframe+1);
1676 }
1677
1678 static void setup_sigframe_v2(struct target_ucontext_v2 *uc,
1679                               target_sigset_t *set, CPUARMState *env)
1680 {
1681     struct target_sigaltstack stack;
1682     int i;
1683     abi_ulong *regspace;
1684
1685     /* Clear all the bits of the ucontext we don't use.  */
1686     memset(uc, 0, offsetof(struct target_ucontext_v2, tuc_mcontext));
1687
1688     memset(&stack, 0, sizeof(stack));
1689     __put_user(target_sigaltstack_used.ss_sp, &stack.ss_sp);
1690     __put_user(target_sigaltstack_used.ss_size, &stack.ss_size);
1691     __put_user(sas_ss_flags(get_sp_from_cpustate(env)), &stack.ss_flags);
1692     memcpy(&uc->tuc_stack, &stack, sizeof(stack));
1693
1694     setup_sigcontext(&uc->tuc_mcontext, env, set->sig[0]);
1695     /* Save coprocessor signal frame.  */
1696     regspace = uc->tuc_regspace;
1697     if (arm_feature(env, ARM_FEATURE_VFP)) {
1698         regspace = setup_sigframe_v2_vfp(regspace, env);
1699     }
1700     if (arm_feature(env, ARM_FEATURE_IWMMXT)) {
1701         regspace = setup_sigframe_v2_iwmmxt(regspace, env);
1702     }
1703
1704     /* Write terminating magic word */
1705     __put_user(0, regspace);
1706
1707     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
1708         __put_user(set->sig[i], &uc->tuc_sigmask.sig[i]);
1709     }
1710 }
1711
1712 /* compare linux/arch/arm/kernel/signal.c:setup_frame() */
1713 static void setup_frame_v1(int usig, struct target_sigaction *ka,
1714                            target_sigset_t *set, CPUARMState *regs)
1715 {
1716         struct sigframe_v1 *frame;
1717         abi_ulong frame_addr = get_sigframe(ka, regs, sizeof(*frame));
1718         int i;
1719
1720         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
1721                 return;
1722
1723         setup_sigcontext(&frame->sc, regs, set->sig[0]);
1724
1725     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
1726         __put_user(set->sig[i], &frame->extramask[i - 1]);
1727     }
1728
1729         setup_return(regs, ka, &frame->retcode, frame_addr, usig,
1730                      frame_addr + offsetof(struct sigframe_v1, retcode));
1731
1732         unlock_user_struct(frame, frame_addr, 1);
1733 }
1734
1735 static void setup_frame_v2(int usig, struct target_sigaction *ka,
1736                            target_sigset_t *set, CPUARMState *regs)
1737 {
1738         struct sigframe_v2 *frame;
1739         abi_ulong frame_addr = get_sigframe(ka, regs, sizeof(*frame));
1740
1741         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
1742                 return;
1743
1744         setup_sigframe_v2(&frame->uc, set, regs);
1745
1746         setup_return(regs, ka, &frame->retcode, frame_addr, usig,
1747                      frame_addr + offsetof(struct sigframe_v2, retcode));
1748
1749         unlock_user_struct(frame, frame_addr, 1);
1750 }
1751
1752 static void setup_frame(int usig, struct target_sigaction *ka,
1753                         target_sigset_t *set, CPUARMState *regs)
1754 {
1755     if (get_osversion() >= 0x020612) {
1756         setup_frame_v2(usig, ka, set, regs);
1757     } else {
1758         setup_frame_v1(usig, ka, set, regs);
1759     }
1760 }
1761
1762 /* compare linux/arch/arm/kernel/signal.c:setup_rt_frame() */
1763 static void setup_rt_frame_v1(int usig, struct target_sigaction *ka,
1764                               target_siginfo_t *info,
1765                               target_sigset_t *set, CPUARMState *env)
1766 {
1767         struct rt_sigframe_v1 *frame;
1768         abi_ulong frame_addr = get_sigframe(ka, env, sizeof(*frame));
1769         struct target_sigaltstack stack;
1770         int i;
1771         abi_ulong info_addr, uc_addr;
1772
1773         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
1774             return /* 1 */;
1775
1776         info_addr = frame_addr + offsetof(struct rt_sigframe_v1, info);
1777         __put_user(info_addr, &frame->pinfo);
1778         uc_addr = frame_addr + offsetof(struct rt_sigframe_v1, uc);
1779         __put_user(uc_addr, &frame->puc);
1780         copy_siginfo_to_user(&frame->info, info);
1781
1782         /* Clear all the bits of the ucontext we don't use.  */
1783         memset(&frame->uc, 0, offsetof(struct target_ucontext_v1, tuc_mcontext));
1784
1785         memset(&stack, 0, sizeof(stack));
1786         __put_user(target_sigaltstack_used.ss_sp, &stack.ss_sp);
1787         __put_user(target_sigaltstack_used.ss_size, &stack.ss_size);
1788         __put_user(sas_ss_flags(get_sp_from_cpustate(env)), &stack.ss_flags);
1789         memcpy(&frame->uc.tuc_stack, &stack, sizeof(stack));
1790
1791         setup_sigcontext(&frame->uc.tuc_mcontext, env, set->sig[0]);
1792         for(i = 0; i < TARGET_NSIG_WORDS; i++) {
1793             __put_user(set->sig[i], &frame->uc.tuc_sigmask.sig[i]);
1794         }
1795
1796         setup_return(env, ka, &frame->retcode, frame_addr, usig,
1797                      frame_addr + offsetof(struct rt_sigframe_v1, retcode));
1798
1799         env->regs[1] = info_addr;
1800         env->regs[2] = uc_addr;
1801
1802         unlock_user_struct(frame, frame_addr, 1);
1803 }
1804
1805 static void setup_rt_frame_v2(int usig, struct target_sigaction *ka,
1806                               target_siginfo_t *info,
1807                               target_sigset_t *set, CPUARMState *env)
1808 {
1809         struct rt_sigframe_v2 *frame;
1810         abi_ulong frame_addr = get_sigframe(ka, env, sizeof(*frame));
1811         abi_ulong info_addr, uc_addr;
1812
1813         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
1814             return /* 1 */;
1815
1816         info_addr = frame_addr + offsetof(struct rt_sigframe_v2, info);
1817         uc_addr = frame_addr + offsetof(struct rt_sigframe_v2, uc);
1818         copy_siginfo_to_user(&frame->info, info);
1819
1820         setup_sigframe_v2(&frame->uc, set, env);
1821
1822         setup_return(env, ka, &frame->retcode, frame_addr, usig,
1823                      frame_addr + offsetof(struct rt_sigframe_v2, retcode));
1824
1825         env->regs[1] = info_addr;
1826         env->regs[2] = uc_addr;
1827
1828         unlock_user_struct(frame, frame_addr, 1);
1829 }
1830
1831 static void setup_rt_frame(int usig, struct target_sigaction *ka,
1832                            target_siginfo_t *info,
1833                            target_sigset_t *set, CPUARMState *env)
1834 {
1835     if (get_osversion() >= 0x020612) {
1836         setup_rt_frame_v2(usig, ka, info, set, env);
1837     } else {
1838         setup_rt_frame_v1(usig, ka, info, set, env);
1839     }
1840 }
1841
1842 static int
1843 restore_sigcontext(CPUARMState *env, struct target_sigcontext *sc)
1844 {
1845         int err = 0;
1846         uint32_t cpsr;
1847
1848     __get_user(env->regs[0], &sc->arm_r0);
1849     __get_user(env->regs[1], &sc->arm_r1);
1850     __get_user(env->regs[2], &sc->arm_r2);
1851     __get_user(env->regs[3], &sc->arm_r3);
1852     __get_user(env->regs[4], &sc->arm_r4);
1853     __get_user(env->regs[5], &sc->arm_r5);
1854     __get_user(env->regs[6], &sc->arm_r6);
1855     __get_user(env->regs[7], &sc->arm_r7);
1856     __get_user(env->regs[8], &sc->arm_r8);
1857     __get_user(env->regs[9], &sc->arm_r9);
1858     __get_user(env->regs[10], &sc->arm_r10);
1859     __get_user(env->regs[11], &sc->arm_fp);
1860     __get_user(env->regs[12], &sc->arm_ip);
1861     __get_user(env->regs[13], &sc->arm_sp);
1862     __get_user(env->regs[14], &sc->arm_lr);
1863     __get_user(env->regs[15], &sc->arm_pc);
1864 #ifdef TARGET_CONFIG_CPU_32
1865     __get_user(cpsr, &sc->arm_cpsr);
1866         cpsr_write(env, cpsr, CPSR_USER | CPSR_EXEC);
1867 #endif
1868
1869         err |= !valid_user_regs(env);
1870
1871         return err;
1872 }
1873
1874 static long do_sigreturn_v1(CPUARMState *env)
1875 {
1876         abi_ulong frame_addr;
1877         struct sigframe_v1 *frame = NULL;
1878         target_sigset_t set;
1879         sigset_t host_set;
1880         int i;
1881
1882         /*
1883          * Since we stacked the signal on a 64-bit boundary,
1884          * then 'sp' should be word aligned here.  If it's
1885          * not, then the user is trying to mess with us.
1886          */
1887         frame_addr = env->regs[13];
1888         if (frame_addr & 7) {
1889             goto badframe;
1890         }
1891
1892         if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
1893                 goto badframe;
1894
1895     __get_user(set.sig[0], &frame->sc.oldmask);
1896     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
1897         __get_user(set.sig[i], &frame->extramask[i - 1]);
1898     }
1899
1900         target_to_host_sigset_internal(&host_set, &set);
1901         do_sigprocmask(SIG_SETMASK, &host_set, NULL);
1902
1903         if (restore_sigcontext(env, &frame->sc))
1904                 goto badframe;
1905
1906 #if 0
1907         /* Send SIGTRAP if we're single-stepping */
1908         if (ptrace_cancel_bpt(current))
1909                 send_sig(SIGTRAP, current, 1);
1910 #endif
1911         unlock_user_struct(frame, frame_addr, 0);
1912         return env->regs[0];
1913
1914 badframe:
1915         force_sig(TARGET_SIGSEGV /* , current */);
1916         return 0;
1917 }
1918
1919 static abi_ulong *restore_sigframe_v2_vfp(CPUARMState *env, abi_ulong *regspace)
1920 {
1921     int i;
1922     abi_ulong magic, sz;
1923     uint32_t fpscr, fpexc;
1924     struct target_vfp_sigframe *vfpframe;
1925     vfpframe = (struct target_vfp_sigframe *)regspace;
1926
1927     __get_user(magic, &vfpframe->magic);
1928     __get_user(sz, &vfpframe->size);
1929     if (magic != TARGET_VFP_MAGIC || sz != sizeof(*vfpframe)) {
1930         return 0;
1931     }
1932     for (i = 0; i < 32; i++) {
1933         __get_user(float64_val(env->vfp.regs[i]), &vfpframe->ufp.fpregs[i]);
1934     }
1935     __get_user(fpscr, &vfpframe->ufp.fpscr);
1936     vfp_set_fpscr(env, fpscr);
1937     __get_user(fpexc, &vfpframe->ufp_exc.fpexc);
1938     /* Sanitise FPEXC: ensure VFP is enabled, FPINST2 is invalid
1939      * and the exception flag is cleared
1940      */
1941     fpexc |= (1 << 30);
1942     fpexc &= ~((1 << 31) | (1 << 28));
1943     env->vfp.xregs[ARM_VFP_FPEXC] = fpexc;
1944     __get_user(env->vfp.xregs[ARM_VFP_FPINST], &vfpframe->ufp_exc.fpinst);
1945     __get_user(env->vfp.xregs[ARM_VFP_FPINST2], &vfpframe->ufp_exc.fpinst2);
1946     return (abi_ulong*)(vfpframe + 1);
1947 }
1948
1949 static abi_ulong *restore_sigframe_v2_iwmmxt(CPUARMState *env,
1950                                              abi_ulong *regspace)
1951 {
1952     int i;
1953     abi_ulong magic, sz;
1954     struct target_iwmmxt_sigframe *iwmmxtframe;
1955     iwmmxtframe = (struct target_iwmmxt_sigframe *)regspace;
1956
1957     __get_user(magic, &iwmmxtframe->magic);
1958     __get_user(sz, &iwmmxtframe->size);
1959     if (magic != TARGET_IWMMXT_MAGIC || sz != sizeof(*iwmmxtframe)) {
1960         return 0;
1961     }
1962     for (i = 0; i < 16; i++) {
1963         __get_user(env->iwmmxt.regs[i], &iwmmxtframe->regs[i]);
1964     }
1965     __get_user(env->vfp.xregs[ARM_IWMMXT_wCSSF], &iwmmxtframe->wcssf);
1966     __get_user(env->vfp.xregs[ARM_IWMMXT_wCASF], &iwmmxtframe->wcssf);
1967     __get_user(env->vfp.xregs[ARM_IWMMXT_wCGR0], &iwmmxtframe->wcgr0);
1968     __get_user(env->vfp.xregs[ARM_IWMMXT_wCGR1], &iwmmxtframe->wcgr1);
1969     __get_user(env->vfp.xregs[ARM_IWMMXT_wCGR2], &iwmmxtframe->wcgr2);
1970     __get_user(env->vfp.xregs[ARM_IWMMXT_wCGR3], &iwmmxtframe->wcgr3);
1971     return (abi_ulong*)(iwmmxtframe + 1);
1972 }
1973
1974 static int do_sigframe_return_v2(CPUARMState *env, target_ulong frame_addr,
1975                                  struct target_ucontext_v2 *uc)
1976 {
1977     sigset_t host_set;
1978     abi_ulong *regspace;
1979
1980     target_to_host_sigset(&host_set, &uc->tuc_sigmask);
1981     do_sigprocmask(SIG_SETMASK, &host_set, NULL);
1982
1983     if (restore_sigcontext(env, &uc->tuc_mcontext))
1984         return 1;
1985
1986     /* Restore coprocessor signal frame */
1987     regspace = uc->tuc_regspace;
1988     if (arm_feature(env, ARM_FEATURE_VFP)) {
1989         regspace = restore_sigframe_v2_vfp(env, regspace);
1990         if (!regspace) {
1991             return 1;
1992         }
1993     }
1994     if (arm_feature(env, ARM_FEATURE_IWMMXT)) {
1995         regspace = restore_sigframe_v2_iwmmxt(env, regspace);
1996         if (!regspace) {
1997             return 1;
1998         }
1999     }
2000
2001     if (do_sigaltstack(frame_addr + offsetof(struct target_ucontext_v2, tuc_stack), 0, get_sp_from_cpustate(env)) == -EFAULT)
2002         return 1;
2003
2004 #if 0
2005     /* Send SIGTRAP if we're single-stepping */
2006     if (ptrace_cancel_bpt(current))
2007             send_sig(SIGTRAP, current, 1);
2008 #endif
2009
2010     return 0;
2011 }
2012
2013 static long do_sigreturn_v2(CPUARMState *env)
2014 {
2015         abi_ulong frame_addr;
2016         struct sigframe_v2 *frame = NULL;
2017
2018         /*
2019          * Since we stacked the signal on a 64-bit boundary,
2020          * then 'sp' should be word aligned here.  If it's
2021          * not, then the user is trying to mess with us.
2022          */
2023         frame_addr = env->regs[13];
2024         if (frame_addr & 7) {
2025             goto badframe;
2026         }
2027
2028         if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
2029                 goto badframe;
2030
2031         if (do_sigframe_return_v2(env, frame_addr, &frame->uc))
2032                 goto badframe;
2033
2034         unlock_user_struct(frame, frame_addr, 0);
2035         return env->regs[0];
2036
2037 badframe:
2038         unlock_user_struct(frame, frame_addr, 0);
2039         force_sig(TARGET_SIGSEGV /* , current */);
2040         return 0;
2041 }
2042
2043 long do_sigreturn(CPUARMState *env)
2044 {
2045     if (get_osversion() >= 0x020612) {
2046         return do_sigreturn_v2(env);
2047     } else {
2048         return do_sigreturn_v1(env);
2049     }
2050 }
2051
2052 static long do_rt_sigreturn_v1(CPUARMState *env)
2053 {
2054         abi_ulong frame_addr;
2055         struct rt_sigframe_v1 *frame = NULL;
2056         sigset_t host_set;
2057
2058         /*
2059          * Since we stacked the signal on a 64-bit boundary,
2060          * then 'sp' should be word aligned here.  If it's
2061          * not, then the user is trying to mess with us.
2062          */
2063         frame_addr = env->regs[13];
2064         if (frame_addr & 7) {
2065             goto badframe;
2066         }
2067
2068         if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
2069                 goto badframe;
2070
2071         target_to_host_sigset(&host_set, &frame->uc.tuc_sigmask);
2072         do_sigprocmask(SIG_SETMASK, &host_set, NULL);
2073
2074         if (restore_sigcontext(env, &frame->uc.tuc_mcontext))
2075                 goto badframe;
2076
2077         if (do_sigaltstack(frame_addr + offsetof(struct rt_sigframe_v1, uc.tuc_stack), 0, get_sp_from_cpustate(env)) == -EFAULT)
2078                 goto badframe;
2079
2080 #if 0
2081         /* Send SIGTRAP if we're single-stepping */
2082         if (ptrace_cancel_bpt(current))
2083                 send_sig(SIGTRAP, current, 1);
2084 #endif
2085         unlock_user_struct(frame, frame_addr, 0);
2086         return env->regs[0];
2087
2088 badframe:
2089         unlock_user_struct(frame, frame_addr, 0);
2090         force_sig(TARGET_SIGSEGV /* , current */);
2091         return 0;
2092 }
2093
2094 static long do_rt_sigreturn_v2(CPUARMState *env)
2095 {
2096         abi_ulong frame_addr;
2097         struct rt_sigframe_v2 *frame = NULL;
2098
2099         /*
2100          * Since we stacked the signal on a 64-bit boundary,
2101          * then 'sp' should be word aligned here.  If it's
2102          * not, then the user is trying to mess with us.
2103          */
2104         frame_addr = env->regs[13];
2105         if (frame_addr & 7) {
2106             goto badframe;
2107         }
2108
2109         if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
2110                 goto badframe;
2111
2112         if (do_sigframe_return_v2(env, frame_addr, &frame->uc))
2113                 goto badframe;
2114
2115         unlock_user_struct(frame, frame_addr, 0);
2116         return env->regs[0];
2117
2118 badframe:
2119         unlock_user_struct(frame, frame_addr, 0);
2120         force_sig(TARGET_SIGSEGV /* , current */);
2121         return 0;
2122 }
2123
2124 long do_rt_sigreturn(CPUARMState *env)
2125 {
2126     if (get_osversion() >= 0x020612) {
2127         return do_rt_sigreturn_v2(env);
2128     } else {
2129         return do_rt_sigreturn_v1(env);
2130     }
2131 }
2132
2133 #elif defined(TARGET_SPARC)
2134
2135 #define __SUNOS_MAXWIN   31
2136
2137 /* This is what SunOS does, so shall I. */
2138 struct target_sigcontext {
2139         abi_ulong sigc_onstack;      /* state to restore */
2140
2141         abi_ulong sigc_mask;         /* sigmask to restore */
2142         abi_ulong sigc_sp;           /* stack pointer */
2143         abi_ulong sigc_pc;           /* program counter */
2144         abi_ulong sigc_npc;          /* next program counter */
2145         abi_ulong sigc_psr;          /* for condition codes etc */
2146         abi_ulong sigc_g1;           /* User uses these two registers */
2147         abi_ulong sigc_o0;           /* within the trampoline code. */
2148
2149         /* Now comes information regarding the users window set
2150          * at the time of the signal.
2151          */
2152         abi_ulong sigc_oswins;       /* outstanding windows */
2153
2154         /* stack ptrs for each regwin buf */
2155         char *sigc_spbuf[__SUNOS_MAXWIN];
2156
2157         /* Windows to restore after signal */
2158         struct {
2159                 abi_ulong locals[8];
2160                 abi_ulong ins[8];
2161         } sigc_wbuf[__SUNOS_MAXWIN];
2162 };
2163 /* A Sparc stack frame */
2164 struct sparc_stackf {
2165         abi_ulong locals[8];
2166         abi_ulong ins[8];
2167         /* It's simpler to treat fp and callers_pc as elements of ins[]
2168          * since we never need to access them ourselves.
2169          */
2170         char *structptr;
2171         abi_ulong xargs[6];
2172         abi_ulong xxargs[1];
2173 };
2174
2175 typedef struct {
2176         struct {
2177                 abi_ulong psr;
2178                 abi_ulong pc;
2179                 abi_ulong npc;
2180                 abi_ulong y;
2181                 abi_ulong u_regs[16]; /* globals and ins */
2182         }               si_regs;
2183         int             si_mask;
2184 } __siginfo_t;
2185
2186 typedef struct {
2187         abi_ulong       si_float_regs[32];
2188         unsigned   long si_fsr;
2189         unsigned   long si_fpqdepth;
2190         struct {
2191                 unsigned long *insn_addr;
2192                 unsigned long insn;
2193         } si_fpqueue [16];
2194 } qemu_siginfo_fpu_t;
2195
2196
2197 struct target_signal_frame {
2198         struct sparc_stackf     ss;
2199         __siginfo_t             info;
2200         abi_ulong               fpu_save;
2201         abi_ulong               insns[2] __attribute__ ((aligned (8)));
2202         abi_ulong               extramask[TARGET_NSIG_WORDS - 1];
2203         abi_ulong               extra_size; /* Should be 0 */
2204         qemu_siginfo_fpu_t      fpu_state;
2205 };
2206 struct target_rt_signal_frame {
2207         struct sparc_stackf     ss;
2208         siginfo_t               info;
2209         abi_ulong               regs[20];
2210         sigset_t                mask;
2211         abi_ulong               fpu_save;
2212         unsigned int            insns[2];
2213         stack_t                 stack;
2214         unsigned int            extra_size; /* Should be 0 */
2215         qemu_siginfo_fpu_t      fpu_state;
2216 };
2217
2218 #define UREG_O0        16
2219 #define UREG_O6        22
2220 #define UREG_I0        0
2221 #define UREG_I1        1
2222 #define UREG_I2        2
2223 #define UREG_I3        3
2224 #define UREG_I4        4
2225 #define UREG_I5        5
2226 #define UREG_I6        6
2227 #define UREG_I7        7
2228 #define UREG_L0        8
2229 #define UREG_FP        UREG_I6
2230 #define UREG_SP        UREG_O6
2231
2232 static inline abi_ulong get_sigframe(struct target_sigaction *sa, 
2233                                      CPUSPARCState *env,
2234                                      unsigned long framesize)
2235 {
2236         abi_ulong sp;
2237
2238         sp = env->regwptr[UREG_FP];
2239
2240         /* This is the X/Open sanctioned signal stack switching.  */
2241         if (sa->sa_flags & TARGET_SA_ONSTACK) {
2242             if (!on_sig_stack(sp)
2243                 && !((target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size) & 7))
2244                 sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
2245         }
2246         return sp - framesize;
2247 }
2248
2249 static int
2250 setup___siginfo(__siginfo_t *si, CPUSPARCState *env, abi_ulong mask)
2251 {
2252         int err = 0, i;
2253
2254     __put_user(env->psr, &si->si_regs.psr);
2255     __put_user(env->pc, &si->si_regs.pc);
2256     __put_user(env->npc, &si->si_regs.npc);
2257     __put_user(env->y, &si->si_regs.y);
2258         for (i=0; i < 8; i++) {
2259         __put_user(env->gregs[i], &si->si_regs.u_regs[i]);
2260         }
2261         for (i=0; i < 8; i++) {
2262         __put_user(env->regwptr[UREG_I0 + i], &si->si_regs.u_regs[i+8]);
2263         }
2264     __put_user(mask, &si->si_mask);
2265         return err;
2266 }
2267
2268 #if 0
2269 static int
2270 setup_sigcontext(struct target_sigcontext *sc, /*struct _fpstate *fpstate,*/
2271                  CPUSPARCState *env, unsigned long mask)
2272 {
2273         int err = 0;
2274
2275     __put_user(mask, &sc->sigc_mask);
2276     __put_user(env->regwptr[UREG_SP], &sc->sigc_sp);
2277     __put_user(env->pc, &sc->sigc_pc);
2278     __put_user(env->npc, &sc->sigc_npc);
2279     __put_user(env->psr, &sc->sigc_psr);
2280     __put_user(env->gregs[1], &sc->sigc_g1);
2281     __put_user(env->regwptr[UREG_O0], &sc->sigc_o0);
2282
2283         return err;
2284 }
2285 #endif
2286 #define NF_ALIGNEDSZ  (((sizeof(struct target_signal_frame) + 7) & (~7)))
2287
2288 static void setup_frame(int sig, struct target_sigaction *ka,
2289                         target_sigset_t *set, CPUSPARCState *env)
2290 {
2291         abi_ulong sf_addr;
2292         struct target_signal_frame *sf;
2293         int sigframe_size, err, i;
2294
2295         /* 1. Make sure everything is clean */
2296         //synchronize_user_stack();
2297
2298         sigframe_size = NF_ALIGNEDSZ;
2299         sf_addr = get_sigframe(ka, env, sigframe_size);
2300
2301         sf = lock_user(VERIFY_WRITE, sf_addr, 
2302                        sizeof(struct target_signal_frame), 0);
2303         if (!sf)
2304                 goto sigsegv;
2305                 
2306         //fprintf(stderr, "sf: %x pc %x fp %x sp %x\n", sf, env->pc, env->regwptr[UREG_FP], env->regwptr[UREG_SP]);
2307 #if 0
2308         if (invalid_frame_pointer(sf, sigframe_size))
2309                 goto sigill_and_return;
2310 #endif
2311         /* 2. Save the current process state */
2312         err = setup___siginfo(&sf->info, env, set->sig[0]);
2313     __put_user(0, &sf->extra_size);
2314
2315         //save_fpu_state(regs, &sf->fpu_state);
2316         //__put_user(&sf->fpu_state, &sf->fpu_save);
2317
2318     __put_user(set->sig[0], &sf->info.si_mask);
2319         for (i = 0; i < TARGET_NSIG_WORDS - 1; i++) {
2320         __put_user(set->sig[i + 1], &sf->extramask[i]);
2321         }
2322
2323         for (i = 0; i < 8; i++) {
2324         __put_user(env->regwptr[i + UREG_L0], &sf->ss.locals[i]);
2325         }
2326         for (i = 0; i < 8; i++) {
2327         __put_user(env->regwptr[i + UREG_I0], &sf->ss.ins[i]);
2328         }
2329         if (err)
2330                 goto sigsegv;
2331
2332         /* 3. signal handler back-trampoline and parameters */
2333         env->regwptr[UREG_FP] = sf_addr;
2334         env->regwptr[UREG_I0] = sig;
2335         env->regwptr[UREG_I1] = sf_addr + 
2336                 offsetof(struct target_signal_frame, info);
2337         env->regwptr[UREG_I2] = sf_addr + 
2338                 offsetof(struct target_signal_frame, info);
2339
2340         /* 4. signal handler */
2341         env->pc = ka->_sa_handler;
2342         env->npc = (env->pc + 4);
2343         /* 5. return to kernel instructions */
2344         if (ka->sa_restorer)
2345                 env->regwptr[UREG_I7] = ka->sa_restorer;
2346         else {
2347                 uint32_t val32;
2348
2349                 env->regwptr[UREG_I7] = sf_addr + 
2350                         offsetof(struct target_signal_frame, insns) - 2 * 4;
2351
2352                 /* mov __NR_sigreturn, %g1 */
2353                 val32 = 0x821020d8;
2354         __put_user(val32, &sf->insns[0]);
2355
2356                 /* t 0x10 */
2357                 val32 = 0x91d02010;
2358         __put_user(val32, &sf->insns[1]);
2359                 if (err)
2360                         goto sigsegv;
2361
2362                 /* Flush instruction space. */
2363                 //flush_sig_insns(current->mm, (unsigned long) &(sf->insns[0]));
2364                 //              tb_flush(env);
2365         }
2366         unlock_user(sf, sf_addr, sizeof(struct target_signal_frame));
2367         return;
2368 #if 0
2369 sigill_and_return:
2370         force_sig(TARGET_SIGILL);
2371 #endif
2372 sigsegv:
2373         //fprintf(stderr, "force_sig\n");
2374         unlock_user(sf, sf_addr, sizeof(struct target_signal_frame));
2375         force_sig(TARGET_SIGSEGV);
2376 }
2377
2378 static void setup_rt_frame(int sig, struct target_sigaction *ka,
2379                            target_siginfo_t *info,
2380                            target_sigset_t *set, CPUSPARCState *env)
2381 {
2382     fprintf(stderr, "setup_rt_frame: not implemented\n");
2383 }
2384
2385 long do_sigreturn(CPUSPARCState *env)
2386 {
2387         abi_ulong sf_addr;
2388         struct target_signal_frame *sf;
2389         uint32_t up_psr, pc, npc;
2390         target_sigset_t set;
2391         sigset_t host_set;
2392         int err=0, i;
2393
2394         sf_addr = env->regwptr[UREG_FP];
2395         if (!lock_user_struct(VERIFY_READ, sf, sf_addr, 1))
2396                 goto segv_and_exit;
2397 #if 0
2398         fprintf(stderr, "sigreturn\n");
2399         fprintf(stderr, "sf: %x pc %x fp %x sp %x\n", sf, env->pc, env->regwptr[UREG_FP], env->regwptr[UREG_SP]);
2400 #endif
2401         //cpu_dump_state(env, stderr, fprintf, 0);
2402
2403         /* 1. Make sure we are not getting garbage from the user */
2404
2405         if (sf_addr & 3)
2406                 goto segv_and_exit;
2407
2408         __get_user(pc,  &sf->info.si_regs.pc);
2409         __get_user(npc, &sf->info.si_regs.npc);
2410
2411         if ((pc | npc) & 3)
2412                 goto segv_and_exit;
2413
2414         /* 2. Restore the state */
2415         __get_user(up_psr, &sf->info.si_regs.psr);
2416
2417         /* User can only change condition codes and FPU enabling in %psr. */
2418         env->psr = (up_psr & (PSR_ICC /* | PSR_EF */))
2419                   | (env->psr & ~(PSR_ICC /* | PSR_EF */));
2420
2421         env->pc = pc;
2422         env->npc = npc;
2423         __get_user(env->y, &sf->info.si_regs.y);
2424         for (i=0; i < 8; i++) {
2425                 __get_user(env->gregs[i], &sf->info.si_regs.u_regs[i]);
2426         }
2427         for (i=0; i < 8; i++) {
2428                 __get_user(env->regwptr[i + UREG_I0], &sf->info.si_regs.u_regs[i+8]);
2429         }
2430
2431         /* FIXME: implement FPU save/restore:
2432          * __get_user(fpu_save, &sf->fpu_save);
2433          * if (fpu_save)
2434          *        err |= restore_fpu_state(env, fpu_save);
2435          */
2436
2437         /* This is pretty much atomic, no amount locking would prevent
2438          * the races which exist anyways.
2439          */
2440         __get_user(set.sig[0], &sf->info.si_mask);
2441         for(i = 1; i < TARGET_NSIG_WORDS; i++) {
2442             __get_user(set.sig[i], &sf->extramask[i - 1]);
2443         }
2444
2445         target_to_host_sigset_internal(&host_set, &set);
2446         do_sigprocmask(SIG_SETMASK, &host_set, NULL);
2447
2448         if (err)
2449                 goto segv_and_exit;
2450         unlock_user_struct(sf, sf_addr, 0);
2451         return env->regwptr[0];
2452
2453 segv_and_exit:
2454         unlock_user_struct(sf, sf_addr, 0);
2455         force_sig(TARGET_SIGSEGV);
2456 }
2457
2458 long do_rt_sigreturn(CPUSPARCState *env)
2459 {
2460     fprintf(stderr, "do_rt_sigreturn: not implemented\n");
2461     return -TARGET_ENOSYS;
2462 }
2463
2464 #if defined(TARGET_SPARC64) && !defined(TARGET_ABI32)
2465 #define MC_TSTATE 0
2466 #define MC_PC 1
2467 #define MC_NPC 2
2468 #define MC_Y 3
2469 #define MC_G1 4
2470 #define MC_G2 5
2471 #define MC_G3 6
2472 #define MC_G4 7
2473 #define MC_G5 8
2474 #define MC_G6 9
2475 #define MC_G7 10
2476 #define MC_O0 11
2477 #define MC_O1 12
2478 #define MC_O2 13
2479 #define MC_O3 14
2480 #define MC_O4 15
2481 #define MC_O5 16
2482 #define MC_O6 17
2483 #define MC_O7 18
2484 #define MC_NGREG 19
2485
2486 typedef abi_ulong target_mc_greg_t;
2487 typedef target_mc_greg_t target_mc_gregset_t[MC_NGREG];
2488
2489 struct target_mc_fq {
2490     abi_ulong *mcfq_addr;
2491     uint32_t mcfq_insn;
2492 };
2493
2494 struct target_mc_fpu {
2495     union {
2496         uint32_t sregs[32];
2497         uint64_t dregs[32];
2498         //uint128_t qregs[16];
2499     } mcfpu_fregs;
2500     abi_ulong mcfpu_fsr;
2501     abi_ulong mcfpu_fprs;
2502     abi_ulong mcfpu_gsr;
2503     struct target_mc_fq *mcfpu_fq;
2504     unsigned char mcfpu_qcnt;
2505     unsigned char mcfpu_qentsz;
2506     unsigned char mcfpu_enab;
2507 };
2508 typedef struct target_mc_fpu target_mc_fpu_t;
2509
2510 typedef struct {
2511     target_mc_gregset_t mc_gregs;
2512     target_mc_greg_t mc_fp;
2513     target_mc_greg_t mc_i7;
2514     target_mc_fpu_t mc_fpregs;
2515 } target_mcontext_t;
2516
2517 struct target_ucontext {
2518     struct target_ucontext *tuc_link;
2519     abi_ulong tuc_flags;
2520     target_sigset_t tuc_sigmask;
2521     target_mcontext_t tuc_mcontext;
2522 };
2523
2524 /* A V9 register window */
2525 struct target_reg_window {
2526     abi_ulong locals[8];
2527     abi_ulong ins[8];
2528 };
2529
2530 #define TARGET_STACK_BIAS 2047
2531
2532 /* {set, get}context() needed for 64-bit SparcLinux userland. */
2533 void sparc64_set_context(CPUSPARCState *env)
2534 {
2535     abi_ulong ucp_addr;
2536     struct target_ucontext *ucp;
2537     target_mc_gregset_t *grp;
2538     abi_ulong pc, npc, tstate;
2539     abi_ulong fp, i7, w_addr;
2540     unsigned int i;
2541
2542     ucp_addr = env->regwptr[UREG_I0];
2543     if (!lock_user_struct(VERIFY_READ, ucp, ucp_addr, 1))
2544         goto do_sigsegv;
2545     grp  = &ucp->tuc_mcontext.mc_gregs;
2546     __get_user(pc, &((*grp)[MC_PC]));
2547     __get_user(npc, &((*grp)[MC_NPC]));
2548     if ((pc | npc) & 3)
2549         goto do_sigsegv;
2550     if (env->regwptr[UREG_I1]) {
2551         target_sigset_t target_set;
2552         sigset_t set;
2553
2554         if (TARGET_NSIG_WORDS == 1) {
2555             __get_user(target_set.sig[0], &ucp->tuc_sigmask.sig[0]);
2556         } else {
2557             abi_ulong *src, *dst;
2558             src = ucp->tuc_sigmask.sig;
2559             dst = target_set.sig;
2560             for (i = 0; i < TARGET_NSIG_WORDS; i++, dst++, src++) {
2561                 __get_user(*dst, src);
2562             }
2563         }
2564         target_to_host_sigset_internal(&set, &target_set);
2565         do_sigprocmask(SIG_SETMASK, &set, NULL);
2566     }
2567     env->pc = pc;
2568     env->npc = npc;
2569     __get_user(env->y, &((*grp)[MC_Y]));
2570     __get_user(tstate, &((*grp)[MC_TSTATE]));
2571     env->asi = (tstate >> 24) & 0xff;
2572     cpu_put_ccr(env, tstate >> 32);
2573     cpu_put_cwp64(env, tstate & 0x1f);
2574     __get_user(env->gregs[1], (&(*grp)[MC_G1]));
2575     __get_user(env->gregs[2], (&(*grp)[MC_G2]));
2576     __get_user(env->gregs[3], (&(*grp)[MC_G3]));
2577     __get_user(env->gregs[4], (&(*grp)[MC_G4]));
2578     __get_user(env->gregs[5], (&(*grp)[MC_G5]));
2579     __get_user(env->gregs[6], (&(*grp)[MC_G6]));
2580     __get_user(env->gregs[7], (&(*grp)[MC_G7]));
2581     __get_user(env->regwptr[UREG_I0], (&(*grp)[MC_O0]));
2582     __get_user(env->regwptr[UREG_I1], (&(*grp)[MC_O1]));
2583     __get_user(env->regwptr[UREG_I2], (&(*grp)[MC_O2]));
2584     __get_user(env->regwptr[UREG_I3], (&(*grp)[MC_O3]));
2585     __get_user(env->regwptr[UREG_I4], (&(*grp)[MC_O4]));
2586     __get_user(env->regwptr[UREG_I5], (&(*grp)[MC_O5]));
2587     __get_user(env->regwptr[UREG_I6], (&(*grp)[MC_O6]));
2588     __get_user(env->regwptr[UREG_I7], (&(*grp)[MC_O7]));
2589
2590     __get_user(fp, &(ucp->tuc_mcontext.mc_fp));
2591     __get_user(i7, &(ucp->tuc_mcontext.mc_i7));
2592
2593     w_addr = TARGET_STACK_BIAS+env->regwptr[UREG_I6];
2594     if (put_user(fp, w_addr + offsetof(struct target_reg_window, ins[6]), 
2595                  abi_ulong) != 0)
2596         goto do_sigsegv;
2597     if (put_user(i7, w_addr + offsetof(struct target_reg_window, ins[7]), 
2598                  abi_ulong) != 0)
2599         goto do_sigsegv;
2600     /* FIXME this does not match how the kernel handles the FPU in
2601      * its sparc64_set_context implementation. In particular the FPU
2602      * is only restored if fenab is non-zero in:
2603      *   __get_user(fenab, &(ucp->tuc_mcontext.mc_fpregs.mcfpu_enab));
2604      */
2605     __get_user(env->fprs, &(ucp->tuc_mcontext.mc_fpregs.mcfpu_fprs));
2606     {
2607         uint32_t *src = ucp->tuc_mcontext.mc_fpregs.mcfpu_fregs.sregs;
2608         for (i = 0; i < 64; i++, src++) {
2609             if (i & 1) {
2610                 __get_user(env->fpr[i/2].l.lower, src);
2611             } else {
2612                 __get_user(env->fpr[i/2].l.upper, src);
2613             }
2614         }
2615     }
2616     __get_user(env->fsr,
2617                &(ucp->tuc_mcontext.mc_fpregs.mcfpu_fsr));
2618     __get_user(env->gsr,
2619                &(ucp->tuc_mcontext.mc_fpregs.mcfpu_gsr));
2620     unlock_user_struct(ucp, ucp_addr, 0);
2621     return;
2622  do_sigsegv:
2623     unlock_user_struct(ucp, ucp_addr, 0);
2624     force_sig(TARGET_SIGSEGV);
2625 }
2626
2627 void sparc64_get_context(CPUSPARCState *env)
2628 {
2629     abi_ulong ucp_addr;
2630     struct target_ucontext *ucp;
2631     target_mc_gregset_t *grp;
2632     target_mcontext_t *mcp;
2633     abi_ulong fp, i7, w_addr;
2634     int err;
2635     unsigned int i;
2636     target_sigset_t target_set;
2637     sigset_t set;
2638
2639     ucp_addr = env->regwptr[UREG_I0];
2640     if (!lock_user_struct(VERIFY_WRITE, ucp, ucp_addr, 0))
2641         goto do_sigsegv;
2642     
2643     mcp = &ucp->tuc_mcontext;
2644     grp = &mcp->mc_gregs;
2645
2646     /* Skip over the trap instruction, first. */
2647     env->pc = env->npc;
2648     env->npc += 4;
2649
2650     err = 0;
2651
2652     do_sigprocmask(0, NULL, &set);
2653     host_to_target_sigset_internal(&target_set, &set);
2654     if (TARGET_NSIG_WORDS == 1) {
2655         __put_user(target_set.sig[0],
2656                    (abi_ulong *)&ucp->tuc_sigmask);
2657     } else {
2658         abi_ulong *src, *dst;
2659         src = target_set.sig;
2660         dst = ucp->tuc_sigmask.sig;
2661         for (i = 0; i < TARGET_NSIG_WORDS; i++, dst++, src++) {
2662             __put_user(*src, dst);
2663         }
2664         if (err)
2665             goto do_sigsegv;
2666     }
2667
2668     /* XXX: tstate must be saved properly */
2669     //    __put_user(env->tstate, &((*grp)[MC_TSTATE]));
2670     __put_user(env->pc, &((*grp)[MC_PC]));
2671     __put_user(env->npc, &((*grp)[MC_NPC]));
2672     __put_user(env->y, &((*grp)[MC_Y]));
2673     __put_user(env->gregs[1], &((*grp)[MC_G1]));
2674     __put_user(env->gregs[2], &((*grp)[MC_G2]));
2675     __put_user(env->gregs[3], &((*grp)[MC_G3]));
2676     __put_user(env->gregs[4], &((*grp)[MC_G4]));
2677     __put_user(env->gregs[5], &((*grp)[MC_G5]));
2678     __put_user(env->gregs[6], &((*grp)[MC_G6]));
2679     __put_user(env->gregs[7], &((*grp)[MC_G7]));
2680     __put_user(env->regwptr[UREG_I0], &((*grp)[MC_O0]));
2681     __put_user(env->regwptr[UREG_I1], &((*grp)[MC_O1]));
2682     __put_user(env->regwptr[UREG_I2], &((*grp)[MC_O2]));
2683     __put_user(env->regwptr[UREG_I3], &((*grp)[MC_O3]));
2684     __put_user(env->regwptr[UREG_I4], &((*grp)[MC_O4]));
2685     __put_user(env->regwptr[UREG_I5], &((*grp)[MC_O5]));
2686     __put_user(env->regwptr[UREG_I6], &((*grp)[MC_O6]));
2687     __put_user(env->regwptr[UREG_I7], &((*grp)[MC_O7]));
2688
2689     w_addr = TARGET_STACK_BIAS+env->regwptr[UREG_I6];
2690     fp = i7 = 0;
2691     if (get_user(fp, w_addr + offsetof(struct target_reg_window, ins[6]), 
2692                  abi_ulong) != 0)
2693         goto do_sigsegv;
2694     if (get_user(i7, w_addr + offsetof(struct target_reg_window, ins[7]), 
2695                  abi_ulong) != 0)
2696         goto do_sigsegv;
2697     __put_user(fp, &(mcp->mc_fp));
2698     __put_user(i7, &(mcp->mc_i7));
2699
2700     {
2701         uint32_t *dst = ucp->tuc_mcontext.mc_fpregs.mcfpu_fregs.sregs;
2702         for (i = 0; i < 64; i++, dst++) {
2703             if (i & 1) {
2704                 __put_user(env->fpr[i/2].l.lower, dst);
2705             } else {
2706                 __put_user(env->fpr[i/2].l.upper, dst);
2707             }
2708         }
2709     }
2710     __put_user(env->fsr, &(mcp->mc_fpregs.mcfpu_fsr));
2711     __put_user(env->gsr, &(mcp->mc_fpregs.mcfpu_gsr));
2712     __put_user(env->fprs, &(mcp->mc_fpregs.mcfpu_fprs));
2713
2714     if (err)
2715         goto do_sigsegv;
2716     unlock_user_struct(ucp, ucp_addr, 1);
2717     return;
2718  do_sigsegv:
2719     unlock_user_struct(ucp, ucp_addr, 1);
2720     force_sig(TARGET_SIGSEGV);
2721 }
2722 #endif
2723 #elif defined(TARGET_MIPS) || defined(TARGET_MIPS64)
2724
2725 # if defined(TARGET_ABI_MIPSO32)
2726 struct target_sigcontext {
2727     uint32_t   sc_regmask;     /* Unused */
2728     uint32_t   sc_status;
2729     uint64_t   sc_pc;
2730     uint64_t   sc_regs[32];
2731     uint64_t   sc_fpregs[32];
2732     uint32_t   sc_ownedfp;     /* Unused */
2733     uint32_t   sc_fpc_csr;
2734     uint32_t   sc_fpc_eir;     /* Unused */
2735     uint32_t   sc_used_math;
2736     uint32_t   sc_dsp;         /* dsp status, was sc_ssflags */
2737     uint32_t   pad0;
2738     uint64_t   sc_mdhi;
2739     uint64_t   sc_mdlo;
2740     target_ulong   sc_hi1;         /* Was sc_cause */
2741     target_ulong   sc_lo1;         /* Was sc_badvaddr */
2742     target_ulong   sc_hi2;         /* Was sc_sigset[4] */
2743     target_ulong   sc_lo2;
2744     target_ulong   sc_hi3;
2745     target_ulong   sc_lo3;
2746 };
2747 # else /* N32 || N64 */
2748 struct target_sigcontext {
2749     uint64_t sc_regs[32];
2750     uint64_t sc_fpregs[32];
2751     uint64_t sc_mdhi;
2752     uint64_t sc_hi1;
2753     uint64_t sc_hi2;
2754     uint64_t sc_hi3;
2755     uint64_t sc_mdlo;
2756     uint64_t sc_lo1;
2757     uint64_t sc_lo2;
2758     uint64_t sc_lo3;
2759     uint64_t sc_pc;
2760     uint32_t sc_fpc_csr;
2761     uint32_t sc_used_math;
2762     uint32_t sc_dsp;
2763     uint32_t sc_reserved;
2764 };
2765 # endif /* O32 */
2766
2767 struct sigframe {
2768     uint32_t sf_ass[4];                 /* argument save space for o32 */
2769     uint32_t sf_code[2];                        /* signal trampoline */
2770     struct target_sigcontext sf_sc;
2771     target_sigset_t sf_mask;
2772 };
2773
2774 struct target_ucontext {
2775     target_ulong tuc_flags;
2776     target_ulong tuc_link;
2777     target_stack_t tuc_stack;
2778     target_ulong pad0;
2779     struct target_sigcontext tuc_mcontext;
2780     target_sigset_t tuc_sigmask;
2781 };
2782
2783 struct target_rt_sigframe {
2784     uint32_t rs_ass[4];               /* argument save space for o32 */
2785     uint32_t rs_code[2];              /* signal trampoline */
2786     struct target_siginfo rs_info;
2787     struct target_ucontext rs_uc;
2788 };
2789
2790 /* Install trampoline to jump back from signal handler */
2791 static inline int install_sigtramp(unsigned int *tramp,   unsigned int syscall)
2792 {
2793     int err = 0;
2794
2795     /*
2796      * Set up the return code ...
2797      *
2798      *         li      v0, __NR__foo_sigreturn
2799      *         syscall
2800      */
2801
2802     __put_user(0x24020000 + syscall, tramp + 0);
2803     __put_user(0x0000000c          , tramp + 1);
2804     return err;
2805 }
2806
2807 static inline void setup_sigcontext(CPUMIPSState *regs,
2808         struct target_sigcontext *sc)
2809 {
2810     int i;
2811
2812     __put_user(exception_resume_pc(regs), &sc->sc_pc);
2813     regs->hflags &= ~MIPS_HFLAG_BMASK;
2814
2815     __put_user(0, &sc->sc_regs[0]);
2816     for (i = 1; i < 32; ++i) {
2817         __put_user(regs->active_tc.gpr[i], &sc->sc_regs[i]);
2818     }
2819
2820     __put_user(regs->active_tc.HI[0], &sc->sc_mdhi);
2821     __put_user(regs->active_tc.LO[0], &sc->sc_mdlo);
2822
2823     /* Rather than checking for dsp existence, always copy.  The storage
2824        would just be garbage otherwise.  */
2825     __put_user(regs->active_tc.HI[1], &sc->sc_hi1);
2826     __put_user(regs->active_tc.HI[2], &sc->sc_hi2);
2827     __put_user(regs->active_tc.HI[3], &sc->sc_hi3);
2828     __put_user(regs->active_tc.LO[1], &sc->sc_lo1);
2829     __put_user(regs->active_tc.LO[2], &sc->sc_lo2);
2830     __put_user(regs->active_tc.LO[3], &sc->sc_lo3);
2831     {
2832         uint32_t dsp = cpu_rddsp(0x3ff, regs);
2833         __put_user(dsp, &sc->sc_dsp);
2834     }
2835
2836     __put_user(1, &sc->sc_used_math);
2837
2838     for (i = 0; i < 32; ++i) {
2839         __put_user(regs->active_fpu.fpr[i].d, &sc->sc_fpregs[i]);
2840     }
2841 }
2842
2843 static inline void
2844 restore_sigcontext(CPUMIPSState *regs, struct target_sigcontext *sc)
2845 {
2846     int i;
2847
2848     __get_user(regs->CP0_EPC, &sc->sc_pc);
2849
2850     __get_user(regs->active_tc.HI[0], &sc->sc_mdhi);
2851     __get_user(regs->active_tc.LO[0], &sc->sc_mdlo);
2852
2853     for (i = 1; i < 32; ++i) {
2854         __get_user(regs->active_tc.gpr[i], &sc->sc_regs[i]);
2855     }
2856
2857     __get_user(regs->active_tc.HI[1], &sc->sc_hi1);
2858     __get_user(regs->active_tc.HI[2], &sc->sc_hi2);
2859     __get_user(regs->active_tc.HI[3], &sc->sc_hi3);
2860     __get_user(regs->active_tc.LO[1], &sc->sc_lo1);
2861     __get_user(regs->active_tc.LO[2], &sc->sc_lo2);
2862     __get_user(regs->active_tc.LO[3], &sc->sc_lo3);
2863     {
2864         uint32_t dsp;
2865         __get_user(dsp, &sc->sc_dsp);
2866         cpu_wrdsp(dsp, 0x3ff, regs);
2867     }
2868
2869     for (i = 0; i < 32; ++i) {
2870         __get_user(regs->active_fpu.fpr[i].d, &sc->sc_fpregs[i]);
2871     }
2872 }
2873
2874 /*
2875  * Determine which stack to use..
2876  */
2877 static inline abi_ulong
2878 get_sigframe(struct target_sigaction *ka, CPUMIPSState *regs, size_t frame_size)
2879 {
2880     unsigned long sp;
2881
2882     /* Default to using normal stack */
2883     sp = regs->active_tc.gpr[29];
2884
2885     /*
2886      * FPU emulator may have its own trampoline active just
2887      * above the user stack, 16-bytes before the next lowest
2888      * 16 byte boundary.  Try to avoid trashing it.
2889      */
2890     sp -= 32;
2891
2892     /* This is the X/Open sanctioned signal stack switching.  */
2893     if ((ka->sa_flags & TARGET_SA_ONSTACK) && (sas_ss_flags (sp) == 0)) {
2894         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
2895     }
2896
2897     return (sp - frame_size) & ~7;
2898 }
2899
2900 static void mips_set_hflags_isa_mode_from_pc(CPUMIPSState *env)
2901 {
2902     if (env->insn_flags & (ASE_MIPS16 | ASE_MICROMIPS)) {
2903         env->hflags &= ~MIPS_HFLAG_M16;
2904         env->hflags |= (env->active_tc.PC & 1) << MIPS_HFLAG_M16_SHIFT;
2905         env->active_tc.PC &= ~(target_ulong) 1;
2906     }
2907 }
2908
2909 # if defined(TARGET_ABI_MIPSO32)
2910 /* compare linux/arch/mips/kernel/signal.c:setup_frame() */
2911 static void setup_frame(int sig, struct target_sigaction * ka,
2912                         target_sigset_t *set, CPUMIPSState *regs)
2913 {
2914     struct sigframe *frame;
2915     abi_ulong frame_addr;
2916     int i;
2917
2918     frame_addr = get_sigframe(ka, regs, sizeof(*frame));
2919     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
2920         goto give_sigsegv;
2921
2922     install_sigtramp(frame->sf_code, TARGET_NR_sigreturn);
2923
2924     setup_sigcontext(regs, &frame->sf_sc);
2925
2926     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
2927         __put_user(set->sig[i], &frame->sf_mask.sig[i]);
2928     }
2929
2930     /*
2931     * Arguments to signal handler:
2932     *
2933     *   a0 = signal number
2934     *   a1 = 0 (should be cause)
2935     *   a2 = pointer to struct sigcontext
2936     *
2937     * $25 and PC point to the signal handler, $29 points to the
2938     * struct sigframe.
2939     */
2940     regs->active_tc.gpr[ 4] = sig;
2941     regs->active_tc.gpr[ 5] = 0;
2942     regs->active_tc.gpr[ 6] = frame_addr + offsetof(struct sigframe, sf_sc);
2943     regs->active_tc.gpr[29] = frame_addr;
2944     regs->active_tc.gpr[31] = frame_addr + offsetof(struct sigframe, sf_code);
2945     /* The original kernel code sets CP0_EPC to the handler
2946     * since it returns to userland using eret
2947     * we cannot do this here, and we must set PC directly */
2948     regs->active_tc.PC = regs->active_tc.gpr[25] = ka->_sa_handler;
2949     mips_set_hflags_isa_mode_from_pc(regs);
2950     unlock_user_struct(frame, frame_addr, 1);
2951     return;
2952
2953 give_sigsegv:
2954     force_sig(TARGET_SIGSEGV/*, current*/);
2955 }
2956
2957 long do_sigreturn(CPUMIPSState *regs)
2958 {
2959     struct sigframe *frame;
2960     abi_ulong frame_addr;
2961     sigset_t blocked;
2962     target_sigset_t target_set;
2963     int i;
2964
2965 #if defined(DEBUG_SIGNAL)
2966     fprintf(stderr, "do_sigreturn\n");
2967 #endif
2968     frame_addr = regs->active_tc.gpr[29];
2969     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
2970         goto badframe;
2971
2972     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
2973         __get_user(target_set.sig[i], &frame->sf_mask.sig[i]);
2974     }
2975
2976     target_to_host_sigset_internal(&blocked, &target_set);
2977     do_sigprocmask(SIG_SETMASK, &blocked, NULL);
2978
2979     restore_sigcontext(regs, &frame->sf_sc);
2980
2981 #if 0
2982     /*
2983      * Don't let your children do this ...
2984      */
2985     __asm__ __volatile__(
2986         "move\t$29, %0\n\t"
2987         "j\tsyscall_exit"
2988         :/* no outputs */
2989         :"r" (&regs));
2990     /* Unreached */
2991 #endif
2992
2993     regs->active_tc.PC = regs->CP0_EPC;
2994     mips_set_hflags_isa_mode_from_pc(regs);
2995     /* I am not sure this is right, but it seems to work
2996     * maybe a problem with nested signals ? */
2997     regs->CP0_EPC = 0;
2998     return -TARGET_QEMU_ESIGRETURN;
2999
3000 badframe:
3001     force_sig(TARGET_SIGSEGV/*, current*/);
3002     return 0;
3003 }
3004 # endif /* O32 */
3005
3006 static void setup_rt_frame(int sig, struct target_sigaction *ka,
3007                            target_siginfo_t *info,
3008                            target_sigset_t *set, CPUMIPSState *env)
3009 {
3010     struct target_rt_sigframe *frame;
3011     abi_ulong frame_addr;
3012     int i;
3013
3014     frame_addr = get_sigframe(ka, env, sizeof(*frame));
3015     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
3016         goto give_sigsegv;
3017
3018     install_sigtramp(frame->rs_code, TARGET_NR_rt_sigreturn);
3019
3020     copy_siginfo_to_user(&frame->rs_info, info);
3021
3022     __put_user(0, &frame->rs_uc.tuc_flags);
3023     __put_user(0, &frame->rs_uc.tuc_link);
3024     __put_user(target_sigaltstack_used.ss_sp, &frame->rs_uc.tuc_stack.ss_sp);
3025     __put_user(target_sigaltstack_used.ss_size, &frame->rs_uc.tuc_stack.ss_size);
3026     __put_user(sas_ss_flags(get_sp_from_cpustate(env)),
3027                &frame->rs_uc.tuc_stack.ss_flags);
3028
3029     setup_sigcontext(env, &frame->rs_uc.tuc_mcontext);
3030
3031     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
3032         __put_user(set->sig[i], &frame->rs_uc.tuc_sigmask.sig[i]);
3033     }
3034
3035     /*
3036     * Arguments to signal handler:
3037     *
3038     *   a0 = signal number
3039     *   a1 = pointer to siginfo_t
3040     *   a2 = pointer to struct ucontext
3041     *
3042     * $25 and PC point to the signal handler, $29 points to the
3043     * struct sigframe.
3044     */
3045     env->active_tc.gpr[ 4] = sig;
3046     env->active_tc.gpr[ 5] = frame_addr
3047                              + offsetof(struct target_rt_sigframe, rs_info);
3048     env->active_tc.gpr[ 6] = frame_addr
3049                              + offsetof(struct target_rt_sigframe, rs_uc);
3050     env->active_tc.gpr[29] = frame_addr;
3051     env->active_tc.gpr[31] = frame_addr
3052                              + offsetof(struct target_rt_sigframe, rs_code);
3053     /* The original kernel code sets CP0_EPC to the handler
3054     * since it returns to userland using eret
3055     * we cannot do this here, and we must set PC directly */
3056     env->active_tc.PC = env->active_tc.gpr[25] = ka->_sa_handler;
3057     mips_set_hflags_isa_mode_from_pc(env);
3058     unlock_user_struct(frame, frame_addr, 1);
3059     return;
3060
3061 give_sigsegv:
3062     unlock_user_struct(frame, frame_addr, 1);
3063     force_sig(TARGET_SIGSEGV/*, current*/);
3064 }
3065
3066 long do_rt_sigreturn(CPUMIPSState *env)
3067 {
3068     struct target_rt_sigframe *frame;
3069     abi_ulong frame_addr;
3070     sigset_t blocked;
3071
3072 #if defined(DEBUG_SIGNAL)
3073     fprintf(stderr, "do_rt_sigreturn\n");
3074 #endif
3075     frame_addr = env->active_tc.gpr[29];
3076     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
3077         goto badframe;
3078
3079     target_to_host_sigset(&blocked, &frame->rs_uc.tuc_sigmask);
3080     do_sigprocmask(SIG_SETMASK, &blocked, NULL);
3081
3082     restore_sigcontext(env, &frame->rs_uc.tuc_mcontext);
3083
3084     if (do_sigaltstack(frame_addr +
3085                        offsetof(struct target_rt_sigframe, rs_uc.tuc_stack),
3086                        0, get_sp_from_cpustate(env)) == -EFAULT)
3087         goto badframe;
3088
3089     env->active_tc.PC = env->CP0_EPC;
3090     mips_set_hflags_isa_mode_from_pc(env);
3091     /* I am not sure this is right, but it seems to work
3092     * maybe a problem with nested signals ? */
3093     env->CP0_EPC = 0;
3094     return -TARGET_QEMU_ESIGRETURN;
3095
3096 badframe:
3097     force_sig(TARGET_SIGSEGV/*, current*/);
3098     return 0;
3099 }
3100
3101 #elif defined(TARGET_SH4)
3102
3103 /*
3104  * code and data structures from linux kernel:
3105  * include/asm-sh/sigcontext.h
3106  * arch/sh/kernel/signal.c
3107  */
3108
3109 struct target_sigcontext {
3110     target_ulong  oldmask;
3111
3112     /* CPU registers */
3113     target_ulong  sc_gregs[16];
3114     target_ulong  sc_pc;
3115     target_ulong  sc_pr;
3116     target_ulong  sc_sr;
3117     target_ulong  sc_gbr;
3118     target_ulong  sc_mach;
3119     target_ulong  sc_macl;
3120
3121     /* FPU registers */
3122     target_ulong  sc_fpregs[16];
3123     target_ulong  sc_xfpregs[16];
3124     unsigned int sc_fpscr;
3125     unsigned int sc_fpul;
3126     unsigned int sc_ownedfp;
3127 };
3128
3129 struct target_sigframe
3130 {
3131     struct target_sigcontext sc;
3132     target_ulong extramask[TARGET_NSIG_WORDS-1];
3133     uint16_t retcode[3];
3134 };
3135
3136
3137 struct target_ucontext {
3138     target_ulong tuc_flags;
3139     struct target_ucontext *tuc_link;
3140     target_stack_t tuc_stack;
3141     struct target_sigcontext tuc_mcontext;
3142     target_sigset_t tuc_sigmask;        /* mask last for extensibility */
3143 };
3144
3145 struct target_rt_sigframe
3146 {
3147     struct target_siginfo info;
3148     struct target_ucontext uc;
3149     uint16_t retcode[3];
3150 };
3151
3152
3153 #define MOVW(n)  (0x9300|((n)-2)) /* Move mem word at PC+n to R3 */
3154 #define TRAP_NOARG 0xc310         /* Syscall w/no args (NR in R3) SH3/4 */
3155
3156 static abi_ulong get_sigframe(struct target_sigaction *ka,
3157                          unsigned long sp, size_t frame_size)
3158 {
3159     if ((ka->sa_flags & TARGET_SA_ONSTACK) && (sas_ss_flags(sp) == 0)) {
3160         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
3161     }
3162
3163     return (sp - frame_size) & -8ul;
3164 }
3165
3166 static void setup_sigcontext(struct target_sigcontext *sc,
3167                             CPUSH4State *regs, unsigned long mask)
3168 {
3169     int i;
3170
3171 #define COPY(x)         __put_user(regs->x, &sc->sc_##x)
3172     COPY(gregs[0]); COPY(gregs[1]);
3173     COPY(gregs[2]); COPY(gregs[3]);
3174     COPY(gregs[4]); COPY(gregs[5]);
3175     COPY(gregs[6]); COPY(gregs[7]);
3176     COPY(gregs[8]); COPY(gregs[9]);
3177     COPY(gregs[10]); COPY(gregs[11]);
3178     COPY(gregs[12]); COPY(gregs[13]);
3179     COPY(gregs[14]); COPY(gregs[15]);
3180     COPY(gbr); COPY(mach);
3181     COPY(macl); COPY(pr);
3182     COPY(sr); COPY(pc);
3183 #undef COPY
3184
3185     for (i=0; i<16; i++) {
3186         __put_user(regs->fregs[i], &sc->sc_fpregs[i]);
3187     }
3188     __put_user(regs->fpscr, &sc->sc_fpscr);
3189     __put_user(regs->fpul, &sc->sc_fpul);
3190
3191     /* non-iBCS2 extensions.. */
3192     __put_user(mask, &sc->oldmask);
3193 }
3194
3195 static void restore_sigcontext(CPUSH4State *regs, struct target_sigcontext *sc,
3196                               target_ulong *r0_p)
3197 {
3198     int i;
3199
3200 #define COPY(x)         __get_user(regs->x, &sc->sc_##x)
3201     COPY(gregs[1]);
3202     COPY(gregs[2]); COPY(gregs[3]);
3203     COPY(gregs[4]); COPY(gregs[5]);
3204     COPY(gregs[6]); COPY(gregs[7]);
3205     COPY(gregs[8]); COPY(gregs[9]);
3206     COPY(gregs[10]); COPY(gregs[11]);
3207     COPY(gregs[12]); COPY(gregs[13]);
3208     COPY(gregs[14]); COPY(gregs[15]);
3209     COPY(gbr); COPY(mach);
3210     COPY(macl); COPY(pr);
3211     COPY(sr); COPY(pc);
3212 #undef COPY
3213
3214     for (i=0; i<16; i++) {
3215         __get_user(regs->fregs[i], &sc->sc_fpregs[i]);
3216     }
3217     __get_user(regs->fpscr, &sc->sc_fpscr);
3218     __get_user(regs->fpul, &sc->sc_fpul);
3219
3220     regs->tra = -1;         /* disable syscall checks */
3221     __get_user(*r0_p, &sc->sc_gregs[0]);
3222 }
3223
3224 static void setup_frame(int sig, struct target_sigaction *ka,
3225                         target_sigset_t *set, CPUSH4State *regs)
3226 {
3227     struct target_sigframe *frame;
3228     abi_ulong frame_addr;
3229     int i;
3230     int err = 0;
3231     int signal;
3232
3233     frame_addr = get_sigframe(ka, regs->gregs[15], sizeof(*frame));
3234     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
3235         goto give_sigsegv;
3236
3237     signal = current_exec_domain_sig(sig);
3238
3239     setup_sigcontext(&frame->sc, regs, set->sig[0]);
3240
3241     for (i = 0; i < TARGET_NSIG_WORDS - 1; i++) {
3242         __put_user(set->sig[i + 1], &frame->extramask[i]);
3243     }
3244
3245     /* Set up to return from userspace.  If provided, use a stub
3246        already in userspace.  */
3247     if (ka->sa_flags & TARGET_SA_RESTORER) {
3248         regs->pr = (unsigned long) ka->sa_restorer;
3249     } else {
3250         /* Generate return code (system call to sigreturn) */
3251         __put_user(MOVW(2), &frame->retcode[0]);
3252         __put_user(TRAP_NOARG, &frame->retcode[1]);
3253         __put_user((TARGET_NR_sigreturn), &frame->retcode[2]);
3254         regs->pr = (unsigned long) frame->retcode;
3255     }
3256
3257     if (err)
3258         goto give_sigsegv;
3259
3260     /* Set up registers for signal handler */
3261     regs->gregs[15] = frame_addr;
3262     regs->gregs[4] = signal; /* Arg for signal handler */
3263     regs->gregs[5] = 0;
3264     regs->gregs[6] = frame_addr += offsetof(typeof(*frame), sc);
3265     regs->pc = (unsigned long) ka->_sa_handler;
3266
3267     unlock_user_struct(frame, frame_addr, 1);
3268     return;
3269
3270 give_sigsegv:
3271     unlock_user_struct(frame, frame_addr, 1);
3272     force_sig(TARGET_SIGSEGV);
3273 }
3274
3275 static void setup_rt_frame(int sig, struct target_sigaction *ka,
3276                            target_siginfo_t *info,
3277                            target_sigset_t *set, CPUSH4State *regs)
3278 {
3279     struct target_rt_sigframe *frame;
3280     abi_ulong frame_addr;
3281     int i;
3282     int err = 0;
3283     int signal;
3284
3285     frame_addr = get_sigframe(ka, regs->gregs[15], sizeof(*frame));
3286     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
3287         goto give_sigsegv;
3288
3289     signal = current_exec_domain_sig(sig);
3290
3291     copy_siginfo_to_user(&frame->info, info);
3292
3293     /* Create the ucontext.  */
3294     __put_user(0, &frame->uc.tuc_flags);
3295     __put_user(0, (unsigned long *)&frame->uc.tuc_link);
3296     __put_user((unsigned long)target_sigaltstack_used.ss_sp,
3297                &frame->uc.tuc_stack.ss_sp);
3298     __put_user(sas_ss_flags(regs->gregs[15]),
3299                &frame->uc.tuc_stack.ss_flags);
3300     __put_user(target_sigaltstack_used.ss_size,
3301                &frame->uc.tuc_stack.ss_size);
3302     setup_sigcontext(&frame->uc.tuc_mcontext,
3303                             regs, set->sig[0]);
3304     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
3305         __put_user(set->sig[i], &frame->uc.tuc_sigmask.sig[i]);
3306     }
3307
3308     /* Set up to return from userspace.  If provided, use a stub
3309        already in userspace.  */
3310     if (ka->sa_flags & TARGET_SA_RESTORER) {
3311         regs->pr = (unsigned long) ka->sa_restorer;
3312     } else {
3313         /* Generate return code (system call to sigreturn) */
3314         __put_user(MOVW(2), &frame->retcode[0]);
3315         __put_user(TRAP_NOARG, &frame->retcode[1]);
3316         __put_user((TARGET_NR_rt_sigreturn), &frame->retcode[2]);
3317         regs->pr = (unsigned long) frame->retcode;
3318     }
3319
3320     if (err)
3321         goto give_sigsegv;
3322
3323     /* Set up registers for signal handler */
3324     regs->gregs[15] = frame_addr;
3325     regs->gregs[4] = signal; /* Arg for signal handler */
3326     regs->gregs[5] = frame_addr + offsetof(typeof(*frame), info);
3327     regs->gregs[6] = frame_addr + offsetof(typeof(*frame), uc);
3328     regs->pc = (unsigned long) ka->_sa_handler;
3329
3330     unlock_user_struct(frame, frame_addr, 1);
3331     return;
3332
3333 give_sigsegv:
3334     unlock_user_struct(frame, frame_addr, 1);
3335     force_sig(TARGET_SIGSEGV);
3336 }
3337
3338 long do_sigreturn(CPUSH4State *regs)
3339 {
3340     struct target_sigframe *frame;
3341     abi_ulong frame_addr;
3342     sigset_t blocked;
3343     target_sigset_t target_set;
3344     target_ulong r0;
3345     int i;
3346     int err = 0;
3347
3348 #if defined(DEBUG_SIGNAL)
3349     fprintf(stderr, "do_sigreturn\n");
3350 #endif
3351     frame_addr = regs->gregs[15];
3352     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
3353         goto badframe;
3354
3355     __get_user(target_set.sig[0], &frame->sc.oldmask);
3356     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
3357         __get_user(target_set.sig[i], &frame->extramask[i - 1]);
3358     }
3359
3360     if (err)
3361         goto badframe;
3362
3363     target_to_host_sigset_internal(&blocked, &target_set);
3364     do_sigprocmask(SIG_SETMASK, &blocked, NULL);
3365
3366     restore_sigcontext(regs, &frame->sc, &r0);
3367
3368     unlock_user_struct(frame, frame_addr, 0);
3369     return r0;
3370
3371 badframe:
3372     unlock_user_struct(frame, frame_addr, 0);
3373     force_sig(TARGET_SIGSEGV);
3374     return 0;
3375 }
3376
3377 long do_rt_sigreturn(CPUSH4State *regs)
3378 {
3379     struct target_rt_sigframe *frame;
3380     abi_ulong frame_addr;
3381     sigset_t blocked;
3382     target_ulong r0;
3383
3384 #if defined(DEBUG_SIGNAL)
3385     fprintf(stderr, "do_rt_sigreturn\n");
3386 #endif
3387     frame_addr = regs->gregs[15];
3388     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
3389         goto badframe;
3390
3391     target_to_host_sigset(&blocked, &frame->uc.tuc_sigmask);
3392     do_sigprocmask(SIG_SETMASK, &blocked, NULL);
3393
3394     restore_sigcontext(regs, &frame->uc.tuc_mcontext, &r0);
3395
3396     if (do_sigaltstack(frame_addr +
3397                        offsetof(struct target_rt_sigframe, uc.tuc_stack),
3398                        0, get_sp_from_cpustate(regs)) == -EFAULT)
3399         goto badframe;
3400
3401     unlock_user_struct(frame, frame_addr, 0);
3402     return r0;
3403
3404 badframe:
3405     unlock_user_struct(frame, frame_addr, 0);
3406     force_sig(TARGET_SIGSEGV);
3407     return 0;
3408 }
3409 #elif defined(TARGET_MICROBLAZE)
3410
3411 struct target_sigcontext {
3412     struct target_pt_regs regs;  /* needs to be first */
3413     uint32_t oldmask;
3414 };
3415
3416 struct target_stack_t {
3417     abi_ulong ss_sp;
3418     int ss_flags;
3419     unsigned int ss_size;
3420 };
3421
3422 struct target_ucontext {
3423     abi_ulong tuc_flags;
3424     abi_ulong tuc_link;
3425     struct target_stack_t tuc_stack;
3426     struct target_sigcontext tuc_mcontext;
3427     uint32_t tuc_extramask[TARGET_NSIG_WORDS - 1];
3428 };
3429
3430 /* Signal frames. */
3431 struct target_signal_frame {
3432     struct target_ucontext uc;
3433     uint32_t extramask[TARGET_NSIG_WORDS - 1];
3434     uint32_t tramp[2];
3435 };
3436
3437 struct rt_signal_frame {
3438     siginfo_t info;
3439     struct ucontext uc;
3440     uint32_t tramp[2];
3441 };
3442
3443 static void setup_sigcontext(struct target_sigcontext *sc, CPUMBState *env)
3444 {
3445     __put_user(env->regs[0], &sc->regs.r0);
3446     __put_user(env->regs[1], &sc->regs.r1);
3447     __put_user(env->regs[2], &sc->regs.r2);
3448     __put_user(env->regs[3], &sc->regs.r3);
3449     __put_user(env->regs[4], &sc->regs.r4);
3450     __put_user(env->regs[5], &sc->regs.r5);
3451     __put_user(env->regs[6], &sc->regs.r6);
3452     __put_user(env->regs[7], &sc->regs.r7);
3453     __put_user(env->regs[8], &sc->regs.r8);
3454     __put_user(env->regs[9], &sc->regs.r9);
3455     __put_user(env->regs[10], &sc->regs.r10);
3456     __put_user(env->regs[11], &sc->regs.r11);
3457     __put_user(env->regs[12], &sc->regs.r12);
3458     __put_user(env->regs[13], &sc->regs.r13);
3459     __put_user(env->regs[14], &sc->regs.r14);
3460     __put_user(env->regs[15], &sc->regs.r15);
3461     __put_user(env->regs[16], &sc->regs.r16);
3462     __put_user(env->regs[17], &sc->regs.r17);
3463     __put_user(env->regs[18], &sc->regs.r18);
3464     __put_user(env->regs[19], &sc->regs.r19);
3465     __put_user(env->regs[20], &sc->regs.r20);
3466     __put_user(env->regs[21], &sc->regs.r21);
3467     __put_user(env->regs[22], &sc->regs.r22);
3468     __put_user(env->regs[23], &sc->regs.r23);
3469     __put_user(env->regs[24], &sc->regs.r24);
3470     __put_user(env->regs[25], &sc->regs.r25);
3471     __put_user(env->regs[26], &sc->regs.r26);
3472     __put_user(env->regs[27], &sc->regs.r27);
3473     __put_user(env->regs[28], &sc->regs.r28);
3474     __put_user(env->regs[29], &sc->regs.r29);
3475     __put_user(env->regs[30], &sc->regs.r30);
3476     __put_user(env->regs[31], &sc->regs.r31);
3477     __put_user(env->sregs[SR_PC], &sc->regs.pc);
3478 }
3479
3480 static void restore_sigcontext(struct target_sigcontext *sc, CPUMBState *env)
3481 {
3482     __get_user(env->regs[0], &sc->regs.r0);
3483     __get_user(env->regs[1], &sc->regs.r1);
3484     __get_user(env->regs[2], &sc->regs.r2);
3485     __get_user(env->regs[3], &sc->regs.r3);
3486     __get_user(env->regs[4], &sc->regs.r4);
3487     __get_user(env->regs[5], &sc->regs.r5);
3488     __get_user(env->regs[6], &sc->regs.r6);
3489     __get_user(env->regs[7], &sc->regs.r7);
3490     __get_user(env->regs[8], &sc->regs.r8);
3491     __get_user(env->regs[9], &sc->regs.r9);
3492     __get_user(env->regs[10], &sc->regs.r10);
3493     __get_user(env->regs[11], &sc->regs.r11);
3494     __get_user(env->regs[12], &sc->regs.r12);
3495     __get_user(env->regs[13], &sc->regs.r13);
3496     __get_user(env->regs[14], &sc->regs.r14);
3497     __get_user(env->regs[15], &sc->regs.r15);
3498     __get_user(env->regs[16], &sc->regs.r16);
3499     __get_user(env->regs[17], &sc->regs.r17);
3500     __get_user(env->regs[18], &sc->regs.r18);
3501     __get_user(env->regs[19], &sc->regs.r19);
3502     __get_user(env->regs[20], &sc->regs.r20);
3503     __get_user(env->regs[21], &sc->regs.r21);
3504     __get_user(env->regs[22], &sc->regs.r22);
3505     __get_user(env->regs[23], &sc->regs.r23);
3506     __get_user(env->regs[24], &sc->regs.r24);
3507     __get_user(env->regs[25], &sc->regs.r25);
3508     __get_user(env->regs[26], &sc->regs.r26);
3509     __get_user(env->regs[27], &sc->regs.r27);
3510     __get_user(env->regs[28], &sc->regs.r28);
3511     __get_user(env->regs[29], &sc->regs.r29);
3512     __get_user(env->regs[30], &sc->regs.r30);
3513     __get_user(env->regs[31], &sc->regs.r31);
3514     __get_user(env->sregs[SR_PC], &sc->regs.pc);
3515 }
3516
3517 static abi_ulong get_sigframe(struct target_sigaction *ka,
3518                               CPUMBState *env, int frame_size)
3519 {
3520     abi_ulong sp = env->regs[1];
3521
3522     if ((ka->sa_flags & TARGET_SA_ONSTACK) != 0 && !on_sig_stack(sp)) {
3523         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
3524     }
3525
3526     return ((sp - frame_size) & -8UL);
3527 }
3528
3529 static void setup_frame(int sig, struct target_sigaction *ka,
3530                         target_sigset_t *set, CPUMBState *env)
3531 {
3532     struct target_signal_frame *frame;
3533     abi_ulong frame_addr;
3534     int i;
3535
3536     frame_addr = get_sigframe(ka, env, sizeof *frame);
3537     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
3538         goto badframe;
3539
3540     /* Save the mask.  */
3541     __put_user(set->sig[0], &frame->uc.tuc_mcontext.oldmask);
3542
3543     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
3544         __put_user(set->sig[i], &frame->extramask[i - 1]);
3545     }
3546
3547     setup_sigcontext(&frame->uc.tuc_mcontext, env);
3548
3549     /* Set up to return from userspace. If provided, use a stub
3550        already in userspace. */
3551     /* minus 8 is offset to cater for "rtsd r15,8" offset */
3552     if (ka->sa_flags & TARGET_SA_RESTORER) {
3553         env->regs[15] = ((unsigned long)ka->sa_restorer)-8;
3554     } else {
3555         uint32_t t;
3556         /* Note, these encodings are _big endian_! */
3557         /* addi r12, r0, __NR_sigreturn */
3558         t = 0x31800000UL | TARGET_NR_sigreturn;
3559         __put_user(t, frame->tramp + 0);
3560         /* brki r14, 0x8 */
3561         t = 0xb9cc0008UL;
3562         __put_user(t, frame->tramp + 1);
3563
3564         /* Return from sighandler will jump to the tramp.
3565            Negative 8 offset because return is rtsd r15, 8 */
3566         env->regs[15] = ((unsigned long)frame->tramp) - 8;
3567     }
3568
3569     /* Set up registers for signal handler */
3570     env->regs[1] = frame_addr;
3571     /* Signal handler args: */
3572     env->regs[5] = sig; /* Arg 0: signum */
3573     env->regs[6] = 0;
3574     /* arg 1: sigcontext */
3575     env->regs[7] = frame_addr += offsetof(typeof(*frame), uc);
3576
3577     /* Offset of 4 to handle microblaze rtid r14, 0 */
3578     env->sregs[SR_PC] = (unsigned long)ka->_sa_handler;
3579
3580     unlock_user_struct(frame, frame_addr, 1);
3581     return;
3582   badframe:
3583     force_sig(TARGET_SIGSEGV);
3584 }
3585
3586 static void setup_rt_frame(int sig, struct target_sigaction *ka,
3587                            target_siginfo_t *info,
3588                            target_sigset_t *set, CPUMBState *env)
3589 {
3590     fprintf(stderr, "Microblaze setup_rt_frame: not implemented\n");
3591 }
3592
3593 long do_sigreturn(CPUMBState *env)
3594 {
3595     struct target_signal_frame *frame;
3596     abi_ulong frame_addr;
3597     target_sigset_t target_set;
3598     sigset_t set;
3599     int i;
3600
3601     frame_addr = env->regs[R_SP];
3602     /* Make sure the guest isn't playing games.  */
3603     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 1))
3604         goto badframe;
3605
3606     /* Restore blocked signals */
3607     __get_user(target_set.sig[0], &frame->uc.tuc_mcontext.oldmask);
3608     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
3609        __get_user(target_set.sig[i], &frame->extramask[i - 1]);
3610     }
3611     target_to_host_sigset_internal(&set, &target_set);
3612     do_sigprocmask(SIG_SETMASK, &set, NULL);
3613
3614     restore_sigcontext(&frame->uc.tuc_mcontext, env);
3615     /* We got here through a sigreturn syscall, our path back is via an
3616        rtb insn so setup r14 for that.  */
3617     env->regs[14] = env->sregs[SR_PC];
3618  
3619     unlock_user_struct(frame, frame_addr, 0);
3620     return env->regs[10];
3621   badframe:
3622     force_sig(TARGET_SIGSEGV);
3623 }
3624
3625 long do_rt_sigreturn(CPUMBState *env)
3626 {
3627     fprintf(stderr, "Microblaze do_rt_sigreturn: not implemented\n");
3628     return -TARGET_ENOSYS;
3629 }
3630
3631 #elif defined(TARGET_CRIS)
3632
3633 struct target_sigcontext {
3634         struct target_pt_regs regs;  /* needs to be first */
3635         uint32_t oldmask;
3636         uint32_t usp;    /* usp before stacking this gunk on it */
3637 };
3638
3639 /* Signal frames. */
3640 struct target_signal_frame {
3641         struct target_sigcontext sc;
3642         uint32_t extramask[TARGET_NSIG_WORDS - 1];
3643         uint16_t retcode[4];      /* Trampoline code. */
3644 };
3645
3646 struct rt_signal_frame {
3647         siginfo_t *pinfo;
3648         void *puc;
3649         siginfo_t info;
3650         struct ucontext uc;
3651         uint16_t retcode[4];      /* Trampoline code. */
3652 };
3653
3654 static void setup_sigcontext(struct target_sigcontext *sc, CPUCRISState *env)
3655 {
3656         __put_user(env->regs[0], &sc->regs.r0);
3657         __put_user(env->regs[1], &sc->regs.r1);
3658         __put_user(env->regs[2], &sc->regs.r2);
3659         __put_user(env->regs[3], &sc->regs.r3);
3660         __put_user(env->regs[4], &sc->regs.r4);
3661         __put_user(env->regs[5], &sc->regs.r5);
3662         __put_user(env->regs[6], &sc->regs.r6);
3663         __put_user(env->regs[7], &sc->regs.r7);
3664         __put_user(env->regs[8], &sc->regs.r8);
3665         __put_user(env->regs[9], &sc->regs.r9);
3666         __put_user(env->regs[10], &sc->regs.r10);
3667         __put_user(env->regs[11], &sc->regs.r11);
3668         __put_user(env->regs[12], &sc->regs.r12);
3669         __put_user(env->regs[13], &sc->regs.r13);
3670         __put_user(env->regs[14], &sc->usp);
3671         __put_user(env->regs[15], &sc->regs.acr);
3672         __put_user(env->pregs[PR_MOF], &sc->regs.mof);
3673         __put_user(env->pregs[PR_SRP], &sc->regs.srp);
3674         __put_user(env->pc, &sc->regs.erp);
3675 }
3676
3677 static void restore_sigcontext(struct target_sigcontext *sc, CPUCRISState *env)
3678 {
3679         __get_user(env->regs[0], &sc->regs.r0);
3680         __get_user(env->regs[1], &sc->regs.r1);
3681         __get_user(env->regs[2], &sc->regs.r2);
3682         __get_user(env->regs[3], &sc->regs.r3);
3683         __get_user(env->regs[4], &sc->regs.r4);
3684         __get_user(env->regs[5], &sc->regs.r5);
3685         __get_user(env->regs[6], &sc->regs.r6);
3686         __get_user(env->regs[7], &sc->regs.r7);
3687         __get_user(env->regs[8], &sc->regs.r8);
3688         __get_user(env->regs[9], &sc->regs.r9);
3689         __get_user(env->regs[10], &sc->regs.r10);
3690         __get_user(env->regs[11], &sc->regs.r11);
3691         __get_user(env->regs[12], &sc->regs.r12);
3692         __get_user(env->regs[13], &sc->regs.r13);
3693         __get_user(env->regs[14], &sc->usp);
3694         __get_user(env->regs[15], &sc->regs.acr);
3695         __get_user(env->pregs[PR_MOF], &sc->regs.mof);
3696         __get_user(env->pregs[PR_SRP], &sc->regs.srp);
3697         __get_user(env->pc, &sc->regs.erp);
3698 }
3699
3700 static abi_ulong get_sigframe(CPUCRISState *env, int framesize)
3701 {
3702         abi_ulong sp;
3703         /* Align the stack downwards to 4.  */
3704         sp = (env->regs[R_SP] & ~3);
3705         return sp - framesize;
3706 }
3707
3708 static void setup_frame(int sig, struct target_sigaction *ka,
3709                         target_sigset_t *set, CPUCRISState *env)
3710 {
3711         struct target_signal_frame *frame;
3712         abi_ulong frame_addr;
3713         int i;
3714
3715         frame_addr = get_sigframe(env, sizeof *frame);
3716         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
3717                 goto badframe;
3718
3719         /*
3720          * The CRIS signal return trampoline. A real linux/CRIS kernel doesn't
3721          * use this trampoline anymore but it sets it up for GDB.
3722          * In QEMU, using the trampoline simplifies things a bit so we use it.
3723          *
3724          * This is movu.w __NR_sigreturn, r9; break 13;
3725          */
3726     __put_user(0x9c5f, frame->retcode+0);
3727     __put_user(TARGET_NR_sigreturn,
3728                frame->retcode + 1);
3729     __put_user(0xe93d, frame->retcode + 2);
3730
3731         /* Save the mask.  */
3732     __put_user(set->sig[0], &frame->sc.oldmask);
3733
3734     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
3735         __put_user(set->sig[i], &frame->extramask[i - 1]);
3736     }
3737
3738         setup_sigcontext(&frame->sc, env);
3739
3740         /* Move the stack and setup the arguments for the handler.  */
3741         env->regs[R_SP] = frame_addr;
3742         env->regs[10] = sig;
3743         env->pc = (unsigned long) ka->_sa_handler;
3744         /* Link SRP so the guest returns through the trampoline.  */
3745         env->pregs[PR_SRP] = frame_addr + offsetof(typeof(*frame), retcode);
3746
3747         unlock_user_struct(frame, frame_addr, 1);
3748         return;
3749   badframe:
3750         force_sig(TARGET_SIGSEGV);
3751 }
3752
3753 static void setup_rt_frame(int sig, struct target_sigaction *ka,
3754                            target_siginfo_t *info,
3755                            target_sigset_t *set, CPUCRISState *env)
3756 {
3757     fprintf(stderr, "CRIS setup_rt_frame: not implemented\n");
3758 }
3759
3760 long do_sigreturn(CPUCRISState *env)
3761 {
3762         struct target_signal_frame *frame;
3763         abi_ulong frame_addr;
3764         target_sigset_t target_set;
3765         sigset_t set;
3766         int i;
3767
3768         frame_addr = env->regs[R_SP];
3769         /* Make sure the guest isn't playing games.  */
3770         if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 1))
3771                 goto badframe;
3772
3773         /* Restore blocked signals */
3774     __get_user(target_set.sig[0], &frame->sc.oldmask);
3775         for(i = 1; i < TARGET_NSIG_WORDS; i++) {
3776         __get_user(target_set.sig[i], &frame->extramask[i - 1]);
3777         }
3778         target_to_host_sigset_internal(&set, &target_set);
3779         do_sigprocmask(SIG_SETMASK, &set, NULL);
3780
3781         restore_sigcontext(&frame->sc, env);
3782         unlock_user_struct(frame, frame_addr, 0);
3783         return env->regs[10];
3784   badframe:
3785         force_sig(TARGET_SIGSEGV);
3786 }
3787
3788 long do_rt_sigreturn(CPUCRISState *env)
3789 {
3790     fprintf(stderr, "CRIS do_rt_sigreturn: not implemented\n");
3791     return -TARGET_ENOSYS;
3792 }
3793
3794 #elif defined(TARGET_OPENRISC)
3795
3796 struct target_sigcontext {
3797     struct target_pt_regs regs;
3798     abi_ulong oldmask;
3799     abi_ulong usp;
3800 };
3801
3802 struct target_ucontext {
3803     abi_ulong tuc_flags;
3804     abi_ulong tuc_link;
3805     target_stack_t tuc_stack;
3806     struct target_sigcontext tuc_mcontext;
3807     target_sigset_t tuc_sigmask;   /* mask last for extensibility */
3808 };
3809
3810 struct target_rt_sigframe {
3811     abi_ulong pinfo;
3812     uint64_t puc;
3813     struct target_siginfo info;
3814     struct target_sigcontext sc;
3815     struct target_ucontext uc;
3816     unsigned char retcode[16];  /* trampoline code */
3817 };
3818
3819 /* This is the asm-generic/ucontext.h version */
3820 #if 0
3821 static int restore_sigcontext(CPUOpenRISCState *regs,
3822                               struct target_sigcontext *sc)
3823 {
3824     unsigned int err = 0;
3825     unsigned long old_usp;
3826
3827     /* Alwys make any pending restarted system call return -EINTR */
3828     current_thread_info()->restart_block.fn = do_no_restart_syscall;
3829
3830     /* restore the regs from &sc->regs (same as sc, since regs is first)
3831      * (sc is already checked for VERIFY_READ since the sigframe was
3832      *  checked in sys_sigreturn previously)
3833      */
3834
3835     if (copy_from_user(regs, &sc, sizeof(struct target_pt_regs))) {
3836         goto badframe;
3837     }
3838
3839     /* make sure the U-flag is set so user-mode cannot fool us */
3840
3841     regs->sr &= ~SR_SM;
3842
3843     /* restore the old USP as it was before we stacked the sc etc.
3844      * (we cannot just pop the sigcontext since we aligned the sp and
3845      *  stuff after pushing it)
3846      */
3847
3848     __get_user(old_usp, &sc->usp);
3849     phx_signal("old_usp 0x%lx", old_usp);
3850
3851     __PHX__ REALLY           /* ??? */
3852     wrusp(old_usp);
3853     regs->gpr[1] = old_usp;
3854
3855     /* TODO: the other ports use regs->orig_XX to disable syscall checks
3856      * after this completes, but we don't use that mechanism. maybe we can
3857      * use it now ?
3858      */
3859
3860     return err;
3861
3862 badframe:
3863     return 1;
3864 }
3865 #endif
3866
3867 /* Set up a signal frame.  */
3868
3869 static void setup_sigcontext(struct target_sigcontext *sc,
3870                             CPUOpenRISCState *regs,
3871                             unsigned long mask)
3872 {
3873     unsigned long usp = regs->gpr[1];
3874
3875     /* copy the regs. they are first in sc so we can use sc directly */
3876
3877     /*copy_to_user(&sc, regs, sizeof(struct target_pt_regs));*/
3878
3879     /* Set the frametype to CRIS_FRAME_NORMAL for the execution of
3880        the signal handler. The frametype will be restored to its previous
3881        value in restore_sigcontext. */
3882     /*regs->frametype = CRIS_FRAME_NORMAL;*/
3883
3884     /* then some other stuff */
3885     __put_user(mask, &sc->oldmask);
3886     __put_user(usp, &sc->usp);
3887 }
3888
3889 static inline unsigned long align_sigframe(unsigned long sp)
3890 {
3891     unsigned long i;
3892     i = sp & ~3UL;
3893     return i;
3894 }
3895
3896 static inline abi_ulong get_sigframe(struct target_sigaction *ka,
3897                                      CPUOpenRISCState *regs,
3898                                      size_t frame_size)
3899 {
3900     unsigned long sp = regs->gpr[1];
3901     int onsigstack = on_sig_stack(sp);
3902
3903     /* redzone */
3904     /* This is the X/Open sanctioned signal stack switching.  */
3905     if ((ka->sa_flags & TARGET_SA_ONSTACK) != 0 && !onsigstack) {
3906         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
3907     }
3908
3909     sp = align_sigframe(sp - frame_size);
3910
3911     /*
3912      * If we are on the alternate signal stack and would overflow it, don't.
3913      * Return an always-bogus address instead so we will die with SIGSEGV.
3914      */
3915
3916     if (onsigstack && !likely(on_sig_stack(sp))) {
3917         return -1L;
3918     }
3919
3920     return sp;
3921 }
3922
3923 static void setup_frame(int sig, struct target_sigaction *ka,
3924                         target_sigset_t *set, CPUOpenRISCState *env)
3925 {
3926     qemu_log("Not implement.\n");
3927 }
3928
3929 static void setup_rt_frame(int sig, struct target_sigaction *ka,
3930                            target_siginfo_t *info,
3931                            target_sigset_t *set, CPUOpenRISCState *env)
3932 {
3933     int err = 0;
3934     abi_ulong frame_addr;
3935     unsigned long return_ip;
3936     struct target_rt_sigframe *frame;
3937     abi_ulong info_addr, uc_addr;
3938
3939     frame_addr = get_sigframe(ka, env, sizeof(*frame));
3940     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0)) {
3941         goto give_sigsegv;
3942     }
3943
3944     info_addr = frame_addr + offsetof(struct target_rt_sigframe, info);
3945     __put_user(info_addr, &frame->pinfo);
3946     uc_addr = frame_addr + offsetof(struct target_rt_sigframe, uc);
3947     __put_user(uc_addr, &frame->puc);
3948
3949     if (ka->sa_flags & SA_SIGINFO) {
3950         copy_siginfo_to_user(&frame->info, info);
3951     }
3952
3953     /*err |= __clear_user(&frame->uc, offsetof(struct ucontext, uc_mcontext));*/
3954     __put_user(0, &frame->uc.tuc_flags);
3955     __put_user(0, &frame->uc.tuc_link);
3956     __put_user(target_sigaltstack_used.ss_sp,
3957                &frame->uc.tuc_stack.ss_sp);
3958     __put_user(sas_ss_flags(env->gpr[1]), &frame->uc.tuc_stack.ss_flags);
3959     __put_user(target_sigaltstack_used.ss_size,
3960                &frame->uc.tuc_stack.ss_size);
3961     setup_sigcontext(&frame->sc, env, set->sig[0]);
3962
3963     /*err |= copy_to_user(frame->uc.tuc_sigmask, set, sizeof(*set));*/
3964
3965     /* trampoline - the desired return ip is the retcode itself */
3966     return_ip = (unsigned long)&frame->retcode;
3967     /* This is l.ori r11,r0,__NR_sigreturn, l.sys 1 */
3968     __put_user(0xa960, (short *)(frame->retcode + 0));
3969     __put_user(TARGET_NR_rt_sigreturn, (short *)(frame->retcode + 2));
3970     __put_user(0x20000001, (unsigned long *)(frame->retcode + 4));
3971     __put_user(0x15000000, (unsigned long *)(frame->retcode + 8));
3972
3973     if (err) {
3974         goto give_sigsegv;
3975     }
3976
3977     /* TODO what is the current->exec_domain stuff and invmap ? */
3978
3979     /* Set up registers for signal handler */
3980     env->pc = (unsigned long)ka->_sa_handler; /* what we enter NOW */
3981     env->gpr[9] = (unsigned long)return_ip;     /* what we enter LATER */
3982     env->gpr[3] = (unsigned long)sig;           /* arg 1: signo */
3983     env->gpr[4] = (unsigned long)&frame->info;  /* arg 2: (siginfo_t*) */
3984     env->gpr[5] = (unsigned long)&frame->uc;    /* arg 3: ucontext */
3985
3986     /* actually move the usp to reflect the stacked frame */
3987     env->gpr[1] = (unsigned long)frame;
3988
3989     return;
3990
3991 give_sigsegv:
3992     unlock_user_struct(frame, frame_addr, 1);
3993     if (sig == TARGET_SIGSEGV) {
3994         ka->_sa_handler = TARGET_SIG_DFL;
3995     }
3996     force_sig(TARGET_SIGSEGV);
3997 }
3998
3999 long do_sigreturn(CPUOpenRISCState *env)
4000 {
4001
4002     qemu_log("do_sigreturn: not implemented\n");
4003     return -TARGET_ENOSYS;
4004 }
4005
4006 long do_rt_sigreturn(CPUOpenRISCState *env)
4007 {
4008     qemu_log("do_rt_sigreturn: not implemented\n");
4009     return -TARGET_ENOSYS;
4010 }
4011 /* TARGET_OPENRISC */
4012
4013 #elif defined(TARGET_S390X)
4014
4015 #define __NUM_GPRS 16
4016 #define __NUM_FPRS 16
4017 #define __NUM_ACRS 16
4018
4019 #define S390_SYSCALL_SIZE   2
4020 #define __SIGNAL_FRAMESIZE      160 /* FIXME: 31-bit mode -> 96 */
4021
4022 #define _SIGCONTEXT_NSIG        64
4023 #define _SIGCONTEXT_NSIG_BPW    64 /* FIXME: 31-bit mode -> 32 */
4024 #define _SIGCONTEXT_NSIG_WORDS  (_SIGCONTEXT_NSIG / _SIGCONTEXT_NSIG_BPW)
4025 #define _SIGMASK_COPY_SIZE    (sizeof(unsigned long)*_SIGCONTEXT_NSIG_WORDS)
4026 #define PSW_ADDR_AMODE            0x0000000000000000UL /* 0x80000000UL for 31-bit */
4027 #define S390_SYSCALL_OPCODE ((uint16_t)0x0a00)
4028
4029 typedef struct {
4030     target_psw_t psw;
4031     target_ulong gprs[__NUM_GPRS];
4032     unsigned int acrs[__NUM_ACRS];
4033 } target_s390_regs_common;
4034
4035 typedef struct {
4036     unsigned int fpc;
4037     double   fprs[__NUM_FPRS];
4038 } target_s390_fp_regs;
4039
4040 typedef struct {
4041     target_s390_regs_common regs;
4042     target_s390_fp_regs     fpregs;
4043 } target_sigregs;
4044
4045 struct target_sigcontext {
4046     target_ulong   oldmask[_SIGCONTEXT_NSIG_WORDS];
4047     target_sigregs *sregs;
4048 };
4049
4050 typedef struct {
4051     uint8_t callee_used_stack[__SIGNAL_FRAMESIZE];
4052     struct target_sigcontext sc;
4053     target_sigregs sregs;
4054     int signo;
4055     uint8_t retcode[S390_SYSCALL_SIZE];
4056 } sigframe;
4057
4058 struct target_ucontext {
4059     target_ulong tuc_flags;
4060     struct target_ucontext *tuc_link;
4061     target_stack_t tuc_stack;
4062     target_sigregs tuc_mcontext;
4063     target_sigset_t tuc_sigmask;   /* mask last for extensibility */
4064 };
4065
4066 typedef struct {
4067     uint8_t callee_used_stack[__SIGNAL_FRAMESIZE];
4068     uint8_t retcode[S390_SYSCALL_SIZE];
4069     struct target_siginfo info;
4070     struct target_ucontext uc;
4071 } rt_sigframe;
4072
4073 static inline abi_ulong
4074 get_sigframe(struct target_sigaction *ka, CPUS390XState *env, size_t frame_size)
4075 {
4076     abi_ulong sp;
4077
4078     /* Default to using normal stack */
4079     sp = env->regs[15];
4080
4081     /* This is the X/Open sanctioned signal stack switching.  */
4082     if (ka->sa_flags & TARGET_SA_ONSTACK) {
4083         if (!sas_ss_flags(sp)) {
4084             sp = target_sigaltstack_used.ss_sp +
4085                  target_sigaltstack_used.ss_size;
4086         }
4087     }
4088
4089     /* This is the legacy signal stack switching. */
4090     else if (/* FIXME !user_mode(regs) */ 0 &&
4091              !(ka->sa_flags & TARGET_SA_RESTORER) &&
4092              ka->sa_restorer) {
4093         sp = (abi_ulong) ka->sa_restorer;
4094     }
4095
4096     return (sp - frame_size) & -8ul;
4097 }
4098
4099 static void save_sigregs(CPUS390XState *env, target_sigregs *sregs)
4100 {
4101     int i;
4102     //save_access_regs(current->thread.acrs); FIXME
4103
4104     /* Copy a 'clean' PSW mask to the user to avoid leaking
4105        information about whether PER is currently on.  */
4106     __put_user(env->psw.mask, &sregs->regs.psw.mask);
4107     __put_user(env->psw.addr, &sregs->regs.psw.addr);
4108     for (i = 0; i < 16; i++) {
4109         __put_user(env->regs[i], &sregs->regs.gprs[i]);
4110     }
4111     for (i = 0; i < 16; i++) {
4112         __put_user(env->aregs[i], &sregs->regs.acrs[i]);
4113     }
4114     /*
4115      * We have to store the fp registers to current->thread.fp_regs
4116      * to merge them with the emulated registers.
4117      */
4118     //save_fp_regs(&current->thread.fp_regs); FIXME
4119     for (i = 0; i < 16; i++) {
4120         __put_user(env->fregs[i].ll, &sregs->fpregs.fprs[i]);
4121     }
4122 }
4123
4124 static void setup_frame(int sig, struct target_sigaction *ka,
4125                         target_sigset_t *set, CPUS390XState *env)
4126 {
4127     sigframe *frame;
4128     abi_ulong frame_addr;
4129
4130     frame_addr = get_sigframe(ka, env, sizeof(*frame));
4131     qemu_log("%s: frame_addr 0x%llx\n", __FUNCTION__,
4132              (unsigned long long)frame_addr);
4133     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0)) {
4134             goto give_sigsegv;
4135     }
4136
4137     qemu_log("%s: 1\n", __FUNCTION__);
4138     __put_user(set->sig[0], &frame->sc.oldmask[0]);
4139
4140     save_sigregs(env, &frame->sregs);
4141
4142     __put_user((abi_ulong)(unsigned long)&frame->sregs,
4143                (abi_ulong *)&frame->sc.sregs);
4144
4145     /* Set up to return from userspace.  If provided, use a stub
4146        already in userspace.  */
4147     if (ka->sa_flags & TARGET_SA_RESTORER) {
4148             env->regs[14] = (unsigned long)
4149                     ka->sa_restorer | PSW_ADDR_AMODE;
4150     } else {
4151             env->regs[14] = (unsigned long)
4152                     frame->retcode | PSW_ADDR_AMODE;
4153             __put_user(S390_SYSCALL_OPCODE | TARGET_NR_sigreturn,
4154                        (uint16_t *)(frame->retcode));
4155     }
4156
4157     /* Set up backchain. */
4158     __put_user(env->regs[15], (abi_ulong *) frame);
4159
4160     /* Set up registers for signal handler */
4161     env->regs[15] = frame_addr;
4162     env->psw.addr = (target_ulong) ka->_sa_handler | PSW_ADDR_AMODE;
4163
4164     env->regs[2] = sig; //map_signal(sig);
4165     env->regs[3] = frame_addr += offsetof(typeof(*frame), sc);
4166
4167     /* We forgot to include these in the sigcontext.
4168        To avoid breaking binary compatibility, they are passed as args. */
4169     env->regs[4] = 0; // FIXME: no clue... current->thread.trap_no;
4170     env->regs[5] = 0; // FIXME: no clue... current->thread.prot_addr;
4171
4172     /* Place signal number on stack to allow backtrace from handler.  */
4173     __put_user(env->regs[2], (int *) &frame->signo);
4174     unlock_user_struct(frame, frame_addr, 1);
4175     return;
4176
4177 give_sigsegv:
4178     qemu_log("%s: give_sigsegv\n", __FUNCTION__);
4179     force_sig(TARGET_SIGSEGV);
4180 }
4181
4182 static void setup_rt_frame(int sig, struct target_sigaction *ka,
4183                            target_siginfo_t *info,
4184                            target_sigset_t *set, CPUS390XState *env)
4185 {
4186     int i;
4187     rt_sigframe *frame;
4188     abi_ulong frame_addr;
4189
4190     frame_addr = get_sigframe(ka, env, sizeof *frame);
4191     qemu_log("%s: frame_addr 0x%llx\n", __FUNCTION__,
4192              (unsigned long long)frame_addr);
4193     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0)) {
4194         goto give_sigsegv;
4195     }
4196
4197     qemu_log("%s: 1\n", __FUNCTION__);
4198     copy_siginfo_to_user(&frame->info, info);
4199
4200     /* Create the ucontext.  */
4201     __put_user(0, &frame->uc.tuc_flags);
4202     __put_user((abi_ulong)0, (abi_ulong *)&frame->uc.tuc_link);
4203     __put_user(target_sigaltstack_used.ss_sp, &frame->uc.tuc_stack.ss_sp);
4204     __put_user(sas_ss_flags(get_sp_from_cpustate(env)),
4205                       &frame->uc.tuc_stack.ss_flags);
4206     __put_user(target_sigaltstack_used.ss_size, &frame->uc.tuc_stack.ss_size);
4207     save_sigregs(env, &frame->uc.tuc_mcontext);
4208     for (i = 0; i < TARGET_NSIG_WORDS; i++) {
4209         __put_user((abi_ulong)set->sig[i],
4210         (abi_ulong *)&frame->uc.tuc_sigmask.sig[i]);
4211     }
4212
4213     /* Set up to return from userspace.  If provided, use a stub
4214        already in userspace.  */
4215     if (ka->sa_flags & TARGET_SA_RESTORER) {
4216         env->regs[14] = (unsigned long) ka->sa_restorer | PSW_ADDR_AMODE;
4217     } else {
4218         env->regs[14] = (unsigned long) frame->retcode | PSW_ADDR_AMODE;
4219         __put_user(S390_SYSCALL_OPCODE | TARGET_NR_rt_sigreturn,
4220                    (uint16_t *)(frame->retcode));
4221     }
4222
4223     /* Set up backchain. */
4224     __put_user(env->regs[15], (abi_ulong *) frame);
4225
4226     /* Set up registers for signal handler */
4227     env->regs[15] = frame_addr;
4228     env->psw.addr = (target_ulong) ka->_sa_handler | PSW_ADDR_AMODE;
4229
4230     env->regs[2] = sig; //map_signal(sig);
4231     env->regs[3] = frame_addr + offsetof(typeof(*frame), info);
4232     env->regs[4] = frame_addr + offsetof(typeof(*frame), uc);
4233     return;
4234
4235 give_sigsegv:
4236     qemu_log("%s: give_sigsegv\n", __FUNCTION__);
4237     force_sig(TARGET_SIGSEGV);
4238 }
4239
4240 static int
4241 restore_sigregs(CPUS390XState *env, target_sigregs *sc)
4242 {
4243     int err = 0;
4244     int i;
4245
4246     for (i = 0; i < 16; i++) {
4247         __get_user(env->regs[i], &sc->regs.gprs[i]);
4248     }
4249
4250     __get_user(env->psw.mask, &sc->regs.psw.mask);
4251     qemu_log("%s: sc->regs.psw.addr 0x%llx env->psw.addr 0x%llx\n",
4252              __FUNCTION__, (unsigned long long)sc->regs.psw.addr,
4253              (unsigned long long)env->psw.addr);
4254     __get_user(env->psw.addr, &sc->regs.psw.addr);
4255     /* FIXME: 31-bit -> | PSW_ADDR_AMODE */
4256
4257     for (i = 0; i < 16; i++) {
4258         __get_user(env->aregs[i], &sc->regs.acrs[i]);
4259     }
4260     for (i = 0; i < 16; i++) {
4261         __get_user(env->fregs[i].ll, &sc->fpregs.fprs[i]);
4262     }
4263
4264     return err;
4265 }
4266
4267 long do_sigreturn(CPUS390XState *env)
4268 {
4269     sigframe *frame;
4270     abi_ulong frame_addr = env->regs[15];
4271     qemu_log("%s: frame_addr 0x%llx\n", __FUNCTION__,
4272              (unsigned long long)frame_addr);
4273     target_sigset_t target_set;
4274     sigset_t set;
4275
4276     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1)) {
4277         goto badframe;
4278     }
4279     __get_user(target_set.sig[0], &frame->sc.oldmask[0]);
4280
4281     target_to_host_sigset_internal(&set, &target_set);
4282     do_sigprocmask(SIG_SETMASK, &set, NULL); /* ~_BLOCKABLE? */
4283
4284     if (restore_sigregs(env, &frame->sregs)) {
4285         goto badframe;
4286     }
4287
4288     unlock_user_struct(frame, frame_addr, 0);
4289     return env->regs[2];
4290
4291 badframe:
4292     force_sig(TARGET_SIGSEGV);
4293     return 0;
4294 }
4295
4296 long do_rt_sigreturn(CPUS390XState *env)
4297 {
4298     rt_sigframe *frame;
4299     abi_ulong frame_addr = env->regs[15];
4300     qemu_log("%s: frame_addr 0x%llx\n", __FUNCTION__,
4301              (unsigned long long)frame_addr);
4302     sigset_t set;
4303
4304     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1)) {
4305         goto badframe;
4306     }
4307     target_to_host_sigset(&set, &frame->uc.tuc_sigmask);
4308
4309     do_sigprocmask(SIG_SETMASK, &set, NULL); /* ~_BLOCKABLE? */
4310
4311     if (restore_sigregs(env, &frame->uc.tuc_mcontext)) {
4312         goto badframe;
4313     }
4314
4315     if (do_sigaltstack(frame_addr + offsetof(rt_sigframe, uc.tuc_stack), 0,
4316                        get_sp_from_cpustate(env)) == -EFAULT) {
4317         goto badframe;
4318     }
4319     unlock_user_struct(frame, frame_addr, 0);
4320     return env->regs[2];
4321
4322 badframe:
4323     unlock_user_struct(frame, frame_addr, 0);
4324     force_sig(TARGET_SIGSEGV);
4325     return 0;
4326 }
4327
4328 #elif defined(TARGET_PPC) && !defined(TARGET_PPC64)
4329
4330 /* FIXME: Many of the structures are defined for both PPC and PPC64, but
4331    the signal handling is different enough that we haven't implemented
4332    support for PPC64 yet.  Hence the restriction above.
4333
4334    There are various #if'd blocks for code for TARGET_PPC64.  These
4335    blocks should go away so that we can successfully run 32-bit and
4336    64-bit binaries on a QEMU configured for PPC64.  */
4337
4338 /* Size of dummy stack frame allocated when calling signal handler.
4339    See arch/powerpc/include/asm/ptrace.h.  */
4340 #if defined(TARGET_PPC64)
4341 #define SIGNAL_FRAMESIZE 128
4342 #else
4343 #define SIGNAL_FRAMESIZE 64
4344 #endif
4345
4346 /* See arch/powerpc/include/asm/sigcontext.h.  */
4347 struct target_sigcontext {
4348     target_ulong _unused[4];
4349     int32_t signal;
4350 #if defined(TARGET_PPC64)
4351     int32_t pad0;
4352 #endif
4353     target_ulong handler;
4354     target_ulong oldmask;
4355     target_ulong regs;      /* struct pt_regs __user * */
4356     /* TODO: PPC64 includes extra bits here.  */
4357 };
4358
4359 /* Indices for target_mcontext.mc_gregs, below.
4360    See arch/powerpc/include/asm/ptrace.h for details.  */
4361 enum {
4362     TARGET_PT_R0 = 0,
4363     TARGET_PT_R1 = 1,
4364     TARGET_PT_R2 = 2,
4365     TARGET_PT_R3 = 3,
4366     TARGET_PT_R4 = 4,
4367     TARGET_PT_R5 = 5,
4368     TARGET_PT_R6 = 6,
4369     TARGET_PT_R7 = 7,
4370     TARGET_PT_R8 = 8,
4371     TARGET_PT_R9 = 9,
4372     TARGET_PT_R10 = 10,
4373     TARGET_PT_R11 = 11,
4374     TARGET_PT_R12 = 12,
4375     TARGET_PT_R13 = 13,
4376     TARGET_PT_R14 = 14,
4377     TARGET_PT_R15 = 15,
4378     TARGET_PT_R16 = 16,
4379     TARGET_PT_R17 = 17,
4380     TARGET_PT_R18 = 18,
4381     TARGET_PT_R19 = 19,
4382     TARGET_PT_R20 = 20,
4383     TARGET_PT_R21 = 21,
4384     TARGET_PT_R22 = 22,
4385     TARGET_PT_R23 = 23,
4386     TARGET_PT_R24 = 24,
4387     TARGET_PT_R25 = 25,
4388     TARGET_PT_R26 = 26,
4389     TARGET_PT_R27 = 27,
4390     TARGET_PT_R28 = 28,
4391     TARGET_PT_R29 = 29,
4392     TARGET_PT_R30 = 30,
4393     TARGET_PT_R31 = 31,
4394     TARGET_PT_NIP = 32,
4395     TARGET_PT_MSR = 33,
4396     TARGET_PT_ORIG_R3 = 34,
4397     TARGET_PT_CTR = 35,
4398     TARGET_PT_LNK = 36,
4399     TARGET_PT_XER = 37,
4400     TARGET_PT_CCR = 38,
4401     /* Yes, there are two registers with #39.  One is 64-bit only.  */
4402     TARGET_PT_MQ = 39,
4403     TARGET_PT_SOFTE = 39,
4404     TARGET_PT_TRAP = 40,
4405     TARGET_PT_DAR = 41,
4406     TARGET_PT_DSISR = 42,
4407     TARGET_PT_RESULT = 43,
4408     TARGET_PT_REGS_COUNT = 44
4409 };
4410
4411 /* See arch/powerpc/include/asm/ucontext.h.  Only used for 32-bit PPC;
4412    on 64-bit PPC, sigcontext and mcontext are one and the same.  */
4413 struct target_mcontext {
4414     target_ulong mc_gregs[48];
4415     /* Includes fpscr.  */
4416     uint64_t mc_fregs[33];
4417     target_ulong mc_pad[2];
4418     /* We need to handle Altivec and SPE at the same time, which no
4419        kernel needs to do.  Fortunately, the kernel defines this bit to
4420        be Altivec-register-large all the time, rather than trying to
4421        twiddle it based on the specific platform.  */
4422     union {
4423         /* SPE vector registers.  One extra for SPEFSCR.  */
4424         uint32_t spe[33];
4425         /* Altivec vector registers.  The packing of VSCR and VRSAVE
4426            varies depending on whether we're PPC64 or not: PPC64 splits
4427            them apart; PPC32 stuffs them together.  */
4428 #if defined(TARGET_PPC64)
4429 #define QEMU_NVRREG 34
4430 #else
4431 #define QEMU_NVRREG 33
4432 #endif
4433         ppc_avr_t altivec[QEMU_NVRREG];
4434 #undef QEMU_NVRREG
4435     } mc_vregs __attribute__((__aligned__(16)));
4436 };
4437
4438 struct target_ucontext {
4439     target_ulong tuc_flags;
4440     target_ulong tuc_link;    /* struct ucontext __user * */
4441     struct target_sigaltstack tuc_stack;
4442 #if !defined(TARGET_PPC64)
4443     int32_t tuc_pad[7];
4444     target_ulong tuc_regs;    /* struct mcontext __user *
4445                                 points to uc_mcontext field */
4446 #endif
4447     target_sigset_t tuc_sigmask;
4448 #if defined(TARGET_PPC64)
4449     target_sigset_t unused[15]; /* Allow for uc_sigmask growth */
4450     struct target_sigcontext tuc_mcontext;
4451 #else
4452     int32_t tuc_maskext[30];
4453     int32_t tuc_pad2[3];
4454     struct target_mcontext tuc_mcontext;
4455 #endif
4456 };
4457
4458 /* See arch/powerpc/kernel/signal_32.c.  */
4459 struct target_sigframe {
4460     struct target_sigcontext sctx;
4461     struct target_mcontext mctx;
4462     int32_t abigap[56];
4463 };
4464
4465 struct target_rt_sigframe {
4466     struct target_siginfo info;
4467     struct target_ucontext uc;
4468     int32_t abigap[56];
4469 };
4470
4471 /* We use the mc_pad field for the signal return trampoline.  */
4472 #define tramp mc_pad
4473
4474 /* See arch/powerpc/kernel/signal.c.  */
4475 static target_ulong get_sigframe(struct target_sigaction *ka,
4476                                  CPUPPCState *env,
4477                                  int frame_size)
4478 {
4479     target_ulong oldsp, newsp;
4480
4481     oldsp = env->gpr[1];
4482
4483     if ((ka->sa_flags & TARGET_SA_ONSTACK) &&
4484         (sas_ss_flags(oldsp) == 0)) {
4485         oldsp = (target_sigaltstack_used.ss_sp
4486                  + target_sigaltstack_used.ss_size);
4487     }
4488
4489     newsp = (oldsp - frame_size) & ~0xFUL;
4490
4491     return newsp;
4492 }
4493
4494 static void save_user_regs(CPUPPCState *env, struct target_mcontext *frame,
4495                           int sigret)
4496 {
4497     target_ulong msr = env->msr;
4498     int i;
4499     target_ulong ccr = 0;
4500
4501     /* In general, the kernel attempts to be intelligent about what it
4502        needs to save for Altivec/FP/SPE registers.  We don't care that
4503        much, so we just go ahead and save everything.  */
4504
4505     /* Save general registers.  */
4506     for (i = 0; i < ARRAY_SIZE(env->gpr); i++) {
4507        __put_user(env->gpr[i], &frame->mc_gregs[i]);
4508     }
4509     __put_user(env->nip, &frame->mc_gregs[TARGET_PT_NIP]);
4510     __put_user(env->ctr, &frame->mc_gregs[TARGET_PT_CTR]);
4511     __put_user(env->lr, &frame->mc_gregs[TARGET_PT_LNK]);
4512     __put_user(env->xer, &frame->mc_gregs[TARGET_PT_XER]);
4513
4514     for (i = 0; i < ARRAY_SIZE(env->crf); i++) {
4515         ccr |= env->crf[i] << (32 - ((i + 1) * 4));
4516     }
4517     __put_user(ccr, &frame->mc_gregs[TARGET_PT_CCR]);
4518
4519     /* Save Altivec registers if necessary.  */
4520     if (env->insns_flags & PPC_ALTIVEC) {
4521         for (i = 0; i < ARRAY_SIZE(env->avr); i++) {
4522             ppc_avr_t *avr = &env->avr[i];
4523             ppc_avr_t *vreg = &frame->mc_vregs.altivec[i];
4524
4525             __put_user(avr->u64[0], &vreg->u64[0]);
4526             __put_user(avr->u64[1], &vreg->u64[1]);
4527         }
4528         /* Set MSR_VR in the saved MSR value to indicate that
4529            frame->mc_vregs contains valid data.  */
4530         msr |= MSR_VR;
4531         __put_user((uint32_t)env->spr[SPR_VRSAVE],
4532                    &frame->mc_vregs.altivec[32].u32[3]);
4533     }
4534
4535     /* Save floating point registers.  */
4536     if (env->insns_flags & PPC_FLOAT) {
4537         for (i = 0; i < ARRAY_SIZE(env->fpr); i++) {
4538             __put_user(env->fpr[i], &frame->mc_fregs[i]);
4539         }
4540         __put_user((uint64_t) env->fpscr, &frame->mc_fregs[32]);
4541     }
4542
4543     /* Save SPE registers.  The kernel only saves the high half.  */
4544     if (env->insns_flags & PPC_SPE) {
4545 #if defined(TARGET_PPC64)
4546         for (i = 0; i < ARRAY_SIZE(env->gpr); i++) {
4547             __put_user(env->gpr[i] >> 32, &frame->mc_vregs.spe[i]);
4548         }
4549 #else
4550         for (i = 0; i < ARRAY_SIZE(env->gprh); i++) {
4551             __put_user(env->gprh[i], &frame->mc_vregs.spe[i]);
4552         }
4553 #endif
4554         /* Set MSR_SPE in the saved MSR value to indicate that
4555            frame->mc_vregs contains valid data.  */
4556         msr |= MSR_SPE;
4557         __put_user(env->spe_fscr, &frame->mc_vregs.spe[32]);
4558     }
4559
4560     /* Store MSR.  */
4561     __put_user(msr, &frame->mc_gregs[TARGET_PT_MSR]);
4562
4563     /* Set up the sigreturn trampoline: li r0,sigret; sc.  */
4564     if (sigret) {
4565         __put_user(0x38000000UL | sigret, &frame->tramp[0]);
4566         __put_user(0x44000002UL, &frame->tramp[1]);
4567     }
4568 }
4569
4570 static void restore_user_regs(CPUPPCState *env,
4571                               struct target_mcontext *frame, int sig)
4572 {
4573     target_ulong save_r2 = 0;
4574     target_ulong msr;
4575     target_ulong ccr;
4576
4577     int i;
4578
4579     if (!sig) {
4580         save_r2 = env->gpr[2];
4581     }
4582
4583     /* Restore general registers.  */
4584     for (i = 0; i < ARRAY_SIZE(env->gpr); i++) {
4585         __get_user(env->gpr[i], &frame->mc_gregs[i]);
4586     }
4587     __get_user(env->nip, &frame->mc_gregs[TARGET_PT_NIP]);
4588     __get_user(env->ctr, &frame->mc_gregs[TARGET_PT_CTR]);
4589     __get_user(env->lr, &frame->mc_gregs[TARGET_PT_LNK]);
4590     __get_user(env->xer, &frame->mc_gregs[TARGET_PT_XER]);
4591     __get_user(ccr, &frame->mc_gregs[TARGET_PT_CCR]);
4592
4593     for (i = 0; i < ARRAY_SIZE(env->crf); i++) {
4594         env->crf[i] = (ccr >> (32 - ((i + 1) * 4))) & 0xf;
4595     }
4596
4597     if (!sig) {
4598         env->gpr[2] = save_r2;
4599     }
4600     /* Restore MSR.  */
4601     __get_user(msr, &frame->mc_gregs[TARGET_PT_MSR]);
4602
4603     /* If doing signal return, restore the previous little-endian mode.  */
4604     if (sig)
4605         env->msr = (env->msr & ~MSR_LE) | (msr & MSR_LE);
4606
4607     /* Restore Altivec registers if necessary.  */
4608     if (env->insns_flags & PPC_ALTIVEC) {
4609         for (i = 0; i < ARRAY_SIZE(env->avr); i++) {
4610             ppc_avr_t *avr = &env->avr[i];
4611             ppc_avr_t *vreg = &frame->mc_vregs.altivec[i];
4612
4613             __get_user(avr->u64[0], &vreg->u64[0]);
4614             __get_user(avr->u64[1], &vreg->u64[1]);
4615         }
4616         /* Set MSR_VEC in the saved MSR value to indicate that
4617            frame->mc_vregs contains valid data.  */
4618         __get_user(env->spr[SPR_VRSAVE],
4619                    (target_ulong *)(&frame->mc_vregs.altivec[32].u32[3]));
4620     }
4621
4622     /* Restore floating point registers.  */
4623     if (env->insns_flags & PPC_FLOAT) {
4624         uint64_t fpscr;
4625         for (i = 0; i < ARRAY_SIZE(env->fpr); i++) {
4626             __get_user(env->fpr[i], &frame->mc_fregs[i]);
4627         }
4628         __get_user(fpscr, &frame->mc_fregs[32]);
4629         env->fpscr = (uint32_t) fpscr;
4630     }
4631
4632     /* Save SPE registers.  The kernel only saves the high half.  */
4633     if (env->insns_flags & PPC_SPE) {
4634 #if defined(TARGET_PPC64)
4635         for (i = 0; i < ARRAY_SIZE(env->gpr); i++) {
4636             uint32_t hi;
4637
4638             __get_user(hi, &frame->mc_vregs.spe[i]);
4639             env->gpr[i] = ((uint64_t)hi << 32) | ((uint32_t) env->gpr[i]);
4640         }
4641 #else
4642         for (i = 0; i < ARRAY_SIZE(env->gprh); i++) {
4643             __get_user(env->gprh[i], &frame->mc_vregs.spe[i]);
4644         }
4645 #endif
4646         __get_user(env->spe_fscr, &frame->mc_vregs.spe[32]);
4647     }
4648 }
4649
4650 static void setup_frame(int sig, struct target_sigaction *ka,
4651                         target_sigset_t *set, CPUPPCState *env)
4652 {
4653     struct target_sigframe *frame;
4654     struct target_sigcontext *sc;
4655     target_ulong frame_addr, newsp;
4656     int err = 0;
4657     int signal;
4658
4659     frame_addr = get_sigframe(ka, env, sizeof(*frame));
4660     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 1))
4661         goto sigsegv;
4662     sc = &frame->sctx;
4663
4664     signal = current_exec_domain_sig(sig);
4665
4666     __put_user(ka->_sa_handler, &sc->handler);
4667     __put_user(set->sig[0], &sc->oldmask);
4668 #if defined(TARGET_PPC64)
4669     __put_user(set->sig[0] >> 32, &sc->_unused[3]);
4670 #else
4671     __put_user(set->sig[1], &sc->_unused[3]);
4672 #endif
4673     __put_user(h2g(&frame->mctx), &sc->regs);
4674     __put_user(sig, &sc->signal);
4675
4676     /* Save user regs.  */
4677     save_user_regs(env, &frame->mctx, TARGET_NR_sigreturn);
4678
4679     /* The kernel checks for the presence of a VDSO here.  We don't
4680        emulate a vdso, so use a sigreturn system call.  */
4681     env->lr = (target_ulong) h2g(frame->mctx.tramp);
4682
4683     /* Turn off all fp exceptions.  */
4684     env->fpscr = 0;
4685
4686     /* Create a stack frame for the caller of the handler.  */
4687     newsp = frame_addr - SIGNAL_FRAMESIZE;
4688     err |= put_user(env->gpr[1], newsp, target_ulong);
4689
4690     if (err)
4691         goto sigsegv;
4692
4693     /* Set up registers for signal handler.  */
4694     env->gpr[1] = newsp;
4695     env->gpr[3] = signal;
4696     env->gpr[4] = frame_addr + offsetof(struct target_sigframe, sctx);
4697     env->nip = (target_ulong) ka->_sa_handler;
4698     /* Signal handlers are entered in big-endian mode.  */
4699     env->msr &= ~MSR_LE;
4700
4701     unlock_user_struct(frame, frame_addr, 1);
4702     return;
4703
4704 sigsegv:
4705     unlock_user_struct(frame, frame_addr, 1);
4706     qemu_log("segfaulting from setup_frame\n");
4707     force_sig(TARGET_SIGSEGV);
4708 }
4709
4710 static void setup_rt_frame(int sig, struct target_sigaction *ka,
4711                            target_siginfo_t *info,
4712                            target_sigset_t *set, CPUPPCState *env)
4713 {
4714     struct target_rt_sigframe *rt_sf;
4715     struct target_mcontext *frame;
4716     target_ulong rt_sf_addr, newsp = 0;
4717     int i, err = 0;
4718     int signal;
4719
4720     rt_sf_addr = get_sigframe(ka, env, sizeof(*rt_sf));
4721     if (!lock_user_struct(VERIFY_WRITE, rt_sf, rt_sf_addr, 1))
4722         goto sigsegv;
4723
4724     signal = current_exec_domain_sig(sig);
4725
4726     copy_siginfo_to_user(&rt_sf->info, info);
4727
4728     __put_user(0, &rt_sf->uc.tuc_flags);
4729     __put_user(0, &rt_sf->uc.tuc_link);
4730     __put_user((target_ulong)target_sigaltstack_used.ss_sp,
4731                &rt_sf->uc.tuc_stack.ss_sp);
4732     __put_user(sas_ss_flags(env->gpr[1]),
4733                &rt_sf->uc.tuc_stack.ss_flags);
4734     __put_user(target_sigaltstack_used.ss_size,
4735                &rt_sf->uc.tuc_stack.ss_size);
4736     __put_user(h2g (&rt_sf->uc.tuc_mcontext),
4737                &rt_sf->uc.tuc_regs);
4738     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
4739         __put_user(set->sig[i], &rt_sf->uc.tuc_sigmask.sig[i]);
4740     }
4741
4742     frame = &rt_sf->uc.tuc_mcontext;
4743     save_user_regs(env, frame, TARGET_NR_rt_sigreturn);
4744
4745     /* The kernel checks for the presence of a VDSO here.  We don't
4746        emulate a vdso, so use a sigreturn system call.  */
4747     env->lr = (target_ulong) h2g(frame->tramp);
4748
4749     /* Turn off all fp exceptions.  */
4750     env->fpscr = 0;
4751
4752     /* Create a stack frame for the caller of the handler.  */
4753     newsp = rt_sf_addr - (SIGNAL_FRAMESIZE + 16);
4754     __put_user(env->gpr[1], (target_ulong *)(uintptr_t) newsp);
4755
4756     if (err)
4757         goto sigsegv;
4758
4759     /* Set up registers for signal handler.  */
4760     env->gpr[1] = newsp;
4761     env->gpr[3] = (target_ulong) signal;
4762     env->gpr[4] = (target_ulong) h2g(&rt_sf->info);
4763     env->gpr[5] = (target_ulong) h2g(&rt_sf->uc);
4764     env->gpr[6] = (target_ulong) h2g(rt_sf);
4765     env->nip = (target_ulong) ka->_sa_handler;
4766     /* Signal handlers are entered in big-endian mode.  */
4767     env->msr &= ~MSR_LE;
4768
4769     unlock_user_struct(rt_sf, rt_sf_addr, 1);
4770     return;
4771
4772 sigsegv:
4773     unlock_user_struct(rt_sf, rt_sf_addr, 1);
4774     qemu_log("segfaulting from setup_rt_frame\n");
4775     force_sig(TARGET_SIGSEGV);
4776
4777 }
4778
4779 long do_sigreturn(CPUPPCState *env)
4780 {
4781     struct target_sigcontext *sc = NULL;
4782     struct target_mcontext *sr = NULL;
4783     target_ulong sr_addr = 0, sc_addr;
4784     sigset_t blocked;
4785     target_sigset_t set;
4786
4787     sc_addr = env->gpr[1] + SIGNAL_FRAMESIZE;
4788     if (!lock_user_struct(VERIFY_READ, sc, sc_addr, 1))
4789         goto sigsegv;
4790
4791 #if defined(TARGET_PPC64)
4792     set.sig[0] = sc->oldmask + ((long)(sc->_unused[3]) << 32);
4793 #else
4794     __get_user(set.sig[0], &sc->oldmask);
4795     __get_user(set.sig[1], &sc->_unused[3]);
4796 #endif
4797     target_to_host_sigset_internal(&blocked, &set);
4798     do_sigprocmask(SIG_SETMASK, &blocked, NULL);
4799
4800     __get_user(sr_addr, &sc->regs);
4801     if (!lock_user_struct(VERIFY_READ, sr, sr_addr, 1))
4802         goto sigsegv;
4803     restore_user_regs(env, sr, 1);
4804
4805     unlock_user_struct(sr, sr_addr, 1);
4806     unlock_user_struct(sc, sc_addr, 1);
4807     return -TARGET_QEMU_ESIGRETURN;
4808
4809 sigsegv:
4810     unlock_user_struct(sr, sr_addr, 1);
4811     unlock_user_struct(sc, sc_addr, 1);
4812     qemu_log("segfaulting from do_sigreturn\n");
4813     force_sig(TARGET_SIGSEGV);
4814     return 0;
4815 }
4816
4817 /* See arch/powerpc/kernel/signal_32.c.  */
4818 static int do_setcontext(struct target_ucontext *ucp, CPUPPCState *env, int sig)
4819 {
4820     struct target_mcontext *mcp;
4821     target_ulong mcp_addr;
4822     sigset_t blocked;
4823     target_sigset_t set;
4824
4825     if (copy_from_user(&set, h2g(ucp) + offsetof(struct target_ucontext, tuc_sigmask),
4826                        sizeof (set)))
4827         return 1;
4828
4829 #if defined(TARGET_PPC64)
4830     fprintf (stderr, "do_setcontext: not implemented\n");
4831     return 0;
4832 #else
4833     __get_user(mcp_addr, &ucp->tuc_regs);
4834
4835     if (!lock_user_struct(VERIFY_READ, mcp, mcp_addr, 1))
4836         return 1;
4837
4838     target_to_host_sigset_internal(&blocked, &set);
4839     do_sigprocmask(SIG_SETMASK, &blocked, NULL);
4840     restore_user_regs(env, mcp, sig);
4841
4842     unlock_user_struct(mcp, mcp_addr, 1);
4843     return 0;
4844 #endif
4845 }
4846
4847 long do_rt_sigreturn(CPUPPCState *env)
4848 {
4849     struct target_rt_sigframe *rt_sf = NULL;
4850     target_ulong rt_sf_addr;
4851
4852     rt_sf_addr = env->gpr[1] + SIGNAL_FRAMESIZE + 16;
4853     if (!lock_user_struct(VERIFY_READ, rt_sf, rt_sf_addr, 1))
4854         goto sigsegv;
4855
4856     if (do_setcontext(&rt_sf->uc, env, 1))
4857         goto sigsegv;
4858
4859     do_sigaltstack(rt_sf_addr
4860                    + offsetof(struct target_rt_sigframe, uc.tuc_stack),
4861                    0, env->gpr[1]);
4862
4863     unlock_user_struct(rt_sf, rt_sf_addr, 1);
4864     return -TARGET_QEMU_ESIGRETURN;
4865
4866 sigsegv:
4867     unlock_user_struct(rt_sf, rt_sf_addr, 1);
4868     qemu_log("segfaulting from do_rt_sigreturn\n");
4869     force_sig(TARGET_SIGSEGV);
4870     return 0;
4871 }
4872
4873 #elif defined(TARGET_M68K)
4874
4875 struct target_sigcontext {
4876     abi_ulong  sc_mask;
4877     abi_ulong  sc_usp;
4878     abi_ulong  sc_d0;
4879     abi_ulong  sc_d1;
4880     abi_ulong  sc_a0;
4881     abi_ulong  sc_a1;
4882     unsigned short sc_sr;
4883     abi_ulong  sc_pc;
4884 };
4885
4886 struct target_sigframe
4887 {
4888     abi_ulong pretcode;
4889     int sig;
4890     int code;
4891     abi_ulong psc;
4892     char retcode[8];
4893     abi_ulong extramask[TARGET_NSIG_WORDS-1];
4894     struct target_sigcontext sc;
4895 };
4896  
4897 typedef int target_greg_t;
4898 #define TARGET_NGREG 18
4899 typedef target_greg_t target_gregset_t[TARGET_NGREG];
4900
4901 typedef struct target_fpregset {
4902     int f_fpcntl[3];
4903     int f_fpregs[8*3];
4904 } target_fpregset_t;
4905
4906 struct target_mcontext {
4907     int version;
4908     target_gregset_t gregs;
4909     target_fpregset_t fpregs;
4910 };
4911
4912 #define TARGET_MCONTEXT_VERSION 2
4913
4914 struct target_ucontext {
4915     abi_ulong tuc_flags;
4916     abi_ulong tuc_link;
4917     target_stack_t tuc_stack;
4918     struct target_mcontext tuc_mcontext;
4919     abi_long tuc_filler[80];
4920     target_sigset_t tuc_sigmask;
4921 };
4922
4923 struct target_rt_sigframe
4924 {
4925     abi_ulong pretcode;
4926     int sig;
4927     abi_ulong pinfo;
4928     abi_ulong puc;
4929     char retcode[8];
4930     struct target_siginfo info;
4931     struct target_ucontext uc;
4932 };
4933
4934 static void setup_sigcontext(struct target_sigcontext *sc, CPUM68KState *env,
4935         abi_ulong mask)
4936 {
4937     __put_user(mask, &sc->sc_mask);
4938     __put_user(env->aregs[7], &sc->sc_usp);
4939     __put_user(env->dregs[0], &sc->sc_d0);
4940     __put_user(env->dregs[1], &sc->sc_d1);
4941     __put_user(env->aregs[0], &sc->sc_a0);
4942     __put_user(env->aregs[1], &sc->sc_a1);
4943     __put_user(env->sr, &sc->sc_sr);
4944     __put_user(env->pc, &sc->sc_pc);
4945 }
4946
4947 static void
4948 restore_sigcontext(CPUM68KState *env, struct target_sigcontext *sc, int *pd0)
4949 {
4950     int temp;
4951
4952     __get_user(env->aregs[7], &sc->sc_usp);
4953     __get_user(env->dregs[1], &sc->sc_d1);
4954     __get_user(env->aregs[0], &sc->sc_a0);
4955     __get_user(env->aregs[1], &sc->sc_a1);
4956     __get_user(env->pc, &sc->sc_pc);
4957     __get_user(temp, &sc->sc_sr);
4958     env->sr = (env->sr & 0xff00) | (temp & 0xff);
4959
4960     *pd0 = tswapl(sc->sc_d0);
4961 }
4962
4963 /*
4964  * Determine which stack to use..
4965  */
4966 static inline abi_ulong
4967 get_sigframe(struct target_sigaction *ka, CPUM68KState *regs,
4968              size_t frame_size)
4969 {
4970     unsigned long sp;
4971
4972     sp = regs->aregs[7];
4973
4974     /* This is the X/Open sanctioned signal stack switching.  */
4975     if ((ka->sa_flags & TARGET_SA_ONSTACK) && (sas_ss_flags (sp) == 0)) {
4976         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
4977     }
4978
4979     return ((sp - frame_size) & -8UL);
4980 }
4981
4982 static void setup_frame(int sig, struct target_sigaction *ka,
4983                         target_sigset_t *set, CPUM68KState *env)
4984 {
4985     struct target_sigframe *frame;
4986     abi_ulong frame_addr;
4987     abi_ulong retcode_addr;
4988     abi_ulong sc_addr;
4989     int i;
4990
4991     frame_addr = get_sigframe(ka, env, sizeof *frame);
4992     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
4993         goto give_sigsegv;
4994
4995     __put_user(sig, &frame->sig);
4996
4997     sc_addr = frame_addr + offsetof(struct target_sigframe, sc);
4998     __put_user(sc_addr, &frame->psc);
4999
5000     setup_sigcontext(&frame->sc, env, set->sig[0]);
5001
5002     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
5003         __put_user(set->sig[i], &frame->extramask[i - 1]);
5004     }
5005
5006     /* Set up to return from userspace.  */
5007
5008     retcode_addr = frame_addr + offsetof(struct target_sigframe, retcode);
5009     __put_user(retcode_addr, &frame->pretcode);
5010
5011     /* moveq #,d0; trap #0 */
5012
5013     __put_user(0x70004e40 + (TARGET_NR_sigreturn << 16),
5014                       (long *)(frame->retcode));
5015
5016     /* Set up to return from userspace */
5017
5018     env->aregs[7] = frame_addr;
5019     env->pc = ka->_sa_handler;
5020
5021     unlock_user_struct(frame, frame_addr, 1);
5022     return;
5023
5024 give_sigsegv:
5025     force_sig(TARGET_SIGSEGV);
5026 }
5027
5028 static inline int target_rt_setup_ucontext(struct target_ucontext *uc,
5029                                            CPUM68KState *env)
5030 {
5031     target_greg_t *gregs = uc->tuc_mcontext.gregs;
5032
5033     __put_user(TARGET_MCONTEXT_VERSION, &uc->tuc_mcontext.version);
5034     __put_user(env->dregs[0], &gregs[0]);
5035     __put_user(env->dregs[1], &gregs[1]);
5036     __put_user(env->dregs[2], &gregs[2]);
5037     __put_user(env->dregs[3], &gregs[3]);
5038     __put_user(env->dregs[4], &gregs[4]);
5039     __put_user(env->dregs[5], &gregs[5]);
5040     __put_user(env->dregs[6], &gregs[6]);
5041     __put_user(env->dregs[7], &gregs[7]);
5042     __put_user(env->aregs[0], &gregs[8]);
5043     __put_user(env->aregs[1], &gregs[9]);
5044     __put_user(env->aregs[2], &gregs[10]);
5045     __put_user(env->aregs[3], &gregs[11]);
5046     __put_user(env->aregs[4], &gregs[12]);
5047     __put_user(env->aregs[5], &gregs[13]);
5048     __put_user(env->aregs[6], &gregs[14]);
5049     __put_user(env->aregs[7], &gregs[15]);
5050     __put_user(env->pc, &gregs[16]);
5051     __put_user(env->sr, &gregs[17]);
5052
5053     return 0;
5054 }
5055  
5056 static inline int target_rt_restore_ucontext(CPUM68KState *env,
5057                                              struct target_ucontext *uc,
5058                                              int *pd0)
5059 {
5060     int temp;
5061     target_greg_t *gregs = uc->tuc_mcontext.gregs;
5062     
5063     __get_user(temp, &uc->tuc_mcontext.version);
5064     if (temp != TARGET_MCONTEXT_VERSION)
5065         goto badframe;
5066
5067     /* restore passed registers */
5068     __get_user(env->dregs[0], &gregs[0]);
5069     __get_user(env->dregs[1], &gregs[1]);
5070     __get_user(env->dregs[2], &gregs[2]);
5071     __get_user(env->dregs[3], &gregs[3]);
5072     __get_user(env->dregs[4], &gregs[4]);
5073     __get_user(env->dregs[5], &gregs[5]);
5074     __get_user(env->dregs[6], &gregs[6]);
5075     __get_user(env->dregs[7], &gregs[7]);
5076     __get_user(env->aregs[0], &gregs[8]);
5077     __get_user(env->aregs[1], &gregs[9]);
5078     __get_user(env->aregs[2], &gregs[10]);
5079     __get_user(env->aregs[3], &gregs[11]);
5080     __get_user(env->aregs[4], &gregs[12]);
5081     __get_user(env->aregs[5], &gregs[13]);
5082     __get_user(env->aregs[6], &gregs[14]);
5083     __get_user(env->aregs[7], &gregs[15]);
5084     __get_user(env->pc, &gregs[16]);
5085     __get_user(temp, &gregs[17]);
5086     env->sr = (env->sr & 0xff00) | (temp & 0xff);
5087
5088     *pd0 = env->dregs[0];
5089     return 0;
5090
5091 badframe:
5092     return 1;
5093 }
5094
5095 static void setup_rt_frame(int sig, struct target_sigaction *ka,
5096                            target_siginfo_t *info,
5097                            target_sigset_t *set, CPUM68KState *env)
5098 {
5099     struct target_rt_sigframe *frame;
5100     abi_ulong frame_addr;
5101     abi_ulong retcode_addr;
5102     abi_ulong info_addr;
5103     abi_ulong uc_addr;
5104     int err = 0;
5105     int i;
5106
5107     frame_addr = get_sigframe(ka, env, sizeof *frame);
5108     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0))
5109         goto give_sigsegv;
5110
5111     __put_user(sig, &frame->sig);
5112
5113     info_addr = frame_addr + offsetof(struct target_rt_sigframe, info);
5114     __put_user(info_addr, &frame->pinfo);
5115
5116     uc_addr = frame_addr + offsetof(struct target_rt_sigframe, uc);
5117     __put_user(uc_addr, &frame->puc);
5118
5119     copy_siginfo_to_user(&frame->info, info);
5120
5121     /* Create the ucontext */
5122
5123     __put_user(0, &frame->uc.tuc_flags);
5124     __put_user(0, &frame->uc.tuc_link);
5125     __put_user(target_sigaltstack_used.ss_sp,
5126                &frame->uc.tuc_stack.ss_sp);
5127     __put_user(sas_ss_flags(env->aregs[7]),
5128                &frame->uc.tuc_stack.ss_flags);
5129     __put_user(target_sigaltstack_used.ss_size,
5130                &frame->uc.tuc_stack.ss_size);
5131     err |= target_rt_setup_ucontext(&frame->uc, env);
5132
5133     if (err)
5134             goto give_sigsegv;
5135
5136     for(i = 0; i < TARGET_NSIG_WORDS; i++) {
5137         __put_user(set->sig[i], &frame->uc.tuc_sigmask.sig[i]);
5138     }
5139
5140     /* Set up to return from userspace.  */
5141
5142     retcode_addr = frame_addr + offsetof(struct target_sigframe, retcode);
5143     __put_user(retcode_addr, &frame->pretcode);
5144
5145     /* moveq #,d0; notb d0; trap #0 */
5146
5147     __put_user(0x70004600 + ((TARGET_NR_rt_sigreturn ^ 0xff) << 16),
5148                (long *)(frame->retcode + 0));
5149     __put_user(0x4e40, (short *)(frame->retcode + 4));
5150
5151     if (err)
5152         goto give_sigsegv;
5153
5154     /* Set up to return from userspace */
5155
5156     env->aregs[7] = frame_addr;
5157     env->pc = ka->_sa_handler;
5158
5159     unlock_user_struct(frame, frame_addr, 1);
5160     return;
5161
5162 give_sigsegv:
5163     unlock_user_struct(frame, frame_addr, 1);
5164     force_sig(TARGET_SIGSEGV);
5165 }
5166
5167 long do_sigreturn(CPUM68KState *env)
5168 {
5169     struct target_sigframe *frame;
5170     abi_ulong frame_addr = env->aregs[7] - 4;
5171     target_sigset_t target_set;
5172     sigset_t set;
5173     int d0, i;
5174
5175     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
5176         goto badframe;
5177
5178     /* set blocked signals */
5179
5180     __get_user(target_set.sig[0], &frame->sc.sc_mask);
5181
5182     for(i = 1; i < TARGET_NSIG_WORDS; i++) {
5183         __get_user(target_set.sig[i], &frame->extramask[i - 1]);
5184     }
5185
5186     target_to_host_sigset_internal(&set, &target_set);
5187     do_sigprocmask(SIG_SETMASK, &set, NULL);
5188
5189     /* restore registers */
5190
5191     restore_sigcontext(env, &frame->sc, &d0);
5192
5193     unlock_user_struct(frame, frame_addr, 0);
5194     return d0;
5195
5196 badframe:
5197     force_sig(TARGET_SIGSEGV);
5198     return 0;
5199 }
5200
5201 long do_rt_sigreturn(CPUM68KState *env)
5202 {
5203     struct target_rt_sigframe *frame;
5204     abi_ulong frame_addr = env->aregs[7] - 4;
5205     target_sigset_t target_set;
5206     sigset_t set;
5207     int d0;
5208
5209     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))
5210         goto badframe;
5211
5212     target_to_host_sigset_internal(&set, &target_set);
5213     do_sigprocmask(SIG_SETMASK, &set, NULL);
5214
5215     /* restore registers */
5216
5217     if (target_rt_restore_ucontext(env, &frame->uc, &d0))
5218         goto badframe;
5219
5220     if (do_sigaltstack(frame_addr +
5221                        offsetof(struct target_rt_sigframe, uc.tuc_stack),
5222                        0, get_sp_from_cpustate(env)) == -EFAULT)
5223         goto badframe;
5224
5225     unlock_user_struct(frame, frame_addr, 0);
5226     return d0;
5227
5228 badframe:
5229     unlock_user_struct(frame, frame_addr, 0);
5230     force_sig(TARGET_SIGSEGV);
5231     return 0;
5232 }
5233
5234 #elif defined(TARGET_ALPHA)
5235
5236 struct target_sigcontext {
5237     abi_long sc_onstack;
5238     abi_long sc_mask;
5239     abi_long sc_pc;
5240     abi_long sc_ps;
5241     abi_long sc_regs[32];
5242     abi_long sc_ownedfp;
5243     abi_long sc_fpregs[32];
5244     abi_ulong sc_fpcr;
5245     abi_ulong sc_fp_control;
5246     abi_ulong sc_reserved1;
5247     abi_ulong sc_reserved2;
5248     abi_ulong sc_ssize;
5249     abi_ulong sc_sbase;
5250     abi_ulong sc_traparg_a0;
5251     abi_ulong sc_traparg_a1;
5252     abi_ulong sc_traparg_a2;
5253     abi_ulong sc_fp_trap_pc;
5254     abi_ulong sc_fp_trigger_sum;
5255     abi_ulong sc_fp_trigger_inst;
5256 };
5257
5258 struct target_ucontext {
5259     abi_ulong tuc_flags;
5260     abi_ulong tuc_link;
5261     abi_ulong tuc_osf_sigmask;
5262     target_stack_t tuc_stack;
5263     struct target_sigcontext tuc_mcontext;
5264     target_sigset_t tuc_sigmask;
5265 };
5266
5267 struct target_sigframe {
5268     struct target_sigcontext sc;
5269     unsigned int retcode[3];
5270 };
5271
5272 struct target_rt_sigframe {
5273     target_siginfo_t info;
5274     struct target_ucontext uc;
5275     unsigned int retcode[3];
5276 };
5277
5278 #define INSN_MOV_R30_R16        0x47fe0410
5279 #define INSN_LDI_R0             0x201f0000
5280 #define INSN_CALLSYS            0x00000083
5281
5282 static void setup_sigcontext(struct target_sigcontext *sc, CPUAlphaState *env,
5283                             abi_ulong frame_addr, target_sigset_t *set)
5284 {
5285     int i;
5286
5287     __put_user(on_sig_stack(frame_addr), &sc->sc_onstack);
5288     __put_user(set->sig[0], &sc->sc_mask);
5289     __put_user(env->pc, &sc->sc_pc);
5290     __put_user(8, &sc->sc_ps);
5291
5292     for (i = 0; i < 31; ++i) {
5293         __put_user(env->ir[i], &sc->sc_regs[i]);
5294     }
5295     __put_user(0, &sc->sc_regs[31]);
5296
5297     for (i = 0; i < 31; ++i) {
5298         __put_user(env->fir[i], &sc->sc_fpregs[i]);
5299     }
5300     __put_user(0, &sc->sc_fpregs[31]);
5301     __put_user(cpu_alpha_load_fpcr(env), &sc->sc_fpcr);
5302
5303     __put_user(0, &sc->sc_traparg_a0); /* FIXME */
5304     __put_user(0, &sc->sc_traparg_a1); /* FIXME */
5305     __put_user(0, &sc->sc_traparg_a2); /* FIXME */
5306 }
5307
5308 static void restore_sigcontext(CPUAlphaState *env,
5309                               struct target_sigcontext *sc)
5310 {
5311     uint64_t fpcr;
5312     int i;
5313
5314     __get_user(env->pc, &sc->sc_pc);
5315
5316     for (i = 0; i < 31; ++i) {
5317         __get_user(env->ir[i], &sc->sc_regs[i]);
5318     }
5319     for (i = 0; i < 31; ++i) {
5320         __get_user(env->fir[i], &sc->sc_fpregs[i]);
5321     }
5322
5323     __get_user(fpcr, &sc->sc_fpcr);
5324     cpu_alpha_store_fpcr(env, fpcr);
5325 }
5326
5327 static inline abi_ulong get_sigframe(struct target_sigaction *sa,
5328                                      CPUAlphaState *env,
5329                                      unsigned long framesize)
5330 {
5331     abi_ulong sp = env->ir[IR_SP];
5332
5333     /* This is the X/Open sanctioned signal stack switching.  */
5334     if ((sa->sa_flags & TARGET_SA_ONSTACK) != 0 && !sas_ss_flags(sp)) {
5335         sp = target_sigaltstack_used.ss_sp + target_sigaltstack_used.ss_size;
5336     }
5337     return (sp - framesize) & -32;
5338 }
5339
5340 static void setup_frame(int sig, struct target_sigaction *ka,
5341                         target_sigset_t *set, CPUAlphaState *env)
5342 {
5343     abi_ulong frame_addr, r26;
5344     struct target_sigframe *frame;
5345     int err = 0;
5346
5347     frame_addr = get_sigframe(ka, env, sizeof(*frame));
5348     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0)) {
5349         goto give_sigsegv;
5350     }
5351
5352     setup_sigcontext(&frame->sc, env, frame_addr, set);
5353
5354     if (ka->sa_restorer) {
5355         r26 = ka->sa_restorer;
5356     } else {
5357         __put_user(INSN_MOV_R30_R16, &frame->retcode[0]);
5358         __put_user(INSN_LDI_R0 + TARGET_NR_sigreturn,
5359                    &frame->retcode[1]);
5360         __put_user(INSN_CALLSYS, &frame->retcode[2]);
5361         /* imb() */
5362         r26 = frame_addr;
5363     }
5364
5365     unlock_user_struct(frame, frame_addr, 1);
5366
5367     if (err) {
5368     give_sigsegv:
5369         if (sig == TARGET_SIGSEGV) {
5370             ka->_sa_handler = TARGET_SIG_DFL;
5371         }
5372         force_sig(TARGET_SIGSEGV);
5373     }
5374
5375     env->ir[IR_RA] = r26;
5376     env->ir[IR_PV] = env->pc = ka->_sa_handler;
5377     env->ir[IR_A0] = sig;
5378     env->ir[IR_A1] = 0;
5379     env->ir[IR_A2] = frame_addr + offsetof(struct target_sigframe, sc);
5380     env->ir[IR_SP] = frame_addr;
5381 }
5382
5383 static void setup_rt_frame(int sig, struct target_sigaction *ka,
5384                            target_siginfo_t *info,
5385                            target_sigset_t *set, CPUAlphaState *env)
5386 {
5387     abi_ulong frame_addr, r26;
5388     struct target_rt_sigframe *frame;
5389     int i, err = 0;
5390
5391     frame_addr = get_sigframe(ka, env, sizeof(*frame));
5392     if (!lock_user_struct(VERIFY_WRITE, frame, frame_addr, 0)) {
5393         goto give_sigsegv;
5394     }
5395
5396     copy_siginfo_to_user(&frame->info, info);
5397
5398     __put_user(0, &frame->uc.tuc_flags);
5399     __put_user(0, &frame->uc.tuc_link);
5400     __put_user(set->sig[0], &frame->uc.tuc_osf_sigmask);
5401     __put_user(target_sigaltstack_used.ss_sp,
5402                &frame->uc.tuc_stack.ss_sp);
5403     __put_user(sas_ss_flags(env->ir[IR_SP]),
5404                &frame->uc.tuc_stack.ss_flags);
5405     __put_user(target_sigaltstack_used.ss_size,
5406                &frame->uc.tuc_stack.ss_size);
5407     setup_sigcontext(&frame->uc.tuc_mcontext, env, frame_addr, set);
5408     for (i = 0; i < TARGET_NSIG_WORDS; ++i) {
5409         __put_user(set->sig[i], &frame->uc.tuc_sigmask.sig[i]);
5410     }
5411
5412     if (ka->sa_restorer) {
5413         r26 = ka->sa_restorer;
5414     } else {
5415         __put_user(INSN_MOV_R30_R16, &frame->retcode[0]);
5416         __put_user(INSN_LDI_R0 + TARGET_NR_rt_sigreturn,
5417                    &frame->retcode[1]);
5418         __put_user(INSN_CALLSYS, &frame->retcode[2]);
5419         /* imb(); */
5420         r26 = frame_addr;
5421     }
5422
5423     if (err) {
5424     give_sigsegv:
5425        if (sig == TARGET_SIGSEGV) {
5426             ka->_sa_handler = TARGET_SIG_DFL;
5427         }
5428         force_sig(TARGET_SIGSEGV);
5429     }
5430
5431     env->ir[IR_RA] = r26;
5432     env->ir[IR_PV] = env->pc = ka->_sa_handler;
5433     env->ir[IR_A0] = sig;
5434     env->ir[IR_A1] = frame_addr + offsetof(struct target_rt_sigframe, info);
5435     env->ir[IR_A2] = frame_addr + offsetof(struct target_rt_sigframe, uc);
5436     env->ir[IR_SP] = frame_addr;
5437 }
5438
5439 long do_sigreturn(CPUAlphaState *env)
5440 {
5441     struct target_sigcontext *sc;
5442     abi_ulong sc_addr = env->ir[IR_A0];
5443     target_sigset_t target_set;
5444     sigset_t set;
5445
5446     if (!lock_user_struct(VERIFY_READ, sc, sc_addr, 1)) {
5447         goto badframe;
5448     }
5449
5450     target_sigemptyset(&target_set);
5451     __get_user(target_set.sig[0], &sc->sc_mask);
5452
5453     target_to_host_sigset_internal(&set, &target_set);
5454     do_sigprocmask(SIG_SETMASK, &set, NULL);
5455
5456     restore_sigcontext(env, sc);
5457     unlock_user_struct(sc, sc_addr, 0);
5458     return env->ir[IR_V0];
5459
5460  badframe:
5461     force_sig(TARGET_SIGSEGV);
5462 }
5463
5464 long do_rt_sigreturn(CPUAlphaState *env)
5465 {
5466     abi_ulong frame_addr = env->ir[IR_A0];
5467     struct target_rt_sigframe *frame;
5468     sigset_t set;
5469
5470     if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1)) {
5471         goto badframe;
5472     }
5473     target_to_host_sigset(&set, &frame->uc.tuc_sigmask);
5474     do_sigprocmask(SIG_SETMASK, &set, NULL);
5475
5476     restore_sigcontext(env, &frame->uc.tuc_mcontext);
5477     if (do_sigaltstack(frame_addr + offsetof(struct target_rt_sigframe,
5478                                              uc.tuc_stack),
5479                        0, env->ir[IR_SP]) == -EFAULT) {
5480         goto badframe;
5481     }
5482
5483     unlock_user_struct(frame, frame_addr, 0);
5484     return env->ir[IR_V0];
5485
5486
5487  badframe:
5488     unlock_user_struct(frame, frame_addr, 0);
5489     force_sig(TARGET_SIGSEGV);
5490 }
5491
5492 #else
5493
5494 static void setup_frame(int sig, struct target_sigaction *ka,
5495                         target_sigset_t *set, CPUArchState *env)
5496 {
5497     fprintf(stderr, "setup_frame: not implemented\n");
5498 }
5499
5500 static void setup_rt_frame(int sig, struct target_sigaction *ka,
5501                            target_siginfo_t *info,
5502                            target_sigset_t *set, CPUArchState *env)
5503 {
5504     fprintf(stderr, "setup_rt_frame: not implemented\n");
5505 }
5506
5507 long do_sigreturn(CPUArchState *env)
5508 {
5509     fprintf(stderr, "do_sigreturn: not implemented\n");
5510     return -TARGET_ENOSYS;
5511 }
5512
5513 long do_rt_sigreturn(CPUArchState *env)
5514 {
5515     fprintf(stderr, "do_rt_sigreturn: not implemented\n");
5516     return -TARGET_ENOSYS;
5517 }
5518
5519 #endif
5520
5521 void process_pending_signals(CPUArchState *cpu_env)
5522 {
5523     CPUState *cpu = ENV_GET_CPU(cpu_env);
5524     int sig;
5525     abi_ulong handler;
5526     sigset_t set, old_set;
5527     target_sigset_t target_old_set;
5528     struct emulated_sigtable *k;
5529     struct target_sigaction *sa;
5530     struct sigqueue *q;
5531     TaskState *ts = cpu->opaque;
5532
5533     if (!ts->signal_pending)
5534         return;
5535
5536     /* FIXME: This is not threadsafe.  */
5537     k = ts->sigtab;
5538     for(sig = 1; sig <= TARGET_NSIG; sig++) {
5539         if (k->pending)
5540             goto handle_signal;
5541         k++;
5542     }
5543     /* if no signal is pending, just return */
5544     ts->signal_pending = 0;
5545     return;
5546
5547  handle_signal:
5548 #ifdef DEBUG_SIGNAL
5549     fprintf(stderr, "qemu: process signal %d\n", sig);
5550 #endif
5551     /* dequeue signal */
5552     q = k->first;
5553     k->first = q->next;
5554     if (!k->first)
5555         k->pending = 0;
5556
5557     sig = gdb_handlesig(cpu, sig);
5558     if (!sig) {
5559         sa = NULL;
5560         handler = TARGET_SIG_IGN;
5561     } else {
5562         sa = &sigact_table[sig - 1];
5563         handler = sa->_sa_handler;
5564     }
5565
5566     if (ts->sigsegv_blocked && sig == TARGET_SIGSEGV) {
5567         /* Guest has blocked SIGSEGV but we got one anyway. Assume this
5568          * is a forced SIGSEGV (ie one the kernel handles via force_sig_info
5569          * because it got a real MMU fault), and treat as if default handler.
5570          */
5571         handler = TARGET_SIG_DFL;
5572     }
5573
5574     if (handler == TARGET_SIG_DFL) {
5575         /* default handler : ignore some signal. The other are job control or fatal */
5576         if (sig == TARGET_SIGTSTP || sig == TARGET_SIGTTIN || sig == TARGET_SIGTTOU) {
5577             kill(getpid(),SIGSTOP);
5578         } else if (sig != TARGET_SIGCHLD &&
5579                    sig != TARGET_SIGURG &&
5580                    sig != TARGET_SIGWINCH &&
5581                    sig != TARGET_SIGCONT) {
5582             force_sig(sig);
5583         }
5584     } else if (handler == TARGET_SIG_IGN) {
5585         /* ignore sig */
5586     } else if (handler == TARGET_SIG_ERR) {
5587         force_sig(sig);
5588     } else {
5589         /* compute the blocked signals during the handler execution */
5590         target_to_host_sigset(&set, &sa->sa_mask);
5591         /* SA_NODEFER indicates that the current signal should not be
5592            blocked during the handler */
5593         if (!(sa->sa_flags & TARGET_SA_NODEFER))
5594             sigaddset(&set, target_to_host_signal(sig));
5595
5596         /* block signals in the handler using Linux */
5597         do_sigprocmask(SIG_BLOCK, &set, &old_set);
5598         /* save the previous blocked signal state to restore it at the
5599            end of the signal execution (see do_sigreturn) */
5600         host_to_target_sigset_internal(&target_old_set, &old_set);
5601
5602         /* if the CPU is in VM86 mode, we restore the 32 bit values */
5603 #if defined(TARGET_I386) && !defined(TARGET_X86_64)
5604         {
5605             CPUX86State *env = cpu_env;
5606             if (env->eflags & VM_MASK)
5607                 save_v86_state(env);
5608         }
5609 #endif
5610         /* prepare the stack frame of the virtual CPU */
5611 #if defined(TARGET_ABI_MIPSN32) || defined(TARGET_ABI_MIPSN64)
5612         /* These targets do not have traditional signals.  */
5613         setup_rt_frame(sig, sa, &q->info, &target_old_set, cpu_env);
5614 #else
5615         if (sa->sa_flags & TARGET_SA_SIGINFO)
5616             setup_rt_frame(sig, sa, &q->info, &target_old_set, cpu_env);
5617         else
5618             setup_frame(sig, sa, &target_old_set, cpu_env);
5619 #endif
5620         if (sa->sa_flags & TARGET_SA_RESETHAND)
5621             sa->_sa_handler = TARGET_SIG_DFL;
5622     }
5623     if (q != &k->info)
5624         free_sigqueue(cpu_env, q);
5625 }
This page took 0.335836 seconds and 4 git commands to generate.