diff mbox

[i386] : Implement attribute ((naked))

Message ID CAFULd4Zu_0AT1imVJQsCQXu-OSrkpumof-1MTXz+_H=pH8Mg5Q@mail.gmail.com
State New
Headers show

Commit Message

Uros Bizjak July 31, 2017, 1:17 p.m. UTC
On Sun, Jul 30, 2017 at 10:14 PM, Uros Bizjak <ubizjak@gmail.com> wrote:
> Hello!
>
> attribute ((naked)) generates function body without function frame,
> and as shown in PR 25967 [1], users are looking for this feature also
> for x86 targets. Recently, Daniel introduced a testcase that would
> benefit from this attribute.

Following additional patch enables passing arguments to a naked
function. Testcases gcc.target/i386/naked-3.c and
gcc.target/i386/naked-4.c show necessary decorations (i.e. mregparm
for -m32 and volatile "ret" for function result) to reliably pass
function arguments to and function result from naked functions.

2017-07-31  Uros Bizjak  <ubizjak@gmail.com>

    PR target/25967
    * config/i386/i386.c (ix86_allocate_stack_slots_for_args):
    New function.
    (TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS): Define.

testsuite/ChangeLog:

2017-07-31  Uros Bizjak  <ubizjak@gmail.com>

    PR target/25967
    * gcc.target/i386/naked-3.c (dg-options): Use -O0.
    (naked): Add attribute regparm(1) for x86_32 targets.
    Add integer argument.  Remove global "data" variable.
    (main): Pass integer argument to naked function.
    * gcc.target/i386/naked-4.c: New test.

Bootstrapped and regression tested on x86_64-linux-gnu {-m32}.

Committed to mainline SVN.

Uros.
diff mbox

Patch

Index: config/i386/i386.c
===================================================================
--- config/i386/i386.c	(revision 250736)
+++ config/i386/i386.c	(working copy)
@@ -31676,6 +31676,13 @@  ix86_trampoline_init (rtx m_tramp, tree fndecl, rt
 }
 
 static bool
+ix86_allocate_stack_slots_for_args (void)
+{
+  /* Naked functions should not allocate stack slots for arguments.  */
+  return !ix86_function_naked (current_function_decl);
+}
+
+static bool
 ix86_warn_func_return (tree decl)
 {
   /* Naked functions are implemented entirely in assembly, including the
@@ -52727,6 +52734,8 @@  ix86_run_selftests (void)
 #define TARGET_SETUP_INCOMING_VARARGS ix86_setup_incoming_varargs
 #undef TARGET_MUST_PASS_IN_STACK
 #define TARGET_MUST_PASS_IN_STACK ix86_must_pass_in_stack
+#undef TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS
+#define TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS ix86_allocate_stack_slots_for_args
 #undef TARGET_FUNCTION_ARG_ADVANCE
 #define TARGET_FUNCTION_ARG_ADVANCE ix86_function_arg_advance
 #undef TARGET_FUNCTION_ARG
Index: testsuite/gcc.target/i386/naked-3.c
===================================================================
--- testsuite/gcc.target/i386/naked-3.c	(revision 250736)
+++ testsuite/gcc.target/i386/naked-3.c	(working copy)
@@ -1,17 +1,18 @@ 
 /* { dg-do run { target *-*-linux* *-*-gnu* } } */
-/* { dg-options "-O2" } */
+/* { dg-options "-O0" } */
 
 #include <unistd.h>
 #include <signal.h>
 #include <stdlib.h>
 
-int data;
-
 /* Verify that naked function traps at the end.  */
 
 void
 __attribute__((naked, noinline, noclone))
-naked (void)
+#ifdef __i386__
+__attribute__((regparm(1)))
+#endif
+naked (int data)
 {
   if (data == 0x12345678)
     return;
@@ -32,8 +33,7 @@  int main ()
   s.sa_flags = 0;
   sigaction (SIGILL, &s, NULL);
 
-  data = 0x12345678;
-  naked ();
+  naked (0x12345678);
 
   abort ();
 }
Index: testsuite/gcc.target/i386/naked-4.c
===================================================================
--- testsuite/gcc.target/i386/naked-4.c	(nonexistent)
+++ testsuite/gcc.target/i386/naked-4.c	(working copy)
@@ -0,0 +1,17 @@ 
+/* { dg-do compile } */
+/* { dg-options "-O0" } */
+/* { dg-additional-options "-mregparm=3" { target ia32 } } */
+
+/* Verify that __attribute__((naked)) produces a naked function 
+   that does not allocate stack slots for args.  */
+extern void bar (int);
+
+int
+__attribute__((naked))
+foo (int a, int b, int c)
+{
+  bar (c);
+  asm volatile ("ret" :: "a" (b));
+}
+
+/* { dg-final { scan-assembler-not "%\[re\]bp" } } */