Sequence point after a return statement?

后端 未结 2 1359
无人及你
无人及你 2021-01-14 12:58

In my answer to a question here I explained what happened when postfix ++ was used on a global variable on the same line as a return statement.

The info

相关标签:
2条回答
  • 2021-01-14 13:23

    C 2011 (draft n1570) 6.8 4: “Each of the following is a full expression: … the (optional) expression in a return statement. There is a sequence point between the evaluation of a full expression and the evaluation of the next full expression to be evaluated.”

    So technically the sequence point is not after a return but is between the evaluation of the expression in the return and the next expression. Consider this code, called when a is initially 0:

    int a = 0;
    
    int Foo(void) { return a++; }
    
    void Bar(void)
    {
        int b = Foo() + a;
        …
    }
    

    In Foo() + a, whether Foo() or a is evaluated first is unspecified. We will consider both orders in light of both potential rules (sequence point after return versus sequence point between the expression of the return and the next full expression). If the implementation does a first, then it must do:

    a
    Sequence point
    Foo()
    +
    

    and then some other full expression would follow, so, by either rule, there would be a sequence point, and this code is the same either way, as far as we are concerned. The result is that b is set to 0.

    If the implementation does Foo() first, then, with the “sequence pointer after a return” rule, the implementation must do:

    Sequence point
    Foo()
    Sequence point
    a
    +
    

    This code would have defined behavior: a is incremented by the side effect in Foo, and that is complete before a is accessed, then + is performed. The result is that a is set to 1. Although the result may be 0 or 1 with this “sequence point after return” rule, it is merely unspecified which of the two orders is used; the behavior is not completely undefined.

    However, if the implementation does Foo() first and uses the standard C rule of “sequence point between the expression of a return and the next full expression”, then we have:

    Sequence point
    Foo()
    ???
    a
    ???
    +
    ???
    

    The “???” mark places where the required sequence point might be—anywhere after the return and before the next full expression. In this case, the value of a might be accessed in a and modified in Foo(), and there is no intervening sequence point. That is undefined behavior.

    Therefore, the rule “sequence point after the expression of a return and before next full expression” is different from “sequence point immediately after a return”; the first has undefined behavior in this example, and the second does not.

    0 讨论(0)
  • 2021-01-14 13:32

    I don't think you're going to find what you're looking for. no text regarding sequence points can be found that's true, it's only implied by section 6.8 p4.

    The C++ standard (ISO/IEC 14882:2003) in section 1.9 (footnote 11) states the fact that a sequence point after the return is not explicitily written anywhere in the C standards:

    11) The sequence point at the function return is not explicitly specified in ISO C, and can be considered redundant with sequence points at full-expressions, but the extra clarity is important in C + +. In C + +, there are more ways in which a called function can terminate its execution, such as the throw of an exception.

    0 讨论(0)
提交回复
热议问题