OSDN Git Service

IA64 uses // instead of # for comments in its assembly file.
[pf3gnuchains/gcc-fork.git] / gcc / graphite-clast-to-gimple.c
index 106ff7c..b6b8d31 100644 (file)
@@ -149,7 +149,7 @@ debug_clast_name_indexes_1 (void **slot, void *s ATTRIBUTE_UNUSED)
 
 /* Print to stderr all the elements of MAP.  */
 
-void
+DEBUG_FUNCTION void
 debug_clast_name_indexes (htab_t map)
 {
   htab_traverse (map, debug_clast_name_indexes_1, NULL);
@@ -231,8 +231,15 @@ max_signed_precision_type (tree type1, tree type2)
 {
   int p1 = TYPE_PRECISION (type1);
   int p2 = TYPE_PRECISION (type2);
-  int precision = p1 > p2 ? p1 : p2;
-  tree type = lang_hooks.types.type_for_size (precision, false);
+  int precision;
+  tree type;
+
+  if (p1 > p2)
+    precision = TYPE_UNSIGNED (type1) ? p1 * 2 : p1;
+  else
+    precision = TYPE_UNSIGNED (type2) ? p2 * 2 : p2;
+
+  type = lang_hooks.types.type_for_size (precision, false);
 
   if (!type)
     {
@@ -247,7 +254,6 @@ max_signed_precision_type (tree type1, tree type2)
 static tree
 max_precision_type (tree type1, tree type2)
 {
-
   if (POINTER_TYPE_P (type1))
     return type1;
 
@@ -305,7 +311,7 @@ clast_to_gcc_expression (tree type, struct clast_expr *e,
 
        if (t->var)
          {
-           if (value_one_p (t->val))
+           if (mpz_cmp_si (t->val, 1) == 0)
              {
                tree name = clast_name_to_gcc (t->var, region, newivs,
                                               newivs_index, params_index);
@@ -317,7 +323,7 @@ clast_to_gcc_expression (tree type, struct clast_expr *e,
                return name;
              }
 
-           else if (value_mone_p (t->val))
+           else if (mpz_cmp_si (t->val, -1) == 0)
              {
                tree name = clast_name_to_gcc (t->var, region, newivs,
                                               newivs_index, params_index);
@@ -415,9 +421,9 @@ clast_to_gcc_expression (tree type, struct clast_expr *e,
 /* Return the precision needed to represent the value VAL.  */
 
 static int
-precision_for_value (Value val)
+precision_for_value (mpz_t val)
 {
-  Value x, y, two;
+  mpz_t x, y, two;
   int precision;
 
   value_init (x);
@@ -448,9 +454,9 @@ precision_for_value (Value val)
    UP.  */
 
 static int
-precision_for_interval (Value low, Value up)
+precision_for_interval (mpz_t low, mpz_t up)
 {
-  Value diff;
+  mpz_t diff;
   int precision;
 
   gcc_assert (value_le (low, up));
@@ -463,28 +469,35 @@ precision_for_interval (Value low, Value up)
   return precision;
 }
 
-/* Return a type that could represent the integer value VAL, or
-   otherwise return NULL_TREE.  */
+/* Return a type that could represent the integer value VAL.  */
 
 static tree
-gcc_type_for_interval (Value low, Value up, tree old_type)
+gcc_type_for_interval (mpz_t low, mpz_t up)
 {
   bool unsigned_p = true;
   int precision, prec_up, prec_int;
   tree type;
+  enum machine_mode mode;
 
   gcc_assert (value_le (low, up));
 
-  /* Preserve the signedness of the old IV.  */
-  if ((old_type && !TYPE_UNSIGNED (old_type))
-      || value_neg_p (low))
+  if (value_neg_p (low))
     unsigned_p = false;
 
   prec_up = precision_for_value (up);
   prec_int = precision_for_interval (low, up);
-  precision = prec_up > prec_int ? prec_up : prec_int;
+  precision = MAX (prec_up, prec_int);
+
+  if (precision > BITS_PER_WORD)
+    {
+      gloog_error = true;
+      return integer_type_node;
+    }
+
+  mode = smallest_mode_for_size (precision, MODE_INT);
+  precision = GET_MODE_PRECISION (mode);
+  type = build_nonstandard_integer_type (precision, unsigned_p);
 
-  type = lang_hooks.types.type_for_size (precision, unsigned_p);
   if (!type)
     {
       gloog_error = true;
@@ -498,9 +511,9 @@ gcc_type_for_interval (Value low, Value up, tree old_type)
    otherwise return NULL_TREE.  */
 
 static tree
-gcc_type_for_value (Value val)
+gcc_type_for_value (mpz_t val)
 {
-  return gcc_type_for_interval (val, val, NULL_TREE);
+  return gcc_type_for_interval (val, val);
 }
 
 /* Return the type for the clast_term T used in STMT.  */
@@ -688,7 +701,7 @@ graphite_create_new_guard (sese region, edge entry_edge,
    the iteration domain, and G the context parameters.  */
 
 static void
-compute_bounds_for_level (poly_bb_p pbb, int level, Value low, Value up)
+compute_bounds_for_level (poly_bb_p pbb, int level, mpz_t low, mpz_t up)
 {
   ppl_Pointset_Powerset_C_Polyhedron_t ps;
   ppl_Linear_Expression_t le;
@@ -710,52 +723,25 @@ compute_bounds_for_level (poly_bb_p pbb, int level, Value low, Value up)
 }
 
 /* Compute the type for the induction variable at LEVEL for the
-   statement PBB, based on the transformed schedule of PBB.  OLD_TYPE
-   is the type of the old induction variable for that loop.  */
+   statement PBB, based on the transformed schedule of PBB.  */
 
 static tree
-compute_type_for_level_1 (poly_bb_p pbb, int level, tree old_type)
+compute_type_for_level (poly_bb_p pbb, int level)
 {
-  Value low, up;
+  mpz_t low, up;
   tree type;
 
   value_init (low);
   value_init (up);
 
   compute_bounds_for_level (pbb, level, low, up);
-  type = gcc_type_for_interval (low, up, old_type);
+  type = gcc_type_for_interval (low, up);
 
   value_clear (low);
   value_clear (up);
   return type;
 }
 
-/* Compute the type for the induction variable at LEVEL for the
-   statement PBB, based on the transformed schedule of PBB.  */
-
-static tree
-compute_type_for_level (poly_bb_p pbb, int level)
-{
-  tree oldiv = pbb_to_depth_to_oldiv (pbb, level);
-  tree type = TREE_TYPE (oldiv);
-
-  if (type && POINTER_TYPE_P (type))
-    {
-#ifdef ENABLE_CHECKING
-      tree ctype = compute_type_for_level_1 (pbb, level, type);
-
-      /* In the case of a pointer type, check that after the loop
-        transform, the lower and the upper bounds of the type fit the
-        oldiv pointer type.  */
-      gcc_assert (TYPE_PRECISION (type) >= TYPE_PRECISION (ctype)
-                 && integer_zerop (lower_bound_in_type (ctype, ctype)));
-#endif
-      return type;
-    }
-
-  return compute_type_for_level_1 (pbb, level, type);
-}
-
 /* Walks a CLAST and returns the first statement in the body of a
    loop.  */
 
@@ -790,9 +776,9 @@ gcc_type_for_iv_of_clast_loop (struct clast_for *stmt_for, int level,
   CloogStatement *cs = body->statement;
   poly_bb_p pbb = (poly_bb_p) cloog_statement_usr (cs);
 
-  return max_precision_type (lb_type, max_precision_type
-                            (ub_type, compute_type_for_level (pbb,
-                                                              level - 1)));
+  return max_signed_precision_type (lb_type, max_precision_type
+                                   (ub_type, compute_type_for_level
+                                    (pbb, level - 1)));
 }
 
 /* Creates a new LOOP corresponding to Cloog's STMT.  Inserts an
@@ -1005,6 +991,7 @@ translate_clast_user (sese region, struct clast_user_stmt *stmt, edge next_e,
 
 /* Creates a new if region protecting the loop to be executed, if the execution
    count is zero (lb > ub).  */
+
 static edge
 graphite_create_new_loop_guard (sese region, edge entry_edge,
                                struct clast_for *stmt,
@@ -1022,22 +1009,20 @@ graphite_create_new_loop_guard (sese region, edge entry_edge,
                                     newivs_index, params_index);
   tree ub = clast_to_gcc_expression (type, stmt->UB, region, newivs,
                                     newivs_index, params_index);
-
-  /* XXX: Adding +1 and using LT_EXPR helps with loop latches that have a
+  tree one = POINTER_TYPE_P (type) ? size_one_node
+    : fold_convert (type, integer_one_node);
+  /* Adding +1 and using LT_EXPR helps with loop latches that have a
      loop iteration count of "PARAMETER - 1".  For PARAMETER == 0 this becomes
      2^{32|64}, and the condition lb <= ub is true, even if we do not want this.
-     However lb < ub + 1 is false, as expected.
-     There might be a problem with cases where ub is 2^32.  */
-  tree one;
-  Value gmp_one;
-  value_init (gmp_one);
-  value_set_si (gmp_one, 1);
-  one = gmp_cst_to_tree (type, gmp_one);
-  value_clear (gmp_one);
-
-  ub = fold_build2 (POINTER_TYPE_P (type) ? POINTER_PLUS_EXPR : PLUS_EXPR,
-                   type, ub, one);
-  cond_expr = fold_build2 (LT_EXPR, boolean_type_node, lb, ub);
+     However lb < ub + 1 is false, as expected.  */
+  tree ub_one = fold_build2 (POINTER_TYPE_P (type) ? POINTER_PLUS_EXPR
+                            : PLUS_EXPR, type, ub, one);
+
+  /* When ub + 1 wraps around, use lb <= ub.  */
+  if (integer_zerop (ub_one))
+    cond_expr = fold_build2 (LE_EXPR, boolean_type_node, lb, ub);
+  else
+    cond_expr = fold_build2 (LT_EXPR, boolean_type_node, lb, ub_one);
 
   exit_edge = create_empty_if_region_on_edge (entry_edge, cond_expr);
 
@@ -1469,7 +1454,7 @@ print_clast_stmt (FILE *file, struct clast_stmt *stmt)
 
 /* Prints STMT to STDERR.  */
 
-void
+DEBUG_FUNCTION void
 debug_clast_stmt (struct clast_stmt *stmt)
 {
   print_clast_stmt (stderr, stmt);
@@ -1518,7 +1503,7 @@ print_generated_program (FILE *file, scop_p scop)
 
 /* Prints to STDERR the code generated by CLooG for SCOP.  */
 
-void
+DEBUG_FUNCTION void
 debug_generated_program (scop_p scop)
 {
   print_generated_program (stderr, scop);