Assignment operator sequencing in C11 expressions

前端 未结 3 1901
既然无缘
既然无缘 2020-12-03 11:40

Introduction

The C11 standard (ISO/IEC 9899:2011) has introduced a new definition of side effect sequencing within an expression (see related question). The se

3条回答
  •  执笔经年
    2020-12-03 12:18

    Update

    I am changing my answer here, this is not well defined in C11 although it is in C++11. The key here is that the result of ++i is not an lvalue and therefore does not require an lvalue-to-rvalue conversion after ++i is evaluated and so we can not be assured that the result of ++i will be read afterwards. Which is different than C++ and so the defect report I originally linked to hinges on this critical fact:

    [...] the lvalue expression ++i and then do an lvalue-to-rvalue conversion on the result. guarantees that the incrementation side-effect is sequenced before the computation of the addition operation[...]

    we can see this by going to the C11 draft standard section 6.5.3.1 Prefix increment and decrement operators which says:

    [...]The expression ++E is equivalent to (E+=1).[...]

    and then section 6.5.16 Assignment operators which says (emphasis mine going forward):

    An assignment operator stores a value in the object designated by the left operand. An assignment expression has the value of the left operand after the assignment,111 but is not an lvalue.[...]

    and footnote 111 says:

    The implementation is permitted to read the object to determine the value but is not required to, even when the object has volatile-qualified type.

    There is no requirement to read the object to determine it's value even if it is volatile.

    Original Answer

    As far as I can tell this is actually well defined and this example was removed from the C++ draft standard which uses similar language. We can see this in 637. Sequencing rules and example disagree which says:

    the following expression is still listed as an example of undefined behavior:

    i = ++i + 1;
    

    However, it appears that the new sequencing rules make this expression well-defined:

    and the resolution was to strike the prefix example and use the postfix example instead which is clearly undefined:

    Change the example in 1.9 [intro.execution] paragraph 16 as follows:

    i = ++i i++ + 1; // the behavior is undefined

提交回复
热议问题