序列点和副作用:在C11安静的变化? [英] Sequence points and side effects: Quiet change in C11?

查看:162
本文介绍了序列点和副作用:在C11安静的变化?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

C99§6.5前pressions


  

(1)的前pression是指定一个值的计算运算和操作数的序列,或者,指定的对象或功能,或产生副作用,或执行它们的组合。


  
  

(2)previous和下一个序列点之间的对象应具有其存储的值在由前pression评价修改最多一次。 72)此外,前一个值是只读的,以确定该值将被存储。 73)


与脚注


  

72)的浮点状态标志不是一个对象,并且可以多次设置一个前pression内。


  
  

73)这一段使得不确定的语句前pressions如

  I = + I + 1;
    A [++] =我;


  
  

同时允许

  I = I + 1;
    一个[我] =我;


其中C11§6.5改为(文(1)具有增编):


  

(1)[...]操作者的操作数的值计算是操作者的结果的值计算之前测序


  
  

(2)如果一个标量对象上的副作用是相对于同一标量对象在任一个不同的副作用,或使用相同的标量对象的值的值计算unsequenced,行为是不确定的。如果有一个前pression的SUBEX pressions多个允许排序,该行为是未定义如果在任何排序中发生这样的unsequenced副作用。 84)


,其中脚注84 C11是相同的C99中73

我有点糊涂了......我读C11(2)[...]或者(在同一标对象在不同的​​副作用)或(使用同一个标量对象的值的值计算)[...] 这似乎甚至不允许富= ++我(有一个副作用,我们使用不同的改变对象的值)。我不是一个母语,虽然如此,这将是很好,如果能告诉我这句话应该如何经分析。我明白了C99,但我不太明白C11的措辞。

总之,实际的问题:这是从C99到C11的变化,或者是这些措辞相同呢?如果是这样,为什么它已经被改变?如果没有的话,可能会有人给一个前pression这是UB在C99,但不是在C11或相反的例子吗?


解决方案

C11(和C ++ 11)已完全重新设计测序的措辞,因为C11目前拥有的线程,它必须解释线程之间有什么顺序访问相同的数据装置。该委员会的目的是为了让事情向后兼容C99的情况下,只有一个执行线程。

让我们来看看C99版:



  1.   

    在previous和下一个顺序点之间




  2.   

    对象




  3.   




  4.   

    其存储的值修改最多一次




  5.   

    由前pression的评价。



相比,新文本


  

如果在一个副作用


不同terminolgie 4,修改储值


  

标对象


在previous措辞在第2限制新的文本只是说
一些关于标对象


  

是相对于unsequenced要么


unsequenced的概念是在1.两个语句泛化
由一序列点分离。认为修改两个线程
不使用锁或类似的东西的数据相同。


  

同样的标量对象在不同的​​副作用


对象只允许进行一次改性


  

或一个值
  使用同一个标量对象的值计算,


或该值的读出可能不会同时出现在修改


  

该行为是未定义的。


在须在第3被隐含这样说。所有的应当的领先优势,以UB如果
他们并不满足。

C99 §6.5 Expressions

(1) An expression is a sequence of operators and operands that specifies computation of a value, or that designates an object or a function, or that generates side effects, or that performs a combination thereof.

(2) Between the previous and next sequence point an object shall have its stored value modified at most once by the evaluation of an expression.72) Furthermore, the prior value shall be read only to determine the value to be stored.73)

with the footnotes

72) A floating-point status flag is not an object and can be set more than once within an expression.

73) This paragraph renders undefined statement expressions such as

    i = ++i + 1;
    a[i++] = i;

while allowing

    i = i + 1;
    a[i] = i;

where C11 §6.5 changed to (the text of (1) has an addendum):

(1) […] The value computations of the operands of an operator are sequenced before the value computation of the result of the operator.

(2) If a side effect on a scalar object is unsequenced relative to either a different side effect on the same scalar object or a value computation using the value of the same scalar object, the behavior is undefined. If there are multiple allowable orderings of the subexpressions of an expression, the behavior is undefined if such an unsequenced side effect occurs in any of the orderings.84)

where footnote 84 in C11 is the same as 73 in C99.

I'm a little confused… I read C11 (2) as "[…] either (a different side effect on the same scalar object) or (a value computation using the value of the same scalar object) […]" which seems to not even allow foo = ++i (there is a side effect and we use a value depending on the changed object). I'm not a native speaker, though, so it would be nice if one could tell me how this sentence should be "parsed". I understand C99, but I don't quite understand the wording of C11.

Anyway, the actual question: Is this a change from C99 to C11, or are these wordings equivalent? And if so, why it has been changed? And if not, could someone give an example of an expression which is UB in C99 but not in C11 or vice versa?

解决方案

C11 (and also C++11) has completely reworked the wording of sequencing because C11 now has threads, and it had to explain what sequencing between threads that access the same data means. The intention of the committee was to keep things backward compatible to C99 for the case where there is only one thread of execution.

Let's have a look at the C99 version:

  1. Between the previous and next sequence point

  2. an object

  3. shall have

  4. its stored value modified at most once

  5. by the evaluation of an expression.

compared to the new text

If a side effect on

different terminolgie for 4, modifying the stored value

a scalar object

a restriction of the previous wording in 2. The new text only says something about scalar objects

is unsequenced relative to either

unsequenced is a generalization of the concept in 1. that two statements were separated by a sequence point. Think of two threads that modify the same data without using a lock or something similar.

a different side effect on the same scalar object

the object is only allowed be modified once

or a value computation using the value of the same scalar object,

or a read of the value may not appear concurrently to the modification

the behavior is undefined.

The "shall" in 3. is saying this implicitly. All "shall"s lead to UB if they are not fulfilled.

这篇关于序列点和副作用:在C11安静的变化?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆