Jump to content
  • Advertisement
Sign in to follow this  
littlekid

how and when shoud I use volatile keyword?

This topic is 2699 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

suppose i have this code

[source]
class Thread
{
public:
void PostQuitSignal()
{
quit_ = true;
}

Desc GetDesc()
{
return desc_;
}

private:
void ThreadLoop()
{
while (!quit_)
{
//do other main thread logic like read message queues etc
}
}

bool quit_; //does this need to be volatile??
Desc desc_; //this struct is magically initialize with all values at constructor and never changes anymore, does this need to be volatile too??
};
[/source]

suppose in a mulithread app, the above class when started will run ThreadLoop function. Does the variable "quit_" and "desc_" need to be volatile??

regards

Share this post


Link to post
Share on other sites
Advertisement
`quit_' should definitely be volatile. Otherwise the compiler might optimize the `while (!quit_)' loop, if it can determine that `quit_' can't possibly be changed by the code inside the loop.

Share this post


Link to post
Share on other sites
That's a misuse of the volatile keyword.

The volatile keyword is aimed at I/O, not multiprocessing. While it may work for your particular hardware and compiler, the only guarantees you have with volatile are that it won't get optimized out or reordered. It does not provide any guarantees about multiprocessing environments. Volatile variables provide no guarantees about cache coherence or memory boundaries, so it has no guarantee for usefulness between threads. Just because it is not optimized out does not mean it will be shared between threads or processors in the way you are expecting.

This is not what you want. What you are looking for is a multiprocessing flag or other IPC to indicate your status.


Choose the right tool for the job.

Use a semaphore or other communication function provided by your multiprocessing library, not a volatile variable.

Share this post


Link to post
Share on other sites
Hmmm... I've used `volatile' before for this purpose and it worked fine, but I will be happy to use a more specific tool to get the job done if one is available.

Using a semaphore for a variable that will only be changed by the main thread seems expensive and unnecessary. What is an example of "flag function" (with POSIX threads of Boost.Thread, for instance)?

Share this post


Link to post
Share on other sites

Hmmm... I've used `volatile' before for this purpose and it worked fine, but I will be happy to use a more specific tool to get the job done if one is available.

Using a semaphore for a variable that will only be changed by the main thread seems expensive and unnecessary. What is an example of "flag function" (with POSIX threads of Boost.Thread, for instance)?


Just because it happened to work for you doesn't mean it is the right way to do it. As mentioned, volatile provides absolutely no guarantees about cache coherency or memory barriers. While your system might have happened to do this work for you, you had no guarantee that it would, nor do you have any guarantees that other systems will do it.


Boost cut their Semaphore class because people were misusing it for communication; use a condition variable instead.


Visual C++ has actually implemented additional pessimizations when you use volatile keyword because people misuse the keyword as you described. On that system use InterlockedIncrement to set your flag and ensure it will be immediately propagate beyond the original thread and across multiple processors.

Share this post


Link to post
Share on other sites
hi, @frob, what libraries do you suggest I use?? I am currently using most stuff from boost threads.

lastly i am using gcc4.6 so I have access to std::atomic, but i did not use it as I thought writing and reading a bool is guarantee to be atomic?

regards

Share this post


Link to post
Share on other sites
hi, @ frob, I don't understand how to use boost.conditional_variable to replace the quit variable. As in this case, the quit_ variable is use as a flag by the thread to determine if it need to terminate, if not it continue processing its stuff. However wouldn't boost.conditional_variable cause the said thread to sleep or block when the condition is not met?

regards

Share this post


Link to post
Share on other sites

[quote name='alvaro' timestamp='1304349607' post='4805482']
Hmmm... I've used `volatile' before for this purpose and it worked fine, but I will be happy to use a more specific tool to get the job done if one is available.


Just because it happened to work for you doesn't mean it is the right way to do it.[/quote]

I didn't claim that it was the right way to do it, and I thought I showed a good disposition to learn the right way to do it. I am still trying to learn, not trying to fight you.

Condition variables seem to block until something happens. I don't see a need for that in the situation we are talking about. We just want the child thread to go about its business until someone sets the quit_ flag. Whenever it sees that flag has been set, it will quit, and presumably the main thread will be waiting for this to happen, using join.

So could you please provide some code showing how to do this with some multithreading library? POSIX threads and Boost.Thread are the two I have used before, so it would be great if you could write it using one of those.

Share this post


Link to post
Share on other sites

lastly i am using gcc4.6 so I have access to std::atomic, but i did not use it as I thought writing and reading a bool is guarantee to be atomic?


C++ has no guarantees that reading or writing are ever atomic or synchronized, not even for bool values.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!