https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66960

--- Comment #3 from H.J. Lu <hjl.tools at gmail dot com> ---
From

https://gcc.gnu.org/ml/gcc-patches/2015-09/msg02246.html

To be feature complete, it would be nice to have two styles of interrupt
functions, one that returns with iret, and one that returns with ret.
The point is that the user might want to call functions from a interrupt
handler and not save and restore all call clobbered registers.  By
allowing a ret style interrupt handler, calls to a ret style interrupt
routine can avoid saving and restoring all call clobbered registers.

[hjl@gnu-6 interrupt-7]$ cat call-1.i
extern void bar (void);

void
 __attribute__ ((interrupt))
fn1 (void *frame)
{
  bar ();
}

void
 __attribute__ ((interrupt))
fn2 (void *frame)
{
  bar ();
}
[hjl@gnu-6 interrupt-7]$ make
/export/build/gnu/gcc/build-x86_64-linux/gcc/xgcc
-B/export/build/gnu/gcc/build-x86_64-linux/gcc/ -O2 -Wall -Wunused-parameter
-mno-push-args -mno-sse -m32 -S -o call-1.s call-1.i
[hjl@gnu-6 interrupt-7]$ cat call-1.s
        .file   "call-1.i"
        .text
        .p2align 4,,15
        .globl  fn1
        .type   fn1, @function
fn1:
.LFB3:
        .cfi_startproc
        pushl   %ecx
        .cfi_def_cfa_offset 8
        .cfi_offset 1, -8
        pushl   %edx
        .cfi_def_cfa_offset 12
        .cfi_offset 2, -12
        pushl   %eax
        .cfi_def_cfa_offset 16
        .cfi_offset 0, -16
        call    bar
        popl    %eax
        .cfi_restore 0
        .cfi_def_cfa_offset 12
        popl    %edx
        .cfi_restore 2
        .cfi_def_cfa_offset 8
        popl    %ecx
        .cfi_restore 1
        .cfi_def_cfa_offset 4
        iret
        .cfi_endproc
.LFE3:
        .size   fn1, .-fn1
        .p2align 4,,15
        .globl  fn2
        .type   fn2, @function
fn2:
.LFB1:
        .cfi_startproc
        pushl   %ecx
        .cfi_def_cfa_offset 8
        .cfi_offset 1, -8
        pushl   %edx
        .cfi_def_cfa_offset 12
        .cfi_offset 2, -12
        pushl   %eax
        .cfi_def_cfa_offset 16
        .cfi_offset 0, -16
        call    bar
        popl    %eax
        .cfi_restore 0
        .cfi_def_cfa_offset 12
        popl    %edx
        .cfi_restore 2
        .cfi_def_cfa_offset 8
        popl    %ecx
        .cfi_restore 1
        .cfi_def_cfa_offset 4
        iret
        .cfi_endproc
.LFE1:
        .size   fn2, .-fn2
        .ident  "GCC: (GNU) 6.0.0 20150929 (experimental)"
        .section        .note.GNU-stack,"",@progbits
[hjl@gnu-6 interrupt-7]$  

Both fn1 and fn2 have to save and restore caller-saved registers.
If all registers in bar are callee-saved, fn1 and fn2 can be
much smaller.

Reply via email to