Make HW trap reflection more arch-independent
authorBarret Rhoden <brho@cs.berkeley.edu>
Thu, 21 Jan 2016 19:44:08 +0000 (14:44 -0500)
committerBarret Rhoden <brho@cs.berkeley.edu>
Tue, 2 Feb 2016 22:43:52 +0000 (17:43 -0500)
This isn't perfect, since the list of traps is somewhat arch-dependent, but
it's a little better.  For the most part, we're probably only ever going to
handle certain common traps, and I'd like to avoid duplicate code.

If an architecture is unable to produce certain traps, then they can just
pick an unused trap number.  So long as they are all distinct, the switch
statement will be fine.

Signed-off-by: Barret Rhoden <brho@cs.berkeley.edu>
user/parlib/include/riscv/trap.h
user/parlib/include/x86/trap.h
user/pthread/pthread.c

index e739f3d..7a4060e 100644 (file)
 
 __BEGIN_DECLS
 
+#error fix these numbers
+
+#define HW_TRAP_DIV_ZERO               0
+#define HW_TRAP_GP_FAULT               1
+#define HW_TRAP_PAGE_FAULT             2
+
 #error implement these
 static bool has_refl_fault(struct user_context *ctx)
 {
index 07e580c..541fd04 100644 (file)
 
 __BEGIN_DECLS
 
+#define HW_TRAP_DIV_ZERO               0
+#define HW_TRAP_GP_FAULT               13
+#define HW_TRAP_PAGE_FAULT             14
+
 static bool has_refl_fault(struct user_context *ctx)
 {
        switch (ctx->type) {
index 9c69da8..bc71697 100644 (file)
@@ -16,6 +16,7 @@
 #include <parlib/event.h>
 #include <parlib/ucq.h>
 #include <parlib/signal.h>
+#include <parlib/arch/trap.h>
 
 struct pthread_queue ready_queue = TAILQ_HEAD_INITIALIZER(ready_queue);
 struct pthread_queue active_queue = TAILQ_HEAD_INITIALIZER(active_queue);
@@ -312,30 +313,25 @@ static void pth_thread_refl_fault(struct uthread *uthread, unsigned int trap_nr,
        __pthread_generic_yield(pthread);
        pthread->state = PTH_BLK_SYSC;
 
-       /* TODO: RISCV/x86 issue! (0 is divby0, 14 is PF, etc) */
-#if defined(__i386__) || defined(__x86_64__) 
-       switch(trap_nr) {
-               case 0:
-                       handle_div_by_zero(uthread, err, aux);
-                       break;
-               case 13:
-                       handle_gp_fault(uthread, err, aux);
-                       break;
-               case 14:
-                       handle_page_fault(uthread, err, aux);
-                       break;
-               default:
-                       printf("Pthread has unhandled fault: %d, err: %d, aux: %p\n",
-                              trap_nr, err, aux);
-                       /* Note that uthread.c already copied out our ctx into the uth
-                        * struct */
-                       print_user_context(&uthread->u_ctx);
-                       printf("Turn on printx to spew unhandled, malignant trap info\n");
-                       exit(-1);
+       switch (trap_nr) {
+       case HW_TRAP_DIV_ZERO:
+               handle_div_by_zero(uthread, err, aux);
+               break;
+       case HW_TRAP_GP_FAULT:
+               handle_gp_fault(uthread, err, aux);
+               break;
+       case HW_TRAP_PAGE_FAULT:
+               handle_page_fault(uthread, err, aux);
+               break;
+       default:
+               printf("Pthread has unhandled fault: %d, err: %d, aux: %p\n",
+                      trap_nr, err, aux);
+               /* Note that uthread.c already copied out our ctx into the uth
+                * struct */
+               print_user_context(&uthread->u_ctx);
+               printf("Turn on printx to spew unhandled, malignant trap info\n");
+               exit(-1);
        }
-#else
-       #error "Handling hardware faults is currently only supported on x86"
-#endif
 }
 
 /* Akaros pthread extensions / hacks */