mm: Clean up the functional interface
[akaros.git] / kern / src / rendez.c
index 1fb75b7..576eaf6 100644 (file)
@@ -40,8 +40,7 @@ void rendez_sleep(struct rendez *rv, int (*cond)(void*), void *arg)
                if (should_abort(&cle)) {
                        cv_unlock_irqsave(&rv->cv, &irq_state);
                        dereg_abortable_cv(&cle);
                if (should_abort(&cle)) {
                        cv_unlock_irqsave(&rv->cv, &irq_state);
                        dereg_abortable_cv(&cle);
-                       set_errno(EINTR);
-                       error("syscall aborted");
+                       error(EINTR, "syscall aborted");
                }
                cv_wait(&rv->cv);
                cpu_relax();
                }
                cv_wait(&rv->cv);
                cpu_relax();
@@ -53,9 +52,11 @@ void rendez_sleep(struct rendez *rv, int (*cond)(void*), void *arg)
 /* Force a wakeup of all waiters on the rv, including non-timeout users.  For
  * those, they will just wake up, see the condition is still false (probably)
  * and go back to sleep. */
 /* Force a wakeup of all waiters on the rv, including non-timeout users.  For
  * those, they will just wake up, see the condition is still false (probably)
  * and go back to sleep. */
-static void rendez_alarm_handler(struct alarm_waiter *awaiter)
+static void rendez_alarm_handler(struct alarm_waiter *awaiter,
+                                 struct hw_trapframe *hw_tf)
 {
        struct rendez *rv = (struct rendez*)awaiter->data;
 {
        struct rendez *rv = (struct rendez*)awaiter->data;
+
        rendez_wakeup(rv);
 }
 
        rendez_wakeup(rv);
 }
 
@@ -68,7 +69,8 @@ void rendez_sleep_timeout(struct rendez *rv, int (*cond)(void*), void *arg,
        struct cv_lookup_elm cle;
        struct timer_chain *pcpui_tchain = &per_cpu_info[core_id()].tchain;
 
        struct cv_lookup_elm cle;
        struct timer_chain *pcpui_tchain = &per_cpu_info[core_id()].tchain;
 
-       assert(usec > 0);
+       if (!usec)
+               return;
        /* Doing this cond check early, but then unlocking again.  Mostly just to
         * avoid weird issues with the CV lock and the alarm tchain lock. */
        cv_lock_irqsave(&rv->cv, &irq_state);
        /* Doing this cond check early, but then unlocking again.  Mostly just to
         * avoid weird issues with the CV lock and the alarm tchain lock. */
        cv_lock_irqsave(&rv->cv, &irq_state);
@@ -78,8 +80,11 @@ void rendez_sleep_timeout(struct rendez *rv, int (*cond)(void*), void *arg,
        }
        cv_unlock_irqsave(&rv->cv, &irq_state);
        /* The handler will call rendez_wake, but won't mess with the condition
        }
        cv_unlock_irqsave(&rv->cv, &irq_state);
        /* The handler will call rendez_wake, but won't mess with the condition
-        * state.  It's enough to break us out of cv_wait() to see .on_tchain. */
-       init_awaiter(&awaiter, rendez_alarm_handler);
+        * state.  It's enough to break us out of cv_wait() to see .on_tchain.
+        * Since all we're doing is poking a rendez, we might as well just do it
+        * from IRQ ctx instead of mucking with an extra RKM.  It also avoids issues
+        * with unset_alarm blocking. */
+       init_awaiter_irq(&awaiter, rendez_alarm_handler);
        awaiter.data = rv;
        set_awaiter_rel(&awaiter, usec);
        /* Set our alarm on this cpu's tchain.  Note that when we sleep in cv_wait,
        awaiter.data = rv;
        set_awaiter_rel(&awaiter, usec);
        /* Set our alarm on this cpu's tchain.  Note that when we sleep in cv_wait,
@@ -97,8 +102,7 @@ void rendez_sleep_timeout(struct rendez *rv, int (*cond)(void*), void *arg,
                        cv_unlock_irqsave(&rv->cv, &irq_state);
                        unset_alarm(pcpui_tchain, &awaiter);
                        dereg_abortable_cv(&cle);
                        cv_unlock_irqsave(&rv->cv, &irq_state);
                        unset_alarm(pcpui_tchain, &awaiter);
                        dereg_abortable_cv(&cle);
-                       set_errno(EINTR);
-                       error("syscall aborted");
+                       error(EINTR, "syscall aborted");
                }
                cv_wait(&rv->cv);
                cpu_relax();
                }
                cv_wait(&rv->cv);
                cpu_relax();