summaryrefslogtreecommitdiff
path: root/libgo/runtime/lock_futex.c
diff options
context:
space:
mode:
Diffstat (limited to 'libgo/runtime/lock_futex.c')
-rw-r--r--libgo/runtime/lock_futex.c16
1 files changed, 14 insertions, 2 deletions
diff --git a/libgo/runtime/lock_futex.c b/libgo/runtime/lock_futex.c
index fa27013289..33ef073c90 100644
--- a/libgo/runtime/lock_futex.c
+++ b/libgo/runtime/lock_futex.c
@@ -124,26 +124,36 @@ runtime_notewakeup(Note *n)
void
runtime_notesleep(Note *n)
{
+ M *m = runtime_m();
+
/* For gccgo it's OK to sleep in non-g0, and it happens in
stoptheworld because we have not implemented preemption.
if(runtime_g() != runtime_m()->g0)
runtime_throw("notesleep not on g0");
*/
- while(runtime_atomicload((uint32*)&n->key) == 0)
+ while(runtime_atomicload((uint32*)&n->key) == 0) {
+ m->blocked = true;
runtime_futexsleep((uint32*)&n->key, 0, -1);
+ m->blocked = false;
+ }
}
static bool
notetsleep(Note *n, int64 ns, int64 deadline, int64 now)
{
+ M *m = runtime_m();
+
// Conceptually, deadline and now are local variables.
// They are passed as arguments so that the space for them
// does not count against our nosplit stack sequence.
if(ns < 0) {
- while(runtime_atomicload((uint32*)&n->key) == 0)
+ while(runtime_atomicload((uint32*)&n->key) == 0) {
+ m->blocked = true;
runtime_futexsleep((uint32*)&n->key, 0, -1);
+ m->blocked = false;
+ }
return true;
}
@@ -152,7 +162,9 @@ notetsleep(Note *n, int64 ns, int64 deadline, int64 now)
deadline = runtime_nanotime() + ns;
for(;;) {
+ m->blocked = true;
runtime_futexsleep((uint32*)&n->key, 0, ns);
+ m->blocked = false;
if(runtime_atomicload((uint32*)&n->key) != 0)
break;
now = runtime_nanotime();