diff options
Diffstat (limited to 'meta/packages/gcc/gcc-3.4.4/gcc34-arm-ldm.patch')
-rw-r--r-- | meta/packages/gcc/gcc-3.4.4/gcc34-arm-ldm.patch | 119 |
1 files changed, 119 insertions, 0 deletions
diff --git a/meta/packages/gcc/gcc-3.4.4/gcc34-arm-ldm.patch b/meta/packages/gcc/gcc-3.4.4/gcc34-arm-ldm.patch new file mode 100644 index 0000000000..142052fdf0 --- /dev/null +++ b/meta/packages/gcc/gcc-3.4.4/gcc34-arm-ldm.patch | |||
@@ -0,0 +1,119 @@ | |||
1 | --- gcc-3.4.0/gcc/config/arm/arm.c.arm-ldm 2004-02-27 09:51:05.000000000 -0500 | ||
2 | +++ gcc-3.4.0/gcc/config/arm/arm.c 2004-04-24 18:16:25.000000000 -0400 | ||
3 | @@ -8520,6 +8520,26 @@ | ||
4 | return_used_this_function = 0; | ||
5 | } | ||
6 | |||
7 | +/* Return the number (counting from 0) of | ||
8 | + the least significant set bit in MASK. */ | ||
9 | + | ||
10 | +#ifdef __GNUC__ | ||
11 | +inline | ||
12 | +#endif | ||
13 | +static int | ||
14 | +number_of_first_bit_set (mask) | ||
15 | + int mask; | ||
16 | +{ | ||
17 | + int bit; | ||
18 | + | ||
19 | + for (bit = 0; | ||
20 | + (mask & (1 << bit)) == 0; | ||
21 | + ++bit) | ||
22 | + continue; | ||
23 | + | ||
24 | + return bit; | ||
25 | +} | ||
26 | + | ||
27 | const char * | ||
28 | arm_output_epilogue (rtx sibling) | ||
29 | { | ||
30 | @@ -8753,27 +8773,47 @@ | ||
31 | saved_regs_mask |= (1 << PC_REGNUM); | ||
32 | } | ||
33 | |||
34 | - /* Load the registers off the stack. If we only have one register | ||
35 | - to load use the LDR instruction - it is faster. */ | ||
36 | - if (saved_regs_mask == (1 << LR_REGNUM)) | ||
37 | - { | ||
38 | - /* The exception handler ignores the LR, so we do | ||
39 | - not really need to load it off the stack. */ | ||
40 | - if (eh_ofs) | ||
41 | - asm_fprintf (f, "\tadd\t%r, %r, #4\n", SP_REGNUM, SP_REGNUM); | ||
42 | - else | ||
43 | - asm_fprintf (f, "\tldr\t%r, [%r], #4\n", LR_REGNUM, SP_REGNUM); | ||
44 | - } | ||
45 | - else if (saved_regs_mask) | ||
46 | + if (saved_regs_mask) | ||
47 | { | ||
48 | - if (saved_regs_mask & (1 << SP_REGNUM)) | ||
49 | - /* Note - write back to the stack register is not enabled | ||
50 | - (ie "ldmfd sp!..."). We know that the stack pointer is | ||
51 | - in the list of registers and if we add writeback the | ||
52 | - instruction becomes UNPREDICTABLE. */ | ||
53 | - print_multi_reg (f, "ldmfd\t%r", SP_REGNUM, saved_regs_mask); | ||
54 | + /* Load the registers off the stack. If we only have one register | ||
55 | + to load use the LDR instruction - it is faster. */ | ||
56 | + if (bit_count (saved_regs_mask) == 1) | ||
57 | + { | ||
58 | + int reg = number_of_first_bit_set (saved_regs_mask); | ||
59 | + | ||
60 | + switch (reg) | ||
61 | + { | ||
62 | + case SP_REGNUM: | ||
63 | + /* Mustn't use base writeback when loading SP. */ | ||
64 | + asm_fprintf (f, "\tldr\t%r, [%r]\n", SP_REGNUM, SP_REGNUM); | ||
65 | + break; | ||
66 | + | ||
67 | + case LR_REGNUM: | ||
68 | + if (eh_ofs) | ||
69 | + { | ||
70 | + /* The exception handler ignores the LR, so we do | ||
71 | + not really need to load it off the stack. */ | ||
72 | + asm_fprintf (f, "\tadd\t%r, %r, #4\n", SP_REGNUM, SP_REGNUM); | ||
73 | + break; | ||
74 | + } | ||
75 | + /* else fall through */ | ||
76 | + | ||
77 | + default: | ||
78 | + asm_fprintf (f, "\tldr\t%r, [%r], #4\n", reg, SP_REGNUM); | ||
79 | + break; | ||
80 | + } | ||
81 | + } | ||
82 | else | ||
83 | - print_multi_reg (f, "ldmfd\t%r!", SP_REGNUM, saved_regs_mask); | ||
84 | + { | ||
85 | + if (saved_regs_mask & (1 << SP_REGNUM)) | ||
86 | + /* Note - write back to the stack register is not enabled | ||
87 | + (ie "ldmfd sp!..."). We know that the stack pointer is | ||
88 | + in the list of registers and if we add writeback the | ||
89 | + instruction becomes UNPREDICTABLE. */ | ||
90 | + print_multi_reg (f, "ldmfd\t%r", SP_REGNUM, saved_regs_mask); | ||
91 | + else | ||
92 | + print_multi_reg (f, "ldmfd\t%r!", SP_REGNUM, saved_regs_mask); | ||
93 | + } | ||
94 | } | ||
95 | |||
96 | if (current_function_pretend_args_size) | ||
97 | @@ -11401,22 +11441,6 @@ | ||
98 | } | ||
99 | } | ||
100 | |||
101 | -/* Return the number (counting from 0) of | ||
102 | - the least significant set bit in MASK. */ | ||
103 | - | ||
104 | -inline static int | ||
105 | -number_of_first_bit_set (int mask) | ||
106 | -{ | ||
107 | - int bit; | ||
108 | - | ||
109 | - for (bit = 0; | ||
110 | - (mask & (1 << bit)) == 0; | ||
111 | - ++bit) | ||
112 | - continue; | ||
113 | - | ||
114 | - return bit; | ||
115 | -} | ||
116 | - | ||
117 | /* Generate code to return from a thumb function. | ||
118 | If 'reg_containing_return_addr' is -1, then the return address is | ||
119 | actually on the stack, at the stack pointer. */ | ||