summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--cgopt.c91
1 files changed, 46 insertions, 45 deletions
diff --git a/cgopt.c b/cgopt.c
index 0d27fe6..48f9950 100644
--- a/cgopt.c
+++ b/cgopt.c
@@ -705,7 +705,7 @@ static void optimize_b_stack_access2 (struct instruction *instruction)
}
# endif
-static void compute_maximum_b_stack_offsets (register int b_offset)
+static void compute_extreme_stack_offsets (int *b_offset,int *min_a_offset)
{
struct instruction *instruction;
@@ -748,32 +748,50 @@ static void compute_maximum_b_stack_offsets (register int b_offset)
break;
else
#endif
- internal_error_in_function ("compute_maximum_b_stack_offsets");
+ internal_error_in_function ("compute_extreme_stack_offsets");
/* only first argument of movem or mod might be register indirect */
/* no break ! */
case 1:
if (instruction->instruction_parameters[0].parameter_type==P_INDIRECT
&& instruction->instruction_parameters[0].parameter_data.reg.r==B_STACK_POINTER)
{
- instruction->instruction_parameters[0].parameter_data.reg.u=b_offset;
- if (instruction->instruction_parameters[0].parameter_offset<b_offset)
- b_offset=instruction->instruction_parameters[0].parameter_offset;
+ instruction->instruction_parameters[0].parameter_data.reg.u=*b_offset;
+ if (instruction->instruction_parameters[0].parameter_offset<*b_offset)
+ *b_offset=instruction->instruction_parameters[0].parameter_offset;
+ }
+ else if (instruction->instruction_parameters[0].parameter_type==P_INDIRECT
+ && instruction->instruction_parameters[0].parameter_data.reg.r==A_STACK_POINTER)
+ {
+ if (instruction->instruction_parameters[0].parameter_offset<*min_a_offset)
+ *min_a_offset=instruction->instruction_parameters[0].parameter_offset;
}
break;
case 2:
if (instruction->instruction_parameters[0].parameter_type==P_INDIRECT
&& instruction->instruction_parameters[0].parameter_data.reg.r==B_STACK_POINTER)
{
- instruction->instruction_parameters[0].parameter_data.reg.u=b_offset;
- if (instruction->instruction_parameters[0].parameter_offset<b_offset)
- b_offset=instruction->instruction_parameters[0].parameter_offset;
+ instruction->instruction_parameters[0].parameter_data.reg.u=*b_offset;
+ if (instruction->instruction_parameters[0].parameter_offset<*b_offset)
+ *b_offset=instruction->instruction_parameters[0].parameter_offset;
+ }
+ else if (instruction->instruction_parameters[0].parameter_type==P_INDIRECT
+ && instruction->instruction_parameters[0].parameter_data.reg.r==A_STACK_POINTER)
+ {
+ if (instruction->instruction_parameters[0].parameter_offset<*min_a_offset)
+ *min_a_offset=instruction->instruction_parameters[0].parameter_offset;
}
if (instruction->instruction_parameters[1].parameter_type==P_INDIRECT
&& instruction->instruction_parameters[1].parameter_data.reg.r==B_STACK_POINTER)
{
- instruction->instruction_parameters[1].parameter_data.reg.u=b_offset;
- if (instruction->instruction_parameters[1].parameter_offset<b_offset)
- b_offset=instruction->instruction_parameters[1].parameter_offset;
+ instruction->instruction_parameters[1].parameter_data.reg.u=*b_offset;
+ if (instruction->instruction_parameters[1].parameter_offset<*b_offset)
+ *b_offset=instruction->instruction_parameters[1].parameter_offset;
+ }
+ else if (instruction->instruction_parameters[1].parameter_type==P_INDIRECT
+ && instruction->instruction_parameters[1].parameter_data.reg.r==A_STACK_POINTER)
+ {
+ if (instruction->instruction_parameters[1].parameter_offset<*min_a_offset)
+ *min_a_offset=instruction->instruction_parameters[1].parameter_offset;
}
}
}
@@ -805,6 +823,7 @@ void optimize_stack_access (struct basic_block *block,int *a_offset_p,int *b_off
)
{
struct instruction *instruction;
+ int min_a_offset;
# ifdef M68000
a_offset=0;
@@ -818,21 +837,20 @@ void optimize_stack_access (struct basic_block *block,int *a_offset_p,int *b_off
previous_b_stack_parameter=NULL;
# endif
+ b_offset=0;
+
+ compute_extreme_stack_offsets (b_offset_p, &min_a_offset);
+
# ifdef THUMB2
- int fix_a_offset=0;
- if (*a_offset_p <= -256)
+ int fix_a_offset = 0;
+ if (min_a_offset <= -256)
{
- fix_a_offset=0-*a_offset_p;
+ fix_a_offset=-min_a_offset;
insert_decrement_a_stack_pointer (block->block_instructions,fix_a_offset);
- i_add_i_r (fix_a_offset,A_STACK_POINTER);
- *a_offset_p=0;
+ *a_offset_p+=fix_a_offset;
}
# endif
- b_offset=0;
-
- compute_maximum_b_stack_offsets (*b_offset_p);
-
# ifdef M68000
for_l (instruction,block->block_instructions,instruction_next){
switch (instruction->instruction_arity){
@@ -916,38 +934,20 @@ void optimize_stack_access (struct basic_block *block,int *a_offset_p,int *b_off
for_l (instruction,block->block_instructions,instruction_next){
if (instruction->instruction_icode==IMOVE){
# ifdef ARM
+# ifdef THUMB2
+ if (instruction->instruction_parameters[1].parameter_data.reg.r==A_STACK_POINTER)
+ instruction->instruction_parameters[1].parameter_offset+=fix_a_offset;
+ if (instruction->instruction_parameters[0].parameter_data.reg.r==A_STACK_POINTER)
+ instruction->instruction_parameters[0].parameter_offset+=fix_a_offset;
+# endif
if (instruction->instruction_parameters[1].parameter_type==P_INDIRECT &&
instruction->instruction_parameters[1].parameter_data.reg.r==A_STACK_POINTER)
{
-# ifdef THUMB2
- int offset=instruction->instruction_parameters[1].parameter_offset+=fix_a_offset;
- if (offset < -255)
- {
- insert_decrement_a_stack_pointer (instruction,-offset);
- instruction->instruction_parameters[1].parameter_offset=0;
- if (instruction->instruction_next)
- insert_decrement_a_stack_pointer (instruction->instruction_next,offset);
- else
- i_lea_id_r (-offset,A_STACK_POINTER,A_STACK_POINTER);
- }
-# endif
previous_a_stack_parameter=&instruction->instruction_parameters[1];
previous_a_stack_parameter_icode=IMOVE;
} else if (instruction->instruction_parameters[0].parameter_type==P_INDIRECT &&
instruction->instruction_parameters[0].parameter_data.reg.r==A_STACK_POINTER)
{
-# ifdef THUMB2
- int offset=instruction->instruction_parameters[0].parameter_offset+=fix_a_offset;
- if (offset < -255)
- {
- insert_decrement_a_stack_pointer (instruction,-offset);
- instruction->instruction_parameters[0].parameter_offset=0;
- if (instruction->instruction_next)
- insert_decrement_a_stack_pointer (instruction->instruction_next,offset);
- else
- i_lea_id_r (-offset,A_STACK_POINTER,A_STACK_POINTER);
- }
-# endif
previous_a_stack_parameter=&instruction->instruction_parameters[0];
previous_a_stack_parameter_icode=IMOVE;
}
@@ -1206,7 +1206,8 @@ void optimize_stack_access (struct basic_block *block,int *a_offset_p,int *b_off
}
if (previous_a_stack_parameter!=NULL && *a_offset_p!=0 && is_int_instruction (previous_a_stack_parameter_icode)){
- if (previous_a_stack_parameter->parameter_type==P_INDIRECT){
+ if (previous_a_stack_parameter->parameter_type==P_INDIRECT
+ && -255 <= *a_offset_p && *a_offset_p <= 255){
if (previous_a_stack_parameter->parameter_offset==0){
previous_a_stack_parameter->parameter_type=P_INDIRECT_POST_ADD;
previous_a_stack_parameter->parameter_offset=*a_offset_p;