ia64.c (got_symbolic_operand): Do require a symbol+offset operand to have its offset...
authorZack Weinberg <zack@gcc.gnu.org>
Mon, 2 Aug 2004 03:23:01 +0000 (03:23 +0000)
committerZack Weinberg <zack@gcc.gnu.org>
Mon, 2 Aug 2004 03:23:01 +0000 (03:23 +0000)
* config/ia64/ia64.c (got_symbolic_operand): Do require a
symbol+offset operand to have its offset be zero mod 0x3fff
when GOT entries are in use.  Clarify logic in SYMBOL_REF
case.  Clarify comments.
(ia64_expand_load_address): Split a symbol+offset load when
the offset is nonzero mod 0x3fff, not 0x1fff.
testsuite:
* gcc.dg/ia64-got-1.c: New test case.

From-SVN: r85426

gcc/ChangeLog
gcc/config/ia64/ia64.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/ia64-got-1.c [new file with mode: 0644]

index f604e8dc4bb3b72cd217e5ca29e21ffc0c8127dc..31af54e5adcd86c03fdabfe98764331fe330a5d1 100644 (file)
@@ -1,3 +1,12 @@
+2004-08-01  Zack Weinberg  <zack@codesourcery.com>
+
+       * config/ia64/ia64.c (got_symbolic_operand): Do require a
+       symbol+offset operand to have its offset be zero mod 0x3fff
+       when GOT entries are in use.  Clarify logic in SYMBOL_REF
+       case.  Clarify comments.
+       (ia64_expand_load_address): Split a symbol+offset load when
+       the offset is nonzero mod 0x3fff, not 0x1fff.
+
 2004-08-01  Geoffrey Keating  <geoffk@apple.com>
 
        * config/rs6000/rs6000.c (rs6000_split_multireg_move): Just abort
index 1053447b49968c1957cfb467bb9edb314ef9ef27..66e51ea80813cffc5b6c5386edcaef2cc8294c7b 100644 (file)
@@ -471,6 +471,7 @@ got_symbolic_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
   switch (GET_CODE (op))
     {
     case CONST:
+      /* Accept only (plus (symbol_ref) (const_int)).  */
       op = XEXP (op, 0);
       if (GET_CODE (op) != PLUS)
        return 0;
@@ -479,11 +480,20 @@ got_symbolic_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
       op = XEXP (op, 1);
       if (GET_CODE (op) != CONST_INT)
        return 0;
+
+     /* Ok if we're not using GOT entries at all.  */
+     if (TARGET_NO_PIC || TARGET_AUTO_PIC)
       return 1;
+      
+     /* The low 14 bits of the constant have been forced to zero
+       by ia64_expand_load_address, so that we do not use up so
+       many GOT entries.  Prevent cse from undoing this.  */
+     return (INTVAL (op) & 0x3fff) == 0;
 
     case SYMBOL_REF:
-      if (SYMBOL_REF_SMALL_ADDR_P (op))
-       return 0;
+      /* This sort of load should not be used for things in sdata.  */
+      return !SYMBOL_REF_SMALL_ADDR_P (op);
+
     case LABEL_REF:
       return 1;
 
@@ -1125,7 +1135,7 @@ ia64_expand_load_address (rtx dest, rtx src)
   if (GET_CODE (src) == CONST
       && GET_CODE (XEXP (src, 0)) == PLUS
       && GET_CODE (XEXP (XEXP (src, 0), 1)) == CONST_INT
-      && (INTVAL (XEXP (XEXP (src, 0), 1)) & 0x1fff) != 0)
+      && (INTVAL (XEXP (XEXP (src, 0), 1)) & 0x3fff) != 0)
     {
       rtx sym = XEXP (XEXP (src, 0), 0);
       HOST_WIDE_INT ofs, hi, lo;
index 6d579426bd514c30f19a0c5d22b99604fcf1203e..433700b936e93cb6551999de6173c9fe2913b60a 100644 (file)
@@ -1,12 +1,16 @@
+2004-08-01  Zack Weinberg  <zack@codesourcery.com>
+
+       * gcc.dg/ia64-got-1.c: New test case.
+
 2004-08-01  Mark Mitchell  <mark@codesourcery.com>
 
        PR c++/16489
        * g++.dg/init/null1.C: New test.
        * g++.dg/tc1/dr76.C: Adjust error marker.
-       
+
        PR c++/16529
        * g++.dg/parse/namespace10.C: New test.
-       
+
        PR c++/16810
        * g++.dg/inherit/ptrmem2.C: New test.
 
@@ -31,8 +35,8 @@
 
 2004-07-30  Richard Henderson  <rth@redhat.com>
 
-        * gfortran.fortran-torture/execute/intrinsic_nearest.f90: Disable
-        tests of nearest around zero.
+       * gfortran.fortran-torture/execute/intrinsic_nearest.f90: Disable
+       tests of nearest around zero.
 
 2004-07-30  Andrew Pinski  <apinski@apple.com>
 
@@ -86,7 +90,7 @@
 
        * gcc.dg/darwin-bool-1.c: New test.
        * gcc.dg/darwin-bool-2.c: New test.
-       
+
 2004-07-28  Richard Henderson  <rth@redhat.com>
 
        * gfortran.fortran-torture/execute/intrinsic_spacing.f90: Pass
diff --git a/gcc/testsuite/gcc.dg/ia64-got-1.c b/gcc/testsuite/gcc.dg/ia64-got-1.c
new file mode 100644 (file)
index 0000000..d53560f
--- /dev/null
@@ -0,0 +1,23 @@
+/* { dg-do compile { target ia64*-*-* } } */
+/* { dg-options "-O2 -fPIC" } */
+
+/* { dg-final { scan-assembler "@ltoffx\\(object#\\)" } } */
+/* { dg-final { scan-assembler "@ltoffx\\(object#\[-+\]16384\\)" } } */
+/* { dg-final { scan-assembler-not "@ltoffx\\(object#\[-+\]1\\)" } } */
+/* { dg-final { scan-assembler-not "@ltoffx\\(object#\[-+\]8191\\)" } } */
+/* { dg-final { scan-assembler-not "@ltoffx\\(object#\[-+\]8192\\)" } } */
+/* { dg-final { scan-assembler-not "@ltoffx\\(object#\[-+\]8193\\)" } } */
+/* { dg-final { scan-assembler-not "@ltoffx\\(object#\[-+\]16383\\)" } } */
+/* { dg-final { scan-assembler-not "@ltoffx\\(object#\[-+\]16385\\)" } } */
+
+/* must not be in sdata */
+extern char object[];
+
+#define r(n) char *r_##n (void) { return &object[n]; }
+#define R(n) char *R_##n (void) { return &object[-n]; }
+
+#define t(n) r(n) R(n)
+
+t(0) t(1)
+t(8191) t(8192) t(8193)
+t(16383) t(16384) t(16385)