This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

More fr30 fun



The nested function tests were failing pretty miserably on the fr30.

The fr30 is a STRICT_ALIGNMENT target.  So hopefully it's obvious that
this code can never work correctly:


#define INITIALIZE_TRAMPOLINE(ADDR, FNADDR, STATIC_CHAIN)                      
\
do                                                                             
\
{                                                                              
\
  emit_move_insn (gen_rtx (MEM, SImode, plus_constant (ADDR, 
2)),STATIC_CHAIN);\
  emit_move_insn (gen_rtx (MEM, SImode, plus_constant (ADDR, 8)), FNADDR);     
\
} while (0);

No matter what, one of those two SImode stores is only going to be 16bit
aligned.  This causes numerous unpleasant things to happen.

I considered using HImode stores, but it seemed easier to simply guarantee the
trampoline itself would always be 32bit aligned, then insert two nops to
ensure that the location of the static chain and fnaddr were always going to
be 32bit aligned, then set TRAMPOLINE_ALIGNMENT to make sure the trampoline
itself was always 32bit aligned.


	* fr30.h (TRAMPOLINE_TEMPLATE): Use nops to ensure the static chain
	and destination functions are 32bit aligned within the trampoline.
	(TRAMPOLINE_SIZE, INITIALIZE_TRAMPOLINE): Corresponding changes.
	(TRAMPOLINE_ALIGNMENT): Define.

Index: fr30.h
===================================================================
RCS file: /cvs/cvsfiles/devo/gcc/config/fr30/fr30.h,v
retrieving revision 1.38
diff -c -3 -p -r1.38 fr30.h
*** fr30.h	2000/01/14 07:38:46	1.38
--- fr30.h	2000/01/14 09:21:43
*************** typedef int CUMULATIVE_ARGS;
*** 1139,1160 ****
  
  /* On the FR30, the trampoline is:
  
     ldi:32 STATIC, r12
     ldi:32 FUNCTION, r0
!    jmp    @r0 */
     
  /* A C statement to output, on the stream FILE, assembler code for a block of
     data that contains the constant parts of a trampoline.  This code should 
not
     include a label--the label is taken care of automatically.  */
  #define TRAMPOLINE_TEMPLATE(FILE)						\
  {										\
    fprintf (FILE, "\tldi:32\t#0, %s\n", reg_names [STATIC_CHAIN_REGNUM]);	\
    fprintf (FILE, "\tldi:32\t#0, %s\n", reg_names 
[COMPILER_SCRATCH_REGISTER]);	\
    fprintf (FILE, "\tjmp\t@%s\n", reg_names [COMPILER_SCRATCH_REGISTER]);	\
  }
  
  /* A C expression for the size in bytes of the trampoline, as an integer.  */
! #define TRAMPOLINE_SIZE 14
  
  /* A C statement to initialize the variable parts of a trampoline.  ADDR is 
an
     RTX for the address of the trampoline; FNADDR is an RTX for the address of
--- 1139,1174 ----
  
  /* On the FR30, the trampoline is:
  
+    nop
     ldi:32 STATIC, r12
+    nop
     ldi:32 FUNCTION, r0
!    jmp    @r0
! 
!    The no-ops are to guarantee that the the static chain and final
!    target are 32 bit ailgned within the trampoline.  That allows us to
!    initialize those locations with simple SImode stores.   The alternative
!    would be to use HImode stores.  */
     
  /* A C statement to output, on the stream FILE, assembler code for a block of
     data that contains the constant parts of a trampoline.  This code should 
not
     include a label--the label is taken care of automatically.  */
  #define TRAMPOLINE_TEMPLATE(FILE)						\
  {										\
+   fprintf (FILE, "\tnop\n");							\
    fprintf (FILE, "\tldi:32\t#0, %s\n", reg_names [STATIC_CHAIN_REGNUM]);	\
+   fprintf (FILE, "\tnop\n");							\
    fprintf (FILE, "\tldi:32\t#0, %s\n", reg_names 
[COMPILER_SCRATCH_REGISTER]);	\
    fprintf (FILE, "\tjmp\t@%s\n", reg_names [COMPILER_SCRATCH_REGISTER]);	\
  }
  
  /* A C expression for the size in bytes of the trampoline, as an integer.  */
! #define TRAMPOLINE_SIZE 18
! 
! /* We want the trampoline to be aligned on a 32bit boundary so that we can
!    make sure the location of the static chain & target function within
!    the trampoline is also aligned on a 32bit boundary.  */
! #define TRAMPOLINE_ALIGNMENT 32
  
  /* A C statement to initialize the variable parts of a trampoline.  ADDR is 
an
     RTX for the address of the trampoline; FNADDR is an RTX for the address of
*************** typedef int CUMULATIVE_ARGS;
*** 1163,1170 ****
  #define INITIALIZE_TRAMPOLINE(ADDR, FNADDR, STATIC_CHAIN)			\
  do										\
  {										\
!   emit_move_insn (gen_rtx (MEM, SImode, plus_constant (ADDR, 2)), 
STATIC_CHAIN);\
!   emit_move_insn (gen_rtx (MEM, SImode, plus_constant (ADDR, 8)), FNADDR);	\
  } while (0);
  
  /*}}}*/ 
--- 1177,1184 ----
  #define INITIALIZE_TRAMPOLINE(ADDR, FNADDR, STATIC_CHAIN)			\
  do										\
  {										\
!   emit_move_insn (gen_rtx (MEM, SImode, plus_constant (ADDR, 4)), 
STATIC_CHAIN);\
!   emit_move_insn (gen_rtx (MEM, SImode, plus_constant (ADDR, 12)), FNADDR);	\
  } while (0);
  
  /*}}}*/ 







Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]