views:

546

answers:

4

Hey guys...so I'm trying to brush up on my C threads and a question I've found is this:

Given a global variable int x = 0; implement the function void useless(int n) which creates n threads which in a loop increase x by 1, each thread terminates when x reaches 100.

I just don't have a handle on threads and need a solid example to base my foundation. This must use pthread system calls as much as possible.

+2  A: 

You need a mutex to protect the variable. Each thread will lock the mutex, increment the variable and release the mutex. Each thread that doesn't do this is a rogue thread.

Jonathan Leffler
I think that the InterlockedIncrement API doesn't use a mutext; instead it just uses a `LOCK:` opcode prefix.
ChrisW
I don't think InterlockedIncrement alone will cut it here, since you have to protect the compare against 100 as well as the increment.
Dan Olson
Is there an InterlockedIncrement API in POSIX pthreads?
Pete Kirkham
@ChrisW: can you provide a context for the InterlockedIncrement API? @Pete: InterlockedIncrement is not a standard part of C, nor is it a part of POSIX. The POSIX thread primitives start 'pthread_'. You can write one easily enough - but it is not standard.
Jonathan Leffler
@ChrisW: also, what is the 'LOCK:' prefix? That is a label in C - are you confusing C with C# perchance?
Jonathan Leffler
@Pete: InterlockedIncrement and simplings are part of Win32. Even if there is not a standard posix API for it in phreads most platforms have something similar. On Linux you have the atomic_add and siblings you can use, on Solaris it is atomic_add_32 and similar (man atomic_ops) and I bet you'll find them on most modern OS's (at least I have). If you want to be relatively platform independent, creating a simple .h file with defines mapping in the right implementation depending on the current platform is a piece of a cake as it is normally just a handful of calls and they work the same all over.
Fredrik
The LOCK prefix is applied to an x86 instruction to say the the processor bus is locked for the duration, making it into an atomic operation.
Pete Kirkham
I know there's an InterlockedIncrement in win32. The OP wanted to use POSIX pthreads. Apache Portable Runtime has a portable interlocked increment, but I think the unix version used mutexes rather than mapping to all the different flavours last time I looked.
Pete Kirkham
@Pete: the OP didn't say it had to be POSIX. He said "This must use pthread system calls as much as possible". As there are no atomic POSIX defined operations (that I know of), POSIX falls outside the "as much as possible" requirement. Using locks alone is not always a complete solution, you probably want the variable to be volatile as well.
Fredrik
A: 

What you need is a critical section. Under windows, this would be EnterCriticalSection, but in the pthread environment, the equivalent is pthread_mutex_lock. See here for some pointers.

Bob Moore
The markup also smartly allows you to use `backticks` to represent `__code__` which disables all other markup. Don't dis the SO markup unless you actually understand it.
Chris Lutz
A: 

I would think that InterlockedIncrement is sufficient, if it is ok for each thread to exit if X >= 100.

I would never use a critical section unless I really have to as this can lead to a high level of contention. Whereas InterlockedIncrement has no contention at all, at least not that might affect over all performance.

Steve
+2  A: 
Pete Kirkham