to unwind the stack. Add a temporary workaround where we simply don't
allow the thread to exit (a kernel thread exit is a relatively uncommon
event in a rump kernel anyway).
apart from testing that rumpuser_thread_create() can actually survive
an unschedule/schedule cycle (which may or may not be necessary with
other hypercall implementations).
count) with atomic operations. As pthread_spin_lock is not adaptive lock, it
can have hugely negative impact if contended here, especially with priority
inversions. Now contended rwlock(9) no longer falls flat in RUMP kernels.
sleeps in between. If it helps, good. If it doesn't, oh well, at
least we tried. pthread_create() returning EAGAIN has been observed in
real life at least on Linux (buildrump.sh issue #40)
have been possible for "readers" to reach visibility before "writer"
when another CPU took the lock, thus leading the previous owner to
incorrectly think that it still owned the lock in rw_write_held().
Also, remove duplicate clause from assert().
Reduce the set of hypercalls to one: "do block i/o". This not only
eliminates a lot of pseudo-duplicate code, it also gives the
hypervisor a lot more freedom on how to optimize the i/o.
It's then the hypervisor's problem to translate it accordingly.
Now we no longer have to worry about the kernel having to know the
hypervisor's time and vice versa.
a spin mutex (i.e. does not relinquish cpu context while trying to
take the mutex).
Bump the hypercall interface version number. I'll be doing a bunch
of other cleanups to simplify the interface for the benefit of
alternative hypervisor implementations. I'll be riding this bump
and doing a second one only after I'm finished with all of the
changes.
is done in rumpuser for simplicity, since on the kernel side things
we assume we have only one pointer of space). As a side-effect,
we can no longer know if the current thread is holding on to a
mutex locked without curlwp context (basically all mutexes inited
outside of mutex_init()). The only thing that called rumpuser_mutex_held()
for a non-kmutex was the giant lock. So, instead implement recursive
locking for the giant lock in the rump kernel and get rid of the
now-unused recursive pthread mutex in the hypercall interface.
interlock. This is applicable in cases where the actual interlock
is the CPU the currently running thread is scheduled on. Borrowing
the scheduler lock as the mutex mandated by pthread_cond_wait()
does away with need to have an additional mutex. This both optimizes
runtime execution and simplifies code, as the extra lock typically
lead to quite some trickeries to avoid the dungeon collapsing due
to zaps from the wand of deadlock.
the source files from src/sys/rump/librump/rumpuser to src/lib/librumpuser
(from where it is already built). Even so, keep rumpuser.h in
sys/rump/include for kernel source tree self-containment.