[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[avr-gcc-list] the framepointer
From: |
Ruud Vlaming |
Subject: |
[avr-gcc-list] the framepointer |
Date: |
Sat, 19 Apr 2008 13:42:16 +0200 |
User-agent: |
KMail/1.9.1 |
Hi
After my rather embarressing mistake accusing the gcc of buggy behaviour
i tried to understand the way framepointers are implemented in the avr.c
backend. I have a few questions and remarks, that may be helpfull to other
with the same problems.
First, I see in the avr.c a special handling for the main function inside
static void avr_output_function_prologue (FILE *file, HOST_WIDE_INT size)
....
if (main_p)
{
fprintf (file, ("\t"
AS1 (ldi,r28) ",lo8(%s - " HOST_WIDE_INT_PRINT_DEC ")" CR_TAB
AS1 (ldi,r29) ",hi8(%s - " HOST_WIDE_INT_PRINT_DEC ")" CR_TAB
AS2 (out,__SP_H__,r29) CR_TAB
AS2 (out,__SP_L__,r28) "\n"),
avr_init_stack, size, avr_init_stack, size);
prologue_size += 4;
}
....
Now, I don't understand how this can work. It sets up the framepointer
and stackpointer, but does not handle the size parameter, so i don't
see how the stackpointer is later shifted to make room for the frame,
if needed, ie: inside the function it never seems to reach any
instructions like
prologue_size += out_adj_frame_ptr (file, size);
prologue_size += out_set_stack_ptr (file, -1, -1);
What do i miss?
Second, the generated code could be optimized a little more
with the following change, since pushing registers in a noreturn
function does not seem to make much sense:
if (frame_pointer_needed)
{
if (!noreturn_func_p)
{ fprintf (file, "\t"
AS1 (push,r28) CR_TAB
AS1 (push,r29) "\n");
prologue_size += 2; }
fprintf (file, "\t"
AS2 (in,r28,__SP_L__) CR_TAB
AS2 (in,r29,__SP_H__) "\n");
prologue_size += 2;
....
and noreturn_func_p must be coupled to the noretrun attribute.
NB: this is untested code, it is just in idea.
Third, I have hacked the avr.c backend to make possible the "bikini"
attribute. This works like the naked attribute only it defines a framepointer
when needed. Maybe this is of very special need only, i don't know, but
in my code it can make a difference of 2-4% compared to using no
attribute, and makes code correct for the rare cases a framepointer
is needed by the compiler when you stated -fomit-frame-pointer.
I am not saying this should be incorporated into the public code.
Since the avr.c file is big, i attached the diff:
diff -c avr.c avr_hack.c > avr_hack.c.diff
Note, this is the avr.c of version 4.2.3.
I hope it is of use to somebody.
regards
Ruud
avr_hack.c.diff
Description: Text Data
- [avr-gcc-list] the framepointer,
Ruud Vlaming <=