diff options
author | Daniel Dunbar <daniel@zuster.org> | 2008-09-03 21:13:56 +0000 |
---|---|---|
committer | Daniel Dunbar <daniel@zuster.org> | 2008-09-03 21:13:56 +0000 |
commit | b0d34c8e4a2367827083515d60eec73f5bb4de92 (patch) | |
tree | ddbe1527ce7d57f23f532a94ddd9983d38b28d6d /clang/lib/Sema/SemaChecking.cpp | |
parent | 9fed8f5b9c0e9f4e6377e1385de3e31319dbc841 (diff) | |
download | bcm5719-llvm-b0d34c8e4a2367827083515d60eec73f5bb4de92.tar.gz bcm5719-llvm-b0d34c8e4a2367827083515d60eec73f5bb4de92.zip |
Add __builtin_object_size support.
- Currently CodeGen always returns a conservative value for this (-1
or 0 depending on the context).
llvm-svn: 55735
Diffstat (limited to 'clang/lib/Sema/SemaChecking.cpp')
-rw-r--r-- | clang/lib/Sema/SemaChecking.cpp | 33 |
1 files changed, 29 insertions, 4 deletions
diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp index e5e80db2bef..1c1c594edc4 100644 --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -62,6 +62,9 @@ Sema::CheckFunctionCall(FunctionDecl *FDecl, CallExpr *TheCallRaw) { if (SemaBuiltinPrefetch(TheCall.get())) return true; return TheCall.take(); + case Builtin::BI__builtin_object_size: + if (SemaBuiltinObjectSize(TheCall.get())) + return true; } // Search the KnownFunctionIDs for the identifier. @@ -300,8 +303,7 @@ bool Sema::SemaBuiltinPrefetch(CallExpr *TheCall) { QualType RWType = Arg->getType(); const BuiltinType *BT = RWType->getAsBuiltinType(); - // FIXME: 32 is wrong, needs to be proper width of Int - llvm::APSInt Result(32); + llvm::APSInt Result; if (!BT || BT->getKind() != BuiltinType::Int || !Arg->isIntegerConstantExpr(Result, Context)) { if (Diag(TheCall->getLocStart(), diag::err_prefetch_invalid_argument, @@ -316,12 +318,12 @@ bool Sema::SemaBuiltinPrefetch(CallExpr *TheCall) { // is 3. if (i==1) { if (Result.getSExtValue() < 0 || Result.getSExtValue() > 1) - res |= Diag(TheCall->getLocStart(), diag::err_prefetch_invalid_range, + res |= Diag(TheCall->getLocStart(), diag::err_argument_invalid_range, "0", "1", SourceRange(Arg->getLocStart(), Arg->getLocEnd())); } else { if (Result.getSExtValue() < 0 || Result.getSExtValue() > 3) - res |= Diag(TheCall->getLocStart(), diag::err_prefetch_invalid_range, + res |= Diag(TheCall->getLocStart(), diag::err_argument_invalid_range, "0", "3", SourceRange(Arg->getLocStart(), Arg->getLocEnd())); } @@ -330,6 +332,29 @@ bool Sema::SemaBuiltinPrefetch(CallExpr *TheCall) { return res; } +/// SemaBuiltinObjectSize - Handle __builtin_object_size(void *ptr, +/// int type). This simply type checks that type is one of the defined +/// constants (0-3). +bool Sema::SemaBuiltinObjectSize(CallExpr *TheCall) { + Expr *Arg = TheCall->getArg(1); + QualType ArgType = Arg->getType(); + const BuiltinType *BT = ArgType->getAsBuiltinType(); + llvm::APSInt Result(32); + if (!BT || BT->getKind() != BuiltinType::Int || + !Arg->isIntegerConstantExpr(Result, Context)) { + return Diag(TheCall->getLocStart(), diag::err_object_size_invalid_argument, + SourceRange(Arg->getLocStart(), Arg->getLocEnd())); + } + + if (Result.getSExtValue() < 0 || Result.getSExtValue() > 3) { + return Diag(TheCall->getLocStart(), diag::err_argument_invalid_range, + "0", "3", + SourceRange(Arg->getLocStart(), Arg->getLocEnd())); + } + + return false; +} + /// CheckPrintfArguments - Check calls to printf (and similar functions) for /// correct use of format strings. /// |