[PATCH] D77545: Represent FP options in AST by special Expression node

Serge Pavlov via Phabricator via cfe-commits cfe-commits at lists.llvm.org
Thu Apr 9 10:38:11 PDT 2020


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





More information about the cfe-commits mailing list