public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
* Fix x86-64 PIC
@ 2002-10-29 11:23 Jan Hubicka
  2002-10-29 12:39 ` Jakub Jelinek
  0 siblings, 1 reply; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 11:23 UTC (permalink / raw)
  To: gcc-patches, rth


Hi,
I've found that we generate lousy code for x86-64 PIC because we refuse any
symbolic addresses in address operand. 
This patch reorders the checks to be done in proper order (IE do not check
sign_extended_value for values otherwise special cased for PIC)

Bootstrapped x86-64 with -fPIC forced into the bootstrap flags, i386 bootstrap in progress. OK?
Honza
Tue Oct 29 20:19:33 CET 2002  Jan Hubicka  <jh@suse.cz>
	* i386.c (legitimate_address_p): Reorder checks.

Index: i386.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386.c,v
retrieving revision 1.446.2.2
diff -c -3 -p -r1.446.2.2 i386.c
*** i386.c	23 Oct 2002 15:48:29 -0000	1.446.2.2
--- i386.c	29 Oct 2002 19:17:53 -0000
*************** legitimate_address_p (mode, addr, strict
*** 5406,5428 ****
      {
        reason_rtx = disp;
  
-       if (TARGET_64BIT)
- 	{
- 	  if (!x86_64_sign_extended_value (disp))
- 	    {
- 	      reason = "displacement is out of range";
- 	      goto report_error;
- 	    }
- 	}
-       else
- 	{
- 	  if (GET_CODE (disp) == CONST_DOUBLE)
- 	    {
- 	      reason = "displacement is a const_double";
- 	      goto report_error;
- 	    }
- 	}
- 
        if (GET_CODE (disp) == CONST
  	  && GET_CODE (XEXP (disp, 0)) == UNSPEC)
  	switch (XINT (XEXP (disp, 0), 1))
--- 5426,5431 ----
*************** legitimate_address_p (mode, addr, strict
*** 5491,5496 ****
--- 5494,5515 ----
  	  reason = "displacement is not constant";
  	  goto report_error;
  	}
+       else if (TARGET_64BIT)
+ 	{
+ 	  if (!x86_64_sign_extended_value (disp))
+ 	    {
+ 	      reason = "displacement is out of range";
+ 	      goto report_error;
+ 	    }
+ 	}
+       else
+ 	{
+ 	  if (GET_CODE (disp) == CONST_DOUBLE)
+ 	    {
+ 	      reason = "displacement is a const_double";
+ 	      goto report_error;
+ 	    }
+ 	}
      }
  
    /* Everything looks valid.  */

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 11:23 Fix x86-64 PIC Jan Hubicka
@ 2002-10-29 12:39 ` Jakub Jelinek
  2002-10-29 12:41   ` Jan Hubicka
  0 siblings, 1 reply; 10+ messages in thread
From: Jakub Jelinek @ 2002-10-29 12:39 UTC (permalink / raw)
  To: Jan Hubicka; +Cc: gcc-patches, rth

On Tue, Oct 29, 2002 at 08:23:14PM +0100, Jan Hubicka wrote:
> 
> Hi,
> I've found that we generate lousy code for x86-64 PIC because we refuse any
> symbolic addresses in address operand. 
> This patch reorders the checks to be done in proper order (IE do not check
> sign_extended_value for values otherwise special cased for PIC)

Could you please post some testcases of source lousy code?
I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
changes don't catch.
Thanks.

	Jakub

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:39 ` Jakub Jelinek
@ 2002-10-29 12:41   ` Jan Hubicka
  2002-10-29 12:47     ` Jakub Jelinek
  2002-10-29 12:48     ` Jan Hubicka
  0 siblings, 2 replies; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 12:41 UTC (permalink / raw)
  To: Jakub Jelinek; +Cc: Jan Hubicka, gcc-patches, rth

> On Tue, Oct 29, 2002 at 08:23:14PM +0100, Jan Hubicka wrote:
> > 
> > Hi,
> > I've found that we generate lousy code for x86-64 PIC because we refuse any
> > symbolic addresses in address operand. 
> > This patch reorders the checks to be done in proper order (IE do not check
> > sign_extended_value for values otherwise special cased for PIC)
> 
> Could you please post some testcases of source lousy code?
> I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> changes don't catch.

static int t;
q()
{
  t=1;
}
&t is not sign_extended_value, but t(%rip) is valid and recognized by the
pic_operand later.

Honza
> Thanks.
> 
> 	Jakub

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:41   ` Jan Hubicka
@ 2002-10-29 12:47     ` Jakub Jelinek
  2002-10-29 12:48       ` Jan Hubicka
  2002-10-29 12:55       ` Jan Hubicka
  2002-10-29 12:48     ` Jan Hubicka
  1 sibling, 2 replies; 10+ messages in thread
From: Jakub Jelinek @ 2002-10-29 12:47 UTC (permalink / raw)
  To: Jan Hubicka; +Cc: gcc-patches, rth

On Tue, Oct 29, 2002 at 09:41:07PM +0100, Jan Hubicka wrote:
> > Could you please post some testcases of source lousy code?
> > I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> > changes don't catch.
> 
> static int t;
> q()
> {
>   t=1;
> }
> &t is not sign_extended_value, but t(%rip) is valid and recognized by the
> pic_operand later.

With -O2 -fpic I get:
q:
	movl    $1, t(%rip)
        ret
t is a x86_64_sign_extended_value in CM_SMALL_PIC model (since 2002-10-21).

	Jakub

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:47     ` Jakub Jelinek
@ 2002-10-29 12:48       ` Jan Hubicka
  2002-10-29 12:55       ` Jan Hubicka
  1 sibling, 0 replies; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 12:48 UTC (permalink / raw)
  To: Jakub Jelinek; +Cc: Jan Hubicka, gcc-patches, rth

> On Tue, Oct 29, 2002 at 09:41:07PM +0100, Jan Hubicka wrote:
> > > Could you please post some testcases of source lousy code?
> > > I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> > > changes don't catch.
> > 
> > static int t;
> > q()
> > {
> >   t=1;
> > }
> > &t is not sign_extended_value, but t(%rip) is valid and recognized by the
> > pic_operand later.
> 
> With -O2 -fpic I get:
> q:
> 	movl    $1, t(%rip)
>         ret
> t is a x86_64_sign_extended_value in CM_SMALL_PIC model (since 2002-10-21).

That is wrong.

Honza
> 
> 	Jakub

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:41   ` Jan Hubicka
  2002-10-29 12:47     ` Jakub Jelinek
@ 2002-10-29 12:48     ` Jan Hubicka
  2002-10-29 12:55       ` Jakub Jelinek
  1 sibling, 1 reply; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 12:48 UTC (permalink / raw)
  To: Jan Hubicka; +Cc: Jakub Jelinek, gcc-patches, rth

> > On Tue, Oct 29, 2002 at 08:23:14PM +0100, Jan Hubicka wrote:
> > > 
> > > Hi,
> > > I've found that we generate lousy code for x86-64 PIC because we refuse any
> > > symbolic addresses in address operand. 
> > > This patch reorders the checks to be done in proper order (IE do not check
> > > sign_extended_value for values otherwise special cased for PIC)
> > 
> > Could you please post some testcases of source lousy code?
> > I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> > changes don't catch.
> 
> static int t;
> q()
> {
>   t=1;
> }
> &t is not sign_extended_value, but t(%rip) is valid and recognized by the
> pic_operand later.
It also looks like you've added following hunk to sign_extended_value:
        if (GET_CODE (XEXP (value, 0)) == UNSPEC
            && XVECLEN (XEXP (value, 0), 0) == 1
            && XINT (XEXP (value, 0), 1) ==  15)
         return 1;
This is invalid.  We can't accept GOTPCREL references as sign extended
values.  For instance you can use GOTPCREL in construction like

mov $addr%GOTPCREL(%ri), %reg

Sign_extended_value should really return 1 only for cases that can be
encoded in sign extended immediate fields, that are also used in memory
addresses except for RIP relative ones that are special case.
Honza

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:47     ` Jakub Jelinek
  2002-10-29 12:48       ` Jan Hubicka
@ 2002-10-29 12:55       ` Jan Hubicka
  1 sibling, 0 replies; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 12:55 UTC (permalink / raw)
  To: Jakub Jelinek; +Cc: Jan Hubicka, gcc-patches, rth

> On Tue, Oct 29, 2002 at 09:41:07PM +0100, Jan Hubicka wrote:
> > > Could you please post some testcases of source lousy code?
> > > I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> > > changes don't catch.
> > 
> > static int t;
> > q()
> > {
> >   t=1;
> > }
> > &t is not sign_extended_value, but t(%rip) is valid and recognized by the
> > pic_operand later.
> 
> With -O2 -fpic I get:
> q:
> 	movl    $1, t(%rip)
>         ret
> t is a x86_64_sign_extended_value in CM_SMALL_PIC model (since 2002-10-21).
OK,
I now see what you did.  I had old checkout that had this broken.
I don't think it makes sense to add allowrip for
x86_64_sign_extended_value and I think you are wrong to allow it in
x86_64_general_operand and friends since these can not be RIP relative
except for addresses that goes trought valid_address code anyway.  What
did you needed?

Honza

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:48     ` Jan Hubicka
@ 2002-10-29 12:55       ` Jakub Jelinek
  2002-10-29 13:04         ` Jan Hubicka
  2002-10-29 14:46         ` Jan Hubicka
  0 siblings, 2 replies; 10+ messages in thread
From: Jakub Jelinek @ 2002-10-29 12:55 UTC (permalink / raw)
  To: Jan Hubicka; +Cc: gcc-patches, rth

On Tue, Oct 29, 2002 at 09:48:02PM +0100, Jan Hubicka wrote:
> > > Could you please post some testcases of source lousy code?
> > > I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> > > changes don't catch.
> > 
> > static int t;
> > q()
> > {
> >   t=1;
> > }
> > &t is not sign_extended_value, but t(%rip) is valid and recognized by the
> > pic_operand later.
> It also looks like you've added following hunk to sign_extended_value:
>         if (GET_CODE (XEXP (value, 0)) == UNSPEC
>             && XVECLEN (XEXP (value, 0), 0) == 1
>             && XINT (XEXP (value, 0), 1) ==  15)
>          return 1;
> This is invalid.  We can't accept GOTPCREL references as sign extended
> values.  For instance you can use GOTPCREL in construction like
> 
> mov $addr%GOTPCREL(%ri), %reg
> 
> Sign_extended_value should really return 1 only for cases that can be
> encoded in sign extended immediate fields, that are also used in memory
> addresses except for RIP relative ones that are special case.

Symbols binding locally (and label_refs) in CM_SMALL_PIC model never
generate foo@GOTPCREL(%rip), but foo(%rip), and the latter is proper sign
extended value in CM_SMALL_PIC model.
Ie. with static int t; t will be x86_64_sign_extended_value, while
int u; will not.
Please give me a testcase where you think current code does things wrongly.

	Jakub

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:55       ` Jakub Jelinek
@ 2002-10-29 13:04         ` Jan Hubicka
  2002-10-29 14:46         ` Jan Hubicka
  1 sibling, 0 replies; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 13:04 UTC (permalink / raw)
  To: Jakub Jelinek; +Cc: Jan Hubicka, gcc-patches, rth

> On Tue, Oct 29, 2002 at 09:48:02PM +0100, Jan Hubicka wrote:
> > > > Could you please post some testcases of source lousy code?
> > > > I'd like to know what valid 32-bit sign extended values my recent x86_64_sign_extended_value
> > > > changes don't catch.
> > > 
> > > static int t;
> > > q()
> > > {
> > >   t=1;
> > > }
> > > &t is not sign_extended_value, but t(%rip) is valid and recognized by the
> > > pic_operand later.
> > It also looks like you've added following hunk to sign_extended_value:
> >         if (GET_CODE (XEXP (value, 0)) == UNSPEC
> >             && XVECLEN (XEXP (value, 0), 0) == 1
> >             && XINT (XEXP (value, 0), 1) ==  15)
> >          return 1;
> > This is invalid.  We can't accept GOTPCREL references as sign extended
> > values.  For instance you can use GOTPCREL in construction like
> > 
> > mov $addr%GOTPCREL(%ri), %reg
> > 
> > Sign_extended_value should really return 1 only for cases that can be
> > encoded in sign extended immediate fields, that are also used in memory
> > addresses except for RIP relative ones that are special case.
> 
> Symbols binding locally (and label_refs) in CM_SMALL_PIC model never
> generate foo@GOTPCREL(%rip), but foo(%rip), and the latter is proper sign
> extended value in CM_SMALL_PIC model.
> Ie. with static int t; t will be x86_64_sign_extended_value, while
> int u; will not.
> Please give me a testcase where you think current code does things wrongly.
OK, I didn't suceeded to produce wrong code, as the 'i' constraint
makes reload to force operand to go into register, but for instance
testcase:
 static int q,e;
 int *
 main()
 {
    return ((long)&q)-(long)&e;
 }

Produces
(insn 11 10 15 0 (nil) (parallel [
				  (set (reg:DI 59) (minus:DI (reg/f:DI 60)
				  		   (symbol_ref/v:DI ("e"))))
				  (clobber (reg:CC 17 flags)) ]))

That is not valid - you can not have symbol_ref immediate in PIC as
immediates in instructions can not be RIP relative - you always must use
lea for them.

Honza

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Fix x86-64 PIC
  2002-10-29 12:55       ` Jakub Jelinek
  2002-10-29 13:04         ` Jan Hubicka
@ 2002-10-29 14:46         ` Jan Hubicka
  1 sibling, 0 replies; 10+ messages in thread
From: Jan Hubicka @ 2002-10-29 14:46 UTC (permalink / raw)
  To: Jakub Jelinek; +Cc: Jan Hubicka, gcc-patches, rth

Hi,
Here is updated patch that fix somewhat inconsistent situation.
It makes sign_extended_operand, local_symbolic_operand and
legitimate_pic_address_disp_p do what they are supposed to do (and have
in comments) and fixes the rest to deal with these.

Jakub, can you please check wehtehr it does good job for your testcases?

Tue Oct 29 23:41:46 CET 2002  Jan Hubicka  <jh@suse.cz>
	* i386-protos.h (x86_64_sign_extended_value): Fix prototype.
	* i386.c (x86_64_general_operand, x86_64_szext_general_operand,
	x86_64_nonmemory_operand, x86_64_movabs_operand, 
	x86_64_szext_nonmemory_operand, x86_64_immediate_operand,
	ix86_expand_int_movcc): Update call of x86_64_sign_extended_value.
	(local_symbolic_operand): Do not care the 64bit limits.
	(x86_64_sign_extended_value): Remove allow_rip support.
	(legitimate_pic_address_disp_p): Handle all cases allowed
	with RIP addressing.
	(legitimate_address_p): Use legitimate_pic_address_disp_p for PIC.
	(legitimize_pic_address): Reorganize.
	* i386.h (EXTRA_CONSTRAINT): Update call of x86_64_sign_extended_value.
Index: i386-protos.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386-protos.h,v
retrieving revision 1.77.4.5
diff -c -3 -p -r1.77.4.5 i386-protos.h
*** i386-protos.h	29 Oct 2002 19:49:58 -0000	1.77.4.5
--- i386-protos.h	29 Oct 2002 22:40:54 -0000
*************** extern int ix86_attr_length_address_defa
*** 154,160 ****
  
  extern enum machine_mode ix86_fp_compare_mode PARAMS ((enum rtx_code));
  
! extern int x86_64_sign_extended_value PARAMS ((rtx, int));
  extern int x86_64_zero_extended_value PARAMS ((rtx));
  extern rtx ix86_libcall_value PARAMS ((enum machine_mode));
  extern bool ix86_function_value_regno_p PARAMS ((int));
--- 154,160 ----
  
  extern enum machine_mode ix86_fp_compare_mode PARAMS ((enum rtx_code));
  
! extern int x86_64_sign_extended_value PARAMS ((rtx));
  extern int x86_64_zero_extended_value PARAMS ((rtx));
  extern rtx ix86_libcall_value PARAMS ((enum machine_mode));
  extern bool ix86_function_value_regno_p PARAMS ((int));
Index: i386.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386.c,v
retrieving revision 1.447.2.18
diff -c -3 -p -r1.447.2.18 i386.c
*** i386.c	29 Oct 2002 19:49:58 -0000	1.447.2.18
--- i386.c	29 Oct 2002 22:40:57 -0000
*************** x86_64_general_operand (op, mode)
*** 2946,2952 ****
      return general_operand (op, mode);
    if (nonimmediate_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op, 1);
  }
  
  /* Return nonzero if OP is general operand representable on x86_64
--- 2946,2952 ----
      return general_operand (op, mode);
    if (nonimmediate_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op);
  }
  
  /* Return nonzero if OP is general operand representable on x86_64
*************** x86_64_szext_general_operand (op, mode)
*** 2961,2967 ****
      return general_operand (op, mode);
    if (nonimmediate_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op, 1) || x86_64_zero_extended_value (op);
  }
  
  /* Return nonzero if OP is nonmemory operand representable on x86_64.  */
--- 2961,2967 ----
      return general_operand (op, mode);
    if (nonimmediate_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op) || x86_64_zero_extended_value (op);
  }
  
  /* Return nonzero if OP is nonmemory operand representable on x86_64.  */
*************** x86_64_nonmemory_operand (op, mode)
*** 2975,2981 ****
      return nonmemory_operand (op, mode);
    if (register_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op, 1);
  }
  
  /* Return nonzero if OP is nonmemory operand acceptable by movabs patterns.  */
--- 2975,2981 ----
      return nonmemory_operand (op, mode);
    if (register_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op);
  }
  
  /* Return nonzero if OP is nonmemory operand acceptable by movabs patterns.  */
*************** x86_64_movabs_operand (op, mode)
*** 2987,2993 ****
  {
    if (!TARGET_64BIT || !flag_pic)
      return nonmemory_operand (op, mode);
!   if (register_operand (op, mode) || x86_64_sign_extended_value (op, 0))
      return 1;
    if (CONSTANT_P (op) && !symbolic_reference_mentioned_p (op))
      return 1;
--- 2987,2993 ----
  {
    if (!TARGET_64BIT || !flag_pic)
      return nonmemory_operand (op, mode);
!   if (register_operand (op, mode) || x86_64_sign_extended_value (op))
      return 1;
    if (CONSTANT_P (op) && !symbolic_reference_mentioned_p (op))
      return 1;
*************** x86_64_szext_nonmemory_operand (op, mode
*** 3005,3011 ****
      return nonmemory_operand (op, mode);
    if (register_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op, 0) || x86_64_zero_extended_value (op);
  }
  
  /* Return nonzero if OP is immediate operand representable on x86_64.  */
--- 3005,3011 ----
      return nonmemory_operand (op, mode);
    if (register_operand (op, mode))
      return 1;
!   return x86_64_sign_extended_value (op) || x86_64_zero_extended_value (op);
  }
  
  /* Return nonzero if OP is immediate operand representable on x86_64.  */
*************** x86_64_immediate_operand (op, mode)
*** 3017,3023 ****
  {
    if (!TARGET_64BIT)
      return immediate_operand (op, mode);
!   return x86_64_sign_extended_value (op, 0);
  }
  
  /* Return nonzero if OP is immediate operand representable on x86_64.  */
--- 3017,3023 ----
  {
    if (!TARGET_64BIT)
      return immediate_operand (op, mode);
!   return x86_64_sign_extended_value (op);
  }
  
  /* Return nonzero if OP is immediate operand representable on x86_64.  */
*************** local_symbolic_operand (op, mode)
*** 3137,3146 ****
  {
    if (GET_CODE (op) == CONST
        && GET_CODE (XEXP (op, 0)) == PLUS
!       && GET_CODE (XEXP (XEXP (op, 0), 1)) == CONST_INT
!       && (ix86_cmodel != CM_SMALL_PIC
! 	  || (INTVAL (XEXP (XEXP (op, 0), 1)) >= -16*1024*1024
! 	      && INTVAL (XEXP (XEXP (op, 0), 1)) < 16*1024*1024)))
      op = XEXP (XEXP (op, 0), 0);
  
    if (GET_CODE (op) == LABEL_REF)
--- 3137,3143 ----
  {
    if (GET_CODE (op) == CONST
        && GET_CODE (XEXP (op, 0)) == PLUS
!       && GET_CODE (XEXP (XEXP (op, 0), 1)) == CONST_INT)
      op = XEXP (XEXP (op, 0), 0);
  
    if (GET_CODE (op) == LABEL_REF)
*************** ix86_can_use_return_insn_p ()
*** 3942,3950 ****
  \f
  /* Return 1 if VALUE can be stored in the sign extended immediate field.  */
  int
! x86_64_sign_extended_value (value, allow_rip)
       rtx value;
-      int allow_rip;
  {
    switch (GET_CODE (value))
      {
--- 3939,3946 ----
  \f
  /* Return 1 if VALUE can be stored in the sign extended immediate field.  */
  int
! x86_64_sign_extended_value (value)
       rtx value;
  {
    switch (GET_CODE (value))
      {
*************** x86_64_sign_extended_value (value, allow
*** 3966,3982 ****
  	 library.  Don't count TLS SYMBOL_REFs here, since they should fit
  	 only if inside of UNSPEC handled below.  */
        case SYMBOL_REF:
! 	return (ix86_cmodel == CM_SMALL || ix86_cmodel == CM_KERNEL
! 		|| (allow_rip
! 		    && ix86_cmodel == CM_SMALL_PIC
! 		    && (CONSTANT_POOL_ADDRESS_P (value)
! 			|| SYMBOL_REF_FLAG (value))
! 		    && ! tls_symbolic_operand (value, GET_MODE (value))));
  
        /* For certain code models, the code is near as well.  */
        case LABEL_REF:
! 	return ix86_cmodel != CM_LARGE
! 	       && (allow_rip || ix86_cmodel != CM_SMALL_PIC);
  
        /* We also may accept the offsetted memory references in certain special
           cases.  */
--- 3962,3972 ----
  	 library.  Don't count TLS SYMBOL_REFs here, since they should fit
  	 only if inside of UNSPEC handled below.  */
        case SYMBOL_REF:
! 	return (ix86_cmodel == CM_SMALL || ix86_cmodel == CM_KERNEL);
  
        /* For certain code models, the code is near as well.  */
        case LABEL_REF:
! 	return ix86_cmodel != CM_LARGE;
  
        /* We also may accept the offsetted memory references in certain special
           cases.  */
*************** x86_64_sign_extended_value (value, allow
*** 4022,4047 ****
  		      && offset > 0
  		      && trunc_int_for_mode (offset, SImode) == offset)
  		    return 1;
- 		  /* For CM_SMALL_PIC, we can make similar assumptions
- 		     as for CM_SMALL model, if we know the symbol is local
- 		     to the shared library.  Disallow any TLS symbols,
- 		     since they should always be enclosed in an UNSPEC.  */
- 		  if (ix86_cmodel == CM_SMALL_PIC
- 		      && allow_rip
- 		      && (CONSTANT_POOL_ADDRESS_P (op1)
- 			  || SYMBOL_REF_FLAG (op1))
- 		      && ! tls_symbolic_operand (op1, GET_MODE (op1))
- 		      && offset < 16*1024*1024
- 		      && offset >= -16*1024*1024
- 		      && trunc_int_for_mode (offset, SImode) == offset)
- 		    return 1;
  		  break;
  		case LABEL_REF:
  		  /* These conditions are similar to SYMBOL_REF ones, just the
  		     constraints for code models differ.  */
! 		  if ((ix86_cmodel == CM_SMALL || ix86_cmodel == CM_MEDIUM
! 		       || (ix86_cmodel == CM_SMALL_PIC && allow_rip
! 			   && offset >= -16*1024*1024))
  		      && offset < 16*1024*1024
  		      && trunc_int_for_mode (offset, SImode) == offset)
  		    return 1;
--- 4012,4022 ----
  		      && offset > 0
  		      && trunc_int_for_mode (offset, SImode) == offset)
  		    return 1;
  		  break;
  		case LABEL_REF:
  		  /* These conditions are similar to SYMBOL_REF ones, just the
  		     constraints for code models differ.  */
! 		  if ((ix86_cmodel == CM_SMALL || ix86_cmodel == CM_MEDIUM)
  		      && offset < 16*1024*1024
  		      && trunc_int_for_mode (offset, SImode) == offset)
  		    return 1;
*************** legitimate_pic_address_disp_p (disp)
*** 5248,5255 ****
  
    /* In 64bit mode we can allow direct addresses of symbols and labels
       when they are not dynamic symbols.  */
!   if (TARGET_64BIT && local_symbolic_operand (disp, Pmode))
!     return 1;
    if (GET_CODE (disp) != CONST)
      return 0;
    disp = XEXP (disp, 0);
--- 5223,5252 ----
  
    /* In 64bit mode we can allow direct addresses of symbols and labels
       when they are not dynamic symbols.  */
!   if (TARGET_64BIT)
!     {
!       /* TLS references should always be enclosed in UNSPEC.  */
!       if (tls_symbolic_operand (disp, GET_MODE (disp)))
! 	return 0;
!       if (GET_CODE (disp) == SYMBOL_REF
! 	  && ix86_cmodel == CM_SMALL_PIC
! 	  && (CONSTANT_POOL_ADDRESS_P (disp)
! 	      || SYMBOL_REF_FLAG (disp)))
! 	return 1;
!       if (GET_CODE (disp) == LABEL_REF)
! 	return 1;
!       if (GET_CODE (disp) == CONST
! 	  && GET_CODE (XEXP (disp, 0)) == PLUS
! 	  && ((GET_CODE (XEXP (XEXP (disp, 0), 0)) == SYMBOL_REF
! 	       && ix86_cmodel == CM_SMALL_PIC
! 	       && (CONSTANT_POOL_ADDRESS_P (XEXP (XEXP (disp, 0), 0))
! 		   || SYMBOL_REF_FLAG (XEXP (XEXP (disp, 0), 0))))
! 	      || GET_CODE (XEXP (XEXP (disp, 0), 0)) == LABEL_REF)
! 	  && GET_CODE (XEXP (XEXP (disp, 0), 1)) == CONST_INT
! 	  && INTVAL (XEXP (XEXP (disp, 0), 1)) < 16*1024*1024
! 	  && INTVAL (XEXP (XEXP (disp, 0), 1)) >= -16*1024*1024)
! 	return 1;
!     }
    if (GET_CODE (disp) != CONST)
      return 0;
    disp = XEXP (disp, 0);
*************** legitimate_address_p (mode, addr, strict
*** 5456,5478 ****
      {
        reason_rtx = disp;
  
-       if (TARGET_64BIT)
- 	{
- 	  if (!x86_64_sign_extended_value (disp, !(index || base)))
- 	    {
- 	      reason = "displacement is out of range";
- 	      goto report_error;
- 	    }
- 	}
-       else
- 	{
- 	  if (GET_CODE (disp) == CONST_DOUBLE)
- 	    {
- 	      reason = "displacement is a const_double";
- 	      goto report_error;
- 	    }
- 	}
- 
        if (GET_CODE (disp) == CONST
  	  && GET_CODE (XEXP (disp, 0)) == UNSPEC)
  	switch (XINT (XEXP (disp, 0), 1))
--- 5453,5458 ----
*************** legitimate_address_p (mode, addr, strict
*** 5550,5555 ****
--- 5530,5545 ----
  	  reason = "displacement is not constant";
  	  goto report_error;
  	}
+       else if (TARGET_64BIT && !x86_64_sign_extended_value (disp))
+ 	{
+ 	  reason = "displacement is out of range";
+ 	  goto report_error;
+ 	}
+       else if (!TARGET_64BIT && GET_CODE (disp) == CONST_DOUBLE)
+ 	{
+ 	  reason = "displacement is a const_double";
+ 	  goto report_error;
+ 	}
      }
  
    /* Everything looks valid.  */
*************** legitimize_pic_address (orig, reg)
*** 5611,5638 ****
    return machopic_legitimize_pic_address (orig, GET_MODE (orig), reg);
  #endif
  
!   if (local_symbolic_operand (addr, Pmode))
!     {
!       /* In 64bit mode we can address such objects directly.  */
!       if (TARGET_64BIT)
! 	new = addr;
!       else
! 	{
! 	  /* This symbol may be referenced via a displacement from the PIC
! 	     base address (@GOTOFF).  */
! 
! 	  if (reload_in_progress)
! 	    regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
! 	  new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTOFF);
! 	  new = gen_rtx_CONST (Pmode, new);
! 	  new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new);
  
! 	  if (reg != 0)
! 	    {
! 	      emit_move_insn (reg, new);
! 	      new = reg;
! 	    }
!       	}
      }
    else if (GET_CODE (addr) == SYMBOL_REF)
      {
--- 5601,5624 ----
    return machopic_legitimize_pic_address (orig, GET_MODE (orig), reg);
  #endif
  
!   if (TARGET_64BIT && legitimate_pic_address_disp_p (addr))
!     new = addr;
!   else if (!TARGET_64BIT && local_symbolic_operand (addr, Pmode))
!     {
!       /* This symbol may be referenced via a displacement from the PIC
! 	 base address (@GOTOFF).  */
! 
!       if (reload_in_progress)
! 	regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
!       new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTOFF);
!       new = gen_rtx_CONST (Pmode, new);
!       new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new);
  
!       if (reg != 0)
! 	{
! 	  emit_move_insn (reg, new);
! 	  new = reg;
! 	}
      }
    else if (GET_CODE (addr) == SYMBOL_REF)
      {
*************** ix86_expand_vector_move (mode, operands)
*** 7922,7935 ****
    if ((reload_in_progress | reload_completed) == 0
        && register_operand (operands[0], mode)
        && CONSTANT_P (operands[1]))
!     {
!       rtx addr = gen_reg_rtx (Pmode);
!       emit_move_insn (addr, XEXP (force_const_mem (mode, operands[1]), 0));
!       operands[1] = gen_rtx_MEM (mode, addr);
!     }
  
    /* Make operand1 a register if it isn't already.  */
!   if ((reload_in_progress | reload_completed) == 0
        && !register_operand (operands[0], mode)
        && !register_operand (operands[1], mode))
      {
--- 7908,7917 ----
    if ((reload_in_progress | reload_completed) == 0
        && register_operand (operands[0], mode)
        && CONSTANT_P (operands[1]))
!     operands[1] = force_const_mem (mode, operands[1]);
  
    /* Make operand1 a register if it isn't already.  */
!   if (!no_new_pseudos
        && !register_operand (operands[0], mode)
        && !register_operand (operands[1], mode))
      {
*************** ix86_expand_int_movcc (operands)
*** 9322,9328 ****
  
        if ((diff == 1 || diff == 2 || diff == 4 || diff == 8
  	   || diff == 3 || diff == 5 || diff == 9)
! 	  && (mode != DImode || x86_64_sign_extended_value (GEN_INT (cf), 0)))
  	{
  	  /*
  	   * xorl dest,dest
--- 9304,9310 ----
  
        if ((diff == 1 || diff == 2 || diff == 4 || diff == 8
  	   || diff == 3 || diff == 5 || diff == 9)
! 	  && (mode != DImode || x86_64_sign_extended_value (GEN_INT (cf))))
  	{
  	  /*
  	   * xorl dest,dest
Index: i386.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386.h,v
retrieving revision 1.280.4.14
diff -c -3 -p -r1.280.4.14 i386.h
*** i386.h	29 Oct 2002 19:49:59 -0000	1.280.4.14
--- i386.h	29 Oct 2002 22:40:59 -0000
*************** enum reg_class
*** 1435,1441 ****
     constraint, the value returned should be 0 regardless of VALUE.  */
  
  #define EXTRA_CONSTRAINT(VALUE, D)				\
!   ((D) == 'e' ? x86_64_sign_extended_value (VALUE, 0)		\
     : (D) == 'Z' ? x86_64_zero_extended_value (VALUE)		\
     : (D) == 'C' ? standard_sse_constant_p (VALUE)		\
     : 0)
--- 1435,1441 ----
     constraint, the value returned should be 0 regardless of VALUE.  */
  
  #define EXTRA_CONSTRAINT(VALUE, D)				\
!   ((D) == 'e' ? x86_64_sign_extended_value (VALUE)		\
     : (D) == 'Z' ? x86_64_zero_extended_value (VALUE)		\
     : (D) == 'C' ? standard_sse_constant_p (VALUE)		\
     : 0)
*************** do {							\
*** 2558,2564 ****
    case CONST:							\
    case LABEL_REF:						\
    case SYMBOL_REF:						\
!     if (TARGET_64BIT && !x86_64_sign_extended_value (RTX, 0))	\
        return 3;							\
      if (TARGET_64BIT && !x86_64_zero_extended_value (RTX))	\
        return 2;							\
--- 2558,2564 ----
    case CONST:							\
    case LABEL_REF:						\
    case SYMBOL_REF:						\
!     if (TARGET_64BIT && !x86_64_sign_extended_value (RTX))	\
        return 3;							\
      if (TARGET_64BIT && !x86_64_zero_extended_value (RTX))	\
        return 2;							\

^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2002-10-29 22:46 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2002-10-29 11:23 Fix x86-64 PIC Jan Hubicka
2002-10-29 12:39 ` Jakub Jelinek
2002-10-29 12:41   ` Jan Hubicka
2002-10-29 12:47     ` Jakub Jelinek
2002-10-29 12:48       ` Jan Hubicka
2002-10-29 12:55       ` Jan Hubicka
2002-10-29 12:48     ` Jan Hubicka
2002-10-29 12:55       ` Jakub Jelinek
2002-10-29 13:04         ` Jan Hubicka
2002-10-29 14:46         ` Jan Hubicka

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).