Thread questions concerning synchronization

Started by
3 comments, last by AnthonyS 15 years, 9 months ago
I'm continuing my journey of thread programming with the current game I'm working on and I have a question. This issue is moot with a single processor system however I'm wondering out of curiosity. On a multi-processor system with 2 different cores running 2 different threads what happens if one thread attempts to read from a block of memory while the second thread is writing to it at the exact same time. Normally with simple threads if one thread writes and one thread reads there's not much of a problem but I am wondering what happens if this "race" condition occurs. Do you basically need to synchronize just to be absolutely sure or is this some sort of moot point? I suspect I'll need to synchronize, however (and thankfully so) there are only a few threads running and one and only one thread will ever write to a block of memory that another thread will read from. Thanks in advance for the responses.
Advertisement
Quote:Original post by atimes
I'm continuing my journey of thread programming with the current game I'm working on and I have a question.

This issue is moot with a single processor system however I'm wondering out of curiosity. On a multi-processor system with 2 different cores running 2 different threads what happens if one thread attempts to read from a block of memory while the second thread is writing to it at the exact same time. Normally with simple threads if one thread writes and one thread reads there's not much of a problem but I am wondering what happens if this "race" condition occurs.


For all practical purposes, undefined.

Quote:Do you basically need to synchronize just to be absolutely sure or is this some sort of moot point? I suspect I'll need to synchronize, however (and thankfully so) there are only a few threads running and one and only one thread will ever write to a block of memory that another thread will read from.


Yes you do, unless you know very specifically you do not need to.

Much of this depends on cache, pipeline, and size of memory being handled. Part of it is related to code re-ordering and optimizations performed by compiler.

For types < sizeof(void*), the writes will likely be atomic (all n bytes will be written in one go), but that is completely insufficient guarantee that code using that data will behave properly. In worst case scenario, writing 1234 over 4321, could result in other thread reading 4334, since only parts of bytes were written (I believe this is unlikely/impossible on most architectures, but even such problems can theoretically occur).

But when it comes to thread-safe code, unless you have specific guarantee about something, you cannot assume anything.
This is dependent on your architecture, and may require combing through the processors development manual. If you're programming for a standard x86 system, word sized writes occur atomically. This knowledge can lead to substantial performance boosts with some multi-threaded code. Actually, one of the easier ways to determine if you can get away with this is to search a linux code base for a file titled "atomic.h", then look for the functions named atomic_read and atomic_write(or something like that) and see how they implemented it.

Remember, if you're developing for an out of order cpu, you'll have to consider memory fencing too. Luckily, on standard x86 this isn't a problem, yet...

If you decide to go this route it may behoove you to write the code in assembler, and declare the variables as volatile to avoid complications that can arise due to a funky compiler.
Quote:Original post by AnthonyS
Remember, if you're developing for an out of order cpu, you'll have to consider memory fencing too. Luckily, on standard x86 this isn't a problem, yet...

Are you saying x86 CPU's aren't out of order? O.o

Quote:Original post by Spoonbender
Quote:Original post by AnthonyS
Remember, if you're developing for an out of order cpu, you'll have to consider memory fencing too. Luckily, on standard x86 this isn't a problem, yet...

Are you saying x86 CPU's aren't out of order? O.o


Internally they MAY perform out of order instructions, but specifications dictate that the user will never notice the implications. Itanium architecture, on the other hand, is a different story.

There is one caveat, if you are using simd instructions in multi-threaded code you will certainly have to use the sfence/mfence instruction at the end of your functions.

This topic is closed to new replies.

Advertisement