x86-64 medium model fix

Jan Hubicka jh@suse.cz
Mon Aug 1 09:57:00 GMT 2005


Hi,
currently addresses of far static symbols will be output using:
   leaq   symbol@GOTOFF, %reg
this is wrong, since we really want 64bit GOT relocation here, so it should be
movabs.  This patch fixes it by adding new predicates and getting right
attribute on mov pattern.  It also includes GOT that we will end up using
relatively soon for large model in similar fashion.  I also noticed that
symbol@GOTOFF is accepted as valid address operand that is not quite right
either.

Bootstrapped/regtested x86_64-linux, OK?

Honza

2005-08-01  Jan Hubicka  <jh@suse.cz>
	* i386.c (legitimate_pic_address_disp_p): GOTOFF is not valid address
	in MEDIUM pic because it is 64bit.
	* (legitimate_address_p): Likewise.
	* i386.md (movdi*): Choose imov instead of lea for 64bit PIC operands.
	* predicates.md (pic_64bit_operand): New predicate.
Index: config/i386/i386.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386.c,v
retrieving revision 1.846
diff -c -3 -p -r1.846 i386.c
*** config/i386/i386.c	31 Jul 2005 09:12:28 -0000	1.846
--- config/i386/i386.c	31 Jul 2005 19:33:41 -0000
*************** legitimate_pic_address_disp_p (rtx disp)
*** 5535,5542 ****
  	return false;
        return GET_CODE (XVECEXP (disp, 0, 0)) == SYMBOL_REF;
      case UNSPEC_GOTOFF:
!       if (GET_CODE (XVECEXP (disp, 0, 0)) == SYMBOL_REF
! 	  || GET_CODE (XVECEXP (disp, 0, 0)) == LABEL_REF)
          return local_symbolic_operand (XVECEXP (disp, 0, 0), Pmode);
        return false;
      case UNSPEC_GOTTPOFF:
--- 5553,5561 ----
  	return false;
        return GET_CODE (XVECEXP (disp, 0, 0)) == SYMBOL_REF;
      case UNSPEC_GOTOFF:
!       if ((GET_CODE (XVECEXP (disp, 0, 0)) == SYMBOL_REF
! 	   || GET_CODE (XVECEXP (disp, 0, 0)) == LABEL_REF)
! 	  && !TARGET_64BIT)
          return local_symbolic_operand (XVECEXP (disp, 0, 0), Pmode);
        return false;
      case UNSPEC_GOTTPOFF:
*************** legitimate_address_p (enum machine_mode 
*** 5692,5697 ****
--- 5711,5722 ----
  	  {
  	  case UNSPEC_GOT:
  	  case UNSPEC_GOTOFF:
+ 	    gcc_assert (flag_pic);
+ 	    if (!TARGET_64BIT)
+ 	      goto is_legitimate_pic;
+ 	    reason = "64bit address unspec";
+ 	    goto report_error;
+  
  	  case UNSPEC_GOTPCREL:
  	    gcc_assert (flag_pic);
  	    goto is_legitimate_pic;
Index: config/i386/i386.md
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386.md,v
retrieving revision 1.651
diff -c -3 -p -r1.651 i386.md
*** config/i386/i386.md	31 Jul 2005 09:12:30 -0000	1.651
--- config/i386/i386.md	31 Jul 2005 19:33:45 -0000
***************
*** 1200,1207 ****
  	      (const_string "sselog1")
  	    (eq_attr "alternative" "7,8,9,10,11")
  	      (const_string "ssemov")
! 	    (and (ne (symbol_ref "flag_pic") (const_int 0))
! 		 (match_operand:SI 1 "symbolic_operand" ""))
  	      (const_string "lea")
  	   ]
  	   (const_string "imov")))
--- 1202,1210 ----
  	      (const_string "sselog1")
  	    (eq_attr "alternative" "7,8,9,10,11")
  	      (const_string "ssemov")
!  	    (and (ne (symbol_ref "flag_pic") (const_int 0))
! 		 (and (not (match_operand:DI 1 "pic_64bit_operand" ""))
! 		      (match_operand:DI 1 "symbolic_operand" "")))
  	      (const_string "lea")
  	   ]
  	   (const_string "imov")))
***************
*** 2020,2026 ****
  	    (eq_attr "alternative" "4")
  	      (const_string "multi")
   	    (and (ne (symbol_ref "flag_pic") (const_int 0))
! 		 (match_operand:DI 1 "symbolic_operand" ""))
  	      (const_string "lea")
  	   ]
  	   (const_string "imov")))
--- 2023,2030 ----
  	    (eq_attr "alternative" "4")
  	      (const_string "multi")
   	    (and (ne (symbol_ref "flag_pic") (const_int 0))
! 		 (and (not (match_operand:DI 1 "pic_64bit_operand" ""))
! 		      (match_operand:DI 1 "symbolic_operand" "")))
  	      (const_string "lea")
  	   ]
  	   (const_string "imov")))
Index: config/i386/predicates.md
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/predicates.md,v
retrieving revision 1.20
diff -c -3 -p -r1.20 predicates.md
*** config/i386/predicates.md	31 Jul 2005 09:12:33 -0000	1.20
--- config/i386/predicates.md	31 Jul 2005 19:33:46 -0000
***************
*** 318,323 ****
--- 318,340 ----
  	      (match_operand 0 "x86_64_zext_immediate_operand")))
      (match_operand 0 "nonmemory_operand")))
  
+ ;; Return true when operand is UNSPEC translating into 64bit relocation.
+ (define_predicate "pic_64bit_operand"
+   (match_code "const")
+ {
+   if (!TARGET_64BIT)
+     return 0;
+   op = XEXP (op, 0);
+   if (GET_CODE (op) == PLUS && GET_CODE (XEXP (op, 1)) == CONST_INT)
+     op = XEXP (op, 0);
+   if (GET_CODE (op) == UNSPEC
+       && (XINT (op, 1) == UNSPEC_GOTOFF
+ 	  || XINT (op, 1) == UNSPEC_GOT))
+     return 1;
+   return 0;
+ })
+ 
+ 
  ;; Return nonzero if OP is nonmemory operand acceptable by movabs patterns.
  (define_predicate "x86_64_movabs_operand"
    (if_then_else (match_test "!TARGET_64BIT || !flag_pic")



More information about the Gcc-patches mailing list