r217198 - Don't emit prologues or epilogues for naked functions (PR18791, PR20028)

Hans Wennborg hans at hanshq.net
Thu Sep 4 15:16:35 PDT 2014


Author: hans
Date: Thu Sep  4 17:16:33 2014
New Revision: 217198

URL: http://llvm.org/viewvc/llvm-project?rev=217198&view=rev
Log:
Don't emit prologues or epilogues for naked functions (PR18791, PR20028)

For naked functions with parameters, Clang would still emit stores in the prologue
that would clobber the stack, because LLVM doesn't set up a stack frame. (This
shows up in -O0 compiles, because the stores are optimized away otherwise.)

For example:

  __attribute__((naked)) int f(int x) {
    asm("movl $42, %eax");
    asm("retl");
  }

Would result in:

  _Z1fi:
  movl    12(%esp), %eax
  movl    %eax, (%esp)    <--- Oops.
  movl    $42, %eax
  retl

Differential Revision: http://reviews.llvm.org/D5183

Modified:
    cfe/trunk/lib/CodeGen/CGCall.cpp
    cfe/trunk/test/CodeGen/attr-naked.c

Modified: cfe/trunk/lib/CodeGen/CGCall.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGCall.cpp?rev=217198&r1=217197&r2=217198&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGCall.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGCall.cpp Thu Sep  4 17:16:33 2014
@@ -1462,6 +1462,10 @@ static bool shouldAddNonNullAttr(const D
 void CodeGenFunction::EmitFunctionProlog(const CGFunctionInfo &FI,
                                          llvm::Function *Fn,
                                          const FunctionArgList &Args) {
+  if (CurCodeDecl && CurCodeDecl->hasAttr<NakedAttr>())
+    // Naked functions don't have prologues.
+    return;
+
   // If this is an implicit-return-zero function, go ahead and
   // initialize the return value.  TODO: it might be nice to have
   // a more general mechanism for this that didn't require synthesized
@@ -1985,6 +1989,12 @@ static llvm::StoreInst *findDominatingSt
 void CodeGenFunction::EmitFunctionEpilog(const CGFunctionInfo &FI,
                                          bool EmitRetDbgLoc,
                                          SourceLocation EndLoc) {
+  if (CurCodeDecl && CurCodeDecl->hasAttr<NakedAttr>()) {
+    // Naked functions don't have epilogues.
+    Builder.CreateUnreachable();
+    return;
+  }
+
   // Functions with no result always return void.
   if (!ReturnValue) {
     Builder.CreateRetVoid();

Modified: cfe/trunk/test/CodeGen/attr-naked.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/attr-naked.c?rev=217198&r1=217197&r2=217198&view=diff
==============================================================================
--- cfe/trunk/test/CodeGen/attr-naked.c (original)
+++ cfe/trunk/test/CodeGen/attr-naked.c Thu Sep  4 17:16:33 2014
@@ -12,7 +12,15 @@ void t1()
 // Make sure this doesn't explode in the verifier.
 // (It doesn't really make sense, but it isn't invalid.)
 // CHECK: define void @t2() [[NAKED]] {
-__attribute((naked, always_inline)) void t2()  {
+__attribute((naked, always_inline)) void t2() {
+}
+
+// Make sure not to generate prolog or epilog for naked functions.
+__attribute((naked)) void t3(int x) {
+// CHECK: define void @t3(i32)
+// CHECK-NOT: alloca
+// CHECK-NOT: store
+// CHECK: unreachable
 }
 
 // CHECK: attributes [[NAKED]] = { naked noinline nounwind{{.*}} }





More information about the cfe-commits mailing list