parlib: Implement join/detach() for all uthreads
[akaros.git] / user / vmm / io.c
index 4368ed5..a640c27 100644 (file)
@@ -1,5 +1,4 @@
 #include <stdio.h>
-#include <pthread.h>
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <fcntl.h>
@@ -55,7 +54,7 @@ void regp(uint32_t **reg)
 
 static void configaddr(uint32_t val)
 {
-       printf("%s 0x%lx\n", __func__, val);
+       printd("%s 0x%lx\n", __func__, val);
        cf8 = val;
 }
 
@@ -64,7 +63,7 @@ static void configread32(uint32_t edx, uint64_t *reg)
        uint32_t *r = &cf8;
        regp(&r);
        *reg = *r;
-       printf("%s: 0x%lx 0x%lx, 0x%lx 0x%lx\n", __func__, cf8, edx, r, *reg);
+       printd("%s: 0x%lx 0x%lx, 0x%lx 0x%lx\n", __func__, cf8, edx, r, *reg);
 }
 
 static void configread16(uint32_t edx, uint64_t *reg)
@@ -74,7 +73,7 @@ static void configread16(uint32_t edx, uint64_t *reg)
        configread32(edx, &val);
        val >>= which;
        *reg = val;
-       printf("%s: 0x%lx, 0x%lx 0x%lx\n", __func__, edx, val, *reg);
+       printd("%s: 0x%lx, 0x%lx 0x%lx\n", __func__, edx, val, *reg);
 }
 
 static void configread8(uint32_t edx, uint64_t *reg)
@@ -84,7 +83,7 @@ static void configread8(uint32_t edx, uint64_t *reg)
        configread32(edx, &val);
        val >>= which;
        *reg = val;
-       printf("%s: 0x%lx, 0x%lx 0x%lx\n", __func__, edx, val, *reg);
+       printd("%s: 0x%lx, 0x%lx 0x%lx\n", __func__, edx, val, *reg);
 }
 
 static void configwrite32(uint32_t addr, uint32_t val)
@@ -92,17 +91,17 @@ static void configwrite32(uint32_t addr, uint32_t val)
        uint32_t *r = &cf8;
        regp(&r);
        *r = val;
-       printf("%s 0x%lx 0x%lx\n", __func__, addr, val);
+       printd("%s 0x%lx 0x%lx\n", __func__, addr, val);
 }
 
 static void configwrite16(uint32_t addr, uint16_t val)
 {
-       printf("%s 0x%lx 0x%lx\n", __func__, addr, val);
+       printd("%s 0x%lx 0x%lx\n", __func__, addr, val);
 }
 
 static void configwrite8(uint32_t addr, uint8_t val)
 {
-       printf("%s 0x%lx 0x%lx\n", __func__, addr, val);
+       printd("%s 0x%lx 0x%lx\n", __func__, addr, val);
 }
 
 /* this is very minimal. It needs to move to vmm/io.c but we don't
@@ -112,7 +111,7 @@ static void configwrite8(uint32_t addr, uint8_t val)
  * It would have been nice had intel encoded the IO exit info as nicely as they
  * encoded, some of the other exits.
  */
-bool io(struct guest_thread *vm_thread)
+int io(struct guest_thread *vm_thread)
 {
 
        /* Get a pointer to the memory at %rip. This is quite messy and part of the
@@ -125,11 +124,10 @@ bool io(struct guest_thread *vm_thread)
        uintptr_t ip;
        uint32_t edx;
        struct vm_trapframe *vm_tf = &(vm_thread->uthread.u_ctx.tf.vm_tf);
-       /* for now, we're going to be a bit crude. In kernel, p is about v, so we just blow away
-        * the upper 34 bits and take the rest + 1M as our address
-        * TODO: put this in vmctl somewhere?
-        */
-       ip = vm_tf->tf_rip & 0x3fffffff;
+
+       /* Get the RIP of the io access. */
+       if (rippa(vm_thread, (uint64_t *)&ip))
+               return VM_PAGE_FAULT;
        edx = vm_tf->tf_rdx;
        ip8 = (void *)ip;
        ip16 = (void *)ip;
@@ -141,12 +139,12 @@ bool io(struct guest_thread *vm_thread)
                if (edx == 0xcf8) {
                        //printf("Set cf8 ");
                        configaddr(vm_tf->tf_rax);
-                       return true;
+                       return 0;
                }
                if (edx == 0xcfc) {
                        //printf("Set cfc ");
                        configwrite32(edx, vm_tf->tf_rax);
-                       return true;
+                       return 0;
                }
                /* While it is perfectly legal to do IO operations to
                 * nonexistant places, we print a warning here as it
@@ -164,7 +162,7 @@ bool io(struct guest_thread *vm_thread)
                 * Windows 98, not Linux.
                 */
                printf("(out rax, edx): unhandled IO address dx @%p is 0x%x\n", ip8, edx);
-               return true;
+               return 0;
        }
        // out %al, %dx
        if (*ip8 == 0xee) {
@@ -172,51 +170,51 @@ bool io(struct guest_thread *vm_thread)
                /* out al %edx */
                if (edx == 0xcfb) { // special!
                        printf("Just ignore the damned cfb write\n");
-                       return true;
+                       return 0;
                }
                if ((edx&~3) == 0xcfc) {
                        //printf("ignoring write to cfc ");
-                       return true;
+                       return 0;
                }
                /* Another case where we print a message but it's not an error. */
                printf("out al, dx: unhandled IO address dx @%p is 0x%x\n", ip8, edx);
-               return true;
+               return 0;
        }
        if (*ip8 == 0xec) {
                vm_tf->tf_rip += 1;
                //printf("configread8 ");
                configread8(edx, &vm_tf->tf_rax);
-               return true;
+               return 0;
        }
        if (*ip8 == 0xed) {
                vm_tf->tf_rip += 1;
                if (edx == 0xcf8) {
                        //printf("read cf8 0x%lx\n", v->regs.tf_rax);
                        vm_tf->tf_rax = cf8;
-                       return true;
+                       return 0;
                }
                //printf("configread32 ");
                configread32(edx, &vm_tf->tf_rax);
-               return true;
+               return 0;
        }
        /* Detects when something is written to the PIC. */
        if (*ip8 == 0xe6) {
                vm_tf->tf_rip += 2;
-               return true;
+               return 0;
        }
        /* Detects when something is read from the PIC, so
         * a value signifying there is no PIC is given.
         */
        if (*ip16 == 0x21e4) {
                vm_tf->tf_rip += 2;
-               vm_tf->tf_rax = ~0ULL;
-               return true;
+               vm_tf->tf_rax |= 0x00000ff;
+               return 0;
        }
        if (*ip16 == 0xed66) {
                vm_tf->tf_rip += 2;
                //printf("configread16 ");
                configread16(edx, &vm_tf->tf_rax);
-               return true;
+               return 0;
        }
 
        /* This is, so far, the only case in which we indicate
@@ -228,6 +226,6 @@ bool io(struct guest_thread *vm_thread)
         * instructions to the CPU.
         */
        printf("unknown IO %p %x %x\n", ip8, *ip8, *ip16);
-       return false;
+       return -1;
 }