Semaphore queues
Asked Answered
E

3

9

I'm extending the functionality of a semaphore. I ran into a roadblock when I realized I don't know the implementation of an actual semaphore and to make sure my code ran correctly, I needed to know this.

I know a semaphore works by blocking threads that are waiting on it when they call sem_wait() and another thread currently has it locked. The thread is then blocked and then put into a wait list for that semaphore.

My question relates to what happens on a sem_post(). Is the next thread pulled off the waiting list, set as the locking thread, and allowed to be unblocked? Or is the scheme for posting completely different?

Thanks!

Elongation answered 24/3, 2009 at 20:22 Comment(0)
P
11

Semaphores have two operations:

  1. P() To acquire the semaphore (you seem to call this sem_wait)
  2. V() To release the semaphore (you seem to call this sem_post)

Semaphores also have an integer associated to them, which is the number of concurrent threads allowed to pass P() without blocking. Other calls to P() will block until V() is called to free up spots.

That is the classic definition of a semaphore.

Edit: Semaphores do not make any guarantee of order. They don't have to actually use a queue or other FIFO structure. When only one thread is allowed at a time, when it calls V(), another (possibly random) thread will then return from its P() call and continue.

Profession answered 24/3, 2009 at 20:27 Comment(5)
Right, but is it possible to know exactly how the waiting queue works for a semaphore when only 1 thread is allowed to pass at a time?Elongation
Semaphores do not make any guarantee of order. They don't have to actually use a queue or other FIFO structure. When only one thread is allowed at a time, when it calls V(), another (possibly random) thread will then return from its P() call and continue.Profession
@Ben S: Why don't you promote that comment to part of you answer? I think it is what heluimwhippet was after in the first place, and it is well stated.Aldenalder
Semaphores do not make any guarantee of order. +1Alkane
Hi, how about this post rfc1149.net/blog/2011/01/07/the-third-readers-writers-problem when author uses lines like P(orderMutex); // Remember our order of arrival and this Wikipedia article en.wikipedia.org/wiki/… where wrote "signal: Increments the value of semaphore variable by 1. After the increment, if the pre-increment value was negative (meaning there are processes waiting for a resource), it transfers a blocked process from the semaphore's waiting queue to the ready queue" ?Creative
E
13

The next thread to unblock on it's sem_wait() will be whatever thread the OS decides is the next one to context switch into. Nobody makes any guarantee of ordering; it depends on your OS's scheduling strategy. It might be the thread that has been off the CPU for the longest, or the one that has been assigned the highest "priority", or the one that has historically had certain resource-usage statistics, or whatever.

Most likely, your current thread (the one that called sem_post()) will continue running for a while, until it either starts waiting for user input, blocks on another semaphore, or runs out of its os-allotted time slice. Then, the OS will switch in some totally unrelated process to run for a fraction of a second (probably Firefox or something), then go off and handle some network traffic, get itself a cup of tea, and, finally, when it gets around to it, pick whichever of your other threads it feels like, based on something like whether it feels based on past history that the particular thread is more CPU or I/O-bound.

In many OSes, priority is given to I/O-bound processes that haven't been around for very long. The theory is that new processes might be short-lived (if it's been around for five hours already, odds are it won't be finishing up in the next 1ms) so we might as well get them over with. I/O-bound processes are likely to continue to be I/O-bound, which means that chances are they are going to switch off the CPU shortly while waiting for other resources. Basically, the OS wants to find the process that it's going to be able to be done with ASAP, so it can get back to sipping its tea and running your malware.

Eldoneldora answered 24/3, 2009 at 21:39 Comment(0)
P
11

Semaphores have two operations:

  1. P() To acquire the semaphore (you seem to call this sem_wait)
  2. V() To release the semaphore (you seem to call this sem_post)

Semaphores also have an integer associated to them, which is the number of concurrent threads allowed to pass P() without blocking. Other calls to P() will block until V() is called to free up spots.

That is the classic definition of a semaphore.

Edit: Semaphores do not make any guarantee of order. They don't have to actually use a queue or other FIFO structure. When only one thread is allowed at a time, when it calls V(), another (possibly random) thread will then return from its P() call and continue.

Profession answered 24/3, 2009 at 20:27 Comment(5)
Right, but is it possible to know exactly how the waiting queue works for a semaphore when only 1 thread is allowed to pass at a time?Elongation
Semaphores do not make any guarantee of order. They don't have to actually use a queue or other FIFO structure. When only one thread is allowed at a time, when it calls V(), another (possibly random) thread will then return from its P() call and continue.Profession
@Ben S: Why don't you promote that comment to part of you answer? I think it is what heluimwhippet was after in the first place, and it is well stated.Aldenalder
Semaphores do not make any guarantee of order. +1Alkane
Hi, how about this post rfc1149.net/blog/2011/01/07/the-third-readers-writers-problem when author uses lines like P(orderMutex); // Remember our order of arrival and this Wikipedia article en.wikipedia.org/wiki/… where wrote "signal: Increments the value of semaphore variable by 1. After the increment, if the pre-increment value was negative (meaning there are processes waiting for a resource), it transfers a blocked process from the semaphore's waiting queue to the ready queue" ?Creative
G
0

According to the IEEE standards, the behavior of POSIX semaphores:

If the semaphore value resulting from this operation is positive, then no threads were blocked waiting for the semaphore to become unlocked; the semaphore value is simply incremented.

If the value of the semaphore resulting from this operation is zero, then one of the threads blocked waiting for the semaphore shall be allowed to return successfully from its call to sem_wait(). If the Process Scheduling option is supported, the thread to be unblocked shall be chosen in a manner appropriate to the scheduling policies and parameters in effect for the blocked threads. In the case of the schedulers SCHED_FIFO and SCHED_RR, the highest priority waiting thread shall be unblocked, and if there is more than one highest priority thread blocked waiting for the semaphore, then the highest priority thread that has been waiting the longest shall be unblocked. If the Process Scheduling option is not defined, the choice of a thread to unblock is unspecified.

If the Process Sporadic Server option is supported, and the scheduling policy is SCHED_SPORADIC, the semantics are as per SCHED_FIFO above."

Gravity answered 23/12, 2022 at 20:43 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.