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]

alpha builtin_longjmp fix


execute/built-in-setjmp.c was failing at -O3 because register renaming
adjusted the register used to perform the jump.  Which ran afoul of a
cute trick in builtin_setjmp_receiver that expects r27 to contain the
address of the label we just jumped to.

Solved by properly expressing the constraint in register choices.


r~


        * config/alpha/alpha.md (builtin_longjmp_internal): New.
        (builtin_longjmp): Use it instead of emit_indirect_jump.

Index: alpha.md
===================================================================
RCS file: /cvs/gcc/egcs/gcc/config/alpha/alpha.md,v
retrieving revision 1.135
diff -c -p -d -r1.135 alpha.md
*** alpha.md	2001/01/03 22:52:42	1.135
--- alpha.md	2001/01/24 08:57:46
***************
*** 5913,5919 ****
    "lda %0,%1(%0)")
  
  (define_expand "builtin_longjmp"
!   [(unspec_volatile [(match_operand:DI 0 "register_operand" "r")] 3)]
    "! TARGET_OPEN_VMS && ! TARGET_WINDOWS_NT"
    "
  {
--- 5913,5919 ----
    "lda %0,%1(%0)")
  
  (define_expand "builtin_longjmp"
!   [(use (match_operand:DI 0 "register_operand" "r"))]
    "! TARGET_OPEN_VMS && ! TARGET_WINDOWS_NT"
    "
  {
***************
*** 5933,5941 ****
    /* Load the label we are jumping through into $27 so that we know
       where to look for it when we get back to setjmp's function for
       restoring the gp.  */
!   emit_indirect_jump (pv);
    DONE;
  }")
  
  (define_insn "*builtin_setjmp_receiver_sub_label"
    [(unspec_volatile [(label_ref (match_operand 0 "" ""))] 2)]
--- 5933,5951 ----
    /* Load the label we are jumping through into $27 so that we know
       where to look for it when we get back to setjmp's function for
       restoring the gp.  */
!   emit_jump_insn (gen_builtin_longjmp_internal (pv));
!   emit_barrier ();
    DONE;
  }")
+ 
+ ;; This is effectively a copy of indirect_jump, but constrained such
+ ;; that register renaming cannot foil our cunning plan with $27.
+ (define_insn "builtin_longjmp_internal"
+   [(set (pc)
+ 	(unspec_volatile [(match_operand:DI 0 "register_operand" "c")] 3))]
+   ""
+   "jmp $31,(%0),0"
+   [(set_attr "type" "ibr")])
  
  (define_insn "*builtin_setjmp_receiver_sub_label"
    [(unspec_volatile [(label_ref (match_operand 0 "" ""))] 2)]

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