Re: [PATCH 0/24] make atomic_read() behave consistently across all architectures
From: Stefan Richter <stefanr@s5r6.in-berlin.de>
Date: 2007-08-15 13:08:56
Also in:
linux-arch, lkml
Satyam Sharma wrote:
On Wed, 15 Aug 2007, Stefan Richter wrote:quoted
Doesn't "atomic WRT all processors" require volatility?No, it definitely doesn't. Why should it? "Atomic w.r.t. all processors" is just your normal, simple "atomicity" for SMP systems (ensure that that object is modified / set / replaced in main memory atomically) and has nothing to do with "volatile" behaviour. "Volatile behaviour" itself isn't consistently defined (at least definitely not consistently implemented in various gcc versions across platforms), but it is /expected/ to mean something like: "ensure that every such access actually goes all the way to memory, and is not re-ordered w.r.t. to other accesses, as far as the compiler can take care of these". The last "as far as compiler can take care" disclaimer comes about due to CPUs doing their own re-ordering nowadays. For example (say on i386):
[...]
In (A) the compiler optimized "a = 10;" away, but the actual store of the final value "20" to "a" was still "atomic". (B) and (C) also exhibit "volatile" behaviour apart from the "atomicity". But as others replied, it seems some callers out there depend upon atomic ops exhibiting "volatile" behaviour as well, so that answers my initial question, actually. I haven't looked at the code Paul pointed me at, but I wonder if that "forget(x)" macro would help those cases. I'd wish to avoid the "volatile" primitive, personally.
So, looking at load instead of store, understand I correctly that in
your opinion
int b;
b = atomic_read(&a);
if (b)
do_something_time_consuming();
b = atomic_read(&a);
if (b)
do_something_more();
should be changed to explicitly forget(&a) after
do_something_time_consuming?
If so, how about the following:
static inline void A(atomic_t *a)
{
int b = atomic_read(a);
if (b)
do_something_time_consuming();
}
static inline void B(atomic_t *a)
{
int b = atomic_read(a);
if (b)
do_something_more();
}
static void C(atomic_t *a)
{
A(a);
B(b);
}
Would this need forget(a) after A(a)?
(Is the latter actually answered in C99 or is it compiler-dependent?)
--
Stefan Richter
-=====-=-=== =--- -====
http://arcgraph.de/sr/