From f8353034eb57cf20ca4b3be70added7176f26537 Mon Sep 17 00:00:00 2001 From: Eli Friedman Date: Tue, 20 May 2008 08:23:37 +0000 Subject: [PATCH] Add __builtin_frame_address and __builtin_return_address gcc builtins to Sema. No codegen yet. llvm-svn: 51307 --- clang/include/clang/AST/Builtins.def | 2 ++ clang/include/clang/Basic/DiagnosticKinds.def | 3 +++ clang/lib/Sema/Sema.h | 1 + clang/lib/Sema/SemaChecking.cpp | 17 ++++++++++++++++- clang/test/Sema/builtin-stackaddress.c | 16 ++++++++++++++++ 5 files changed, 38 insertions(+), 1 deletion(-) create mode 100644 clang/test/Sema/builtin-stackaddress.c diff --git a/clang/include/clang/AST/Builtins.def b/clang/include/clang/AST/Builtins.def index 4d3812fc9412..0016afdcb88e 100644 --- a/clang/include/clang/AST/Builtins.def +++ b/clang/include/clang/AST/Builtins.def @@ -94,6 +94,8 @@ BUILTIN(__builtin_va_start, "va&.", "n") BUILTIN(__builtin_va_end, "va&", "n") BUILTIN(__builtin_va_copy, "va&a", "n") BUILTIN(__builtin_memcpy, "v*v*vC*z", "n") +BUILTIN(__builtin_return_address, "v*Ui", "n") +BUILTIN(__builtin_frame_address, "v*Ui", "n") // GCC Object size checking builtins BUILTIN(__builtin___memcpy_chk, "v*v*vC*zz", "n") BUILTIN(__builtin___memmove_chk, "v*v*vC*zz", "n") diff --git a/clang/include/clang/Basic/DiagnosticKinds.def b/clang/include/clang/Basic/DiagnosticKinds.def index b5fb1ddf6bf6..3eb08e4b5577 100644 --- a/clang/include/clang/Basic/DiagnosticKinds.def +++ b/clang/include/clang/Basic/DiagnosticKinds.def @@ -1069,4 +1069,7 @@ DIAG(err_shufflevector_nonconstant_argument, ERROR, DIAG(err_shufflevector_argument_too_large, ERROR, "indexes for __builtin_shufflevector must be less than the total number of vector elements") +DIAG(err_stack_const_level, ERROR, + "the level argument for a stack address builtin must be constant") + #undef DIAG diff --git a/clang/lib/Sema/Sema.h b/clang/lib/Sema/Sema.h index b1b99966ddd0..b9b922a376ed 100644 --- a/clang/lib/Sema/Sema.h +++ b/clang/lib/Sema/Sema.h @@ -891,6 +891,7 @@ private: bool CheckBuiltinCFStringArgument(Expr* Arg); bool SemaBuiltinVAStart(CallExpr *TheCall); bool SemaBuiltinUnorderedCompare(CallExpr *TheCall); + bool SemaBuiltinStackAddress(CallExpr *TheCall); Action::ExprResult SemaBuiltinShuffleVector(CallExpr *TheCall); void CheckPrintfArguments(CallExpr *TheCall, bool HasVAListArg, unsigned format_idx); diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp index ce0036e399cd..63c1635ef2b0 100644 --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -58,6 +58,11 @@ Sema::CheckFunctionCall(FunctionDecl *FDecl, CallExpr *TheCallRaw) { if (SemaBuiltinUnorderedCompare(TheCall.get())) return true; return TheCall.take(); + case Builtin::BI__builtin_return_address: + case Builtin::BI__builtin_frame_address: + if (SemaBuiltinStackAddress(TheCall.get())) + return true; + return TheCall.take(); case Builtin::BI__builtin_shufflevector: return SemaBuiltinShuffleVector(TheCall.get()); } @@ -177,7 +182,7 @@ bool Sema::SemaBuiltinVAStart(CallExpr *TheCall) { Diag(TheCall->getArg(1)->getLocStart(), diag::warn_second_parameter_of_va_start_not_last_named_argument); return false; -} +} /// SemaBuiltinUnorderedCompare - Handle functions like __builtin_isgreater and /// friends. This is declared to take (...), so we have to check everything. @@ -209,6 +214,16 @@ bool Sema::SemaBuiltinUnorderedCompare(CallExpr *TheCall) { return false; } +bool Sema::SemaBuiltinStackAddress(CallExpr *TheCall) { + // The signature for these builtins is exact; the only thing we need + // to check is that the argument is a constant. + SourceLocation Loc; + if (!TheCall->getArg(0)->isIntegerConstantExpr(Context, &Loc)) { + return Diag(Loc, diag::err_stack_const_level, TheCall->getSourceRange()); + } + return false; +} + /// SemaBuiltinShuffleVector - Handle __builtin_shufflevector. // This is declared to take (...), so we have to check everything. Action::ExprResult Sema::SemaBuiltinShuffleVector(CallExpr *TheCall) { diff --git a/clang/test/Sema/builtin-stackaddress.c b/clang/test/Sema/builtin-stackaddress.c new file mode 100644 index 000000000000..a828168f3d80 --- /dev/null +++ b/clang/test/Sema/builtin-stackaddress.c @@ -0,0 +1,16 @@ +// RUN: clang -fsyntax-only -verify %s +void* a(unsigned x) { +return __builtin_return_address(0); +} + +void b(unsigned x) { +return __builtin_return_address(x); // expected-error{{the level argument for a stack address builtin must be constant}} +} + +void* a(unsigned x) { +return __builtin_frame_address(0); +} + +void b(unsigned x) { +return __builtin_frame_address(x); // expected-error{{the level argument for a stack address builtin must be constant}} +}