[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
s-watanabe314 wrote: Thank you for confirming. @MaskRay, do you have any comments regarding the handling of warning messages? https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
andykaylor wrote: @s-watanabe314 I apologize for the very long delay in responding. This fell off my radar for a while. I think your latest proposed handling of warnings looks good, but I'd like to see input from @MaskRay also. https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
s-watanabe314 wrote: @andykaylor I would appreciate your comments on this. https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain &TC, const Driver &D, LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None; std::string ComplexRangeStr = ""; std::string GccRangeComplexOption = ""; + std::string LastComplexRangeOption = ""; s-watanabe314 wrote: Does this mean that `= ""` is unnecessary? I initialized it in the same way as `GccRangeComplexOption`, but should I remove it? https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
https://github.com/MaskRay edited https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
s-watanabe314 wrote: > I would like to see warnings for -fno-fast-math overriding explicit complex > range options, especially since GCC doesn't do that. Is "explicit complex range options" referring to the `-fcomplex-arithmetic=` and GCC options? If so, when `-fno-fast-math` overrides other options, should I modify the behavior as follows? - Issue a warning when `-fno-fast-math` overrides explicit options. |Option|Warning| |-|-| |-fcx-limited-range -fno-fast-math|warning: overriding '-fcx-limited-range' option with '-fno-fast-math'| |-fcx-fortran-rules -fno-fast-math|warning: overriding '-fcx-fortran-rules' option with '-fno-fast-math'| |-fcomplex-arithmetic=basic -fno-fast-math|warning: overriding '-fcomplex-arithmetic=basic' option with '-fno-fast-math'| - Do not issue a warning when overriding non-explicit options. |Option|Warning| |-|-| |-ffast-math -fno-fast-math|No warning| |-ffp-model=aggressive -fno-fast-math|No warning| Furthermore, if `-fno-fast-math` means that it resets the state to the default, is a warning always unnecessary if another option is specified after `-fno-fast-math`? To implement this, I think we can assign `CX_None` to `Range` instead of `CX_Full` when the `-fno-fast-math` is specified. - All of the following examples do not issue a warning: |Option|Warning| |-|-| |-fno-fast-math -fcx-limited-range|No warning| |-fno-fast-math -fcx-fortran-rules|No warning| |-fno-fast-math -fcomplex-arithmetic=basic|No warning| |-fno-fast-math -ffp-model=aggressive|No warning| > This may contradict things I've said earlier, but it doesn't seem like we > should treat the GCC options differently than the clang-specific options with > regard to whether or not we issue warnings. Also, the warnings are > referencing options that the user didn't explicitly specify. I agree that we shouldn't treat them differently. `GccRangeComplexOption` is only used to determine whether to issue a warning. I'm considering replacing it with `LastComplexRangeOption`. This would allow the warning message to directly reference the user-specified option. https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -3148,6 +3158,7 @@ static void RenderFloatingPointOptions(const ToolChain &TC, const Driver &D, ComplexArithmeticStr(RangeVal)); } } + LastComplexRangeOption = "-fcomplex-arithmetic"; MaskRay wrote: `Arg::getSpelling` returns the spelling. Don't write the string literal separately. https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain &TC, const Driver &D, LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None; std::string ComplexRangeStr = ""; std::string GccRangeComplexOption = ""; + std::string LastComplexRangeOption = ""; MaskRay wrote: `std::string LastComplexRangeOption` default initialization https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -177,14 +177,83 @@ // RUN: %clang -### -target x86_64 -ffast-math -fcomplex-arithmetic=basic -c %s 2>&1 \ // RUN: | FileCheck --check-prefix=BASIC %s -// BASIC: -complex-range=basic -// FULL: -complex-range=full -// PRMTD: -complex-range=promoted -// BASIC-NOT: -complex-range=improved -// CHECK-NOT: -complex-range=basic -// IMPRVD: -complex-range=improved -// IMPRVD-NOT: -complex-range=basic -// CHECK-NOT: -complex-range=improved +// RUN: %clang -### -target x86_64 -fcx-limited-range -fno-fast-math \ MaskRay wrote: `-target ` has been deprecated for a long time. `--target=` for new tests https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -177,14 +177,45 @@ // RUN: %clang -### -target x86_64 -ffast-math -fcomplex-arithmetic=basic -c %s 2>&1 \ // RUN: | FileCheck --check-prefix=BASIC %s -// BASIC: -complex-range=basic -// FULL: -complex-range=full -// PRMTD: -complex-range=promoted -// BASIC-NOT: -complex-range=improved -// CHECK-NOT: -complex-range=basic -// IMPRVD: -complex-range=improved -// IMPRVD-NOT: -complex-range=basic -// CHECK-NOT: -complex-range=improved +// RUN: %clang -### -target x86_64 -fcx-limited-range -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN21 %s + +// RUN: %clang -### -Werror -target x86_64 -fno-cx-limited-range -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -target x86_64 -fcx-fortran-rules -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN22 %s + +// RUN: %clang -### -Werror -target x86_64 -fno-cx-fortran-rules -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -Werror -target x86_64 -ffast-math -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -target x86_64 -fcomplex-arithmetic=basic -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN23 %s + +// RUN: %clang -### -target x86_64 -fcomplex-arithmetic=promoted -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN24 %s + +// RUN: %clang -### -target x86_64 -fcomplex-arithmetic=improved -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN25 %s + +// RUN: %clang -### -Werror -target x86_64 -fcomplex-arithmetic=full -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -target x86_64 -ffp-model=aggressive -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN23 %s + +// RUN: %clang -### -target x86_64 -ffp-model=fast -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN24 %s + +// RUN: %clang -### -Werror -target x86_64 -ffp-model=precise -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -Werror -target x86_64 -ffp-model=strict -fno-fast-math \ s-watanabe314 wrote: I added test cases. https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain &TC, const Driver &D, LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None; std::string ComplexRangeStr = ""; std::string GccRangeComplexOption = ""; + std::string LastComplexRangeOption = ""; s-watanabe314 wrote: Thank you for your feedback! > If you just set GccRangeComplexOption to empty for -ffast-math and > -fno-fast-math, would that give us reasonable diagnostics? I think it's difficult. I believe diagnostics should be emitted when `Range` specified with options other than `-ffast-math` is overridden by `-fno-fast-math`. To distinguish between these cases, I think we need a variable that determines what options, including Clang-specific options, were specified before `-fno-fast-math`. Even if we empty `GccRangeComplexOption` when `-ffast-math` is spcified, it's impossible to distinguish whether the preceding option before `-fno-fast-math` was `-ffast-math` or `-fcomplex-arithmetic=basic`. If it's acceptable to assign "-ffp-model" or "-fcomplex-arithmetic" to `GccRangeComplexOption`, then a new variable might not be necessary. https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
https://github.com/s-watanabe314 updated
https://github.com/llvm/llvm-project/pull/132680
>From 9265cb96cc3129fada722d7195a1cf04e985ba33 Mon Sep 17 00:00:00 2001
From: s-watanabe314
Date: Fri, 14 Mar 2025 11:56:32 +0900
Subject: [PATCH 1/2] [Clang][Driver] Override complex number calculation
method by -fno-fast-math
This patch fixes a bug where -fno-fast-math doesn't revert the complex
number calculation method to the default. The priority of overriding
options related to complex number calculations differs slightly from
GCC, as discussed in:
https://discourse.llvm.org/t/the-priority-of-fno-fast-math-regarding-complex-number-calculations/84679
---
clang/lib/Driver/ToolChains/Clang.cpp | 22 +-
clang/test/Driver/range.c | 61 +++
2 files changed, 74 insertions(+), 9 deletions(-)
diff --git a/clang/lib/Driver/ToolChains/Clang.cpp
b/clang/lib/Driver/ToolChains/Clang.cpp
index fb3ed2db0e3c0..484ced9885883 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None;
std::string ComplexRangeStr = "";
std::string GccRangeComplexOption = "";
+ std::string LastComplexRangeOption = "";
auto setComplexRange = [&](LangOptions::ComplexRangeKind NewRange) {
// Warn if user expects to perform full implementation of complex
@@ -3015,7 +3016,12 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
if (Aggressive) {
HonorINFs = false;
HonorNaNs = false;
- setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
+ // If the last specified option related to complex range is
+ // -fno-fast-math, override 'Range' without warning.
+ if (LastComplexRangeOption == "-fno-fast-math")
+Range = LangOptions::ComplexRangeKind::CX_Basic;
+ else
+setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
} else {
HonorINFs = true;
HonorNaNs = true;
@@ -3080,6 +3086,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-limited-range");
}
GccRangeComplexOption = "-fcx-limited-range";
+ LastComplexRangeOption = "-fcx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Basic;
break;
case options::OPT_fno_cx_limited_range:
@@ -3093,6 +3100,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-limited-range");
}
GccRangeComplexOption = "-fno-cx-limited-range";
+ LastComplexRangeOption = "-fno-cx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcx_fortran_rules:
@@ -3102,6 +3110,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
else
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-fortran-rules");
GccRangeComplexOption = "-fcx-fortran-rules";
+ LastComplexRangeOption = "-fcx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Improved;
break;
case options::OPT_fno_cx_fortran_rules:
@@ -3114,6 +3123,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-fortran-rules");
}
GccRangeComplexOption = "-fno-cx-fortran-rules";
+ LastComplexRangeOption = "-fno-cx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcomplex_arithmetic_EQ: {
@@ -3148,6 +3158,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ComplexArithmeticStr(RangeVal));
}
}
+ LastComplexRangeOption = "-fcomplex-arithmetic";
Range = RangeVal;
break;
}
@@ -3201,6 +3212,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
} else
D.Diag(diag::err_drv_unsupported_option_argument)
<< A->getSpelling() << Val;
+ LastComplexRangeOption = "-ffp-model";
break;
}
@@ -3386,6 +3398,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
[[fallthrough]];
case options::OPT_ffast_math:
applyFastMath(true);
+ LastComplexRangeOption = "-ffast-math";
if (A->getOption().getID() == options::OPT_Ofast)
LastFpContractOverrideOption = "-Ofast";
else
@@ -3403,6 +3416,13 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ApproxFunc = false;
SignedZeros = true;
restoreFPContractState();
+ // If the last specified option related to complex range is -ffast-math,
+ // override 'Range' without warning.
+
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -177,14 +177,45 @@ // RUN: %clang -### -target x86_64 -ffast-math -fcomplex-arithmetic=basic -c %s 2>&1 \ // RUN: | FileCheck --check-prefix=BASIC %s -// BASIC: -complex-range=basic -// FULL: -complex-range=full -// PRMTD: -complex-range=promoted -// BASIC-NOT: -complex-range=improved -// CHECK-NOT: -complex-range=basic -// IMPRVD: -complex-range=improved -// IMPRVD-NOT: -complex-range=basic -// CHECK-NOT: -complex-range=improved +// RUN: %clang -### -target x86_64 -fcx-limited-range -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN21 %s + +// RUN: %clang -### -Werror -target x86_64 -fno-cx-limited-range -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -target x86_64 -fcx-fortran-rules -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN22 %s + +// RUN: %clang -### -Werror -target x86_64 -fno-cx-fortran-rules -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -Werror -target x86_64 -ffast-math -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -target x86_64 -fcomplex-arithmetic=basic -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN23 %s + +// RUN: %clang -### -target x86_64 -fcomplex-arithmetic=promoted -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN24 %s + +// RUN: %clang -### -target x86_64 -fcomplex-arithmetic=improved -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN25 %s + +// RUN: %clang -### -Werror -target x86_64 -fcomplex-arithmetic=full -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -target x86_64 -ffp-model=aggressive -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN23 %s + +// RUN: %clang -### -target x86_64 -ffp-model=fast -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL,WARN24 %s + +// RUN: %clang -### -Werror -target x86_64 -ffp-model=precise -fno-fast-math \ +// RUN: -c %s 2>&1 | FileCheck --check-prefixes=FULL %s + +// RUN: %clang -### -Werror -target x86_64 -ffp-model=strict -fno-fast-math \ andykaylor wrote: Can you add test cases for when `-fno-fast-math` is followed by other options that change the complex mode? https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain &TC, const Driver &D, LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None; std::string ComplexRangeStr = ""; std::string GccRangeComplexOption = ""; + std::string LastComplexRangeOption = ""; andykaylor wrote: I don't think I remember during our Discourse discussion of this that there was already a `GccRangeComplexOption` variable here. Do we really need another variable? If you just set GccRangeComplexOption to empty for `-ffast-math` and `-fno-fast-math`, would that give us reasonable diagnostics? https://github.com/llvm/llvm-project/pull/132680 ___ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
llvmbot wrote:
@llvm/pr-subscribers-clang
Author: None (s-watanabe314)
Changes
…st-math
This patch fixes a bug where -fno-fast-math doesn't revert the complex number
calculation method to the default. The priority of overriding options related
to complex number calculations differs slightly from GCC, as discussed in:
https://discourse.llvm.org/t/the-priority-of-fno-fast-math-regarding-complex-number-calculations/84679
I will post another patch to add a warning that the option overriding rules are
incompatible with GCC.
In that patch, I will also fix the conditions for warnings related to other
complex number options.
---
Full diff: https://github.com/llvm/llvm-project/pull/132680.diff
2 Files Affected:
- (modified) clang/lib/Driver/ToolChains/Clang.cpp (+21-1)
- (modified) clang/test/Driver/range.c (+53-8)
``diff
diff --git a/clang/lib/Driver/ToolChains/Clang.cpp
b/clang/lib/Driver/ToolChains/Clang.cpp
index fb3ed2db0e3c0..484ced9885883 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None;
std::string ComplexRangeStr = "";
std::string GccRangeComplexOption = "";
+ std::string LastComplexRangeOption = "";
auto setComplexRange = [&](LangOptions::ComplexRangeKind NewRange) {
// Warn if user expects to perform full implementation of complex
@@ -3015,7 +3016,12 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
if (Aggressive) {
HonorINFs = false;
HonorNaNs = false;
- setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
+ // If the last specified option related to complex range is
+ // -fno-fast-math, override 'Range' without warning.
+ if (LastComplexRangeOption == "-fno-fast-math")
+Range = LangOptions::ComplexRangeKind::CX_Basic;
+ else
+setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
} else {
HonorINFs = true;
HonorNaNs = true;
@@ -3080,6 +3086,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-limited-range");
}
GccRangeComplexOption = "-fcx-limited-range";
+ LastComplexRangeOption = "-fcx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Basic;
break;
case options::OPT_fno_cx_limited_range:
@@ -3093,6 +3100,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-limited-range");
}
GccRangeComplexOption = "-fno-cx-limited-range";
+ LastComplexRangeOption = "-fno-cx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcx_fortran_rules:
@@ -3102,6 +3110,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
else
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-fortran-rules");
GccRangeComplexOption = "-fcx-fortran-rules";
+ LastComplexRangeOption = "-fcx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Improved;
break;
case options::OPT_fno_cx_fortran_rules:
@@ -3114,6 +3123,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-fortran-rules");
}
GccRangeComplexOption = "-fno-cx-fortran-rules";
+ LastComplexRangeOption = "-fno-cx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcomplex_arithmetic_EQ: {
@@ -3148,6 +3158,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ComplexArithmeticStr(RangeVal));
}
}
+ LastComplexRangeOption = "-fcomplex-arithmetic";
Range = RangeVal;
break;
}
@@ -3201,6 +3212,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
} else
D.Diag(diag::err_drv_unsupported_option_argument)
<< A->getSpelling() << Val;
+ LastComplexRangeOption = "-ffp-model";
break;
}
@@ -3386,6 +3398,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
[[fallthrough]];
case options::OPT_ffast_math:
applyFastMath(true);
+ LastComplexRangeOption = "-ffast-math";
if (A->getOption().getID() == options::OPT_Ofast)
LastFpContractOverrideOption = "-Ofast";
else
@@ -3403,6 +3416,13 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ApproxFunc = false;
SignedZeros = true;
restoreFPContractState();
+ // If the last specified option related to complex range is -ffast-math,
+ // override 'Range' without w
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
llvmbot wrote:
@llvm/pr-subscribers-clang-driver
Author: None (s-watanabe314)
Changes
…st-math
This patch fixes a bug where -fno-fast-math doesn't revert the complex number
calculation method to the default. The priority of overriding options related
to complex number calculations differs slightly from GCC, as discussed in:
https://discourse.llvm.org/t/the-priority-of-fno-fast-math-regarding-complex-number-calculations/84679
I will post another patch to add a warning that the option overriding rules are
incompatible with GCC.
In that patch, I will also fix the conditions for warnings related to other
complex number options.
---
Full diff: https://github.com/llvm/llvm-project/pull/132680.diff
2 Files Affected:
- (modified) clang/lib/Driver/ToolChains/Clang.cpp (+21-1)
- (modified) clang/test/Driver/range.c (+53-8)
``diff
diff --git a/clang/lib/Driver/ToolChains/Clang.cpp
b/clang/lib/Driver/ToolChains/Clang.cpp
index fb3ed2db0e3c0..484ced9885883 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None;
std::string ComplexRangeStr = "";
std::string GccRangeComplexOption = "";
+ std::string LastComplexRangeOption = "";
auto setComplexRange = [&](LangOptions::ComplexRangeKind NewRange) {
// Warn if user expects to perform full implementation of complex
@@ -3015,7 +3016,12 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
if (Aggressive) {
HonorINFs = false;
HonorNaNs = false;
- setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
+ // If the last specified option related to complex range is
+ // -fno-fast-math, override 'Range' without warning.
+ if (LastComplexRangeOption == "-fno-fast-math")
+Range = LangOptions::ComplexRangeKind::CX_Basic;
+ else
+setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
} else {
HonorINFs = true;
HonorNaNs = true;
@@ -3080,6 +3086,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-limited-range");
}
GccRangeComplexOption = "-fcx-limited-range";
+ LastComplexRangeOption = "-fcx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Basic;
break;
case options::OPT_fno_cx_limited_range:
@@ -3093,6 +3100,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-limited-range");
}
GccRangeComplexOption = "-fno-cx-limited-range";
+ LastComplexRangeOption = "-fno-cx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcx_fortran_rules:
@@ -3102,6 +3110,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
else
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-fortran-rules");
GccRangeComplexOption = "-fcx-fortran-rules";
+ LastComplexRangeOption = "-fcx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Improved;
break;
case options::OPT_fno_cx_fortran_rules:
@@ -3114,6 +3123,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-fortran-rules");
}
GccRangeComplexOption = "-fno-cx-fortran-rules";
+ LastComplexRangeOption = "-fno-cx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcomplex_arithmetic_EQ: {
@@ -3148,6 +3158,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ComplexArithmeticStr(RangeVal));
}
}
+ LastComplexRangeOption = "-fcomplex-arithmetic";
Range = RangeVal;
break;
}
@@ -3201,6 +3212,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
} else
D.Diag(diag::err_drv_unsupported_option_argument)
<< A->getSpelling() << Val;
+ LastComplexRangeOption = "-ffp-model";
break;
}
@@ -3386,6 +3398,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
[[fallthrough]];
case options::OPT_ffast_math:
applyFastMath(true);
+ LastComplexRangeOption = "-ffast-math";
if (A->getOption().getID() == options::OPT_Ofast)
LastFpContractOverrideOption = "-Ofast";
else
@@ -3403,6 +3416,13 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ApproxFunc = false;
SignedZeros = true;
restoreFPContractState();
+ // If the last specified option related to complex range is -ffast-math,
+ // override 'Range' wi
[clang] [Clang][Driver] Override complex number calculation method by -fno-fa… (PR #132680)
https://github.com/s-watanabe314 created
https://github.com/llvm/llvm-project/pull/132680
…st-math
This patch fixes a bug where -fno-fast-math doesn't revert the complex number
calculation method to the default. The priority of overriding options related
to complex number calculations differs slightly from GCC, as discussed in:
https://discourse.llvm.org/t/the-priority-of-fno-fast-math-regarding-complex-number-calculations/84679
I will post another patch to add a warning that the option overriding rules are
incompatible with GCC.
In that patch, I will also fix the conditions for warnings related to other
complex number options.
>From 9265cb96cc3129fada722d7195a1cf04e985ba33 Mon Sep 17 00:00:00 2001
From: s-watanabe314
Date: Fri, 14 Mar 2025 11:56:32 +0900
Subject: [PATCH] [Clang][Driver] Override complex number calculation method by
-fno-fast-math
This patch fixes a bug where -fno-fast-math doesn't revert the complex
number calculation method to the default. The priority of overriding
options related to complex number calculations differs slightly from
GCC, as discussed in:
https://discourse.llvm.org/t/the-priority-of-fno-fast-math-regarding-complex-number-calculations/84679
---
clang/lib/Driver/ToolChains/Clang.cpp | 22 +-
clang/test/Driver/range.c | 61 +++
2 files changed, 74 insertions(+), 9 deletions(-)
diff --git a/clang/lib/Driver/ToolChains/Clang.cpp
b/clang/lib/Driver/ToolChains/Clang.cpp
index fb3ed2db0e3c0..484ced9885883 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -2997,6 +2997,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
LangOptions::ComplexRangeKind Range = LangOptions::ComplexRangeKind::CX_None;
std::string ComplexRangeStr = "";
std::string GccRangeComplexOption = "";
+ std::string LastComplexRangeOption = "";
auto setComplexRange = [&](LangOptions::ComplexRangeKind NewRange) {
// Warn if user expects to perform full implementation of complex
@@ -3015,7 +3016,12 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
if (Aggressive) {
HonorINFs = false;
HonorNaNs = false;
- setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
+ // If the last specified option related to complex range is
+ // -fno-fast-math, override 'Range' without warning.
+ if (LastComplexRangeOption == "-fno-fast-math")
+Range = LangOptions::ComplexRangeKind::CX_Basic;
+ else
+setComplexRange(LangOptions::ComplexRangeKind::CX_Basic);
} else {
HonorINFs = true;
HonorNaNs = true;
@@ -3080,6 +3086,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-limited-range");
}
GccRangeComplexOption = "-fcx-limited-range";
+ LastComplexRangeOption = "-fcx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Basic;
break;
case options::OPT_fno_cx_limited_range:
@@ -3093,6 +3100,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-limited-range");
}
GccRangeComplexOption = "-fno-cx-limited-range";
+ LastComplexRangeOption = "-fno-cx-limited-range";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcx_fortran_rules:
@@ -3102,6 +3110,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
else
EmitComplexRangeDiag(D, GccRangeComplexOption, "-fcx-fortran-rules");
GccRangeComplexOption = "-fcx-fortran-rules";
+ LastComplexRangeOption = "-fcx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Improved;
break;
case options::OPT_fno_cx_fortran_rules:
@@ -3114,6 +3123,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
"-fno-cx-fortran-rules");
}
GccRangeComplexOption = "-fno-cx-fortran-rules";
+ LastComplexRangeOption = "-fno-cx-fortran-rules";
Range = LangOptions::ComplexRangeKind::CX_Full;
break;
case options::OPT_fcomplex_arithmetic_EQ: {
@@ -3148,6 +3158,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
ComplexArithmeticStr(RangeVal));
}
}
+ LastComplexRangeOption = "-fcomplex-arithmetic";
Range = RangeVal;
break;
}
@@ -3201,6 +3212,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
} else
D.Diag(diag::err_drv_unsupported_option_argument)
<< A->getSpelling() << Val;
+ LastComplexRangeOption = "-ffp-model";
break;
}
@@ -3386,6 +3398,7 @@ static void RenderFloatingPointOptions(const ToolChain
&TC, const Driver &D,
[[fallthrough]]
