Author: Serge Pavlov Date: 2020-04-09T13:26:47+07:00 New Revision: c7ff5b38f27f812dcd6e2e8732208a39232dc284
URL: https://github.com/llvm/llvm-project/commit/c7ff5b38f27f812dcd6e2e8732208a39232dc284 DIFF: https://github.com/llvm/llvm-project/commit/c7ff5b38f27f812dcd6e2e8732208a39232dc284.diff LOG: [FPEnv] Use single enum to represent rounding mode Now compiler defines 5 sets of constants to represent rounding mode. These are: 1. `llvm::APFloatBase::roundingMode`. It specifies all 5 rounding modes defined by IEEE-754 and is used in `APFloat` implementation. 2. `clang::LangOptions::FPRoundingModeKind`. It specifies 4 of 5 IEEE-754 rounding modes and a special value for dynamic rounding mode. It is used in clang frontend. 3. `llvm::fp::RoundingMode`. Defines the same values as `clang::LangOptions::FPRoundingModeKind` but in different order. It is used to specify rounding mode in in IR and functions that operate IR. 4. Rounding mode representation used by `FLT_ROUNDS` (C11, 5.2.4.2.2p7). Besides constants for rounding mode it also uses a special value to indicate error. It is convenient to use in intrinsic functions, as it represents platform-independent representation for rounding mode. In this role it is used in some pending patches. 5. Values like `FE_DOWNWARD` and other, which specify rounding mode in library calls `fesetround` and `fegetround`. Often they represent bits of some control register, so they are target-dependent. The same names (not values) and a special name `FE_DYNAMIC` are used in `#pragma STDC FENV_ROUND`. The first 4 sets of constants are target independent and could have the same numerical representation. It would simplify conversion between the representations. Also now `clang::LangOptions::FPRoundingModeKind` and `llvm::fp::RoundingMode` do not contain the value for IEEE-754 rounding direction `roundTiesToAway`, although it is supported natively on some targets. This change defines all the rounding mode type via one `llvm::RoundingMode`, which also contains rounding mode for IEEE rounding direction `roundTiesToAway`. Differential Revision: https://reviews.llvm.org/D77379 Added: Modified: clang/include/clang/Basic/LangOptions.def clang/include/clang/Basic/LangOptions.h clang/include/clang/Sema/Sema.h clang/lib/CodeGen/CodeGenFunction.cpp clang/lib/Frontend/CompilerInvocation.cpp clang/lib/Sema/SemaAttr.cpp clang/lib/Sema/SemaExpr.cpp clang/lib/Serialization/ASTReader.cpp llvm/docs/LangRef.rst llvm/include/llvm/ADT/APFloat.h llvm/include/llvm/ADT/FloatingPointMode.h llvm/include/llvm/IR/FPEnv.h llvm/include/llvm/IR/IRBuilder.h llvm/include/llvm/IR/IntrinsicInst.h llvm/lib/Analysis/ConstantFolding.cpp llvm/lib/IR/FPEnv.cpp llvm/lib/IR/IRBuilder.cpp llvm/lib/IR/IntrinsicInst.cpp llvm/lib/Support/APFloat.cpp llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp llvm/unittests/IR/IRBuilderTest.cpp Removed: ################################################################################ diff --git a/clang/include/clang/Basic/LangOptions.def b/clang/include/clang/Basic/LangOptions.def index 51dc87b0b671..bddd0f0ddcd8 100644 --- a/clang/include/clang/Basic/LangOptions.def +++ b/clang/include/clang/Basic/LangOptions.def @@ -263,7 +263,7 @@ LANGOPT(SinglePrecisionConstants , 1, 0, "treating double-precision floating poi LANGOPT(FastRelaxedMath , 1, 0, "OpenCL fast relaxed math") /// FP_CONTRACT mode (on/off/fast). ENUM_LANGOPT(DefaultFPContractMode, FPContractModeKind, 2, FPC_Off, "FP contraction type") -ENUM_LANGOPT(FPRoundingMode, FPRoundingModeKind, 3, FPR_ToNearest, "FP Rounding Mode type") +ENUM_LANGOPT(FPRoundingMode, RoundingMode, 3, RoundingMode::NearestTiesToEven, "FP Rounding Mode type") ENUM_LANGOPT(FPExceptionMode, FPExceptionModeKind, 2, FPE_Ignore, "FP Exception Behavior Mode type") LANGOPT(NoBitFieldTypeAlign , 1, 0, "bit-field type alignment") LANGOPT(HexagonQdsp6Compat , 1, 0, "hexagon-qdsp6 backward compatibility") diff --git a/clang/include/clang/Basic/LangOptions.h b/clang/include/clang/Basic/LangOptions.h index 0a0cbaf80ae8..95b435ba9f34 100644 --- a/clang/include/clang/Basic/LangOptions.h +++ b/clang/include/clang/Basic/LangOptions.h @@ -19,6 +19,7 @@ #include "clang/Basic/ObjCRuntime.h" #include "clang/Basic/Sanitizers.h" #include "clang/Basic/Visibility.h" +#include "llvm/ADT/FloatingPointMode.h" #include "llvm/ADT/StringRef.h" #include "llvm/ADT/Triple.h" #include <string> @@ -53,6 +54,7 @@ enum class MSVtorDispMode { Never, ForVBaseOverride, ForVFTable }; class LangOptions : public LangOptionsBase { public: using Visibility = clang::Visibility; + using RoundingMode = llvm::RoundingMode; enum GCMode { NonGC, GCOnly, HybridGC }; enum StackProtectorMode { SSPOff, SSPOn, SSPStrong, SSPReq }; @@ -190,23 +192,9 @@ class LangOptions : public LangOptionsBase { FEA_On }; - // Values of the following enumerations correspond to metadata arguments - // specified for constrained floating-point intrinsics: - // http://llvm.org/docs/LangRef.html#constrained-floating-point-intrinsics. - - /// Possible rounding modes. - enum FPRoundingModeKind { - /// Rounding to nearest, corresponds to "round.tonearest". - FPR_ToNearest, - /// Rounding toward -Inf, corresponds to "round.downward". - FPR_Downward, - /// Rounding toward +Inf, corresponds to "round.upward". - FPR_Upward, - /// Rounding toward zero, corresponds to "round.towardzero". - FPR_TowardZero, - /// Is determined by runtime environment, corresponds to "round.dynamic". - FPR_Dynamic - }; + /// Alias for RoundingMode::NearestTiesToEven. + static constexpr unsigned FPR_ToNearest = + static_cast<unsigned>(llvm::RoundingMode::NearestTiesToEven); /// Possible floating point exception behavior. enum FPExceptionModeKind { @@ -386,6 +374,8 @@ class LangOptions : public LangOptionsBase { /// Floating point control options class FPOptions { + using RoundingMode = llvm::RoundingMode; + public: FPOptions() : fp_contract(LangOptions::FPC_Off), fenv_access(LangOptions::FEA_Off), @@ -395,10 +385,10 @@ class FPOptions { // Used for serializing. explicit FPOptions(unsigned I) - : fp_contract(static_cast<LangOptions::FPContractModeKind>(I & 3)), - fenv_access(static_cast<LangOptions::FEnvAccessModeKind>((I >> 2) & 1)), - rounding(static_cast<LangOptions::FPRoundingModeKind>((I >> 3) & 7)), - exceptions(static_cast<LangOptions::FPExceptionModeKind>((I >> 6) & 3)) + : fp_contract(I & 3), + fenv_access((I >> 2) & 1), + rounding ((I >> 3) & 7), + exceptions ((I >> 6) & 3) {} explicit FPOptions(const LangOptions &LangOpts) @@ -437,12 +427,12 @@ class FPOptions { void setDisallowFEnvAccess() { fenv_access = LangOptions::FEA_Off; } - LangOptions::FPRoundingModeKind getRoundingMode() const { - return static_cast<LangOptions::FPRoundingModeKind>(rounding); + RoundingMode getRoundingMode() const { + return static_cast<RoundingMode>(rounding); } - void setRoundingMode(LangOptions::FPRoundingModeKind RM) { - rounding = RM; + void setRoundingMode(RoundingMode RM) { + rounding = static_cast<unsigned>(RM); } LangOptions::FPExceptionModeKind getExceptionMode() const { @@ -454,7 +444,7 @@ class FPOptions { } bool isFPConstrained() const { - return getRoundingMode() != LangOptions::FPR_ToNearest || + return getRoundingMode() != RoundingMode::NearestTiesToEven || getExceptionMode() != LangOptions::FPE_Ignore || allowFEnvAccess(); } diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h index 4645ef8d2cd1..f2b0a9534c04 100644 --- a/clang/include/clang/Sema/Sema.h +++ b/clang/include/clang/Sema/Sema.h @@ -9592,7 +9592,7 @@ class Sema final { void ActOnPragmaFEnvAccess(LangOptions::FEnvAccessModeKind FPC); /// Called to set rounding mode for floating point operations. - void setRoundingMode(LangOptions::FPRoundingModeKind); + void setRoundingMode(llvm::RoundingMode); /// Called to set exception behavior for floating point operations. void setExceptionMode(LangOptions::FPExceptionModeKind); diff --git a/clang/lib/CodeGen/CodeGenFunction.cpp b/clang/lib/CodeGen/CodeGenFunction.cpp index b01a5a4c3685..05bf70e5cb22 100644 --- a/clang/lib/CodeGen/CodeGenFunction.cpp +++ b/clang/lib/CodeGen/CodeGenFunction.cpp @@ -115,21 +115,6 @@ CodeGenFunction::~CodeGenFunction() { OMPBuilder->finalize(); } -// Map the LangOption for rounding mode into -// the corresponding enum in the IR. -static llvm::fp::RoundingMode ToConstrainedRoundingMD( - LangOptions::FPRoundingModeKind Kind) { - - switch (Kind) { - case LangOptions::FPR_ToNearest: return llvm::fp::rmToNearest; - case LangOptions::FPR_Downward: return llvm::fp::rmDownward; - case LangOptions::FPR_Upward: return llvm::fp::rmUpward; - case LangOptions::FPR_TowardZero: return llvm::fp::rmTowardZero; - case LangOptions::FPR_Dynamic: return llvm::fp::rmDynamic; - } - llvm_unreachable("Unsupported FP RoundingMode"); -} - // Map the LangOption for exception behavior into // the corresponding enum in the IR. static llvm::fp::ExceptionBehavior ToConstrainedExceptMD( @@ -144,18 +129,17 @@ static llvm::fp::ExceptionBehavior ToConstrainedExceptMD( } void CodeGenFunction::SetFPModel() { - auto fpRoundingMode = ToConstrainedRoundingMD( - getLangOpts().getFPRoundingMode()); + llvm::RoundingMode RM = getLangOpts().getFPRoundingMode(); auto fpExceptionBehavior = ToConstrainedExceptMD( getLangOpts().getFPExceptionMode()); if (fpExceptionBehavior == llvm::fp::ebIgnore && - fpRoundingMode == llvm::fp::rmToNearest) + RM == llvm::RoundingMode::NearestTiesToEven) // Constrained intrinsics are not used. ; else { Builder.setIsFPConstrained(true); - Builder.setDefaultConstrainedRounding(fpRoundingMode); + Builder.setDefaultConstrainedRounding(RM); Builder.setDefaultConstrainedExcept(fpExceptionBehavior); } } diff --git a/clang/lib/Frontend/CompilerInvocation.cpp b/clang/lib/Frontend/CompilerInvocation.cpp index 23638e16a5b7..cebfb0b3d2af 100644 --- a/clang/lib/Frontend/CompilerInvocation.cpp +++ b/clang/lib/Frontend/CompilerInvocation.cpp @@ -47,6 +47,7 @@ #include "llvm/ADT/APInt.h" #include "llvm/ADT/ArrayRef.h" #include "llvm/ADT/CachedHashString.h" +#include "llvm/ADT/FloatingPointMode.h" #include "llvm/ADT/Hashing.h" #include "llvm/ADT/None.h" #include "llvm/ADT/Optional.h" @@ -3188,9 +3189,9 @@ static void ParseLangArgs(LangOptions &Opts, ArgList &Args, InputKind IK, Diags.Report(diag::err_drv_invalid_value) << A->getAsString(Args) << Val; } - LangOptions::FPRoundingModeKind FPRM = LangOptions::FPR_ToNearest; + auto FPRM = llvm::RoundingMode::NearestTiesToEven; if (Args.hasArg(OPT_frounding_math)) { - FPRM = LangOptions::FPR_Dynamic; + FPRM = llvm::RoundingMode::Dynamic; } Opts.setFPRoundingMode(FPRM); diff --git a/clang/lib/Sema/SemaAttr.cpp b/clang/lib/Sema/SemaAttr.cpp index 6a2f74479c48..9141a28381ad 100644 --- a/clang/lib/Sema/SemaAttr.cpp +++ b/clang/lib/Sema/SemaAttr.cpp @@ -940,7 +940,7 @@ void Sema::ActOnPragmaFPContract(LangOptions::FPContractModeKind FPC) { } } -void Sema::setRoundingMode(LangOptions::FPRoundingModeKind FPR) { +void Sema::setRoundingMode(llvm::RoundingMode FPR) { FPFeatures.setRoundingMode(FPR); } diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index 5c6b9471da11..6f7ff3729688 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -50,6 +50,7 @@ #include "llvm/Support/SaveAndRestore.h" using namespace clang; using namespace sema; +using llvm::RoundingMode; /// Determine whether the use of this declaration is valid, without /// emitting diagnostics. @@ -13639,7 +13640,7 @@ ExprResult Sema::CreateBuiltinBinOp(SourceLocation OpLoc, CompLHSTy = UsualUnaryConversions(LHS.get()).get()->getType(); if (ResultTy->isRealFloatingType() && - (getLangOpts().getFPRoundingMode() != LangOptions::FPR_ToNearest || + (getLangOpts().getFPRoundingMode() != RoundingMode::NearestTiesToEven || getLangOpts().getFPExceptionMode() != LangOptions::FPE_Ignore)) // Mark the current function as usng floating point constrained intrinsics if (FunctionDecl *F = dyn_cast<FunctionDecl>(CurContext)) { diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp index 22a3771e4b85..10276736414b 100644 --- a/clang/lib/Serialization/ASTReader.cpp +++ b/clang/lib/Serialization/ASTReader.cpp @@ -89,6 +89,7 @@ #include "llvm/ADT/APSInt.h" #include "llvm/ADT/ArrayRef.h" #include "llvm/ADT/DenseMap.h" +#include "llvm/ADT/FloatingPointMode.h" #include "llvm/ADT/FoldingSet.h" #include "llvm/ADT/Hashing.h" #include "llvm/ADT/IntrusiveRefCntPtr.h" @@ -139,6 +140,7 @@ using namespace clang; using namespace clang::serialization; using namespace clang::serialization::reader; using llvm::BitstreamCursor; +using llvm::RoundingMode; //===----------------------------------------------------------------------===// // ChainedASTReaderListener implementation diff --git a/llvm/docs/LangRef.rst b/llvm/docs/LangRef.rst index 3b2f7a42128f..5c054516c1e8 100644 --- a/llvm/docs/LangRef.rst +++ b/llvm/docs/LangRef.rst @@ -16556,6 +16556,7 @@ by the intrinsic, this argument must be one of the following strings: "round.downward" "round.upward" "round.towardzero" + "round.tonearestaway" If this argument is "round.dynamic" optimization passes must assume that the rounding mode is unknown and may change at runtime. No transformations that diff --git a/llvm/include/llvm/ADT/APFloat.h b/llvm/include/llvm/ADT/APFloat.h index f230cac4b596..37aa6dce7f11 100644 --- a/llvm/include/llvm/ADT/APFloat.h +++ b/llvm/include/llvm/ADT/APFloat.h @@ -18,6 +18,7 @@ #include "llvm/ADT/APInt.h" #include "llvm/ADT/ArrayRef.h" +#include "llvm/ADT/FloatingPointMode.h" #include "llvm/Support/ErrorHandling.h" #include <memory> @@ -182,13 +183,15 @@ struct APFloatBase { }; /// IEEE-754R 4.3: Rounding-direction attributes. - enum roundingMode { - rmNearestTiesToEven, - rmTowardPositive, - rmTowardNegative, - rmTowardZero, - rmNearestTiesToAway - }; + using roundingMode = llvm::RoundingMode; + + static constexpr roundingMode rmNearestTiesToEven = + RoundingMode::NearestTiesToEven; + static constexpr roundingMode rmTowardPositive = RoundingMode::TowardPositive; + static constexpr roundingMode rmTowardNegative = RoundingMode::TowardNegative; + static constexpr roundingMode rmTowardZero = RoundingMode::TowardZero; + static constexpr roundingMode rmNearestTiesToAway = + RoundingMode::NearestTiesToAway; /// IEEE-754R 7: Default exception handling. /// diff --git a/llvm/include/llvm/ADT/FloatingPointMode.h b/llvm/include/llvm/ADT/FloatingPointMode.h index fd06789c0f6e..c8c83d8be8d6 100644 --- a/llvm/include/llvm/ADT/FloatingPointMode.h +++ b/llvm/include/llvm/ADT/FloatingPointMode.h @@ -18,6 +18,32 @@ namespace llvm { +/// Rounding mode. +/// +/// Enumerates supported rounding modes, as well as some special values. The set +/// of the modes must agree with IEEE-754, 4.3.1 and 4.3.2. The constants +/// assigned to the IEEE rounding modes must agree with the values used by +/// FLT_ROUNDS (C11, 5.2.4.2.2p8). +/// +/// This value is packed into bitfield in some cases, including \c FPOptions, so +/// the rounding mode values and the special value \c Dynamic must fit into the +/// the bit field (now - 3 bits). The value \c Invalid is used only in values +/// returned by intrinsics to indicate errors, it should never be stored as +/// rounding mode value, so it does not need to fit the bit fields. +/// +enum class RoundingMode : int8_t { + // Rounding mode defined in IEEE-754. + TowardZero = 0, ///< roundTowardZero. + NearestTiesToEven = 1, ///< roundTiesToEven. + TowardPositive = 2, ///< roundTowardPositive. + TowardNegative = 3, ///< roundTowardNegative. + NearestTiesToAway = 4, ///< roundTiesToAway. + + // Special values. + Dynamic = 7, ///< Denotes mode unknown at compile time. + Invalid = -1 ///< Denotes invalid value. +}; + /// Represent ssubnormal handling kind for floating point instruction inputs and /// outputs. struct DenormalMode { diff --git a/llvm/include/llvm/IR/FPEnv.h b/llvm/include/llvm/IR/FPEnv.h index 0e7e96ff700a..eadfef2a82f8 100644 --- a/llvm/include/llvm/IR/FPEnv.h +++ b/llvm/include/llvm/IR/FPEnv.h @@ -24,19 +24,6 @@ namespace llvm { namespace fp { -/// Rounding mode used for floating point operations. -/// -/// Each of these values correspond to some metadata argument value of a -/// constrained floating point intrinsic. See the LLVM Language Reference Manual -/// for details. -enum RoundingMode : uint8_t { - rmDynamic, ///< This corresponds to "fpround.dynamic". - rmToNearest, ///< This corresponds to "fpround.tonearest". - rmDownward, ///< This corresponds to "fpround.downward". - rmUpward, ///< This corresponds to "fpround.upward". - rmTowardZero ///< This corresponds to "fpround.tozero". -}; - /// Exception behavior used for floating point operations. /// /// Each of these values correspond to some metadata argument value of a @@ -53,11 +40,11 @@ enum ExceptionBehavior : uint8_t { /// Returns a valid RoundingMode enumerator when given a string /// that is valid as input in constrained intrinsic rounding mode /// metadata. -Optional<fp::RoundingMode> StrToRoundingMode(StringRef); +Optional<RoundingMode> StrToRoundingMode(StringRef); /// For any RoundingMode enumerator, returns a string valid as input in /// constrained intrinsic rounding mode metadata. -Optional<StringRef> RoundingModeToStr(fp::RoundingMode); +Optional<StringRef> RoundingModeToStr(RoundingMode); /// Returns a valid ExceptionBehavior enumerator when given a string /// valid as input in constrained intrinsic exception behavior metadata. @@ -66,9 +53,5 @@ Optional<fp::ExceptionBehavior> StrToExceptionBehavior(StringRef); /// For any ExceptionBehavior enumerator, returns a string valid as /// input in constrained intrinsic exception behavior metadata. Optional<StringRef> ExceptionBehaviorToStr(fp::ExceptionBehavior); - -/// Converts rounding mode represented by fp::RoundingMode to the rounding mode -/// index used by APFloat. For fp::rmDynamic it returns None. -Optional<APFloatBase::roundingMode> getAPFloatRoundingMode(fp::RoundingMode); } #endif diff --git a/llvm/include/llvm/IR/IRBuilder.h b/llvm/include/llvm/IR/IRBuilder.h index 5bc31ab67fe0..b7ed3b9055bc 100644 --- a/llvm/include/llvm/IR/IRBuilder.h +++ b/llvm/include/llvm/IR/IRBuilder.h @@ -105,7 +105,7 @@ class IRBuilderBase { bool IsFPConstrained; fp::ExceptionBehavior DefaultConstrainedExcept; - fp::RoundingMode DefaultConstrainedRounding; + RoundingMode DefaultConstrainedRounding; ArrayRef<OperandBundleDef> DefaultOperandBundles; @@ -116,7 +116,7 @@ class IRBuilderBase { : Context(context), Folder(Folder), Inserter(Inserter), DefaultFPMathTag(FPMathTag), IsFPConstrained(false), DefaultConstrainedExcept(fp::ebStrict), - DefaultConstrainedRounding(fp::rmDynamic), + DefaultConstrainedRounding(RoundingMode::Dynamic), DefaultOperandBundles(OpBundles) { ClearInsertionPoint(); } @@ -268,7 +268,7 @@ class IRBuilderBase { } /// Set the rounding mode handling to be used with constrained floating point - void setDefaultConstrainedRounding(fp::RoundingMode NewRounding) { + void setDefaultConstrainedRounding(RoundingMode NewRounding) { DefaultConstrainedRounding = NewRounding; } @@ -278,7 +278,7 @@ class IRBuilderBase { } /// Get the rounding mode handling used with constrained floating point - fp::RoundingMode getDefaultConstrainedRounding() { + RoundingMode getDefaultConstrainedRounding() { return DefaultConstrainedRounding; } @@ -1130,8 +1130,8 @@ class IRBuilderBase { return (LC && RC) ? Insert(Folder.CreateBinOp(Opc, LC, RC), Name) : nullptr; } - Value *getConstrainedFPRounding(Optional<fp::RoundingMode> Rounding) { - fp::RoundingMode UseRounding = DefaultConstrainedRounding; + Value *getConstrainedFPRounding(Optional<RoundingMode> Rounding) { + RoundingMode UseRounding = DefaultConstrainedRounding; if (Rounding.hasValue()) UseRounding = Rounding.getValue(); @@ -1522,7 +1522,7 @@ class IRBuilderBase { CallInst *CreateConstrainedFPBinOp( Intrinsic::ID ID, Value *L, Value *R, Instruction *FMFSource = nullptr, const Twine &Name = "", MDNode *FPMathTag = nullptr, - Optional<fp::RoundingMode> Rounding = None, + Optional<RoundingMode> Rounding = None, Optional<fp::ExceptionBehavior> Except = None); Value *CreateNeg(Value *V, const Twine &Name = "", @@ -2145,7 +2145,7 @@ class IRBuilderBase { Intrinsic::ID ID, Value *V, Type *DestTy, Instruction *FMFSource = nullptr, const Twine &Name = "", MDNode *FPMathTag = nullptr, - Optional<fp::RoundingMode> Rounding = None, + Optional<RoundingMode> Rounding = None, Optional<fp::ExceptionBehavior> Except = None); // Provided to resolve 'CreateIntCast(Ptr, Ptr, "...")', giving a @@ -2368,7 +2368,7 @@ class IRBuilderBase { CallInst *CreateConstrainedFPCall( Function *Callee, ArrayRef<Value *> Args, const Twine &Name = "", - Optional<fp::RoundingMode> Rounding = None, + Optional<RoundingMode> Rounding = None, Optional<fp::ExceptionBehavior> Except = None); Value *CreateSelect(Value *C, Value *True, Value *False, diff --git a/llvm/include/llvm/IR/IntrinsicInst.h b/llvm/include/llvm/IR/IntrinsicInst.h index 81c9cab190ba..4d6319d87817 100644 --- a/llvm/include/llvm/IR/IntrinsicInst.h +++ b/llvm/include/llvm/IR/IntrinsicInst.h @@ -253,7 +253,7 @@ namespace llvm { public: bool isUnaryOp() const; bool isTernaryOp() const; - Optional<fp::RoundingMode> getRoundingMode() const; + Optional<RoundingMode> getRoundingMode() const; Optional<fp::ExceptionBehavior> getExceptionBehavior() const; // Methods for support type inquiry through isa, cast, and dyn_cast: diff --git a/llvm/lib/Analysis/ConstantFolding.cpp b/llvm/lib/Analysis/ConstantFolding.cpp index fe84af0ff120..eff153144dda 100644 --- a/llvm/lib/Analysis/ConstantFolding.cpp +++ b/llvm/lib/Analysis/ConstantFolding.cpp @@ -1828,10 +1828,8 @@ static Constant *ConstantFoldScalarCall1(StringRef Name, case Intrinsic::experimental_constrained_nearbyint: case Intrinsic::experimental_constrained_rint: { auto CI = cast<ConstrainedFPIntrinsic>(Call); - Optional<fp::RoundingMode> RMOp = CI->getRoundingMode(); - if (RMOp) - RM = getAPFloatRoundingMode(*RMOp); - if (!RM) + RM = CI->getRoundingMode(); + if (!RM || RM.getValue() == RoundingMode::Dynamic) return nullptr; break; } diff --git a/llvm/lib/IR/FPEnv.cpp b/llvm/lib/IR/FPEnv.cpp index ab68f55f834d..40f999e05b98 100644 --- a/llvm/lib/IR/FPEnv.cpp +++ b/llvm/lib/IR/FPEnv.cpp @@ -17,36 +17,42 @@ namespace llvm { -Optional<fp::RoundingMode> StrToRoundingMode(StringRef RoundingArg) { +Optional<RoundingMode> StrToRoundingMode(StringRef RoundingArg) { // For dynamic rounding mode, we use round to nearest but we will set the // 'exact' SDNodeFlag so that the value will not be rounded. - return StringSwitch<Optional<fp::RoundingMode>>(RoundingArg) - .Case("round.dynamic", fp::rmDynamic) - .Case("round.tonearest", fp::rmToNearest) - .Case("round.downward", fp::rmDownward) - .Case("round.upward", fp::rmUpward) - .Case("round.towardzero", fp::rmTowardZero) + return StringSwitch<Optional<RoundingMode>>(RoundingArg) + .Case("round.dynamic", RoundingMode::Dynamic) + .Case("round.tonearest", RoundingMode::NearestTiesToEven) + .Case("round.tonearestaway", RoundingMode::NearestTiesToAway) + .Case("round.downward", RoundingMode::TowardNegative) + .Case("round.upward", RoundingMode::TowardPositive) + .Case("round.towardzero", RoundingMode::TowardZero) .Default(None); } -Optional<StringRef> RoundingModeToStr(fp::RoundingMode UseRounding) { +Optional<StringRef> RoundingModeToStr(RoundingMode UseRounding) { Optional<StringRef> RoundingStr = None; switch (UseRounding) { - case fp::rmDynamic: + case RoundingMode::Dynamic: RoundingStr = "round.dynamic"; break; - case fp::rmToNearest: + case RoundingMode::NearestTiesToEven: RoundingStr = "round.tonearest"; break; - case fp::rmDownward: + case RoundingMode::NearestTiesToAway: + RoundingStr = "round.tonearestaway"; + break; + case RoundingMode::TowardNegative: RoundingStr = "round.downward"; break; - case fp::rmUpward: + case RoundingMode::TowardPositive: RoundingStr = "round.upward"; break; - case fp::rmTowardZero: + case RoundingMode::TowardZero: RoundingStr = "round.towardzero"; break; + default: + break; } return RoundingStr; } @@ -74,21 +80,4 @@ Optional<StringRef> ExceptionBehaviorToStr(fp::ExceptionBehavior UseExcept) { } return ExceptStr; } - -Optional<APFloatBase::roundingMode> -getAPFloatRoundingMode(fp::RoundingMode RM) { - switch (RM) { - case fp::rmDynamic: - return None; - case fp::rmToNearest: - return APFloat::rmNearestTiesToEven; - case fp::rmDownward: - return APFloat::rmTowardNegative; - case fp::rmUpward: - return APFloat::rmTowardPositive; - case fp::rmTowardZero: - return APFloat::rmTowardZero; - } - llvm_unreachable("Unexpected rounding mode"); -} } diff --git a/llvm/lib/IR/IRBuilder.cpp b/llvm/lib/IR/IRBuilder.cpp index bd16e0da3218..d1d93e7dbe73 100644 --- a/llvm/lib/IR/IRBuilder.cpp +++ b/llvm/lib/IR/IRBuilder.cpp @@ -760,7 +760,7 @@ CallInst *IRBuilderBase::CreateIntrinsic(Intrinsic::ID ID, CallInst *IRBuilderBase::CreateConstrainedFPBinOp( Intrinsic::ID ID, Value *L, Value *R, Instruction *FMFSource, const Twine &Name, MDNode *FPMathTag, - Optional<fp::RoundingMode> Rounding, + Optional<RoundingMode> Rounding, Optional<fp::ExceptionBehavior> Except) { Value *RoundingV = getConstrainedFPRounding(Rounding); Value *ExceptV = getConstrainedFPExcept(Except); @@ -794,7 +794,7 @@ Value *IRBuilderBase::CreateNAryOp(unsigned Opc, ArrayRef<Value *> Ops, CallInst *IRBuilderBase::CreateConstrainedFPCast( Intrinsic::ID ID, Value *V, Type *DestTy, Instruction *FMFSource, const Twine &Name, MDNode *FPMathTag, - Optional<fp::RoundingMode> Rounding, + Optional<RoundingMode> Rounding, Optional<fp::ExceptionBehavior> Except) { Value *ExceptV = getConstrainedFPExcept(Except); @@ -857,7 +857,7 @@ CallInst *IRBuilderBase::CreateConstrainedFPCmp( CallInst *IRBuilderBase::CreateConstrainedFPCall( Function *Callee, ArrayRef<Value *> Args, const Twine &Name, - Optional<fp::RoundingMode> Rounding, + Optional<RoundingMode> Rounding, Optional<fp::ExceptionBehavior> Except) { llvm::SmallVector<Value *, 6> UseArgs; diff --git a/llvm/lib/IR/IntrinsicInst.cpp b/llvm/lib/IR/IntrinsicInst.cpp index 1ce17aa63bdb..1ad58fce3564 100644 --- a/llvm/lib/IR/IntrinsicInst.cpp +++ b/llvm/lib/IR/IntrinsicInst.cpp @@ -104,7 +104,7 @@ Value *InstrProfIncrementInst::getStep() const { return ConstantInt::get(Type::getInt64Ty(Context), 1); } -Optional<fp::RoundingMode> ConstrainedFPIntrinsic::getRoundingMode() const { +Optional<RoundingMode> ConstrainedFPIntrinsic::getRoundingMode() const { unsigned NumOperands = getNumArgOperands(); Metadata *MD = cast<MetadataAsValue>(getArgOperand(NumOperands - 2))->getMetadata(); diff --git a/llvm/lib/Support/APFloat.cpp b/llvm/lib/Support/APFloat.cpp index 49f9cf8a32f8..63114faae117 100644 --- a/llvm/lib/Support/APFloat.cpp +++ b/llvm/lib/Support/APFloat.cpp @@ -171,6 +171,12 @@ namespace llvm { return semPPCDoubleDouble; } + constexpr RoundingMode APFloatBase::rmNearestTiesToEven; + constexpr RoundingMode APFloatBase::rmTowardPositive; + constexpr RoundingMode APFloatBase::rmTowardNegative; + constexpr RoundingMode APFloatBase::rmTowardZero; + constexpr RoundingMode APFloatBase::rmNearestTiesToAway; + /* A tight upper bound on number of parts required to hold the value pow(5, power) is @@ -1323,6 +1329,9 @@ bool IEEEFloat::roundAwayFromZero(roundingMode rounding_mode, case rmTowardNegative: return sign; + + default: + break; } llvm_unreachable("Invalid rounding mode found"); } diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp index 8a143c25112e..3579d31d48a4 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp @@ -270,7 +270,7 @@ void FAddendCoef::operator=(const FAddendCoef &That) { } void FAddendCoef::operator+=(const FAddendCoef &That) { - enum APFloat::roundingMode RndMode = APFloat::rmNearestTiesToEven; + RoundingMode RndMode = RoundingMode::NearestTiesToEven; if (isInt() == That.isInt()) { if (isInt()) IntVal += That.IntVal; diff --git a/llvm/unittests/IR/IRBuilderTest.cpp b/llvm/unittests/IR/IRBuilderTest.cpp index ab9cec33bac7..b4a7ad3cf391 100644 --- a/llvm/unittests/IR/IRBuilderTest.cpp +++ b/llvm/unittests/IR/IRBuilderTest.cpp @@ -257,51 +257,51 @@ TEST_F(IRBuilderTest, ConstrainedFP) { ASSERT_TRUE(isa<ConstrainedFPIntrinsic>(V)); auto *CII = cast<ConstrainedFPIntrinsic>(V); EXPECT_EQ(fp::ebStrict, CII->getExceptionBehavior()); - EXPECT_EQ(fp::rmDynamic, CII->getRoundingMode()); + EXPECT_EQ(RoundingMode::Dynamic, CII->getRoundingMode()); Builder.setDefaultConstrainedExcept(fp::ebIgnore); - Builder.setDefaultConstrainedRounding(fp::rmUpward); + Builder.setDefaultConstrainedRounding(RoundingMode::TowardPositive); V = Builder.CreateFAdd(V, V); CII = cast<ConstrainedFPIntrinsic>(V); EXPECT_EQ(fp::ebIgnore, CII->getExceptionBehavior()); - EXPECT_EQ(CII->getRoundingMode(), fp::rmUpward); + EXPECT_EQ(CII->getRoundingMode(), RoundingMode::TowardPositive); Builder.setDefaultConstrainedExcept(fp::ebIgnore); - Builder.setDefaultConstrainedRounding(fp::rmToNearest); + Builder.setDefaultConstrainedRounding(RoundingMode::NearestTiesToEven); V = Builder.CreateFAdd(V, V); CII = cast<ConstrainedFPIntrinsic>(V); EXPECT_EQ(fp::ebIgnore, CII->getExceptionBehavior()); - EXPECT_EQ(fp::rmToNearest, CII->getRoundingMode()); + EXPECT_EQ(RoundingMode::NearestTiesToEven, CII->getRoundingMode()); Builder.setDefaultConstrainedExcept(fp::ebMayTrap); - Builder.setDefaultConstrainedRounding(fp::rmDownward); + Builder.setDefaultConstrainedRounding(RoundingMode::TowardNegative); V = Builder.CreateFAdd(V, V); CII = cast<ConstrainedFPIntrinsic>(V); EXPECT_EQ(fp::ebMayTrap, CII->getExceptionBehavior()); - EXPECT_EQ(fp::rmDownward, CII->getRoundingMode()); + EXPECT_EQ(RoundingMode::TowardNegative, CII->getRoundingMode()); Builder.setDefaultConstrainedExcept(fp::ebStrict); - Builder.setDefaultConstrainedRounding(fp::rmTowardZero); + Builder.setDefaultConstrainedRounding(RoundingMode::TowardZero); V = Builder.CreateFAdd(V, V); CII = cast<ConstrainedFPIntrinsic>(V); EXPECT_EQ(fp::ebStrict, CII->getExceptionBehavior()); - EXPECT_EQ(fp::rmTowardZero, CII->getRoundingMode()); + EXPECT_EQ(RoundingMode::TowardZero, CII->getRoundingMode()); Builder.setDefaultConstrainedExcept(fp::ebIgnore); - Builder.setDefaultConstrainedRounding(fp::rmDynamic); + Builder.setDefaultConstrainedRounding(RoundingMode::Dynamic); V = Builder.CreateFAdd(V, V); CII = cast<ConstrainedFPIntrinsic>(V); EXPECT_EQ(fp::ebIgnore, CII->getExceptionBehavior()); - EXPECT_EQ(fp::rmDynamic, CII->getRoundingMode()); + EXPECT_EQ(RoundingMode::Dynamic, CII->getRoundingMode()); // Now override the defaults. Call = Builder.CreateConstrainedFPBinOp( Intrinsic::experimental_constrained_fadd, V, V, nullptr, "", nullptr, - fp::rmDownward, fp::ebMayTrap); + RoundingMode::TowardNegative, fp::ebMayTrap); CII = cast<ConstrainedFPIntrinsic>(Call); EXPECT_EQ(CII->getIntrinsicID(), Intrinsic::experimental_constrained_fadd); EXPECT_EQ(fp::ebMayTrap, CII->getExceptionBehavior()); - EXPECT_EQ(fp::rmDownward, CII->getRoundingMode()); + EXPECT_EQ(RoundingMode::TowardNegative, CII->getRoundingMode()); Builder.CreateRetVoid(); EXPECT_FALSE(verifyModule(*M)); _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits