trap.c revision 1.106.6.1 1 /* $NetBSD: trap.c,v 1.106.6.1 2015/04/06 15:17:57 skrll Exp $ */
2
3 /*-
4 * Copyright (c) 2001, 2002 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Matthew Fredette.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 /* $OpenBSD: trap.c,v 1.30 2001/09/19 20:50:56 mickey Exp $ */
33
34 /*
35 * Copyright (c) 1998-2004 Michael Shalayeff
36 * All rights reserved.
37 *
38 * Redistribution and use in source and binary forms, with or without
39 * modification, are permitted provided that the following conditions
40 * are met:
41 * 1. Redistributions of source code must retain the above copyright
42 * notice, this list of conditions and the following disclaimer.
43 * 2. Redistributions in binary form must reproduce the above copyright
44 * notice, this list of conditions and the following disclaimer in the
45 * documentation and/or other materials provided with the distribution.
46 *
47 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
48 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
49 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
50 * IN NO EVENT SHALL THE AUTHOR OR HIS RELATIVES BE LIABLE FOR ANY DIRECT,
51 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
52 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
53 * SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
54 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
55 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
56 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
57 * THE POSSIBILITY OF SUCH DAMAGE.
58 */
59
60 #include <sys/cdefs.h>
61 __KERNEL_RCSID(0, "$NetBSD: trap.c,v 1.106.6.1 2015/04/06 15:17:57 skrll Exp $");
62
63 /* #define INTRDEBUG */
64 /* #define TRAPDEBUG */
65 /* #define USERTRACE */
66
67 #include "opt_kgdb.h"
68 #include "opt_ptrace.h"
69
70 #include <sys/param.h>
71 #include <sys/systm.h>
72 #include <sys/kernel.h>
73 #include <sys/syscall.h>
74 #include <sys/syscallvar.h>
75 #include <sys/mutex.h>
76 #include <sys/ktrace.h>
77 #include <sys/proc.h>
78 #include <sys/signalvar.h>
79 #include <sys/acct.h>
80 #include <sys/signal.h>
81 #include <sys/device.h>
82 #include <sys/kauth.h>
83 #include <sys/kmem.h>
84 #include <sys/userret.h>
85
86 #include <net/netisr.h>
87
88 #ifdef KGDB
89 #include <sys/kgdb.h>
90 #endif
91
92 #include <uvm/uvm.h>
93
94 #include <machine/iomod.h>
95 #include <machine/cpufunc.h>
96 #include <machine/reg.h>
97 #include <machine/autoconf.h>
98
99 #include <machine/db_machdep.h>
100
101 #include <hppa/hppa/machdep.h>
102
103 #include <ddb/db_output.h>
104 #include <ddb/db_interface.h>
105
106 #ifdef PTRACE
107 void ss_clear_breakpoints(struct lwp *l);
108 int ss_put_value(struct lwp *, vaddr_t, u_int);
109 int ss_get_value(struct lwp *, vaddr_t, u_int *);
110
111 /* single-step breakpoint */
112 #define SSBREAKPOINT (HPPA_BREAK_KERNEL | (HPPA_BREAK_SS << 13))
113
114 #endif
115
116 #if defined(DEBUG) || defined(DIAGNOSTIC)
117 /*
118 * 0x6fc1000 is a stwm r1, d(sr0, sp), which is the last
119 * instruction in the function prologue that gcc -O0 uses.
120 * When we have this instruction we know the relationship
121 * between the stack pointer and the gcc -O0 frame pointer
122 * (in r3, loaded with the initial sp) for the body of a
123 * function.
124 *
125 * If the given instruction is a stwm r1, d(sr0, sp) where
126 * d > 0, we evaluate to d, else we evaluate to zero.
127 */
128 #define STWM_R1_D_SR0_SP(inst) \
129 (((inst) & 0xffffc001) == 0x6fc10000 ? (((inst) & 0x00003ff) >> 1) : 0)
130 #endif /* DEBUG || DIAGNOSTIC */
131
132 const char *trap_type[] = {
133 "invalid",
134 "HPMC",
135 "power failure",
136 "recovery counter",
137 "external interrupt",
138 "LPMC",
139 "ITLB miss fault",
140 "instruction protection",
141 "Illegal instruction",
142 "break instruction",
143 "privileged operation",
144 "privileged register",
145 "overflow",
146 "conditional",
147 "assist exception",
148 "DTLB miss",
149 "ITLB non-access miss",
150 "DTLB non-access miss",
151 "data protection/rights/alignment",
152 "data break",
153 "TLB dirty",
154 "page reference",
155 "assist emulation",
156 "higher-priv transfer",
157 "lower-priv transfer",
158 "taken branch",
159 "data access rights",
160 "data protection",
161 "unaligned data ref",
162 };
163 int trap_types = __arraycount(trap_type);
164
165 uint8_t fpopmap[] = {
166 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00,
167 0x00, 0x0c, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00,
168 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
169 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
170 0x00, 0x00, 0x00, 0x26, 0x00, 0x00, 0x00, 0x00,
171 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
172 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
173 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
174 };
175
176 void pmap_hptdump(void);
177 void syscall(struct trapframe *, int *);
178
179 #if defined(DEBUG)
180 struct trapframe *sanity_frame;
181 struct lwp *sanity_lwp;
182 const char *sanity_string;
183 void frame_sanity_check(const char *, int, int, struct trapframe *,
184 struct lwp *);
185 #endif
186
187
188 #ifdef USERTRACE
189 /*
190 * USERTRACE is a crude facility that traces the PC of a single user process.
191 * This tracing is normally activated by the dispatching of a certain syscall
192 * with certain arguments - see the activation code in syscall().
193 */
194 static void user_backtrace(struct trapframe *, struct lwp *, int);
195 static void user_backtrace_raw(u_int, u_int);
196
197 u_int rctr_next_iioq;
198 #endif
199
200 static inline void
201 userret(struct lwp *l, register_t pc, u_quad_t oticks)
202 {
203 struct proc *p = l->l_proc;
204
205 if (l->l_md.md_astpending) {
206 l->l_md.md_astpending = 0;
207 //curcpu()->ci_data.cpu_nast++;
208
209 if (curcpu()->ci_want_resched)
210 preempt();
211 }
212
213 mi_userret(l);
214
215 /*
216 * If profiling, charge recent system time to the trapped pc.
217 */
218 if (p->p_stflag & PST_PROFIL) {
219 extern int psratio;
220
221 addupc_task(l, pc, (int)(p->p_sticks - oticks) * psratio);
222 }
223 }
224
225 /*
226 * This handles some messy kernel debugger details.
227 * It dispatches into either kgdb or DDB, and knows
228 * about some special things to do, like skipping over
229 * break instructions and how to really set up for
230 * a single-step.
231 */
232 #if defined(KGDB) || defined(DDB)
233 static int
234 trap_kdebug(int type, int code, struct trapframe *frame)
235 {
236 int handled;
237 u_int tf_iioq_head_old;
238 u_int tf_iioq_tail_old;
239
240 for (;;) {
241
242 /* This trap has not been handled. */
243 handled = 0;
244
245 /* Remember the instruction offset queue. */
246 tf_iioq_head_old = frame->tf_iioq_head;
247 tf_iioq_tail_old = frame->tf_iioq_tail;
248
249 #ifdef KGDB
250 /* Let KGDB handle it (if connected) */
251 if (!handled)
252 handled = kgdb_trap(type, frame);
253 #endif
254 #ifdef DDB
255 /* Let DDB handle it. */
256 if (!handled)
257 handled = kdb_trap(type, code, frame);
258 #endif
259
260 /* If this trap wasn't handled, return now. */
261 if (!handled)
262 return(0);
263
264 /*
265 * If the instruction offset queue head changed, but the offset
266 * queue tail didn't, assume that the user wants to jump to the
267 * head offset, and adjust the tail accordingly. This should
268 * fix the kgdb `jump' command, and can help DDB users who `set'
269 * the offset head but forget the tail.
270 */
271 if (frame->tf_iioq_head != tf_iioq_head_old &&
272 frame->tf_iioq_tail == tf_iioq_tail_old)
273 frame->tf_iioq_tail = frame->tf_iioq_head + 4;
274
275 /*
276 * This is some single-stepping support. If we're trying to
277 * step through a nullified instruction, just advance by hand
278 * and trap again. Otherwise, load the recovery counter with
279 * zero.
280 */
281 if (frame->tf_ipsw & PSW_R) {
282 #ifdef TRAPDEBUG
283 printf("(single stepping at head 0x%x tail 0x%x)\n",
284 frame->tf_iioq_head, frame->tf_iioq_tail);
285 #endif
286 if (frame->tf_ipsw & PSW_N) {
287 #ifdef TRAPDEBUG
288 printf("(single stepping past nullified)\n");
289 #endif
290
291 /* Advance the program counter. */
292 frame->tf_iioq_head = frame->tf_iioq_tail;
293 frame->tf_iioq_tail = frame->tf_iioq_head + 4;
294
295 /* Clear flags. */
296 frame->tf_ipsw &= ~(PSW_N|PSW_X|PSW_Y|PSW_Z|PSW_B|PSW_T|PSW_H|PSW_L);
297
298 /* Simulate another trap. */
299 type = T_RECOVERY;
300 continue;
301 }
302 frame->tf_rctr = 0;
303 }
304
305 /* We handled this trap. */
306 return (1);
307 }
308 /* NOTREACHED */
309 }
310 #else /* !KGDB && !DDB */
311 #define trap_kdebug(t, c, f) (0)
312 #endif /* !KGDB && !DDB */
313
314 #if defined(DEBUG) || defined(USERTRACE)
315 /*
316 * These functions give a crude usermode backtrace. They really only work when
317 * code has been compiled without optimization, as they assume a certain func-
318 * tion prologue sets up a frame pointer and stores the return pointer and arg-
319 * uments in it.
320 */
321 static void
322 user_backtrace_raw(u_int pc, u_int fp)
323 {
324 int frame_number;
325 int arg_number;
326
327 for (frame_number = 0;
328 frame_number < 100 && pc > HPPA_PC_PRIV_MASK && fp;
329 frame_number++) {
330
331 printf("%3d: pc=%08x%s fp=0x%08x", frame_number,
332 pc & ~HPPA_PC_PRIV_MASK, USERMODE(pc) ? " " : "**", fp);
333 for (arg_number = 0; arg_number < 4; arg_number++)
334 printf(" arg%d=0x%08x", arg_number,
335 (int) fuword(HPPA_FRAME_CARG(arg_number, fp)));
336 printf("\n");
337 pc = fuword(((register_t *) fp) - 5); /* fetch rp */
338 if (pc == -1) {
339 printf(" fuword for pc failed\n");
340 break;
341 }
342 fp = fuword(((register_t *) fp) + 0); /* fetch previous fp */
343 if (fp == -1) {
344 printf(" fuword for fp failed\n");
345 break;
346 }
347 }
348 printf(" backtrace stopped with pc %08x fp 0x%08x\n", pc, fp);
349 }
350
351 static void
352 user_backtrace(struct trapframe *tf, struct lwp *l, int type)
353 {
354 struct proc *p = l->l_proc;
355 u_int pc, fp, inst;
356
357 /*
358 * Display any trap type that we have.
359 */
360 if (type >= 0)
361 printf("pid %d (%s) trap #%d\n",
362 p->p_pid, p->p_comm, type & ~T_USER);
363
364 /*
365 * Assuming that the frame pointer in r3 is valid,
366 * dump out a stack trace.
367 */
368 fp = tf->tf_r3;
369 printf("pid %d (%s) backtrace, starting with fp 0x%08x\n",
370 p->p_pid, p->p_comm, fp);
371 user_backtrace_raw(tf->tf_iioq_head, fp);
372
373 /*
374 * In case the frame pointer in r3 is not valid, assuming the stack
375 * pointer is valid and the faulting function is a non-leaf, if we can
376 * find its prologue we can recover its frame pointer.
377 */
378 pc = tf->tf_iioq_head;
379 fp = tf->tf_sp - HPPA_FRAME_SIZE;
380 printf("pid %d (%s) backtrace, starting with sp 0x%08x pc 0x%08x\n",
381 p->p_pid, p->p_comm, tf->tf_sp, pc);
382 for (pc &= ~HPPA_PC_PRIV_MASK; pc > 0; pc -= sizeof(inst)) {
383 inst = fuword((register_t *) pc);
384 if (inst == -1) {
385 printf(" fuword for inst at pc %08x failed\n", pc);
386 break;
387 }
388 /* Check for the prologue instruction that sets sp. */
389 if (STWM_R1_D_SR0_SP(inst)) {
390 fp = tf->tf_sp - STWM_R1_D_SR0_SP(inst);
391 printf(" sp from fp at pc %08x: %08x\n", pc, inst);
392 break;
393 }
394 }
395 user_backtrace_raw(tf->tf_iioq_head, fp);
396 }
397 #endif /* DEBUG || USERTRACE */
398
399 #ifdef DEBUG
400 /*
401 * This sanity-checks a trapframe. It is full of various assumptions about
402 * what a healthy CPU state should be, with some documented elsewhere, some not.
403 */
404 void
405 frame_sanity_check(const char *func, int line, int type, struct trapframe *tf,
406 struct lwp *l)
407 {
408 #if 0
409 extern int kernel_text;
410 extern int etext;
411 #endif
412 struct cpu_info *ci = curcpu();
413
414 #define SANITY(e) \
415 do { \
416 if (sanity_frame == NULL && !(e)) { \
417 sanity_frame = tf; \
418 sanity_lwp = l; \
419 sanity_string = #e; \
420 } \
421 } while (/* CONSTCOND */ 0)
422
423 KASSERT(l != NULL);
424 SANITY((tf->tf_ipsw & ci->ci_psw) == ci->ci_psw);
425 SANITY((ci->ci_psw & PSW_I) == 0 || tf->tf_eiem != 0);
426 if (tf->tf_iisq_head == HPPA_SID_KERNEL) {
427 vaddr_t minsp, maxsp, uv;
428
429 uv = uvm_lwp_getuarea(l);
430
431 /*
432 * If the trap happened in the gateway page, we take the easy
433 * way out and assume that the trapframe is okay.
434 */
435 if ((tf->tf_iioq_head & ~PAGE_MASK) == SYSCALLGATE)
436 goto out;
437
438 SANITY(!USERMODE(tf->tf_iioq_head));
439 SANITY(!USERMODE(tf->tf_iioq_tail));
440
441 /*
442 * Don't check the instruction queues or stack on interrupts
443 * as we could be be in the sti code (outside normal kernel
444 * text) or switching LWPs (curlwp and sp are not in sync)
445 */
446 if ((type & ~T_USER) == T_INTERRUPT)
447 goto out;
448 #if 0
449 SANITY(tf->tf_iioq_head >= (u_int) &kernel_text);
450 SANITY(tf->tf_iioq_head < (u_int) &etext);
451 SANITY(tf->tf_iioq_tail >= (u_int) &kernel_text);
452 SANITY(tf->tf_iioq_tail < (u_int) &etext);
453 #endif
454
455 maxsp = uv + USPACE + PAGE_SIZE;
456 minsp = uv + PAGE_SIZE;
457
458 SANITY(tf->tf_sp >= minsp && tf->tf_sp < maxsp);
459 } else {
460 struct pcb *pcb = lwp_getpcb(l);
461
462 SANITY(USERMODE(tf->tf_iioq_head));
463 SANITY(USERMODE(tf->tf_iioq_tail));
464 SANITY(tf->tf_cr30 == (u_int)pcb->pcb_fpregs);
465 }
466 #undef SANITY
467 out:
468 if (sanity_frame == tf) {
469 printf("insanity: '%s' at %s:%d type 0x%x tf %p lwp %p "
470 "sp 0x%x pc 0x%x\n",
471 sanity_string, func, line, type, sanity_frame, sanity_lwp,
472 tf->tf_sp, tf->tf_iioq_head);
473 (void) trap_kdebug(T_IBREAK, 0, tf);
474 sanity_frame = NULL;
475 sanity_lwp = NULL;
476 }
477 }
478 #endif /* DEBUG */
479
480 void
481 trap(int type, struct trapframe *frame)
482 {
483 struct lwp *l;
484 struct proc *p;
485 struct pcb *pcb;
486 vaddr_t va;
487 struct vm_map *map;
488 struct vmspace *vm;
489 vm_prot_t vftype;
490 pa_space_t space;
491 ksiginfo_t ksi;
492 u_int opcode, onfault;
493 int ret;
494 const char *tts = "reserved";
495 int trapnum;
496 #ifdef DIAGNOSTIC
497 extern int emergency_stack_start, emergency_stack_end;
498 struct cpu_info *ci = curcpu();
499 int oldcpl = ci->ci_cpl;
500 #endif
501
502 trapnum = type & ~T_USER;
503 opcode = frame->tf_iir;
504
505 if (trapnum <= T_EXCEPTION || trapnum == T_HIGHERPL ||
506 trapnum == T_LOWERPL || trapnum == T_TAKENBR ||
507 trapnum == T_IDEBUG || trapnum == T_PERFMON) {
508 va = frame->tf_iioq_head;
509 space = frame->tf_iisq_head;
510 vftype = VM_PROT_EXECUTE;
511 } else {
512 va = frame->tf_ior;
513 space = frame->tf_isr;
514 vftype = inst_store(opcode) ? VM_PROT_WRITE : VM_PROT_READ;
515 }
516
517 KASSERT(curlwp != NULL);
518 l = curlwp;
519 p = l->l_proc;
520 if ((type & T_USER) != 0)
521 LWP_CACHE_CREDS(l, p);
522
523 #ifdef DIAGNOSTIC
524 /*
525 * If we are on the emergency stack, then we either got
526 * a fault on the kernel stack, or we're just handling
527 * a trap for the machine check handler (which also
528 * runs on the emergency stack).
529 *
530 * We *very crudely* differentiate between the two cases
531 * by checking the faulting instruction: if it is the
532 * function prologue instruction that stores the old
533 * frame pointer and updates the stack pointer, we assume
534 * that we faulted on the kernel stack.
535 *
536 * In this case, not completing that instruction will
537 * probably confuse backtraces in kgdb/ddb. Completing
538 * it would be difficult, because we already faulted on
539 * that part of the stack, so instead we fix up the
540 * frame as if the function called has just returned.
541 * This has peculiar knowledge about what values are in
542 * what registers during the "normal gcc -g" prologue.
543 */
544 if (&type >= &emergency_stack_start &&
545 &type < &emergency_stack_end &&
546 type != T_IBREAK && STWM_R1_D_SR0_SP(opcode)) {
547 /* Restore the caller's frame pointer. */
548 frame->tf_r3 = frame->tf_r1;
549 /* Restore the caller's instruction offsets. */
550 frame->tf_iioq_head = frame->tf_rp;
551 frame->tf_iioq_tail = frame->tf_iioq_head + 4;
552 goto dead_end;
553 }
554 #endif /* DIAGNOSTIC */
555
556 #ifdef DEBUG
557 frame_sanity_check(__func__, __LINE__, type, frame, l);
558 #endif /* DEBUG */
559
560 if (frame->tf_flags & TFF_LAST)
561 l->l_md.md_regs = frame;
562
563 if (trapnum <= trap_types)
564 tts = trap_type[trapnum];
565
566 #ifdef TRAPDEBUG
567 if (trapnum != T_INTERRUPT && trapnum != T_IBREAK)
568 printf("trap: %d, %s for %x:%lx at %x:%x, fp=%p, rp=%x\n",
569 type, tts, space, va, frame->tf_iisq_head,
570 frame->tf_iioq_head, frame, frame->tf_rp);
571 else if (trapnum == T_IBREAK)
572 printf("trap: break instruction %x:%x at %x:%x, fp=%p\n",
573 break5(opcode), break13(opcode),
574 frame->tf_iisq_head, frame->tf_iioq_head, frame);
575
576 {
577 extern int etext;
578 if (frame < (struct trapframe *)&etext) {
579 printf("trap: bogus frame ptr %p\n", frame);
580 goto dead_end;
581 }
582 }
583 #endif
584
585 pcb = lwp_getpcb(l);
586
587 /* If this is a trap, not an interrupt, reenable interrupts. */
588 if (trapnum != T_INTERRUPT) {
589 curcpu()->ci_data.cpu_ntrap++;
590 mtctl(frame->tf_eiem, CR_EIEM);
591 }
592
593 switch (type) {
594 case T_NONEXIST:
595 case T_NONEXIST|T_USER:
596 #if !defined(DDB) && !defined(KGDB)
597 /* we've got screwed up by the central scrutinizer */
598 panic ("trap: elvis has just left the building!");
599 break;
600 #else
601 goto dead_end;
602 #endif
603 case T_RECOVERY|T_USER:
604 #ifdef USERTRACE
605 for (;;) {
606 if (frame->tf_iioq_head != rctr_next_iioq)
607 printf("-%08x\nr %08x",
608 rctr_next_iioq - 4,
609 frame->tf_iioq_head);
610 rctr_next_iioq = frame->tf_iioq_head + 4;
611 if (frame->tf_ipsw & PSW_N) {
612 /* Advance the program counter. */
613 frame->tf_iioq_head = frame->tf_iioq_tail;
614 frame->tf_iioq_tail = frame->tf_iioq_head + 4;
615 /* Clear flags. */
616 frame->tf_ipsw &= ~(PSW_N|PSW_X|PSW_Y|PSW_Z|PSW_B|PSW_T|PSW_H|PSW_L);
617 /* Simulate another trap. */
618 continue;
619 }
620 break;
621 }
622 frame->tf_rctr = 0;
623 break;
624 #endif /* USERTRACE */
625 case T_RECOVERY:
626 #if !defined(DDB) && !defined(KGDB)
627 /* XXX will implement later */
628 printf ("trap: handicapped");
629 break;
630 #else
631 goto dead_end;
632 #endif
633
634 case T_EMULATION | T_USER:
635 hppa_fpu_emulate(frame, l, opcode);
636 break;
637
638 case T_DATALIGN:
639 onfault = pcb->pcb_onfault;
640 if (onfault) {
641 ret = EFAULT;
642 do_onfault:
643 frame->tf_iioq_head = onfault;
644 frame->tf_iioq_tail = frame->tf_iioq_head + 4;
645 frame->tf_ret0 = ret;
646 break;
647 }
648 /*FALLTHROUGH*/
649
650 #ifdef DIAGNOSTIC
651 /* these just can't happen ever */
652 case T_PRIV_OP:
653 case T_PRIV_REG:
654 /* these just can't make it to the trap() ever */
655 case T_HPMC:
656 case T_HPMC | T_USER:
657 case T_EMULATION:
658 case T_EXCEPTION:
659 #endif
660 case T_IBREAK:
661 case T_DBREAK:
662 dead_end:
663 if (type & T_USER) {
664 #ifdef DEBUG
665 user_backtrace(frame, l, type);
666 #endif
667 KSI_INIT_TRAP(&ksi);
668 ksi.ksi_signo = SIGILL;
669 ksi.ksi_code = ILL_ILLTRP;
670 ksi.ksi_trap = type;
671 ksi.ksi_addr = (void *)frame->tf_iioq_head;
672 trapsignal(l, &ksi);
673 break;
674 }
675 if (trap_kdebug(type, va, frame))
676 return;
677 else if (type == T_DATALIGN)
678 panic ("trap: %s at 0x%x", tts, (u_int) va);
679 else
680 panic ("trap: no debugger for \"%s\" (%d)", tts, type);
681 break;
682
683 case T_IBREAK | T_USER:
684 case T_DBREAK | T_USER:
685 KSI_INIT_TRAP(&ksi);
686 ksi.ksi_signo = SIGTRAP;
687 ksi.ksi_code = TRAP_TRACE;
688 ksi.ksi_trap = trapnum;
689 ksi.ksi_addr = (void *)(frame->tf_iioq_head & ~HPPA_PC_PRIV_MASK);
690 #ifdef PTRACE
691 ss_clear_breakpoints(l);
692 if (opcode == SSBREAKPOINT)
693 ksi.ksi_code = TRAP_BRKPT;
694 #endif
695 /* pass to user debugger */
696 trapsignal(l, &ksi);
697 break;
698
699 #ifdef PTRACE
700 case T_TAKENBR | T_USER:
701 ss_clear_breakpoints(l);
702
703 KSI_INIT_TRAP(&ksi);
704 ksi.ksi_signo = SIGTRAP;
705 ksi.ksi_code = TRAP_TRACE;
706 ksi.ksi_trap = trapnum;
707 ksi.ksi_addr = (void *)(frame->tf_iioq_head & ~HPPA_PC_PRIV_MASK);
708
709 /* pass to user debugger */
710 trapsignal(l, &ksi);
711 break;
712 #endif
713
714 case T_EXCEPTION | T_USER: { /* co-proc assist trap */
715 uint64_t *fpp;
716 uint32_t *pex, ex, inst;
717 int i;
718
719 hppa_fpu_flush(l);
720 fpp = (uint64_t *)pcb->pcb_fpregs;
721
722 /* skip the status register */
723 pex = (uint32_t *)&fpp[0];
724 pex++;
725
726 /* loop through the exception registers */
727 for (i = 1; i < 8 && !*pex; i++, pex++)
728 ;
729 KASSERT(i < 8);
730 ex = *pex;
731 *pex = 0;
732
733 /* reset the trap flag, as if there was none */
734 fpp[0] &= ~(((uint64_t)HPPA_FPU_T) << 32);
735
736 /* emulate the instruction */
737 inst = ((uint32_t)fpopmap[ex >> 26] << 26) | (ex & 0x03ffffff);
738 hppa_fpu_emulate(frame, l, inst);
739 }
740 break;
741
742 case T_OVERFLOW | T_USER:
743 KSI_INIT_TRAP(&ksi);
744 ksi.ksi_signo = SIGFPE;
745 ksi.ksi_code = SI_NOINFO;
746 ksi.ksi_trap = type;
747 ksi.ksi_addr = (void *)va;
748 trapsignal(l, &ksi);
749 break;
750
751 case T_CONDITION | T_USER:
752 KSI_INIT_TRAP(&ksi);
753 ksi.ksi_signo = SIGFPE;
754 ksi.ksi_code = FPE_INTDIV;
755 ksi.ksi_trap = type;
756 ksi.ksi_addr = (void *)va;
757 trapsignal(l, &ksi);
758 break;
759
760 case T_ILLEGAL | T_USER:
761 #ifdef DEBUG
762 user_backtrace(frame, l, type);
763 #endif
764 KSI_INIT_TRAP(&ksi);
765 ksi.ksi_signo = SIGILL;
766 ksi.ksi_code = ILL_ILLOPC;
767 ksi.ksi_trap = type;
768 ksi.ksi_addr = (void *)va;
769 trapsignal(l, &ksi);
770 break;
771
772 case T_PRIV_OP | T_USER:
773 #ifdef DEBUG
774 user_backtrace(frame, l, type);
775 #endif
776 KSI_INIT_TRAP(&ksi);
777 ksi.ksi_signo = SIGILL;
778 ksi.ksi_code = ILL_PRVOPC;
779 ksi.ksi_trap = type;
780 ksi.ksi_addr = (void *)va;
781 trapsignal(l, &ksi);
782 break;
783
784 case T_PRIV_REG | T_USER:
785 #ifdef DEBUG
786 user_backtrace(frame, l, type);
787 #endif
788 KSI_INIT_TRAP(&ksi);
789 ksi.ksi_signo = SIGILL;
790 ksi.ksi_code = ILL_PRVREG;
791 ksi.ksi_trap = type;
792 ksi.ksi_addr = (void *)va;
793 trapsignal(l, &ksi);
794 break;
795
796 /* these should never got here */
797 case T_HIGHERPL | T_USER:
798 case T_LOWERPL | T_USER:
799 KSI_INIT_TRAP(&ksi);
800 ksi.ksi_signo = SIGSEGV;
801 ksi.ksi_code = SEGV_ACCERR;
802 ksi.ksi_trap = type;
803 ksi.ksi_addr = (void *)va;
804 trapsignal(l, &ksi);
805 break;
806
807 case T_IPROT | T_USER:
808 case T_DPROT | T_USER:
809 KSI_INIT_TRAP(&ksi);
810 ksi.ksi_signo = SIGSEGV;
811 ksi.ksi_code = SEGV_ACCERR;
812 ksi.ksi_trap = type;
813 ksi.ksi_addr = (void *)va;
814 trapsignal(l, &ksi);
815 break;
816
817 case T_DATACC: case T_USER | T_DATACC:
818 case T_ITLBMISS: case T_USER | T_ITLBMISS:
819 case T_DTLBMISS: case T_USER | T_DTLBMISS:
820 case T_ITLBMISSNA: case T_USER | T_ITLBMISSNA:
821 case T_DTLBMISSNA: case T_USER | T_DTLBMISSNA:
822 case T_TLB_DIRTY: case T_USER | T_TLB_DIRTY:
823 vm = p->p_vmspace;
824
825 if (!vm) {
826 #ifdef TRAPDEBUG
827 printf("trap: no vm, p=%p\n", p);
828 #endif
829 goto dead_end;
830 }
831
832 /*
833 * it could be a kernel map for exec_map faults
834 */
835 if (!(type & T_USER) && space == HPPA_SID_KERNEL)
836 map = kernel_map;
837 else {
838 map = &vm->vm_map;
839 }
840
841 va = trunc_page(va);
842
843 if (map->pmap->pm_space != space) {
844 #ifdef TRAPDEBUG
845 printf("trap: space mismatch %d != %d\n",
846 space, map->pmap->pm_space);
847 #endif
848 /* actually dump the user, crap the kernel */
849 goto dead_end;
850 }
851
852 /* Never call uvm_fault in interrupt context. */
853 KASSERT(curcpu()->ci_cpl == 0);
854
855 onfault = pcb->pcb_onfault;
856 pcb->pcb_onfault = 0;
857 ret = uvm_fault(map, va, vftype);
858 pcb->pcb_onfault = onfault;
859
860 #ifdef TRAPDEBUG
861 printf("uvm_fault(%p, %x, %d)=%d\n",
862 map, (u_int)va, vftype, ret);
863 #endif
864
865 /*
866 * If this was a stack access we keep track of the maximum
867 * accessed stack size. Also, if uvm_fault gets a protection
868 * failure it is due to accessing the stack region outside
869 * the current limit and we need to reflect that as an access
870 * error.
871 */
872 if (map != kernel_map && va >= (vaddr_t)vm->vm_minsaddr) {
873 if (ret == 0)
874 uvm_grow(l->l_proc, va);
875 else if (ret == EACCES)
876 ret = EFAULT;
877 }
878
879 if (ret != 0) {
880 if (type & T_USER) {
881 #ifdef DEBUG
882 user_backtrace(frame, l, type);
883 #endif
884 KSI_INIT_TRAP(&ksi);
885 switch (ret) {
886 case EACCES:
887 ksi.ksi_signo = SIGSEGV;
888 ksi.ksi_code = SEGV_ACCERR;
889 break;
890 case ENOMEM:
891 ksi.ksi_signo = SIGKILL;
892 printf("UVM: pid %d (%s), uid %d "
893 "killed: out of swap\n",
894 p->p_pid, p->p_comm,
895 l->l_cred ?
896 kauth_cred_geteuid(l->l_cred)
897 : -1);
898 break;
899 case EINVAL:
900 ksi.ksi_signo = SIGBUS;
901 ksi.ksi_code = BUS_ADRERR;
902 break;
903 default:
904 ksi.ksi_signo = SIGSEGV;
905 ksi.ksi_code = SEGV_MAPERR;
906 break;
907 }
908 ksi.ksi_trap = type;
909 ksi.ksi_addr = (void *)va;
910 trapsignal(l, &ksi);
911 } else {
912 if (onfault) {
913 goto do_onfault;
914 }
915 panic("trap: uvm_fault(%p, %lx, %d): %d",
916 map, va, vftype, ret);
917 }
918 } else if ((type & T_USER) == 0) {
919 extern char ucas_ras_start[];
920 extern char ucas_ras_end[];
921
922 if (frame->tf_iioq_head > (u_int)ucas_ras_start &&
923 frame->tf_iioq_head < (u_int)ucas_ras_end) {
924 frame->tf_iioq_head = (u_int)ucas_ras_start;
925 frame->tf_iioq_tail = (u_int)ucas_ras_start + 4;
926 }
927 }
928 break;
929
930 case T_DATALIGN | T_USER:
931 #ifdef DEBUG
932 user_backtrace(frame, l, type);
933 #endif
934 KSI_INIT_TRAP(&ksi);
935 ksi.ksi_signo = SIGBUS;
936 ksi.ksi_code = BUS_ADRALN;
937 ksi.ksi_trap = type;
938 ksi.ksi_addr = (void *)va;
939 trapsignal(l, &ksi);
940 break;
941
942 case T_INTERRUPT:
943 case T_INTERRUPT|T_USER:
944 hppa_intr(frame);
945 mtctl(frame->tf_eiem, CR_EIEM);
946 break;
947
948 case T_LOWERPL:
949 case T_DPROT:
950 case T_IPROT:
951 case T_OVERFLOW:
952 case T_CONDITION:
953 case T_ILLEGAL:
954 case T_HIGHERPL:
955 case T_TAKENBR:
956 case T_POWERFAIL:
957 case T_LPMC:
958 case T_PAGEREF:
959 case T_DATAPID: case T_DATAPID | T_USER:
960 if (0 /* T-chip */) {
961 break;
962 }
963 /* FALLTHROUGH to unimplemented */
964 default:
965 panic ("trap: unimplemented \'%s\' (%d)", tts, type);
966 }
967
968 #ifdef DIAGNOSTIC
969 if (ci->ci_cpl != oldcpl)
970 printf("WARNING: SPL (%d) NOT LOWERED ON TRAP (%d) EXIT\n",
971 ci->ci_cpl, trapnum);
972 #endif
973
974 if (type & T_USER)
975 userret(l, l->l_md.md_regs->tf_iioq_head, 0);
976
977 #ifdef DEBUG
978 frame_sanity_check(__func__, __LINE__, type, frame, l);
979 if (frame->tf_flags & TFF_LAST && (curlwp->l_flag & LW_IDLE) == 0)
980 frame_sanity_check(__func__, __LINE__, type,
981 curlwp->l_md.md_regs, curlwp);
982 #endif /* DEBUG */
983 }
984
985 void
986 child_return(void *arg)
987 {
988 struct lwp *l = arg;
989
990 /*
991 * Return values in the frame set by cpu_lwp_fork().
992 */
993
994 userret(l, l->l_md.md_regs->tf_iioq_head, 0);
995 ktrsysret(SYS_fork, 0, 0);
996 #ifdef DEBUG
997 frame_sanity_check(__func__, __LINE__, 0, l->l_md.md_regs, l);
998 #endif /* DEBUG */
999 }
1000
1001 /*
1002 * Process the tail end of a posix_spawn() for the child.
1003 */
1004 void
1005 cpu_spawn_return(struct lwp *l)
1006 {
1007
1008 userret(l, l->l_md.md_regs->tf_iioq_head, 0);
1009 #ifdef DEBUG
1010 frame_sanity_check(__func__, __LINE__, 0, l->l_md.md_regs, l);
1011 #endif /* DEBUG */
1012 }
1013
1014 #ifdef PTRACE
1015
1016 #include <sys/ptrace.h>
1017
1018 int
1019 ss_get_value(struct lwp *l, vaddr_t addr, u_int *value)
1020 {
1021 struct uio uio;
1022 struct iovec iov;
1023
1024 iov.iov_base = (void *)value;
1025 iov.iov_len = sizeof(u_int);
1026 uio.uio_iov = &iov;
1027 uio.uio_iovcnt = 1;
1028 uio.uio_offset = (off_t)addr;
1029 uio.uio_resid = sizeof(u_int);
1030 uio.uio_rw = UIO_READ;
1031 UIO_SETUP_SYSSPACE(&uio);
1032
1033 return (process_domem(curlwp, l, &uio));
1034 }
1035
1036 int
1037 ss_put_value(struct lwp *l, vaddr_t addr, u_int value)
1038 {
1039 struct uio uio;
1040 struct iovec iov;
1041
1042 iov.iov_base = (void *)&value;
1043 iov.iov_len = sizeof(u_int);
1044 uio.uio_iov = &iov;
1045 uio.uio_iovcnt = 1;
1046 uio.uio_offset = (off_t)addr;
1047 uio.uio_resid = sizeof(u_int);
1048 uio.uio_rw = UIO_WRITE;
1049 UIO_SETUP_SYSSPACE(&uio);
1050
1051 return (process_domem(curlwp, l, &uio));
1052 }
1053
1054 void
1055 ss_clear_breakpoints(struct lwp *l)
1056 {
1057 /* Restore origional instructions. */
1058 if (l->l_md.md_bpva != 0) {
1059 ss_put_value(l, l->l_md.md_bpva, l->l_md.md_bpsave[0]);
1060 ss_put_value(l, l->l_md.md_bpva + 4, l->l_md.md_bpsave[1]);
1061 l->l_md.md_bpva = 0;
1062 }
1063 }
1064
1065
1066 int
1067 process_sstep(struct lwp *l, int sstep)
1068 {
1069 struct trapframe *tf = l->l_md.md_regs;
1070 int error;
1071
1072 ss_clear_breakpoints(l);
1073
1074 /* We're continuing... */
1075 if (sstep == 0) {
1076 tf->tf_ipsw &= ~PSW_T;
1077 return 0;
1078 }
1079
1080 /*
1081 * Don't touch the syscall gateway page. Instead, insert a
1082 * breakpoint where we're supposed to return.
1083 */
1084 if ((tf->tf_iioq_tail & ~PAGE_MASK) == SYSCALLGATE)
1085 l->l_md.md_bpva = tf->tf_r31 & ~HPPA_PC_PRIV_MASK;
1086 else
1087 l->l_md.md_bpva = tf->tf_iioq_tail & ~HPPA_PC_PRIV_MASK;
1088
1089 error = ss_get_value(l, l->l_md.md_bpva, &l->l_md.md_bpsave[0]);
1090 if (error)
1091 return error;
1092 error = ss_get_value(l, l->l_md.md_bpva + 4, &l->l_md.md_bpsave[1]);
1093 if (error)
1094 return error;
1095
1096 error = ss_put_value(l, l->l_md.md_bpva, SSBREAKPOINT);
1097 if (error)
1098 return error;
1099 error = ss_put_value(l, l->l_md.md_bpva + 4, SSBREAKPOINT);
1100 if (error)
1101 return error;
1102
1103 if ((tf->tf_iioq_tail & ~PAGE_MASK) == SYSCALLGATE)
1104 tf->tf_ipsw &= ~PSW_T;
1105 else
1106 tf->tf_ipsw |= PSW_T;
1107
1108 return 0;
1109 }
1110 #endif
1111
1112
1113 /*
1114 * call actual syscall routine
1115 * from the low-level syscall handler:
1116 * - all HPPA_FRAME_NARGS syscall's arguments supposed to be copied onto
1117 * our stack, this wins compared to copyin just needed amount anyway
1118 * - register args are copied onto stack too
1119 */
1120 void
1121 syscall(struct trapframe *frame, int *args)
1122 {
1123 struct lwp *l;
1124 struct proc *p;
1125 const struct sysent *callp;
1126 size_t nargs64;
1127 int nsys, code, error;
1128 int tmp;
1129 int rval[2];
1130 #ifdef DIAGNOSTIC
1131 struct cpu_info *ci = curcpu();
1132 int oldcpl = ci->ci_cpl;
1133 #endif
1134
1135 curcpu()->ci_data.cpu_nsyscall++;
1136
1137 #ifdef DEBUG
1138 frame_sanity_check(__func__, __LINE__, 0, frame, curlwp);
1139 #endif /* DEBUG */
1140
1141 if (!USERMODE(frame->tf_iioq_head))
1142 panic("syscall");
1143
1144 KASSERT(curlwp != NULL);
1145 l = curlwp;
1146 p = l->l_proc;
1147 l->l_md.md_regs = frame;
1148 nsys = p->p_emul->e_nsysent;
1149 callp = p->p_emul->e_sysent;
1150 code = frame->tf_t1;
1151 LWP_CACHE_CREDS(l, p);
1152
1153 /*
1154 * Restarting a system call is touchy on the HPPA, because syscall
1155 * arguments are passed in registers and the program counter of the
1156 * syscall "point" isn't easily divined.
1157 *
1158 * We handle the first problem by assuming that we will have to restart
1159 * this system call, so we stuff the first four words of the original
1160 * arguments back into the frame as arg0...arg3, which is where we
1161 * found them in the first place. Any further arguments are (still) on
1162 * the user's stack and the syscall code will fetch them from there
1163 * (again).
1164 *
1165 * The program counter problem is addressed below.
1166 */
1167 frame->tf_arg0 = args[0];
1168 frame->tf_arg1 = args[1];
1169 frame->tf_arg2 = args[2];
1170 frame->tf_arg3 = args[3];
1171
1172 /*
1173 * Some special handling for the syscall(2) and
1174 * __syscall(2) system calls.
1175 */
1176 switch (code) {
1177 case SYS_syscall:
1178 code = *args;
1179 args += 1;
1180 break;
1181 case SYS___syscall:
1182 if (callp != sysent)
1183 break;
1184 /*
1185 * NB: even though __syscall(2) takes a quad_t containing the
1186 * system call number, because our argument copying word-swaps
1187 * 64-bit arguments, the least significant word of that quad_t
1188 * is the first word in the argument array.
1189 */
1190 code = *args;
1191 args += 2;
1192 }
1193
1194 /*
1195 * Stacks growing from lower addresses to higher addresses are not
1196 * really such a good idea, because it makes it impossible to overlay a
1197 * struct on top of C stack arguments (the arguments appear in
1198 * reversed order).
1199 *
1200 * You can do the obvious thing (as locore.S does) and copy argument
1201 * words one by one, laying them out in the "right" order in the dest-
1202 * ination buffer, but this ends up word-swapping multi-word arguments
1203 * (like off_t).
1204 *
1205 * FIXME - this works only on native binaries and
1206 * will probably screw up any and all emulation.
1207 *
1208 */
1209
1210 if (code < 0 || code >= nsys)
1211 callp += p->p_emul->e_nosys; /* bad syscall # */
1212 else
1213 callp += code;
1214
1215 nargs64 = SYCALL_NARGS64(callp);
1216 if (nargs64 != 0) {
1217 size_t nargs = callp->sy_narg;
1218
1219 for (size_t i = 0; i < nargs + nargs64;) {
1220 if (SYCALL_ARG_64_P(callp, i)) {
1221 tmp = args[i];
1222 args[i] = args[i + 1];
1223 args[i + 1] = tmp;
1224 i += 2;
1225 } else
1226 i++;
1227 }
1228 }
1229
1230 #ifdef USERTRACE
1231 if (0) {
1232 user_backtrace(frame, l, -1);
1233 frame->tf_ipsw |= PSW_R;
1234 frame->tf_rctr = 0;
1235 printf("r %08x", frame->tf_iioq_head);
1236 rctr_next_iioq = frame->tf_iioq_head + 4;
1237 }
1238 #endif
1239
1240 error = sy_invoke(callp, l, args, rval, code);
1241
1242 switch (error) {
1243 case 0:
1244 l = curlwp; /* changes on exec() */
1245 frame = l->l_md.md_regs;
1246 frame->tf_ret0 = rval[0];
1247 frame->tf_ret1 = rval[1];
1248 frame->tf_t1 = 0;
1249 break;
1250 case ERESTART:
1251 /*
1252 * Now we have to wind back the instruction offset queue to the
1253 * point where the system call will be made again. This is
1254 * inherently tied to the SYSCALL macro.
1255 *
1256 * Currently, the part of the SYSCALL macro that we want to re-
1257 * run reads as:
1258 *
1259 * ldil L%SYSCALLGATE, r1
1260 * ble 4(srX, r1)
1261 * ldi __CONCAT(SYS_,x), t1
1262 * comb,<> %r0, %t1, __cerror
1263 *
1264 * And our offset queue head points to the comb instruction.
1265 * So we need to subtract twelve to reach the ldil.
1266 */
1267 frame->tf_iioq_head -= 12;
1268 frame->tf_iioq_tail = frame->tf_iioq_head + 4;
1269 break;
1270 case EJUSTRETURN:
1271 p = curproc;
1272 break;
1273 default:
1274 if (p->p_emul->e_errno)
1275 error = p->p_emul->e_errno[error];
1276 frame->tf_t1 = error;
1277 break;
1278 }
1279
1280 userret(l, frame->tf_iioq_head, 0);
1281
1282 #ifdef DIAGNOSTIC
1283 if (ci->ci_cpl != oldcpl) {
1284 printf("WARNING: SPL (0x%x) NOT LOWERED ON "
1285 "syscall(0x%x, 0x%x, 0x%x, 0x%x...) EXIT, PID %d\n",
1286 ci->ci_cpl, code, args[0], args[1], args[2], p->p_pid);
1287 ci->ci_cpl = oldcpl;
1288 }
1289 #endif
1290
1291 #ifdef DEBUG
1292 frame_sanity_check(__func__, __LINE__, 0, frame, l);
1293 #endif /* DEBUG */
1294 }
1295
1296 /*
1297 * Start a new LWP
1298 */
1299 void
1300 startlwp(void *arg)
1301 {
1302 ucontext_t *uc = arg;
1303 lwp_t *l = curlwp;
1304 int error __diagused;
1305
1306 error = cpu_setmcontext(l, &uc->uc_mcontext, uc->uc_flags);
1307 KASSERT(error == 0);
1308
1309 kmem_free(uc, sizeof(ucontext_t));
1310 userret(l, l->l_md.md_regs->tf_iioq_head, 0);
1311 }
1312