Is there any easier solution in porting a windows manual-reset event to pthread, than a pthread conditional-variable + pthread mutex + a flag if event is set or unset?
相关问题
- Is shmid returned by shmget() unique across proces
- How to let a thread communicate with another activ
- Inheritance impossible in Windows Runtime Componen
- how to get running process information in java?
- Is TWebBrowser dependant on IE version?
Pthreads are low level constructs. No, there isn't a simpler mechanism;
pthread_cond__*
is conceptually similar to an auto-reset event. Be careful,pthread_cond_wait
may have spurious wakeups, so it should never be used without some sort of external flag regardless of the situation.Building your own wouldn't be too hard, though.
This may not fit your usage, as you will often have a different lock that you'd want to use in place of
ev->mutex
, but this is the gist of how it's typically used.I prefer the pipe approach, because often one doesn't need just an event to wait for, but multiple objects e.g.
WaitForMultipleObjects(...)
. And with using pipes one could easily replace the windowsWaitForMultipleObjects
call withpoll(...)
,select
,pselect
, andepoll
.There was a light-weight method for process synchronization called
Futex
(Fast Userspace Locking system call). There was a functionfutex_fd
to get one or more file descriptors for futexes. This file descriptor, together with possibly many others representing real files, devices, sockets or the like could get passed toselect
,poll
, orepoll
. Unfortunately it was removed from the kernel. So the pipes tricks remain the only facility to do this:We were looking for a similar solution to port some heavily-multithreaded C++ code from Windows to Linux, and ended up writing an open source, MIT-licensed Win32 Events for Linux library. It should be the solution you are looking for, and has been heavily vetted for performance and resource consumption.
It implements manual and auto-reset events, and both the
WaitForSingleObject
andWaitForMultipleObject
functionalities.You can easy implement manual-reset events with pipes:
event is in triggered state -> there is something to read from the pipe
SetEvent -> write()
ResetEvent -> read()
WaitForMultipleObjects -> poll() (or select()) for reading
the "SetEvent" operation should write something (e.g. 1 byte of any value) just to put the pipe in non-empty state, so subsequent "Wait" operation, that is, poll() for data available for read will not block.
The "ResetEvent" operation will read up the data written to make sure pipe is empty again. The read-end of the pipe should be made non-blocking so that trying to reset (read from) already reset event (empty pipe) wont block - fcntl(pipe_out, F_SETFL, O_NONBLOCK) Since there may be more than 1 SetEvents before the ResetEvent, you should code it so that it reads as many bytes as there are in the pipe:
Note that waiting for the event does not read from the pipe and hence the "event" will remain in triggered state until the reset operation.
We (full disclosure: I work at NeoSmart Technologies) wrote an open source (MIT licensed) library called pevents which implements WIN32 manual and auto-reset events on POSIX, and includes both WaitForSingleObject and WaitForMultipleObjects clones. It's seen some adoption since then (it's used in Steam on Linux/Mac) and works fairly well.
Although I'd personally advise you to use POSIX multithreading and signaling paradigms when coding on POSIX machines, pevents gives you another choice if you need it.
I think Windows Events are more akin to a semaphore. I.e. for auto-reset, you'd use a binary semaphore and the sem_timedwait() function.