sepavloff added a comment.

The solution in D76384 <https://reviews.llvm.org/D76384> (Move FPFeatures from 
BinaryOperator bitfields to Trailing storage) causes several concerns.

1. It requires substantial code changes. The patch in D76384 
<https://reviews.llvm.org/D76384> is already large and we need to do similar 
work for UnaryOperator, CallExpr, CXXOperatorCallExpr, CastExpr and probably 
some others. In contrast, using pragma nodes does not require changes to 
existing nodes.

2. This solution means some loss of source information. Pragma is not 
represented in AST and some source analysis tools probably may suffer from it.

3. In some cases pragma anyway must be present in AST. For instance, it is 
useful to have a pragma that sets rounding mode, without need of `fesetround`. 
Such pragma would make codegen to emit some code, it is reasonable to do that 
during treatment of corresponding statement node rather than of CompoundStmt.

4. Replication of FP environment into separate operation nodes actually change 
semantics. IEEE-754 considers FP environment as global state and this viewpoint 
is consistent with hardware viewpoint on many platforms. The replication make 
the environment a sum of operation properties. This change manifests itself in 
some cases. For instance, the following code:

        const float C1 = 3,1415926535;
        const float C2 = 1,4142135623;
        
        #pragma STDC FENV_ACCESS ON
        constexpr float func(float x, float y) {
            return x + y;
        }
        
        #pragma STDC FENV_ROUND FE_DOWNWARD
        float V1 = func(C1, C2);
        
        #pragma STDC FENV_ROUND FE_UPWARD
        float V2 = func(C1, C2);

If FP environment is replicated into every operation in the body of `func`, the 
operations will get "round.dynamic" as rounding mode argument. Such nodes 
cannot be evaluated in compile time. But if FP environment is global state, 
constant evaluator could just set it before evaluation. Behavior of constexpr 
functions in this case produce the same results as for non-constexpr variants.

5. Rounding mode can be turned into local property, but exception status anyway 
would require global state in constant evaluator. A function like:

        constexpr float func(float x, float y) {
            float z = x + y;
            if (fetestexcept(FE_OVERFLOW))
                z = 0;
            return z;
        }

can be evaluated in compile time but exceptions raised by operations need to be 
kept in some global state. So maintaining this global state anyway required for 
constant evaluator, no matter if it contains rounding mode or not.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D77545/new/

https://reviews.llvm.org/D77545



_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to