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]
Other format: [Raw text]

Re: PR 8878


Hi Mark.

I am committing the patch below to the 3.3 branch.  This fixes 8878.

This patch has been tested on x86-linux.

I am closing the PR.

Aldy

2003-04-01  Aldy Hernandez  <aldyh@redhat.com>
	
	PR/8878
        * expr.c (expand_expr): Handle VECTOR_CST.
        (const_vector_from_tree): New.
	
        * varasm.c (output_constant): Handle VECTOR_CST.
	
        * c-typeck.c (digest_init): Build a vector constant from a
        VECTOR_TYPE.

	
Index: expr.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.c,v
retrieving revision 1.498.2.19
diff -c -p -r1.498.2.19 expr.c
*** expr.c	13 Jul 2003 21:37:40 -0000	1.498.2.19
--- expr.c	24 Jul 2003 19:07:21 -0000
*************** static rtx clear_storage_via_libcall PAR
*** 153,159 ****
  static tree clear_storage_libcall_fn PARAMS ((int));
  static rtx compress_float_constant PARAMS ((rtx, rtx));
  static rtx get_subtarget	PARAMS ((rtx));
! static int is_zeros_p		PARAMS ((tree));
  static int mostly_zeros_p	PARAMS ((tree));
  static void store_constructor_field PARAMS ((rtx, unsigned HOST_WIDE_INT,
  					     HOST_WIDE_INT, enum machine_mode,
--- 153,159 ----
  static tree clear_storage_libcall_fn PARAMS ((int));
  static rtx compress_float_constant PARAMS ((rtx, rtx));
  static rtx get_subtarget	PARAMS ((rtx));
! static int is_zeros_p         PARAMS ((tree));
  static int mostly_zeros_p	PARAMS ((tree));
  static void store_constructor_field PARAMS ((rtx, unsigned HOST_WIDE_INT,
  					     HOST_WIDE_INT, enum machine_mode,
*************** static rtx do_store_flag	PARAMS ((tree, 
*** 177,182 ****
--- 177,183 ----
  static void emit_single_push_insn PARAMS ((enum machine_mode, rtx, tree));
  #endif
  static void do_tablejump PARAMS ((rtx, enum machine_mode, rtx, rtx, rtx));
+ static rtx const_vector_from_tree PARAMS ((tree));
  
  /* Record for each mode whether we can move a register directly to or
     from an object of that mode in memory.  If we can't, we won't try
*************** expand_expr (exp, target, tmode, modifie
*** 6793,6798 ****
--- 6794,6802 ----
  
        return temp;
  
+     case VECTOR_CST:
+       return const_vector_from_tree (exp);
+ 
      case CONST_DECL:
        return expand_expr (DECL_INITIAL (exp), target, VOIDmode, modifier);
  
*************** vector_mode_valid_p (mode)
*** 11241,11246 ****
--- 11245,11287 ----
    /* If we have support for the inner mode, we can safely emulate it.
       We may not have V2DI, but me can emulate with a pair of DIs.  */
    return mov_optab->handlers[innermode].insn_code != CODE_FOR_nothing;
+ }
+ 
+ /* Return a CONST_VECTOR rtx for a VECTOR_CST tree.  */
+ static rtx
+ const_vector_from_tree (exp)
+      tree exp;
+ {
+   rtvec v;
+   int units, i;
+   tree link, elt;
+   enum machine_mode inner, mode;
+ 
+   mode = TYPE_MODE (TREE_TYPE (exp));
+ 
+   if (is_zeros_p (exp))
+     return CONST0_RTX (mode);
+ 
+   units = GET_MODE_NUNITS (mode);
+   inner = GET_MODE_INNER (mode);
+ 
+   v = rtvec_alloc (units);
+ 
+   link = TREE_VECTOR_CST_ELTS (exp);
+   for (i = 0; link; link = TREE_CHAIN (link), ++i)
+     {
+       elt = TREE_VALUE (link);
+ 
+       if (TREE_CODE (elt) == REAL_CST)
+ 	RTVEC_ELT (v, i) = CONST_DOUBLE_FROM_REAL_VALUE (TREE_REAL_CST (elt),
+ 							 inner);
+       else
+ 	RTVEC_ELT (v, i) = immed_double_const (TREE_INT_CST_LOW (elt),
+ 					       TREE_INT_CST_HIGH (elt),
+ 					       inner);
+     }
+ 
+   return gen_rtx_raw_CONST_VECTOR (mode, v);
  }
  
  #include "gt-expr.h"
Index: varasm.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/varasm.c,v
retrieving revision 1.324.2.4
diff -c -p -r1.324.2.4 varasm.c
*** varasm.c	29 Apr 2003 12:16:41 -0000	1.324.2.4
--- varasm.c	24 Jul 2003 19:07:24 -0000
*************** output_constant (exp, size, align)
*** 4050,4055 ****
--- 4050,4072 ----
  	  thissize = MIN (TREE_STRING_LENGTH (exp), size);
  	  assemble_string (TREE_STRING_POINTER (exp), thissize);
  	}
+       else if (TREE_CODE (exp) == VECTOR_CST)
+ 	{
+ 	  int elt_size;
+ 	  tree link;
+ 	  unsigned int nalign;
+ 	  enum machine_mode inner;
+ 
+ 	  inner = GET_MODE_INNER (TYPE_MODE (TREE_TYPE (exp)));
+ 	  nalign = MIN (align, GET_MODE_ALIGNMENT (inner));
+ 
+ 	  elt_size = GET_MODE_UNIT_SIZE (TYPE_MODE (TREE_TYPE (exp)));
+ 
+ 	  link = TREE_VECTOR_CST_ELTS (exp);
+ 	  output_constant (TREE_VALUE (link), elt_size, align);
+ 	  while ((link = TREE_CHAIN (link)) != NULL)
+ 	    output_constant (TREE_VALUE (link), elt_size, nalign);
+ 	}
        else
  	abort ();
        break;
Index: c-typeck.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/c-typeck.c,v
retrieving revision 1.213.2.6
diff -c -p -r1.213.2.6 c-typeck.c
*** c-typeck.c	18 Apr 2003 06:50:45 -0000	1.213.2.6
--- c-typeck.c	24 Jul 2003 19:07:28 -0000
*************** digest_init (type, init, require_constan
*** 4759,4764 ****
--- 4759,4772 ----
  	  return inside_init;
  	}
      }
+   /* Build a VECTOR_CST from a *constant* vector constructor.  If the
+      vector constructor is not constant (e.g. {1,2,3,foo()}) then punt
+      below and handle as a constructor.  */
+   if (code == VECTOR_TYPE
+       && comptypes (TREE_TYPE (inside_init), type)
+       && TREE_CONSTANT (inside_init))
+     return build_vector (type, TREE_OPERAND (inside_init, 1));
+ 
  
    /* Any type can be initialized
       from an expression of the same type, optionally with braces.  */


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