Page MenuHomeFreeBSD

sem_post(): wake up the sleeper after adjusting has_waiters
ClosedPublic

Authored by badger on Aug 15 2016, 2:30 PM.

Details

Summary

If the caller of sem_post() wakes up a thread sleeping via sem_wait()
before it clears the has_waiters flag, the caller of sem_wait() has no way of
knowing when it is safe to destroy the semaphore and reuse the memory. This is
because the caller of sem_post() may be interrupted between the wake step and
the clearing of has_waiters. It will then write into the has_waiters flag in
userspace after being preempted for some unknown amount of time.

A test program that illustrates the issue I want to fix is here:
https://people.freebsd.org/~badger/tests/sem_post-stack-corrupt/semaphore.c .
This program can sometimes exit in the otherfunc() function printing
"sem struct changed after yielding". There is a README.txt file in that
same directory describing the test in more detail.

Diff Detail

Repository
rS FreeBSD src repository
Lint
Automatic diff as part of commit; lint not applicable.
Unit
Automatic diff as part of commit; unit tests not applicable.

Event Timeline

badger retitled this revision from to Wake up the sleeper after adjusting has_waiters.Aug 15 2016, 2:30 PM
badger updated this object.
badger edited the test plan for this revision. (Show Details)
badger updated this revision to Diff 19286.
badger retitled this revision from Wake up the sleeper after adjusting has_waiters to sem_post(): wake up the sleeper after adjusting has_waiters.Aug 15 2016, 2:35 PM
badger updated this object.
badger added reviewers: vangyzen, kib.
vangyzen edited edge metadata.Aug 15 2016, 2:56 PM
vangyzen accepted this revision.
This revision is now accepted and ready to land.Aug 15 2016, 2:56 PM
badger added a reviewer: jhb.Aug 15 2016, 3:49 PM
kib edited edge metadata.Aug 15 2016, 3:56 PM
kib accepted this revision.
jhb edited edge metadata.Aug 15 2016, 5:36 PM
jhb accepted this revision.
This revision was automatically updated to reflect the committed changes.