Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > Clarification on the applicability of compile-time optimization to astruct variable which encompasses a mixture of fields declared as volatileand non-volatile individually

Reply
Thread Tools

Clarification on the applicability of compile-time optimization to astruct variable which encompasses a mixture of fields declared as volatileand non-volatile individually

 
 
Uncle Steve
Guest
Posts: n/a
 
      07-06-2012
On Fri, Jul 06, 2012 at 07:39:56PM -0700, Joshua Maurice wrote:
> On Jul 6, 2:20*pm, Uncle Steve <(E-Mail Removed)> wrote:
> > On Fri, Jul 06, 2012 at 04:58:09PM -0700, Joshua Maurice wrote:
> > > To be topical, here's the answer for C11: volatile is useless as a
> > > portable threading construct. Do not use it. It's (maybe) useful in a
> > > portable way only for 3 obscure situations: MMIO, setjmp and longjmp
> > > stuff, and signal handling. If you properly use C11 mutexes, there is
> > > absolutely no need for volatile. To paraphrase you else-thread, there
> > > will be no "funny business" if you use mutexes correctly. It tells the
> > > compiler, the hardware, and anything else relevant, to obey the
> > > semantics of the mutex. volatile is similarly useless when you
> > > correctly use the new "weak" C11 atomics. volatile adds nothing
> > > (portably).

> >
> > > Now, to finally answer your question, C11 threading semantics,
> > > including the lack of useful volatile semantics, is basically copied
> > > wholesale from pthreads. Don't use volatile as a portable threading
> > > construct with pthreads either. pthread mutexes do everything you
> > > need. volatile adds absolutely nothing (portably).

> >
> > > (Yes, you can accomplish useful code with volatile for specific
> > > platform and specific compilers with specific settings. That's an
> > > "advanced" topic that I won't cover now.)

> >
> > > Now, what do you mean by "mutexes are not memory access barriers"?
> > > Mutexes do two things: they provide blocking semantics for mutual
> > > exclusion, and they guarantee visibility ala the usual "happens-
> > > before" semantics. Mutexes are implemented with hardware memory
> > > fences / barriers. This is all true for mutexes in pthreads, win32
> > > threads, Boost threads, ACE threads, C11 threads, C++11 threads, and
> > > every case I can recall seeing the word "mutex".

> >
> > Well, mutexes are barriers for the memory accesses associated with the
> > mutex itself, but not in general. *Reading the above I can tell that
> > you think I'm using POSIX mutexes, however that is not the case.

>
> I strongly suggest that you don't use the word "mutex" for your code
> because you will confuse most readers. Most readers will associate
> "mutex" with both mutual exclusion and "happens-before" global memory
> visibility. That's how the term has been commonly used (ex: posix
> pthreads), and how it will continue to commonly be used (ex: C11).
>
> >*I am
> > using a custom locking scheme that allows for concurrent readers, but
> > is exclusive for writers. *As a consequence, the behavior of
> > variables marked volatile in my code is critical, so I don't want to
> > mistakenly use it in a way that results in surprises.
> >
> > Now you can say that what I am doing is non-portable, but you would
> > be wrong there since my algorithms are in fact portable as long as I
> > am following the rules of the C standard. *Perhaps the proper term is
> > limited portability as I rely on a tiny amount of platform specific
> > asm. *(One instruction.)

>
> I will say it again: the C89 and C99 standards do not mean what you
> think. What the compiler writers and thread library writers understand
> volatile to mean is not what you understand volatile to mean, and at
> the end of the day what the compiler writers and thread library
> writers think is paramount. You may be able to get this to work for
> specific platforms with specific compilers. I suggest you ask in a
> location specific to such implementations for such platform specific
> hackery. However, do not look at the C standard for guidance on this.


Um, what is it that compiler writers and thread library writers
understand volatile to mean?

> In the C11 parlance, what you're trying to write requires the "weak"
> atomics, such as relaxed, acquire, release, and consume memory
> operations. Attempting to write stuff like this without C11 support
> with the C11 primitives is a wholly platform specific affair, and
> neither C89 nor C90 can help you there. volatile specifically cannot
> help you (barring platform specific documentation to the contrary).


You seem to be making too many assumptions about my code.

> From else-thread:
> On Jul 6, 2:29 pm, Uncle Steve <(E-Mail Removed)> wrote:
> > On Sat, Jul 07, 2012 at 12:37:59PM +1200, Ian Collins wrote:
> > > Then use your platform's native threading primitives.

> >
> > Doing so would incur a performance penalty in comparison to my
> > synchronization primitives in some circumstances.

>
> That's your problem. You have broken code. Your options are:
> 1- broken code (e.g. using volatile and asm memory barriers absent
> platform specific guarantees)
> 2- code that relies on platform specific guarantees (e.g. with using
> volatile and asm memory barriers)
> 3- "slow" code (e.g. with posix mutexes)
> 4- C11 code


How do you know, a priori, that my code is broken? Do I have to
change my passwords again?


Regards,

Uncle Steve

--
The moon has never been closer.

 
Reply With Quote
 
 
 
 
Uncle Steve
Guest
Posts: n/a
 
      07-06-2012
On Fri, Jul 06, 2012 at 08:12:57PM -0700, Joshua Maurice wrote:
> On Jul 6, 3:54*pm, Uncle Steve <(E-Mail Removed)> wrote:
> > On Fri, Jul 06, 2012 at 07:39:56PM -0700, Joshua Maurice wrote:
> > > I will say it again: the C89 and C99 standards do not mean what you
> > > think. What the compiler writers and thread library writers understand
> > > volatile to mean is not what you understand volatile to mean, and at
> > > the end of the day what the compiler writers and thread library
> > > writers think is paramount. You may be able to get this to work for
> > > specific platforms with specific compilers. I suggest you ask in a
> > > location specific to such implementations for such platform specific
> > > hackery. However, do not look at the C standard for guidance on this.

> >
> > Um, what is it that compiler writers and thread library writers
> > understand volatile to mean?

>
> http://www.open-std.org/jtc1/sc22/wg...006/n2016.html
>
> > > In the C11 parlance, what you're trying to write requires the "weak"
> > > atomics, such as relaxed, acquire, release, and consume memory
> > > operations. Attempting to write stuff like this without C11 support
> > > with the C11 primitives is a wholly platform specific affair, and
> > > neither C89 nor C90 can help you there. volatile specifically cannot
> > > help you (barring platform specific documentation to the contrary).

> >
> > You seem to be making too many assumptions about my code.

>
> I think it's pretty clear from what you've written else-thread.
>
> > > From else-thread:
> > > On Jul 6, 2:29 pm, Uncle Steve <(E-Mail Removed)> wrote:
> > > > On Sat, Jul 07, 2012 at 12:37:59PM +1200, Ian Collins wrote:
> > > > > Then use your platform's native threading primitives.

> >
> > > > Doing so would incur a performance penalty in comparison to my
> > > > synchronization primitives in some circumstances.

> >
> > > That's your problem. You have broken code. Your options are:
> > > 1- broken code (e.g. using volatile and asm memory barriers absent
> > > platform specific guarantees)
> > > 2- code that relies on platform specific guarantees (e.g. with using
> > > volatile and asm memory barriers)
> > > 3- "slow" code (e.g. with posix mutexes)
> > > 4- C11 code

> >
> > How do you know, a priori, that my code is broken? *Do I have to
> > change my passwords again?

>
> How do I know it's broken? By your own admission, you're using
> volatile to try and affect inter-thread visibility (absent constructs
> that actually give inter-thread visibility). By your previous
> statements about using the C standard to derive useful threading
> semantics for volatile, I doubt you've looked at the compiler
> documentation and hardware documentation for your implementation. Thus
> you have broken code. (I don't think you are trying to nit on "it
> could be right by coincidence".)


Well you know what? You're going to have to wait until version 1.0
before you get to decide how wrong it is.


Regards,

Uncle Steve

--
The moon has never been closer.

 
Reply With Quote
 
 
 
 
Ian Collins
Guest
Posts: n/a
 
      07-06-2012
On 07/ 7/12 06:33 AM, Uncle Steve wrote:
> On Fri, Jul 06, 2012 at 06:11:28PM -0400, Eric Sosman wrote:
>> On 7/6/2012 2:01 PM, Uncle Steve wrote:
>>> On Sat, Jul 07, 2012 at 09:20:57AM +1200, Ian Collins wrote:
>>>> On 07/ 7/12 05:08 AM, Uncle Steve wrote:
>>>>> [...]
>>>>> This is a concern in my mind right now as I'm writing some posix
>>>>> threads code, and so obviously there are a large number of variables
>>>>> which ought to be declared volatile.
>>>>
>>>> What leads you to that conclusion? That line of though usually implies
>>>> you are misunderstanding the relationship between volatile and threads.
>>>>
>>>> What are you trying to achieve with volatile?
>>>
>>> Well, I have some data structures that will be accessed from arbitrary
>>> threads, so I want to make sure there's no funny business happening
>>> behind the scenes where the compiler decides that certain accesses are
>>> optional.

>>
>> Although the latest "C11" Standard adds some multi-threading
>> support, I'll ignore that because (1) C11 implementations are not
>> exactly thick upon the ground as yet, (2) you mentioned you're
>> using Pthreads anyhow, and (3) I haven't studied the C11 threading
>> stuff closely enough to be a competent commentator.
>>
>> So: As long as you're using an established non-C-specific
>> threading framework, I suggest you visit comp.programming.threads,
>> a newsgroup devoted to multi-threading issues. There you will learn
>> that `volatile' is neither necessary *nor* sufficient in connection
>> with variables shared between threads. (You needn't take my word on
>> this: Just browse the comp.programming.threads archives and you'll
>> see the local experts refuting this misunderstanding every couple
>> weeks. It's comp.programming.threads' equivalent of `void main'.)
>>
>> Or, as my first threading teacher put it, "Don't Do That."

>
> Is there are C standard threading framework?


Yes, read C11. If you are familiar with pthreads, you'll see where most
of the new primitives originate.

> Threaded code is a de-facto reality in today's multi-core environment.
> Save for the embedded sector, most systems will run threads in
> parallel, and that is that.


Only if you incorporate threads in your code either explicitly or
implicitly with something like OpenMP.

> C has to recognize this watershed moment
> in the refinement of the language.


It has.

> While the specifics of an implementation within a given operating
> system are not C issues, certain common optimizations can be a problem
> with certain algorithms, and so there ought to be a C solution to the
> problem. What is it about the volatile attribute that makes it
> insufficient in your mind to the problem presented by threaded code?


Given you are the one going against conventional wisdom, what in your
mind makes volatile a solution to the problem presented by threaded code?

In addition, what is "the problem presented by threaded code"?

--
Ian Collins
 
Reply With Quote
 
Uncle Steve
Guest
Posts: n/a
 
      07-06-2012
On Fri, Jul 06, 2012 at 08:33:45PM -0700, Joshua Maurice wrote:
> On Jul 6, 4:25*pm, Uncle Steve <(E-Mail Removed)> wrote:
> > On Fri, Jul 06, 2012 at 08:12:57PM -0700, Joshua Maurice wrote:
> > > On Jul 6, 3:54*pm, Uncle Steve <(E-Mail Removed)> wrote:
> > > > On Fri, Jul 06, 2012 at 07:39:56PM -0700, Joshua Maurice wrote:
> > > > > I will say it again: the C89 and C99 standards do not mean what you
> > > > > think. What the compiler writers and thread library writers understand
> > > > > volatile to mean is not what you understand volatile to mean, and at
> > > > > the end of the day what the compiler writers and thread library
> > > > > writers think is paramount. You may be able to get this to work for
> > > > > specific platforms with specific compilers. I suggest you ask in a
> > > > > location specific to such implementations for such platform specific
> > > > > hackery. However, do not look at the C standard for guidance on this.

> >
> > > > Um, what is it that compiler writers and thread library writers
> > > > understand volatile to mean?

> >
> > >http://www.open-std.org/jtc1/sc22/wg...006/n2016.html

> >
> > > > > In the C11 parlance, what you're trying to write requires the "weak"
> > > > > atomics, such as relaxed, acquire, release, and consume memory
> > > > > operations. Attempting to write stuff like this without C11 support
> > > > > with the C11 primitives is a wholly platform specific affair, and
> > > > > neither C89 nor C90 can help you there. volatile specifically cannot
> > > > > help you (barring platform specific documentation to the contrary).

> >
> > > > You seem to be making too many assumptions about my code.

> >
> > > I think it's pretty clear from what you've written else-thread.

> >
> > > > > From else-thread:
> > > > > On Jul 6, 2:29 pm, Uncle Steve <(E-Mail Removed)> wrote:
> > > > > > On Sat, Jul 07, 2012 at 12:37:59PM +1200, Ian Collins wrote:
> > > > > > > Then use your platform's native threading primitives.

> >
> > > > > > Doing so would incur a performance penalty in comparison to my
> > > > > > synchronization primitives in some circumstances.

> >
> > > > > That's your problem. You have broken code. Your options are:
> > > > > 1- broken code (e.g. using volatile and asm memory barriers absent
> > > > > platform specific guarantees)
> > > > > 2- code that relies on platform specific guarantees (e.g. with using
> > > > > volatile and asm memory barriers)
> > > > > 3- "slow" code (e.g. with posix mutexes)
> > > > > 4- C11 code

> >
> > > > How do you know, a priori, that my code is broken? *Do I have to
> > > > change my passwords again?

> >
> > > How do I know it's broken? By your own admission, you're using
> > > volatile to try and affect inter-thread visibility (absent constructs
> > > that actually give inter-thread visibility). By your previous
> > > statements about using the C standard to derive useful threading
> > > semantics for volatile, I doubt you've looked at the compiler
> > > documentation and hardware documentation for your implementation. Thus
> > > you have broken code. (I don't think you are trying to nit on "it
> > > could be right by coincidence".)

> >
> > Well you know what? *You're going to have to wait until version 1.0
> > before you get to decide how wrong it is.

>
> Let me share with you a story. I currently work for a company selling
> Enterprise software. The software is heavily intertwined with
> databases. We have a license for a large piece of code that does heavy
> duty sorting. We have a contract with the guys who wrote this sorting
> library for support and maintenance. One of our customers upgraded
> some of their hardware, ran some tests - or possibly worse ran actual
> usage - and noticed that one row out of a few billion was "missing".
> Our engine dropped it, somewhere. It should be in the output, but it
> wasn't. Of course, this is very bad for our company. This could cost
> millions of dollars in sales. So, we get the guys who wrote the
> sorting library, and immediately fly them out to us. We get them to
> work on the code. I was only tangentially related to this process. It
> took a week or so of work to find and fix the issue. What was the
> problem? The guys who wrote the sorting library used "volatile", and
> the customer just upgraded to some itanium processor or something. A
> quick fix/hack later, and our customer was back in business, our
> millions of dollars was secure, as was our company image and
> reputation.
>
> Use volatile at your own risk. I don't plan on using your software if
> I can help it.


Well I wouldn't want you to use any software that you didn't want to
run.


Regards,

Uncle Steve

--
The moon has never been closer.

 
Reply With Quote
 
Uncle Steve
Guest
Posts: n/a
 
      07-06-2012
On Sat, Jul 07, 2012 at 03:50:59PM +1200, Ian Collins wrote:
> On 07/ 7/12 09:29 AM, Uncle Steve wrote:
> >On Sat, Jul 07, 2012 at 12:37:59PM +1200, Ian Collins wrote:
> >>On 07/ 7/12 08:27 AM, Uncle Steve wrote:
> >>>On Sat, Jul 07, 2012 at 11:29:02AM +1200, Ian Collins wrote:
> >>>>On 07/ 7/12 06:33 AM, Uncle Steve wrote:
> >>>>>
> >>>>>Is there are C standard threading framework?
> >>>>
> >>>>Yes, read C11. If you are familiar with pthreads, you'll see where most
> >>>>of the new primitives originate.
> >>>
> >>>Well, I don't follow gcc development, so I don't know when those
> >>>features will be available on my system.
> >>
> >>Then use your platform's native threading primitives.

> >
> >Doing so would incur a performance penalty in comparison to my
> >synchronization primitives in some circumstances.

>
> In other words, correctness would incur a performance penalty in
> comparison to your synchronization primitives in some circumstances.


You probably shouldn't be using google translate to massage my code
into something you can understand. It doesn't work like that.

> >>>O.K., so do nested structure elements inherit the parent structure's
> >>>volatile attribute?
> >>
> >>A volatile T is a volatile T no matter what it contains.

> >
> >Look. In threaded applications, the truth associated with the value
> >associated with certain variables can be somewhat indeterminate. If
> >that's true in your code, you might want to be aware of it.

>
> If I could parse that, I'd respond to it.


Yeah well it happens.

> >>>>>While the specifics of an implementation within a given operating
> >>>>>system are not C issues, certain common optimizations can be a problem
> >>>>>with certain algorithms, and so there ought to be a C solution to the
> >>>>>problem. What is it about the volatile attribute that makes it
> >>>>>insufficient in your mind to the problem presented by threaded code?
> >>>>
> >>>>Given you are the one going against conventional wisdom, what in your
> >>>>mind makes volatile a solution to the problem presented by threaded
> >>>>code?
> >>>>
> >>>>In addition, what is "the problem presented by threaded code"?
> >>>
> >>>Well, code optimization from global CSE might eliminate memory
> >>>accesses to variable that could be modified by other threads in ways
> >>>that affect the algorithm. Depends of the code.
> >>
> >>If the code depends on volatile, it is broken. Use the atomics or
> >>synchronisation primitives provided by the language or platform. They
> >>exist for a reason.

> >
> >You aren't listening to me.

>
> You aren't making much sense.
>
> An example of you your synchronization primitives would clear things up.


Sorry, you're going to have to wait.


Regards,

Uncle Steve

--
The moon has never been closer.

 
Reply With Quote
 
Joshua Maurice
Guest
Posts: n/a
 
      07-06-2012
On Jul 6, 11:01*am, Uncle Steve <(E-Mail Removed)> wrote:
> On Sat, Jul 07, 2012 at 09:20:57AM +1200, Ian Collins wrote:
> > On 07/ 7/12 05:08 AM, Uncle Steve wrote:
> > >This is a concern in my mind right now as I'm writing some posix
> > >threads code, and so obviously there are a large number of variables
> > >which ought to be declared volatile.

>
> > What leads you to that conclusion? *That line of though usually implies
> > you are misunderstanding the relationship between volatile and threads.

>
> > What are you trying to achieve with volatile?

>
> Well, I have some data structures that will be accessed from arbitrary
> threads, so I want to make sure there's no funny business happening
> behind the scenes where the compiler decides that certain accesses are
> optional.
>
> [snip]
>
> The variable declared volatile are required otherwise some variable
> accesses are optimized out, giving inaccurate results during the data
> acquisition phase. *The problems here are magnified when these access
> patterns occur with competing threads. *IIRC, mutexes are not memory
> access barriers and solve different problems.


To be topical, here's the answer for C11: volatile is useless as a
portable threading construct. Do not use it. It's (maybe) useful in a
portable way only for 3 obscure situations: MMIO, setjmp and longjmp
stuff, and signal handling. If you properly use C11 mutexes, there is
absolutely no need for volatile. To paraphrase you else-thread, there
will be no "funny business" if you use mutexes correctly. It tells the
compiler, the hardware, and anything else relevant, to obey the
semantics of the mutex. volatile is similarly useless when you
correctly use the new "weak" C11 atomics. volatile adds nothing
(portably).

Now, to finally answer your question, C11 threading semantics,
including the lack of useful volatile semantics, is basically copied
wholesale from pthreads. Don't use volatile as a portable threading
construct with pthreads either. pthread mutexes do everything you
need. volatile adds absolutely nothing (portably).

(Yes, you can accomplish useful code with volatile for specific
platform and specific compilers with specific settings. That's an
"advanced" topic that I won't cover now.)

Now, what do you mean by "mutexes are not memory access barriers"?
Mutexes do two things: they provide blocking semantics for mutual
exclusion, and they guarantee visibility ala the usual "happens-
before" semantics. Mutexes are implemented with hardware memory
fences / barriers. This is all true for mutexes in pthreads, win32
threads, Boost threads, ACE threads, C11 threads, C++11 threads, and
every case I can recall seeing the word "mutex".
 
Reply With Quote
 
Tim Rentsch
Guest
Posts: n/a
 
      07-07-2012
Ben Bacarisse <(E-Mail Removed)> writes:

> [can optimization sometimes be done even though volatile is used?]
>
> To a very large extent, the C standard washes it hands of volatile
> objects. Sure, it says a fair bit about what *may* happen but it also
> says "[w]hat constitutes an access to an object that has volatile-
> qualified type is implementation-defined" (6.7.3 p7) and "[a]n actual
> implementation need not evaluate part of an expression if it can deduce
> that [...] no needed side effects are produced (including any caused by
> [...] accessing a volatile object)" (5.1.2.3 p4).
>
> Together, these give an implementation so much leeway that you often
> need to refer to the implementation, not the standard. For example, an
> implementation may well be able to deduce that the assignment is not a
> "needed side effect", coming as it does at the start of main. Equally,
> an implementation may treat all accesses to volatile-qualified objects
> with kid gloves.


My conclusion is similar to yours, but we're 180 degrees
apart on the reading of 5.1.2.3 p4. Any access to a
volatile object potentially causes a needed side-effect, and
there is -- by definition -- _no way_ for an implementation
to know whether or which accesses to volatile objects will
cause such a side-effect. However an implementation chooses
to define what actions constitute an access to a volatile
object, these actions _must_ be carried out for each such
access that is evaluated during a program execution, whether
it seems to have any bearing on other "needed" side-effects
or not. All the latitude comes from 6.7.3 p7; none comes
from 5.1.2.3 p4, and in fact just the opposite. Such
actions must in fact be carried out during actual execution,
and must not be "optimized away" no matter whether they seem
to have any bearing on other program behavior or not.

Anyway that's my reading/interpretation; I don't mean to
start any arguments about which reading is right, but I
thought you would want to know that they are different.
 
Reply With Quote
 
Ian Collins
Guest
Posts: n/a
 
      07-07-2012
On 07/ 7/12 08:27 AM, Uncle Steve wrote:
> On Sat, Jul 07, 2012 at 11:29:02AM +1200, Ian Collins wrote:
>> On 07/ 7/12 06:33 AM, Uncle Steve wrote:
>>>
>>> Is there are C standard threading framework?

>>
>> Yes, read C11. If you are familiar with pthreads, you'll see where most
>> of the new primitives originate.

>
> Well, I don't follow gcc development, so I don't know when those
> features will be available on my system.


Then use your platform's native threading primitives.

>>> Threaded code is a de-facto reality in today's multi-core environment.
>>> Save for the embedded sector, most systems will run threads in
>>> parallel, and that is that.

>>
>> Only if you incorporate threads in your code either explicitly or
>> implicitly with something like OpenMP.

>
> Well, sure, but I'd like to think that multithreaded applications will
> be popular. It helps to improve the interactivity of applications
> with a GUI frontend for one thing, never mind what you can do with
> message-passing interfaces or asynchronus network I/O threads.


There already are.

>>> C has to recognize this watershed moment
>>> in the refinement of the language.

>>
>> It has.

>
> O.K., so do nested structure elements inherit the parent structure's
> volatile attribute?


A volatile T is a volatile T no matter what it contains.

>>> While the specifics of an implementation within a given operating
>>> system are not C issues, certain common optimizations can be a problem
>>> with certain algorithms, and so there ought to be a C solution to the
>>> problem. What is it about the volatile attribute that makes it
>>> insufficient in your mind to the problem presented by threaded code?

>>
>> Given you are the one going against conventional wisdom, what in your
>> mind makes volatile a solution to the problem presented by threaded code?
>>
>> In addition, what is "the problem presented by threaded code"?

>
> Well, code optimization from global CSE might eliminate memory
> accesses to variable that could be modified by other threads in ways
> that affect the algorithm. Depends of the code.


If the code depends on volatile, it is broken. Use the atomics or
synchronisation primitives provided by the language or platform. They
exist for a reason.

--
Ian Collins
 
Reply With Quote
 
Ben Bacarisse
Guest
Posts: n/a
 
      07-07-2012
Tim Rentsch <(E-Mail Removed)> writes:

> Ben Bacarisse <(E-Mail Removed)> writes:
>
>> [can optimization sometimes be done even though volatile is used?]
>>
>> To a very large extent, the C standard washes it hands of volatile
>> objects. Sure, it says a fair bit about what *may* happen but it also
>> says "[w]hat constitutes an access to an object that has volatile-
>> qualified type is implementation-defined" (6.7.3 p7) and "[a]n actual
>> implementation need not evaluate part of an expression if it can deduce
>> that [...] no needed side effects are produced (including any caused by
>> [...] accessing a volatile object)" (5.1.2.3 p4).
>>
>> Together, these give an implementation so much leeway that you often
>> need to refer to the implementation, not the standard. For example, an
>> implementation may well be able to deduce that the assignment is not a
>> "needed side effect", coming as it does at the start of main. Equally,
>> an implementation may treat all accesses to volatile-qualified objects
>> with kid gloves.

>
> My conclusion is similar to yours, but we're 180 degrees
> apart on the reading of 5.1.2.3 p4. Any access to a
> volatile object potentially causes a needed side-effect, and
> there is -- by definition -- _no way_ for an implementation
> to know whether or which accesses to volatile objects will
> cause such a side-effect. However an implementation chooses
> to define what actions constitute an access to a volatile
> object, these actions _must_ be carried out for each such
> access that is evaluated during a program execution, whether
> it seems to have any bearing on other "needed" side-effects
> or not. All the latitude comes from 6.7.3 p7; none comes
> from 5.1.2.3 p4, and in fact just the opposite. Such
> actions must in fact be carried out during actual execution,
> and must not be "optimized away" no matter whether they seem
> to have any bearing on other program behavior or not.
>
> Anyway that's my reading/interpretation; I don't mean to
> start any arguments about which reading is right, but I
> thought you would want to know that they are different.


OK, I can see that. I.e. is there permission to deduce that the side
effect is needed or simply to deduce that it is produced? I will pin my
colours firmly to fence I am sitting on and say hmmm...

--
Ben.
 
Reply With Quote
 
Joshua Maurice
Guest
Posts: n/a
 
      07-07-2012
On Jul 6, 2:20*pm, Uncle Steve <(E-Mail Removed)> wrote:
> On Fri, Jul 06, 2012 at 04:58:09PM -0700, Joshua Maurice wrote:
> > To be topical, here's the answer for C11: volatile is useless as a
> > portable threading construct. Do not use it. It's (maybe) useful in a
> > portable way only for 3 obscure situations: MMIO, setjmp and longjmp
> > stuff, and signal handling. If you properly use C11 mutexes, there is
> > absolutely no need for volatile. To paraphrase you else-thread, there
> > will be no "funny business" if you use mutexes correctly. It tells the
> > compiler, the hardware, and anything else relevant, to obey the
> > semantics of the mutex. volatile is similarly useless when you
> > correctly use the new "weak" C11 atomics. volatile adds nothing
> > (portably).

>
> > Now, to finally answer your question, C11 threading semantics,
> > including the lack of useful volatile semantics, is basically copied
> > wholesale from pthreads. Don't use volatile as a portable threading
> > construct with pthreads either. pthread mutexes do everything you
> > need. volatile adds absolutely nothing (portably).

>
> > (Yes, you can accomplish useful code with volatile for specific
> > platform and specific compilers with specific settings. That's an
> > "advanced" topic that I won't cover now.)

>
> > Now, what do you mean by "mutexes are not memory access barriers"?
> > Mutexes do two things: they provide blocking semantics for mutual
> > exclusion, and they guarantee visibility ala the usual "happens-
> > before" semantics. Mutexes are implemented with hardware memory
> > fences / barriers. This is all true for mutexes in pthreads, win32
> > threads, Boost threads, ACE threads, C11 threads, C++11 threads, and
> > every case I can recall seeing the word "mutex".

>
> Well, mutexes are barriers for the memory accesses associated with the
> mutex itself, but not in general. *Reading the above I can tell that
> you think I'm using POSIX mutexes, however that is not the case.


I strongly suggest that you don't use the word "mutex" for your code
because you will confuse most readers. Most readers will associate
"mutex" with both mutual exclusion and "happens-before" global memory
visibility. That's how the term has been commonly used (ex: posix
pthreads), and how it will continue to commonly be used (ex: C11).

>*I am
> using a custom locking scheme that allows for concurrent readers, but
> is exclusive for writers. *As a consequence, the behavior of
> variables marked volatile in my code is critical, so I don't want to
> mistakenly use it in a way that results in surprises.
>
> Now you can say that what I am doing is non-portable, but you would
> be wrong there since my algorithms are in fact portable as long as I
> am following the rules of the C standard. *Perhaps the proper term is
> limited portability as I rely on a tiny amount of platform specific
> asm. *(One instruction.)


I will say it again: the C89 and C99 standards do not mean what you
think. What the compiler writers and thread library writers understand
volatile to mean is not what you understand volatile to mean, and at
the end of the day what the compiler writers and thread library
writers think is paramount. You may be able to get this to work for
specific platforms with specific compilers. I suggest you ask in a
location specific to such implementations for such platform specific
hackery. However, do not look at the C standard for guidance on this.

In the C11 parlance, what you're trying to write requires the "weak"
atomics, such as relaxed, acquire, release, and consume memory
operations. Attempting to write stuff like this without C11 support
with the C11 primitives is a wholly platform specific affair, and
neither C89 nor C90 can help you there. volatile specifically cannot
help you (barring platform specific documentation to the contrary).

From else-thread:
On Jul 6, 2:29 pm, Uncle Steve <(E-Mail Removed)> wrote:
> On Sat, Jul 07, 2012 at 12:37:59PM +1200, Ian Collins wrote:
> > Then use your platform's native threading primitives.

>
> Doing so would incur a performance penalty in comparison to my
> synchronization primitives in some circumstances.


That's your problem. You have broken code. Your options are:
1- broken code (e.g. using volatile and asm memory barriers absent
platform specific guarantees)
2- code that relies on platform specific guarantees (e.g. with using
volatile and asm memory barriers)
3- "slow" code (e.g. with posix mutexes)
4- C11 code
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
"Try:" which only encompasses head of compound statement Jameson.Quinn@gmail.com Python 9 08-29-2007 12:58 AM
sizeof(aStruct) returns fault number nass C++ 2 09-22-2006 03:24 PM
Applicability KB 831138: app that uses WebRequest has OutOfMemoryE =?Utf-8?B?dmVjb3pvQG9ubGluZS5ub3NwYW0=?= ASP .Net 9 01-05-2006 08:50 PM
wired / wireless network mixture or not ? ReceT Wireless Networking 3 07-12-2004 02:54 AM
gaussian mixture? GBartgo C++ 2 11-02-2003 12:10 AM



Advertisments