r354190 - [Sema] Diagnose floating point conversions based on target semantics
Erik Pilkington via cfe-commits
cfe-commits at lists.llvm.org
Fri Feb 15 17:11:47 PST 2019
Author: epilk
Date: Fri Feb 15 17:11:47 2019
New Revision: 354190
URL: http://llvm.org/viewvc/llvm-project?rev=354190&view=rev
Log:
[Sema] Diagnose floating point conversions based on target semantics
...instead of just comparing rank. Also, fix a bad warning about
_Float16, since its declared out of order in BuiltinTypes.def,
meaning comparing rank using BuiltinType::getKind() is incorrect.
Differential revision: https://reviews.llvm.org/D58254
Added:
cfe/trunk/test/Sema/conversion-target-dep.c
Modified:
cfe/trunk/include/clang/AST/ASTContext.h
cfe/trunk/lib/AST/ASTContext.cpp
cfe/trunk/lib/Sema/SemaChecking.cpp
Modified: cfe/trunk/include/clang/AST/ASTContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=354190&r1=354189&r2=354190&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/trunk/include/clang/AST/ASTContext.h Fri Feb 15 17:11:47 2019
@@ -2501,6 +2501,11 @@ public:
/// \p LHS < \p RHS, return -1.
int getFloatingTypeOrder(QualType LHS, QualType RHS) const;
+ /// Compare the rank of two floating point types as above, but compare equal
+ /// if both types have the same floating-point semantics on the target (i.e.
+ /// long double and double on AArch64 will return 0).
+ int getFloatingTypeSemanticOrder(QualType LHS, QualType RHS) const;
+
/// Return a real floating point or a complex type (based on
/// \p typeDomain/\p typeSize).
///
Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=354190&r1=354189&r2=354190&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Fri Feb 15 17:11:47 2019
@@ -5608,6 +5608,12 @@ int ASTContext::getFloatingTypeOrder(Qua
return -1;
}
+int ASTContext::getFloatingTypeSemanticOrder(QualType LHS, QualType RHS) const {
+ if (&getFloatTypeSemantics(LHS) == &getFloatTypeSemantics(RHS))
+ return 0;
+ return getFloatingTypeOrder(LHS, RHS);
+}
+
/// getIntegerRank - Return an integer conversion rank (C99 6.3.1.1p1). This
/// routine will assert if passed a built-in type that isn't an integer or enum,
/// or if it is not canonicalized.
Modified: cfe/trunk/lib/Sema/SemaChecking.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaChecking.cpp?rev=354190&r1=354189&r2=354190&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaChecking.cpp (original)
+++ cfe/trunk/lib/Sema/SemaChecking.cpp Fri Feb 15 17:11:47 2019
@@ -10626,14 +10626,16 @@ static void AnalyzeCompoundAssignment(Se
// If source is floating point but target is an integer.
if (ResultBT->isInteger())
- DiagnoseImpCast(S, E, E->getRHS()->getType(), E->getLHS()->getType(),
- E->getExprLoc(), diag::warn_impcast_float_integer);
- // If both source and target are floating points. Builtin FP kinds are ordered
- // by increasing FP rank. FIXME: except _Float16, we currently emit a bogus
- // warning.
- else if (ResultBT->isFloatingPoint() && ResultBT->getKind() < RBT->getKind() &&
- // We don't want to warn for system macro.
- !S.SourceMgr.isInSystemMacro(E->getOperatorLoc()))
+ return DiagnoseImpCast(S, E, E->getRHS()->getType(), E->getLHS()->getType(),
+ E->getExprLoc(), diag::warn_impcast_float_integer);
+
+ if (!ResultBT->isFloatingPoint())
+ return;
+
+ // If both source and target are floating points, warn about losing precision.
+ int Order = S.getASTContext().getFloatingTypeSemanticOrder(
+ QualType(ResultBT, 0), QualType(RBT, 0));
+ if (Order < 0 && !S.SourceMgr.isInSystemMacro(E->getOperatorLoc()))
// warn about dropping FP rank.
DiagnoseImpCast(S, E->getRHS(), E->getLHS()->getType(), E->getOperatorLoc(),
diag::warn_impcast_float_result_precision);
@@ -10952,8 +10954,9 @@ CheckImplicitConversion(Sema &S, Expr *E
if (TargetBT && TargetBT->isFloatingPoint()) {
// ...then warn if we're dropping FP rank.
- // Builtin FP kinds are ordered by increasing FP rank.
- if (SourceBT->getKind() > TargetBT->getKind()) {
+ int Order = S.getASTContext().getFloatingTypeSemanticOrder(
+ QualType(SourceBT, 0), QualType(TargetBT, 0));
+ if (Order > 0) {
// Don't warn about float constants that are precisely
// representable in the target type.
Expr::EvalResult result;
@@ -10971,7 +10974,7 @@ CheckImplicitConversion(Sema &S, Expr *E
DiagnoseImpCast(S, E, T, CC, diag::warn_impcast_float_precision);
}
// ... or possibly if we're increasing rank, too
- else if (TargetBT->getKind() > SourceBT->getKind()) {
+ else if (Order < 0) {
if (S.SourceMgr.isInSystemMacro(CC))
return;
Added: cfe/trunk/test/Sema/conversion-target-dep.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/conversion-target-dep.c?rev=354190&view=auto
==============================================================================
--- cfe/trunk/test/Sema/conversion-target-dep.c (added)
+++ cfe/trunk/test/Sema/conversion-target-dep.c Fri Feb 15 17:11:47 2019
@@ -0,0 +1,24 @@
+// RUN: %clang_cc1 -Wdouble-promotion -Wimplicit-float-conversion %s -triple x86_64-apple-macosx10.12 -verify=x86,expected
+// RUN: %clang_cc1 -Wdouble-promotion -Wimplicit-float-conversion %s -triple armv7-apple-ios9.0 -verify=arm,expected
+
+// On ARM, long double and double both map to double precision 754s, so there
+// isn't any reason to warn on conversions back and forth.
+
+long double ld;
+double d;
+_Float16 f16; // x86-error {{_Float16 is not supported on this target}}
+
+int main() {
+ ld = d; // x86-warning {{implicit conversion increases floating-point precision: 'double' to 'long double'}}
+ d = ld; // x86-warning {{implicit conversion loses floating-point precision: 'long double' to 'double'}}
+
+ ld += d; // x86-warning {{implicit conversion increases floating-point precision: 'double' to 'long double'}}
+ d += ld; // x86-warning {{implicit conversion when assigning computation result loses floating-point precision: 'long double' to 'double'}}
+
+ f16 = ld; // expected-warning {{implicit conversion loses floating-point precision: 'long double' to '_Float16'}}
+ ld = f16; // expected-warning {{implicit conversion increases floating-point precision: '_Float16' to 'long double'}}
+
+ f16 += ld; // expected-warning {{implicit conversion when assigning computation result loses floating-point precision: 'long double' to '_Float16'}}
+ ld += f16; // expected-warning {{implicit conversion increases floating-point precision: '_Float16' to 'long double'}}
+}
+
More information about the cfe-commits
mailing list