diff options
author | Steve Naroff <snaroff@apple.com> | 2008-01-15 19:36:10 +0000 |
---|---|---|
committer | Steve Naroff <snaroff@apple.com> | 2008-01-15 19:36:10 +0000 |
commit | 02f62a9fedbc370fba081303399410a3afdde29f (patch) | |
tree | c4041a93616f35818f52c19798ba6a00c6ded44a | |
parent | b1a17ae9d339e59b81509e593907f2f924231dab (diff) |
- Change Type::isComplexType() to exlude GCC's complex integer extension. In general, we will keep the lowest level Type predicates "pure" (i.e. true to the C99 spec).
- Modify Sema::UsualArithmeticConversions() to work with the new definition of Type::isComplexType().
This is a nice cleanup and also fixes a bug submitted by Eli (which I've added to the test suite).
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@46005 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | AST/Type.cpp | 4 | ||||
-rw-r--r-- | Sema/SemaExpr.cpp | 45 | ||||
-rw-r--r-- | include/clang/AST/Type.h | 2 | ||||
-rw-r--r-- | test/Sema/complex-int.c | 1 |
4 files changed, 34 insertions, 18 deletions
diff --git a/AST/Type.cpp b/AST/Type.cpp index bb3fd9d44b..78e0dbbb27 100644 --- a/AST/Type.cpp +++ b/AST/Type.cpp @@ -74,7 +74,9 @@ bool Type::isUnionType() const { } bool Type::isComplexType() const { - return isa<ComplexType>(CanonicalType); + if (const ComplexType *CT = dyn_cast<ComplexType>(CanonicalType)) + return CT->getElementType()->isFloatingType(); + return false; } bool Type::isComplexIntegerType() const { diff --git a/Sema/SemaExpr.cpp b/Sema/SemaExpr.cpp index 436510f763..c5a9bff5fe 100644 --- a/Sema/SemaExpr.cpp +++ b/Sema/SemaExpr.cpp @@ -951,25 +951,12 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, // Handle complex types first (C99 6.3.1.8p1). if (lhs->isComplexType() || rhs->isComplexType()) { - // Handle GCC complex int extension first. - // FIXME: need to verify these conversion rules are consistent with GCC. - const ComplexType *lhsComplexInt = lhs->getAsComplexIntegerType(); - const ComplexType *rhsComplexInt = rhs->getAsComplexIntegerType(); - - if (lhsComplexInt && rhsComplexInt) { - if (Context.maxIntegerType(lhsComplexInt->getElementType(), - rhsComplexInt->getElementType()) == lhs) { - if (!isCompAssign) promoteExprToType(rhsExpr, lhs); // convert the rhs - return lhs; - } - if (!isCompAssign) promoteExprToType(lhsExpr, rhs); // convert the lhs - return rhs; - } else if (lhsComplexInt && rhs->isIntegerType()) { - // convert the rhs to the lhs complex type. + // if we have an integer operand, the result is the complex type. + if (rhs->isIntegerType()) { // convert the rhs to the lhs complex type. if (!isCompAssign) promoteExprToType(rhsExpr, lhs); return lhs; - } else if (rhsComplexInt && lhs->isIntegerType()) { - // convert the lhs to the rhs complex type. + } + if (lhs->isIntegerType()) { // convert the lhs to the rhs complex type. if (!isCompAssign) promoteExprToType(lhsExpr, rhs); return rhs; } @@ -1035,6 +1022,30 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, } assert(0 && "Sema::UsualArithmeticConversions(): illegal float comparison"); } + if (lhs->isComplexIntegerType() || rhs->isComplexIntegerType()) { + // Handle GCC complex int extension. + // FIXME: need to verify these conversion rules are consistent with GCC. + const ComplexType *lhsComplexInt = lhs->getAsComplexIntegerType(); + const ComplexType *rhsComplexInt = rhs->getAsComplexIntegerType(); + + if (lhsComplexInt && rhsComplexInt) { + if (Context.maxIntegerType(lhsComplexInt->getElementType(), + rhsComplexInt->getElementType()) == lhs) { + if (!isCompAssign) promoteExprToType(rhsExpr, lhs); // convert the rhs + return lhs; + } + if (!isCompAssign) promoteExprToType(lhsExpr, rhs); // convert the lhs + return rhs; + } else if (lhsComplexInt && rhs->isIntegerType()) { + // convert the rhs to the lhs complex type. + if (!isCompAssign) promoteExprToType(rhsExpr, lhs); + return lhs; + } else if (rhsComplexInt && lhs->isIntegerType()) { + // convert the lhs to the rhs complex type. + if (!isCompAssign) promoteExprToType(lhsExpr, rhs); + return rhs; + } + } // Finally, we have two differing integer types. if (Context.maxIntegerType(lhs, rhs) == lhs) { // convert the rhs if (!isCompAssign) promoteExprToType(rhsExpr, lhs); diff --git a/include/clang/AST/Type.h b/include/clang/AST/Type.h index 9c143e9998..ce35c4c3f0 100644 --- a/include/clang/AST/Type.h +++ b/include/clang/AST/Type.h @@ -276,6 +276,8 @@ public: /// Floating point categories. bool isRealFloatingType() const; // C99 6.2.5p10 (float, double, long double) + /// isComplexType() does *not* include complex integers (a GCC extension). + /// isComplexIntegerType() can be used to test for complex integers. bool isComplexType() const; // C99 6.2.5p11 (complex) bool isFloatingType() const; // C99 6.2.5p11 (real floating + complex) bool isRealType() const; // C99 6.2.5p17 (real floating + integer) diff --git a/test/Sema/complex-int.c b/test/Sema/complex-int.c index 90d1e3dc12..1e2f8cf4ed 100644 --- a/test/Sema/complex-int.c +++ b/test/Sema/complex-int.c @@ -7,6 +7,7 @@ __complex__ unsigned xx; __complex__ signed yy; __complex__ int result; int ii; +int aa = 1 + 1.0iF; result = arr*ii; result = ii*brr; |