diff options
| author | Sebastian Redl <sebastian.redl@getdesigned.at> | 2008-11-11 17:56:53 +0000 |
|---|---|---|
| committer | Sebastian Redl <sebastian.redl@getdesigned.at> | 2008-11-11 17:56:53 +0000 |
| commit | 6f28289aca5bf15feb49b95e73f80cf9af99cdb3 (patch) | |
| tree | 71037f611a5ba7b910255fcfb6a419cf159d8ee7 /clang/lib/Sema | |
| parent | 5499e89d06ba27f89dbffb028cbce72e3a3c95ed (diff) | |
| download | bcm5719-llvm-6f28289aca5bf15feb49b95e73f80cf9af99cdb3.tar.gz bcm5719-llvm-6f28289aca5bf15feb49b95e73f80cf9af99cdb3.zip | |
Introduce a single AST node SizeOfAlignOfExpr for all sizeof and alignof expressions, both of values and types.
llvm-svn: 59057
Diffstat (limited to 'clang/lib/Sema')
| -rw-r--r-- | clang/lib/Sema/Sema.h | 10 | ||||
| -rw-r--r-- | clang/lib/Sema/SemaDecl.cpp | 12 | ||||
| -rw-r--r-- | clang/lib/Sema/SemaExpr.cpp | 62 |
3 files changed, 41 insertions, 43 deletions
diff --git a/clang/lib/Sema/Sema.h b/clang/lib/Sema/Sema.h index 7f72928064a..7cd507a0aa3 100644 --- a/clang/lib/Sema/Sema.h +++ b/clang/lib/Sema/Sema.h @@ -624,9 +624,11 @@ public: virtual ExprResult ActOnUnaryOp(SourceLocation OpLoc, tok::TokenKind Op, ExprTy *Input); virtual ExprResult - ActOnSizeOfAlignOfTypeExpr(SourceLocation OpLoc, bool isSizeof, - SourceLocation LParenLoc, TypeTy *Ty, - SourceLocation RParenLoc); + ActOnSizeOfAlignOfExpr(SourceLocation OpLoc, bool isSizeof, bool isType, + void *TyOrEx, const SourceRange &ArgRange); + + bool CheckSizeOfAlignOfOperand(QualType type, SourceLocation OpLoc, + const SourceRange &R, bool isSizeof); virtual ExprResult ActOnPostfixUnaryOp(SourceLocation OpLoc, tok::TokenKind Kind, ExprTy *Input); @@ -1208,8 +1210,6 @@ public: QualType CheckIncrementDecrementOperand(Expr *op, SourceLocation OpLoc); QualType CheckAddressOfOperand(Expr *op, SourceLocation OpLoc); QualType CheckIndirectionOperand(Expr *op, SourceLocation OpLoc); - QualType CheckSizeOfAlignOfOperand(QualType type, SourceLocation OpLoc, - const SourceRange &R, bool isSizeof); QualType CheckRealImagOperand(Expr *&Op, SourceLocation OpLoc); /// type checking primary expressions. diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp index b595ad7f317..fc412a605ed 100644 --- a/clang/lib/Sema/SemaDecl.cpp +++ b/clang/lib/Sema/SemaDecl.cpp @@ -1470,11 +1470,7 @@ bool Sema::CheckArithmeticConstantExpression(const Expr* Init) { default: InitializerElementNotConstant(Init); return true; - case UnaryOperator::SizeOf: - case UnaryOperator::AlignOf: case UnaryOperator::OffsetOf: - // sizeof(E) is a constantexpr if and only if E is not evaluted. - // See C99 6.5.3.4p2 and 6.6p3. if (Exp->getSubExpr()->getType()->isConstantSizeType()) return false; InitializerElementNotConstant(Init); @@ -1487,14 +1483,14 @@ bool Sema::CheckArithmeticConstantExpression(const Expr* Init) { return CheckArithmeticConstantExpression(Exp->getSubExpr()); } } - case Expr::SizeOfAlignOfTypeExprClass: { - const SizeOfAlignOfTypeExpr *Exp = cast<SizeOfAlignOfTypeExpr>(Init); + case Expr::SizeOfAlignOfExprClass: { + const SizeOfAlignOfExpr *Exp = cast<SizeOfAlignOfExpr>(Init); // Special check for void types, which are allowed as an extension - if (Exp->getArgumentType()->isVoidType()) + if (Exp->getTypeOfArgument()->isVoidType()) return false; // alignof always evaluates to a constant. // FIXME: is sizeof(int[3.0]) a constant expression? - if (Exp->isSizeOf() && !Exp->getArgumentType()->isConstantSizeType()) { + if (Exp->isSizeOf() && !Exp->getTypeOfArgument()->isConstantSizeType()) { InitializerElementNotConstant(Init); return true; } diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index a45d6717b79..92efa68cc43 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -654,10 +654,10 @@ Action::ExprResult Sema::ActOnParenExpr(SourceLocation L, SourceLocation R, /// The UsualUnaryConversions() function is *not* called by this routine. /// See C99 6.3.2.1p[2-4] for more details. -QualType Sema::CheckSizeOfAlignOfOperand(QualType exprType, - SourceLocation OpLoc, - const SourceRange &ExprRange, - bool isSizeof) { +bool Sema::CheckSizeOfAlignOfOperand(QualType exprType, + SourceLocation OpLoc, + const SourceRange &ExprRange, + bool isSizeof) { // C99 6.5.3.4p1: if (isa<FunctionType>(exprType) && isSizeof) // alignof(function) is allowed. @@ -669,28 +669,40 @@ QualType Sema::CheckSizeOfAlignOfOperand(QualType exprType, Diag(OpLoc, isSizeof ? diag::err_sizeof_incomplete_type : diag::err_alignof_incomplete_type, exprType.getAsString(), ExprRange); - return QualType(); // error + return true; // error } - // C99 6.5.3.4p4: the type (an unsigned integer type) is size_t. - return Context.getSizeType(); + + return false; } -Action::ExprResult Sema:: -ActOnSizeOfAlignOfTypeExpr(SourceLocation OpLoc, bool isSizeof, - SourceLocation LPLoc, TypeTy *Ty, - SourceLocation RPLoc) { +/// ActOnSizeOfAlignOfExpr - Handle @c sizeof(type) and @c sizeof @c expr and +/// the same for @c alignof and @c __alignof +/// Note that the ArgRange is invalid if isType is false. +Action::ExprResult +Sema::ActOnSizeOfAlignOfExpr(SourceLocation OpLoc, bool isSizeof, bool isType, + void *TyOrEx, const SourceRange &ArgRange) { // If error parsing type, ignore. - if (Ty == 0) return true; - - // Verify that this is a valid expression. - QualType ArgTy = QualType::getFromOpaquePtr(Ty); - - QualType resultType = - CheckSizeOfAlignOfOperand(ArgTy, OpLoc, SourceRange(LPLoc, RPLoc),isSizeof); + if (TyOrEx == 0) return true; - if (resultType.isNull()) + QualType ArgTy; + SourceRange Range; + if (isType) { + ArgTy = QualType::getFromOpaquePtr(TyOrEx); + Range = ArgRange; + } else { + // Get the end location. + Expr *ArgEx = (Expr *)TyOrEx; + Range = ArgEx->getSourceRange(); + ArgTy = ArgEx->getType(); + } + + // Verify that the operand is valid. + if (CheckSizeOfAlignOfOperand(ArgTy, OpLoc, Range, isSizeof)) return true; - return new SizeOfAlignOfTypeExpr(isSizeof, ArgTy, resultType, OpLoc, RPLoc); + + // C99 6.5.3.4p4: the type (an unsigned integer type) is size_t. + return new SizeOfAlignOfExpr(isSizeof, isType, TyOrEx, Context.getSizeType(), + OpLoc, Range.getEnd()); } QualType Sema::CheckRealImagOperand(Expr *&V, SourceLocation Loc) { @@ -2635,8 +2647,6 @@ static inline UnaryOperator::Opcode ConvertTokenKindToUnaryOpcode( case tok::minus: Opc = UnaryOperator::Minus; break; case tok::tilde: Opc = UnaryOperator::Not; break; case tok::exclaim: Opc = UnaryOperator::LNot; break; - case tok::kw_sizeof: Opc = UnaryOperator::SizeOf; break; - case tok::kw___alignof: Opc = UnaryOperator::AlignOf; break; case tok::kw___real: Opc = UnaryOperator::Real; break; case tok::kw___imag: Opc = UnaryOperator::Imag; break; case tok::kw___extension__: Opc = UnaryOperator::Extension; break; @@ -2902,14 +2912,6 @@ Action::ExprResult Sema::ActOnUnaryOp(SourceLocation OpLoc, tok::TokenKind Op, // LNot always has type int. C99 6.5.3.3p5. resultType = Context.IntTy; break; - case UnaryOperator::SizeOf: - resultType = CheckSizeOfAlignOfOperand(Input->getType(), OpLoc, - Input->getSourceRange(), true); - break; - case UnaryOperator::AlignOf: - resultType = CheckSizeOfAlignOfOperand(Input->getType(), OpLoc, - Input->getSourceRange(), false); - break; case UnaryOperator::Real: case UnaryOperator::Imag: resultType = CheckRealImagOperand(Input, OpLoc); |

