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]

[yara-branch] patch for bug fixes, speedup, code improvement


This patch
o fixes bugs in YARA when frame pointer is omitted
o fixes bugs in cover class set calculation when tunning other
  than for pentium4 is used
o improve generated code for crafty (other changes in SPEC
  are insignifciant) by taking allocno sizes into account.
o speeds YARA up for SPECFp lucas (about 20%) by speeding coloring

2006-03-29 Vladimir Makarov <vmakarov@redhat.com>

	* yara-int.h (stack_memory_start_frame_offset): Rename to
	get_stack_memory_start_frame_offset.
	(rounded_slot_memory_size): New prototype.
	(set_non_alloc_regs): New prototype.
	* yara-color.c (setup_reg_subclasses): Don't take fixed registers
	into account.
	(min_reg_class_cover_size, min_reg_class_cover): Rename them to
	final_reg_class_cover_size, final_reg_class_cover.
	(extend_reg_class_cover, set_up_class_translate,
	print_class_cover, find_reg_class_closure): Use the new names.
	(colorable_can_bucket): New variable.
	(add_can_to_bucket, delete_can_from_bucket): Change signature.
	(curr_global_can_cover_class): Remove.
	(global_can_compare): Don't check cover class.  Take allocno sizes
	into account.
	(push_globals_to_stack): Form and use can arrays according to
	their cover classes.
	(global_can_alloc): Initialize colorable_can_bucket.
	* yara-final.c (final_stack_memory_start_frame_offset,
	final_rounded_slot_memory_size): New variables.
	(get_allocno_memory_slot_rtx): Fix bug in calculating displacement
	relative to stack pointer.
	(emit_copy, modify_insn): Don't change offset for elimination to
	set pointer.
	(align_or_allocate_stack_memory): Rename to
	allocate_stack_memory.  Setup
	final_stack_memory_start_frame_offset and
	final_allocate_stack_memory.
	(yara_rewrite): Use the renamed function once.
	* yara.c (set_non_alloc_regs): Make it external, add
	parameter, and call set_up_class_hard_regs and
	set_up_available_class_regs.
	(yara_init_once): Remove calls of set_up_class_hard_regs and
	set_up_available_class_regs.
	* yara-trans.c (get_temp_stack_memory_slot_rtx): Add a
	parameter.  Fix the displacement calculation.
	(rounded_slot_memory_size): New function.
	(stack_memory_start_frame_offset): Rename to
	get_stack_memory_start_frame_offset.
	(assign_copy_secondary): Add parameter to
	get_temp_stack_memory_slot_rtx call.
	* yara-ir.c (modify_offsets_and_frame_pointer_needed): Modify
	no_alloc_regs if necessary.
	

Index: yara-int.h
===================================================================
--- yara-int.h	(revision 112301)
+++ yara-int.h	(working copy)
@@ -911,7 +911,8 @@ extern void yara_trans_init (void);
 extern void yara_trans_finish (void);
 
 /* yara-trans.c: */
-extern HOST_WIDE_INT stack_memory_start_frame_offset (void);
+extern HOST_WIDE_INT rounded_slot_memory_size (void);
+extern HOST_WIDE_INT get_stack_memory_start_frame_offset (void);
 extern void print_memory_slot (FILE *, const char *, int,
 			       struct memory_slot *);
 extern int get_paradoxical_subreg_memory_offset (int, enum machine_mode);
@@ -998,6 +999,7 @@ extern short class_hard_reg_index [N_REG
 extern HARD_REG_SET no_alloc_regs;
 extern int available_class_regs [N_REG_CLASSES];
 
+extern void set_non_alloc_regs (bool);
 extern void *yara_allocate (size_t);
 extern void yara_free (void *addr);
 extern bitmap yara_allocate_bitmap (void);
Index: yara-color.c
===================================================================
--- yara-color.c	(revision 112301)
+++ yara-color.c	(working copy)
@@ -84,15 +84,12 @@ setup_reg_subclasses (void)
 	continue;
 
       COPY_HARD_REG_SET (temp_set1, reg_class_contents [i]);
-      AND_COMPL_HARD_REG_SET (temp_set1, fixed_reg_set);
-      
       for (j = 0; j < N_REG_CLASSES; j++)
 	if (i != j)
 	  {
 	    enum reg_class *p;
 	    
 	    COPY_HARD_REG_SET (temp_set2, reg_class_contents [j]);
-	    AND_COMPL_HARD_REG_SET (temp_set2, fixed_reg_set);
 	    GO_IF_HARD_REG_SUBSET (temp_set1, temp_set2, subclass);
 	    continue;
 	  subclass:
@@ -161,9 +158,9 @@ set_up_closure_classes (void)
 }      
 
 
-static int reg_class_cover_size, min_reg_class_cover_size;
+static int reg_class_cover_size, final_reg_class_cover_size;
 static enum reg_class reg_class_cover [N_REG_CLASSES];
-static enum reg_class min_reg_class_cover [N_REG_CLASSES];
+static enum reg_class final_reg_class_cover [N_REG_CLASSES];
 static HARD_REG_SET reg_class_cover_set;
 static HARD_REG_SET temp_hard_reg_set;
 
@@ -179,7 +176,7 @@ extend_reg_class_cover (void)
   AND_COMPL_HARD_REG_SET (temp_hard_reg_set, reg_class_cover_set);
   GO_IF_HARD_REG_EQUAL (temp_hard_reg_set, zero_hard_reg_set,
 			done);
-  if (reg_class_cover_size >= min_reg_class_cover_size)
+  if (reg_class_cover_size >= final_reg_class_cover_size)
     return false;
   result = false;
   for (i = 0; i < closure_classes_size; i++)
@@ -206,10 +203,10 @@ extend_reg_class_cover (void)
   gcc_unreachable ();
 
  done:
-  if (min_reg_class_cover_size > reg_class_cover_size)
+  if (final_reg_class_cover_size > reg_class_cover_size)
     {
-      min_reg_class_cover_size = reg_class_cover_size;
-      memcpy (min_reg_class_cover, reg_class_cover,
+      final_reg_class_cover_size = reg_class_cover_size;
+      memcpy (final_reg_class_cover, reg_class_cover,
 	      reg_class_cover_size * sizeof (enum reg_class));
     }
   return true;
@@ -225,9 +222,9 @@ set_up_class_translate (void)
 
   for (cl = 0; cl < N_REG_CLASSES; cl++)
     class_translate [cl] = NO_REGS;
-  for (i = 0; i < min_reg_class_cover_size; i++)
+  for (i = 0; i < final_reg_class_cover_size; i++)
     {
-      cl = min_reg_class_cover [i];
+      cl = final_reg_class_cover [i];
       for (cl_ptr = &alloc_reg_class_subclasses [cl] [0];
 	   *cl_ptr != LIM_REG_CLASSES;
 	   cl_ptr++)
@@ -259,8 +256,8 @@ print_class_cover (FILE *f)
   int i;
 
   fprintf (f, "Class cover:\n");
-  for (i = 0; i < min_reg_class_cover_size; i++)
-    fprintf (f, " %s", reg_class_names [min_reg_class_cover [i]]);
+  for (i = 0; i < final_reg_class_cover_size; i++)
+    fprintf (f, " %s", reg_class_names [final_reg_class_cover [i]]);
   fprintf (f, "\nClass translation:\n");
   for (i = 0; i < N_REG_CLASSES; i++)
     fprintf (f, " %s -> %s\n", reg_class_names [i],
@@ -280,7 +277,7 @@ find_reg_class_closure (void)
 
   setup_reg_subclasses ();
   set_up_closure_classes ();
-  min_reg_class_cover_size = N_REG_CLASSES;
+  final_reg_class_cover_size = N_REG_CLASSES;
   reg_class_cover_size = 0;
   CLEAR_HARD_REG_SET (reg_class_cover_set);
   ok_p = extend_reg_class_cover ();
@@ -1337,29 +1334,32 @@ static can_t *sorted_cans;
 /* Number of global cans.  */
 static int global_cans_num;
 
+/* Bucket of cans can be colored currently without spilling.  */
+static can_t colorable_can_bucket;
+
 /* Array of all buckets used for colouring.  I-th bucket contains cans
    conflicting with I other cans uncoloured yet.  */
 static varray_type bucket_varray;
 
-/* Add CAN to BUCKET_NUM-th bucket.  CAN should be not in a bucket
+/* Add CAN to *BUCKET_PTR bucket.  CAN should be not in a bucket
    before the call.  */
 static void
-add_can_to_bucket (can_t can, varray_type *bucket_varray, int bucket_num)
+add_can_to_bucket (can_t can, can_t *bucket_ptr)
 {
   can_t first_can;
 
-  first_can = VARRAY_GENERIC_PTR (*bucket_varray, bucket_num);
+  first_can = *bucket_ptr;
   CAN_NEXT_BUCKET_CAN (can) = first_can;
   CAN_PREV_BUCKET_CAN (can) = NULL;
   if (first_can != NULL)
     CAN_PREV_BUCKET_CAN (first_can) = can;
-  VARRAY_GENERIC_PTR (*bucket_varray, bucket_num) = can;
+  *bucket_ptr = can;
 }
 
-/* Delete CAN from BUCKET_NUM-th bucket.  It should be there before
+/* Delete CAN from *BUCKET_PTR bucket.  It should be there before
    the call.  */
 static void
-delete_can_from_bucket (can_t can, varray_type *bucket_varray, int bucket_num)
+delete_can_from_bucket (can_t can, can_t *bucket_ptr)
 {
   can_t prev_can, next_can;
 
@@ -1369,8 +1369,8 @@ delete_can_from_bucket (can_t can, varra
     CAN_NEXT_BUCKET_CAN (prev_can) = next_can;
   else
     {
-      gcc_assert (VARRAY_GENERIC_PTR (*bucket_varray, bucket_num) == can);
-      VARRAY_GENERIC_PTR (*bucket_varray, bucket_num) = next_can;
+      gcc_assert (*bucket_ptr == can);
+      *bucket_ptr = next_can;
     }
   if (next_can != NULL)
     CAN_PREV_BUCKET_CAN (next_can) = prev_can;
@@ -1380,9 +1380,6 @@ delete_can_from_bucket (can_t can, varra
    colouring.  */
 static varray_type global_stack_varray;
 
-/* Cover class of the global can in consideration.  */
-static enum reg_class curr_global_can_cover_class;
-
 /* Function used to sort cans according to their priorities to choose
    one for spilling.  */
 static int
@@ -1390,24 +1387,21 @@ global_can_compare (const void *c1p, con
 {
   can_t c1 = *(can_t *) c1p;
   can_t c2 = *(can_t *) c2p;
-  int diff;
+  int diff, size1, size2;
 
   if (CAN_IN_GRAPH_P (c1) && ! CAN_IN_GRAPH_P (c2))
     return -1;
   else if (! CAN_IN_GRAPH_P (c1) && CAN_IN_GRAPH_P (c2))
     return 1;
-  else if (CAN_COVER_CLASS (c1) == curr_global_can_cover_class
-	   && CAN_COVER_CLASS (c2) != curr_global_can_cover_class)
-    return -1;
-  else if (CAN_COVER_CLASS (c1) != curr_global_can_cover_class
-	   && CAN_COVER_CLASS (c2) == curr_global_can_cover_class)
-    return 1;
   else
     {
+      gcc_assert (CAN_COVER_CLASS (c1) == CAN_COVER_CLASS (c2));
+      size1 = reg_class_nregs [CAN_COVER_CLASS (c1)] [CAN_MODE (c1)];
+      size2 = reg_class_nregs [CAN_COVER_CLASS (c2)] [CAN_MODE (c2)];
       diff = ((CAN_MEMORY_COST (c1) - CAN_COVER_CLASS_COST (c1))
-	      / (CAN_LEFT_CONFLICTS_NUM (c1) + 1)
+	      / (CAN_LEFT_CONFLICTS_NUM (c1) + 1) * size1
 	      - (CAN_MEMORY_COST (c2) - CAN_COVER_CLASS_COST (c2))
-	      / (CAN_LEFT_CONFLICTS_NUM (c2) + 1));
+	      / (CAN_LEFT_CONFLICTS_NUM (c2) + 1) * size2);
       if (diff != 0)
 	return diff;
       return CAN_NUM (c1) - CAN_NUM (c2);
@@ -1419,62 +1413,131 @@ global_can_compare (const void *c1p, con
 static void
 push_globals_to_stack (void)
 {
-  int i, n, size = 0, cans_num_to_sort;
+  int i, size = 0, conflicts_num, conflict_size;
+  int first_non_empty_bucket_num;
   can_t can, conflict_can;
-  can_t *sorted_global_cans, *can_vec;
+  can_t *can_vec, *sorted_global_cans, *bucket_ptr;
+  enum reg_class cover_class;
+  int num, cover_class_cans_num [N_REG_CLASSES];
+  can_t *cover_class_cans [N_REG_CLASSES];
 
-  sorted_global_cans = yara_allocate (sizeof (can_t) * global_cans_num);
-  for (n = i = 0; i < cans_num; i++)
-    if (CAN_GLOBAL_P (cans [i]))
-      sorted_global_cans [n++] = cans [i];
-  gcc_assert (n == global_cans_num);
-  cans_num_to_sort = global_cans_num;
-  for (n = 0; n < global_cans_num; n++)
-    {
-      for (i = 0; i < (int) VARRAY_ACTIVE_SIZE (bucket_varray); i++)
-	if (VARRAY_GENERIC_PTR (bucket_varray, i) != NULL)
-	  break;
-      if (i >= (int) VARRAY_ACTIVE_SIZE (bucket_varray))
-	break;
-      can = VARRAY_GENERIC_PTR (bucket_varray, i);
-      gcc_assert (CAN_LEFT_CONFLICTS_NUM (can) == i);
-      curr_global_can_cover_class = CAN_COVER_CLASS (can);
-      if (curr_global_can_cover_class != NO_REGS)
+  sorted_global_cans = yara_allocate (sizeof (can_t) * cans_num);
+  for (i = 0; i < final_reg_class_cover_size; i++)
+    {
+      cover_class = final_reg_class_cover [i];
+      cover_class_cans_num [cover_class] = 0;
+      cover_class_cans [cover_class] = NULL;
+    }
+  for (i = 0; i < cans_num; i++)
+    if (CAN_GLOBAL_P (cans [i])
+	&& (cover_class = CAN_COVER_CLASS (cans [i])) != NO_REGS)
+      cover_class_cans_num [cover_class]++;
+  for (num = i = 0; i < final_reg_class_cover_size; i++)
+    {
+      cover_class = final_reg_class_cover [i];
+      if (cover_class_cans_num [cover_class] != 0)
 	{
-	  size
-	    = reg_class_nregs [curr_global_can_cover_class] [CAN_MODE (can)];
-	  gcc_assert (size > 0);
-	  if (i + size > available_class_regs [curr_global_can_cover_class])
-	    {
-	      qsort (sorted_global_cans, cans_num_to_sort, sizeof (can_t),
-		     global_can_compare);
-	      cans_num_to_sort = global_cans_num - n;
-	      can = sorted_global_cans [0];
-	      size = (reg_class_nregs [curr_global_can_cover_class]
-		      [CAN_MODE (can)]);
-	      gcc_assert
-		(CAN_IN_GRAPH_P (can)
-		 && CAN_COVER_CLASS (can) == curr_global_can_cover_class);
+	  cover_class_cans [cover_class] = sorted_global_cans + num;
+	  num += cover_class_cans_num [cover_class];
+	  cover_class_cans_num [cover_class] = 0;
+	}
+    }
+  gcc_assert (num <= cans_num);
+  for (i = 0; i < cans_num; i++)
+    if (CAN_GLOBAL_P (cans [i])
+	&& (cover_class = CAN_COVER_CLASS (cans [i])) != NO_REGS)
+      cover_class_cans [cover_class] [cover_class_cans_num [cover_class]++]
+	= cans [i];
+  first_non_empty_bucket_num = 0;
+  for (;;)
+    {
+      if (colorable_can_bucket != NULL)
+	{
+	  can = colorable_can_bucket;
+	  cover_class = CAN_COVER_CLASS (can);
+	  if (cover_class != NO_REGS)
+	    size = reg_class_nregs [cover_class] [CAN_MODE (can)];
+	  gcc_assert (CAN_LEFT_CONFLICTS_NUM (can)
+		      + reg_class_nregs [cover_class] [CAN_MODE (can)]
+		      <= available_class_regs [cover_class]);
+	  bucket_ptr = &colorable_can_bucket;
+	}
+      else
+	{
+	  for (i = first_non_empty_bucket_num;
+	       i < (int) VARRAY_ACTIVE_SIZE (bucket_varray);
+	       i++)
+	    if (VARRAY_GENERIC_PTR (bucket_varray, i) != NULL)
+	      break;
+	  if (i >= (int) VARRAY_ACTIVE_SIZE (bucket_varray))
+	    break;
+	  first_non_empty_bucket_num = i;
+	  bucket_ptr = (can_t *) &VARRAY_GENERIC_PTR (bucket_varray, i);
+	  can = *bucket_ptr;
+	  gcc_assert (CAN_LEFT_CONFLICTS_NUM (can) == i);
+	  cover_class = CAN_COVER_CLASS (can);
+	  if (cover_class != NO_REGS)
+	    {
+	      size = reg_class_nregs [cover_class] [CAN_MODE (can)];
+	      gcc_assert (size > 0);
+	      if (i + size > available_class_regs [cover_class])
+		{
+		  num = cover_class_cans_num [cover_class];
+		  gcc_assert (num > 0);
+		  can_vec = cover_class_cans [cover_class];
+		  qsort (can_vec, num, sizeof (can_t), global_can_compare);
+		  for (num--; ! CAN_IN_GRAPH_P (can_vec [num]); num--)
+		    ;
+		  gcc_assert (num >= 0);
+		  cover_class_cans_num [cover_class] = num;
+		  can = can_vec [0];
+		  cover_class_cans [cover_class]++;
+		  size = reg_class_nregs [cover_class] [CAN_MODE (can)];
+		  gcc_assert (CAN_IN_GRAPH_P (can)
+			      && CAN_COVER_CLASS (can) == cover_class
+			      && (CAN_LEFT_CONFLICTS_NUM (can) + size
+				  > available_class_regs [cover_class]));
+		  bucket_ptr = ((can_t *) &VARRAY_GENERIC_PTR
+				(bucket_varray, CAN_LEFT_CONFLICTS_NUM (can)));
+		}
 	    }
 	}
-      delete_can_from_bucket (can, &bucket_varray,
-			      CAN_LEFT_CONFLICTS_NUM (can));
+      delete_can_from_bucket (can, bucket_ptr);
       CAN_IN_GRAPH_P (can) = false;
       VARRAY_PUSH_GENERIC_PTR (global_stack_varray, can);
-      if (curr_global_can_cover_class == NO_REGS)
+      if (cover_class == NO_REGS)
 	continue;
       can_vec = CAN_CONFLICT_CAN_VEC (can);
       for (i = 0; (conflict_can = can_vec [i]) != NULL; i++)
 	{
-	  if (curr_global_can_cover_class != CAN_COVER_CLASS (conflict_can))
+	  if (cover_class != CAN_COVER_CLASS (conflict_can))
 	    continue;
 	  if (CAN_IN_GRAPH_P (conflict_can))
 	    {
-	      delete_can_from_bucket (conflict_can, &bucket_varray,
-				      CAN_LEFT_CONFLICTS_NUM (conflict_can));
+	      conflicts_num = CAN_LEFT_CONFLICTS_NUM (conflict_can);
+	      conflict_size
+		= reg_class_nregs [cover_class] [CAN_MODE (conflict_can)];
+	      gcc_assert (CAN_LEFT_CONFLICTS_NUM (conflict_can) >= size);
 	      CAN_LEFT_CONFLICTS_NUM (conflict_can) -= size;
-	      add_can_to_bucket (conflict_can, &bucket_varray,
-				 CAN_LEFT_CONFLICTS_NUM (conflict_can));
+	      if (conflicts_num + conflict_size
+		  <= available_class_regs [cover_class])
+		continue;
+	      delete_can_from_bucket
+		(conflict_can,
+		 (can_t *) &VARRAY_GENERIC_PTR (bucket_varray, conflicts_num));
+	      conflicts_num = CAN_LEFT_CONFLICTS_NUM (conflict_can);
+	      if (conflicts_num + conflict_size
+		  <= available_class_regs [cover_class])
+		add_can_to_bucket (conflict_can, &colorable_can_bucket);
+	      else
+		{
+		  if (first_non_empty_bucket_num > conflicts_num)
+		    first_non_empty_bucket_num = conflicts_num;
+		  add_can_to_bucket
+		    (conflict_can,
+		     (can_t *) &VARRAY_GENERIC_PTR (bucket_varray,
+						    conflicts_num));
+		}
 	    }
 	}
     }
@@ -1703,7 +1766,6 @@ pop_globals_from_stack (void)
 static void
 global_can_alloc (void)
 {
-    {
   int i, j, hard_regno, conflict_cans_size;
   can_t can, conflict_can;
   can_t *can_vec;
@@ -1712,6 +1774,7 @@ global_can_alloc (void)
 
   global_cans_num = 0;
   /* Put the global cans into the corresponding buckets.  */
+  colorable_can_bucket = NULL;
   VARRAY_GENERIC_PTR_NOGC_INIT (bucket_varray, cans_num,
 				"buckets of global cans");
   for (i = 0; i < cans_num; i++)
@@ -1748,7 +1811,13 @@ global_can_alloc (void)
       CAN_LEFT_CONFLICTS_NUM (can) = conflict_cans_size;
       while (conflict_cans_size >= (int) VARRAY_ACTIVE_SIZE (bucket_varray))
 	VARRAY_PUSH_GENERIC_PTR (bucket_varray, NULL);
-      add_can_to_bucket (can, &bucket_varray, conflict_cans_size);
+      if (conflict_cans_size + reg_class_nregs [cover_class] [CAN_MODE (can)]
+	  <= available_class_regs [cover_class])
+	add_can_to_bucket (can, &colorable_can_bucket);
+      else
+	add_can_to_bucket (can,
+			   (can_t *) &VARRAY_GENERIC_PTR (bucket_varray,
+							  conflict_cans_size));
     }
   VARRAY_GENERIC_PTR_NOGC_INIT (global_stack_varray, global_cans_num,
 				"stack of global cans");
@@ -1756,7 +1825,6 @@ global_can_alloc (void)
   pop_globals_from_stack ();
   VARRAY_FREE (global_stack_varray);
   VARRAY_FREE (bucket_varray);
-    }
 }
 
 
Index: yara-final.c
===================================================================
--- yara-final.c	(revision 112301)
+++ yara-final.c	(working copy)
@@ -66,7 +66,7 @@ static void add_copy_list (copy_t);
 static void modify_insn (rtx, bool);
 static void clean_insn (rtx);
 
-static void align_or_allocate_stack_memory (bool);
+static void allocate_stack_memory (void);
 
 static bitmap insn_to_be_removed_p;
 
@@ -1631,6 +1631,14 @@ eliminate_regs (rtx x)
   return x;
 }
 
+/* Offset between frame and stack memory slot area after the
+   allocation.  */
+static HOST_WIDE_INT final_stack_memory_start_frame_offset;
+
+/* Size of stack slots after allocation of all necessary stack
+   memory.  */
+static int final_rounded_slot_memory_size;
+
 static rtx
 get_allocno_memory_slot_rtx (struct memory_slot *memory_slot, int offset,
 			     enum machine_mode mode,
@@ -1652,17 +1660,26 @@ get_allocno_memory_slot_rtx (struct memo
     {
       HOST_WIDE_INT disp;
 
+#ifdef FRAME_GROWS_DOWNWARD
       if (stack_frame_pointer_can_be_eliminated_p
 	  && obligatory_stack_frame_pointer_elimination_p)
-	disp = (stack_memory_start_frame_offset ()
-		+ frame_stack_pointer_offset);
+	disp = (frame_stack_pointer_offset
+		+ final_stack_memory_start_frame_offset
+		+ memory_slot->start - memory_slot->size + 2
+		- final_rounded_slot_memory_size);
       else
-	disp = (stack_memory_start_frame_offset ()
-		+ frame_hard_frame_pointer_offset);
-#ifdef FRAME_GROWS_DOWNWARD
-      disp -= memory_slot->start;
+	disp = (final_stack_memory_start_frame_offset
+		+ frame_hard_frame_pointer_offset - memory_slot->start);
 #else
-      disp += memory_slot->start;
+      if (stack_frame_pointer_can_be_eliminated_p
+	  && obligatory_stack_frame_pointer_elimination_p)
+	disp = (frame_stack_pointer_offset
+		- final_stack_memory_start_frame_offset
+		+ memory_slot->start + memory_slot->size
+		- final_rounded_slot_memory_size);
+      else
+	disp = (final_stack_memory_start_frame_offset
+		+ frame_hard_frame_pointer_offset + memory_slot->start);
 #endif
       mem = gen_rtx_MEM (mode,
 			 gen_rtx_PLUS
@@ -1998,8 +2015,6 @@ emit_copy (copy_t cp)
 #endif
 	  elimination_subst_reg = gen_allocno_reg_rtx (Pmode, elim->to, dst);
 	  offset = elim->offset;
-	  if (elim->to == STACK_POINTER_REGNUM)
-	    offset += slot_memory_size;
 	  interm_elimination_regno
 	    = INSN_ALLOCNO_INTERM_ELIMINATION_REGNO (dst);
 	  regno = ALLOCNO_REGNO (dst);
@@ -2837,8 +2852,6 @@ modify_insn (rtx insn, bool non_operand_
 	    }
 	  interm_regno = INSN_ALLOCNO_INTERM_ELIMINATION_REGNO (a);
 	  offset = elim->offset;
-	  if (elim->to == STACK_POINTER_REGNUM)
-	    offset += slot_memory_size;
 	  if (interm_regno < 0)
 	    to = elim->to;
 	  else
@@ -2946,7 +2959,7 @@ clean_insn (rtx insn)
 /* Allign stack or allocate memory on the stack for all stack slots
    currently existing.  */
 static void
-align_or_allocate_stack_memory (bool align_p)
+allocate_stack_memory (void)
 {
   int align;
 
@@ -2957,10 +2970,13 @@ align_or_allocate_stack_memory (bool ali
      boundary.  */
   if ((unsigned) align * BITS_PER_UNIT > PREFERRED_STACK_BOUNDARY)
     align = (int) PREFERRED_STACK_BOUNDARY / BITS_PER_UNIT;
-  (void) assign_stack_local (BLKmode, (align_p ? 0 : slot_memory_size),
+  (void) assign_stack_local (BLKmode, 0, align * BITS_PER_UNIT);
+  final_stack_memory_start_frame_offset
+    = get_stack_memory_start_frame_offset ();
+  (void) assign_stack_local (BLKmode, slot_memory_size,
 			     align * BITS_PER_UNIT);
-  if (align_p)
-    update_elim_offsets ();
+  final_rounded_slot_memory_size = rounded_slot_memory_size ();
+  update_elim_offsets ();
 }
 
 
@@ -2982,7 +2998,7 @@ yara_rewrite (void)
       finish_locations ();
     }
   no_new_pseudos = 0;
-  align_or_allocate_stack_memory (true);
+  allocate_stack_memory ();
   FOR_EACH_BB (bb)
     {
       bound = NEXT_INSN (BB_END (bb));
@@ -3042,7 +3058,6 @@ yara_rewrite (void)
     }
   commit_edge_insertions ();
   no_new_pseudos = 1;
-  align_or_allocate_stack_memory (false);
   if ((YARA_PARAMS & YARA_NO_COPY_SYNC) == 0)
     yara_free_bitmap (insn_to_be_removed_p);
 }
Index: yara.c
===================================================================
--- yara.c	(revision 112301)
+++ yara.c	(working copy)
@@ -58,9 +58,6 @@ HARD_REG_SET reg_mode_hard_regset [FIRST
 int memory_move_cost [MAX_MACHINE_MODE] [N_REG_CLASSES] [2];
 int register_move_cost [MAX_MACHINE_MODE] [N_REG_CLASSES] [N_REG_CLASSES];
 bool class_subset_p [N_REG_CLASSES] [N_REG_CLASSES];
-short class_hard_regs [N_REG_CLASSES] [FIRST_PSEUDO_REGISTER];
-int class_hard_regs_num [N_REG_CLASSES];
-short class_hard_reg_index [N_REG_CLASSES] [FIRST_PSEUDO_REGISTER];
 
 
 
@@ -140,19 +137,9 @@ set_class_subset_and_move_costs (void)
 
 
 
-HARD_REG_SET no_alloc_regs;
-
-static void
-set_non_alloc_regs (void)
-{
-  COPY_HARD_REG_SET (no_alloc_regs, fixed_reg_set);
-  
-  if (! stack_frame_pointer_can_be_eliminated_p
-      || ! obligatory_stack_frame_pointer_elimination_p)
-    SET_HARD_REG_BIT (no_alloc_regs, HARD_FRAME_POINTER_REGNUM);
-}
-
-
+short class_hard_regs [N_REG_CLASSES] [FIRST_PSEUDO_REGISTER];
+int class_hard_regs_num [N_REG_CLASSES];
+short class_hard_reg_index [N_REG_CLASSES] [FIRST_PSEUDO_REGISTER];
 
 #ifdef REG_ALLOC_ORDER
 static int hard_reg_alloc_order[FIRST_PSEUDO_REGISTER] = REG_ALLOC_ORDER;
@@ -211,6 +198,18 @@ set_up_available_class_regs (void)
     }
 }
 
+HARD_REG_SET no_alloc_regs;
+
+void
+set_non_alloc_regs (bool use_hard_frame_p)
+{
+  COPY_HARD_REG_SET (no_alloc_regs, fixed_reg_set);
+  if (! use_hard_frame_p)
+    SET_HARD_REG_BIT (no_alloc_regs, HARD_FRAME_POINTER_REGNUM);
+  set_up_class_hard_regs ();
+  set_up_available_class_regs ();
+}
+
 
 
 static void print_disposition (FILE *);
@@ -393,9 +392,7 @@ yara_init_once (void)
   set_inner_mode ();
   set_reg_mode_hard_regset ();
   set_class_subset_and_move_costs ();
-  set_non_alloc_regs ();
-  set_up_class_hard_regs ();
-  set_up_available_class_regs ();
+  set_non_alloc_regs (flag_omit_frame_pointer);
   yara_ir_init_once ();
   yara_trans_init_once ();
   yara_color_init_once ();
Index: yara-trans.c
===================================================================
--- yara-trans.c	(revision 112301)
+++ yara-trans.c	(working copy)
@@ -100,7 +100,8 @@ static void finish_memory_slots (void);
 static void set_up_temp_mems_and_addresses (void);
 static rtx get_temp_const_int (HOST_WIDE_INT);
 static rtx get_temp_disp (rtx, HOST_WIDE_INT);
-static rtx get_temp_stack_memory_slot_rtx (enum machine_mode, HOST_WIDE_INT);
+static rtx get_temp_stack_memory_slot_rtx (enum machine_mode, HOST_WIDE_INT,
+					   int);
 
 static enum reg_class get_allocno_reg_class (allocno_t);
 static int non_pseudo_allocno_copy_cost (allocno_t);
@@ -533,10 +534,25 @@ decrease_align_count (int align)
     }
 }
 
+/* Return size of the aligned simulated stack area.  */
+HOST_WIDE_INT
+rounded_slot_memory_size (void)
+{
+  int align;
+
+  align = slot_memory_alignment;
+  /* Ignore alignment we can't do with expected alignment of the
+     boundary.  */
+  if ((unsigned) align * BITS_PER_UNIT > PREFERRED_STACK_BOUNDARY)
+    align = PREFERRED_STACK_BOUNDARY / BITS_PER_UNIT;
+  
+  return CEIL_ROUND (slot_memory_size, (unsigned) align);
+}
+
 /* Return the displacement of the simulated stack area start relative
    to frame pointer.  */
 HOST_WIDE_INT
-stack_memory_start_frame_offset (void)
+get_stack_memory_start_frame_offset (void)
 {
   int align, size;
   int frame_off, frame_alignment, frame_phase;
@@ -1316,7 +1332,8 @@ get_temp_disp (rtx disp, HOST_WIDE_INT o
 }
 
 static rtx
-get_temp_stack_memory_slot_rtx (enum machine_mode mode, HOST_WIDE_INT disp)
+get_temp_stack_memory_slot_rtx (enum machine_mode mode, HOST_WIDE_INT disp,
+				int size)
 {
   rtx mem;
   HOST_WIDE_INT offset;
@@ -1326,20 +1343,25 @@ get_temp_stack_memory_slot_rtx (enum mac
     {
       /* disp is addressed from the stack bottom in this case.  */
       mem = temp_stack_disp_mem [mode];
-      offset = (stack_memory_start_frame_offset ()
-		- frame_stack_pointer_offset);
+      offset = (frame_stack_pointer_offset + disp
+		- rounded_slot_memory_size ());
+#ifdef FRAME_GROWS_DOWNWARD
+      offset += get_stack_memory_start_frame_offset () - size + 2;
+#else
+      offset += size - get_stack_memory_start_frame_offset ();
+#endif
     }
   else
     {
       mem = temp_hard_frame_disp_mem [mode];
-      offset = (stack_memory_start_frame_offset ()
-		- frame_hard_frame_pointer_offset);
-    }
+      offset = (get_stack_memory_start_frame_offset ()
+		+ frame_hard_frame_pointer_offset);
 #ifdef FRAME_GROWS_DOWNWARD
-  offset -= disp;
+      offset -= disp;
 #else
-  offset += disp;
+      offset += disp;
 #endif
+    }
   XEXP (XEXP (mem, 0), 1) = get_temp_const_int (disp);
   return mem;
 }
@@ -1769,7 +1791,8 @@ assign_copy_secondary (copy_t cp)
 	  {
 	    x = slot->mem;
 	    if (x == NULL)
-	      x = get_temp_stack_memory_slot_rtx (mode, slot->start);
+	      x = get_temp_stack_memory_slot_rtx (mode, slot->start,
+						  slot->size);
 	  }
 	else
 	  gcc_unreachable ();
Index: yara-ir.c
===================================================================
--- yara-ir.c	(revision 112301)
+++ yara-ir.c	(working copy)
@@ -647,6 +647,15 @@ modify_offsets_and_frame_pointer_needed 
 	  obligatory_stack_frame_pointer_elimination_p = ep->obligatory;
 	}
     }
+  /* Check that NO_ALLOC_REGS should be changed.  */
+  if (stack_frame_pointer_can_be_eliminated_p
+      && obligatory_stack_frame_pointer_elimination_p)
+    {
+      if (TEST_HARD_REG_BIT (no_alloc_regs, HARD_FRAME_POINTER_REGNUM))
+	set_non_alloc_regs (true);
+    }
+  else if (! TEST_HARD_REG_BIT (no_alloc_regs, HARD_FRAME_POINTER_REGNUM))
+    set_non_alloc_regs (false);
 }
 
 static void

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