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: [PATCH][ARM] Fix PR target/64460: Set 'shift' attr properly on some patterns


Now with patch attached

Kyrill

On 12/01/15 14:27, Kyrill Tkachov wrote:
Hi all,

In this PR we ICE when compiling with -mtune=xscale. The ICE is a
segfault in xscale_sched_adjust_cost.
The root cause is that xscale_sched_adjust_cost uses the value of the
'shift' insn attribute to index
the recog operands. In GCC 5 the form and number of operands in those
patterns were updated but the
shift value was not:

Author: rearnsha <rearnsha@138bc75d-0d04-0410-961f-82ee72b054a4>
Date:   Thu May 29 09:39:07 2014 +0000

              * arm/iterators.md (shiftable_ops): New code iterator.
              (t2_binop0, arith_shift_insn): New code attributes.
          * arm/predicates.md (shift_nomul_operator): New predicate.
              * arm/arm.md (insn_enabled): Delete.
              (enabled): Remove insn_enabled test.
              (*arith_shiftsi): Delete.  Replace with ...
              (*<arith_shift_insn>_multsi): ... new pattern.
          (*<arith_shift_insn>_shiftsi): ... new pattern.
          * config/arm/arm.c (arm_print_operand): Handle operand format 'b'.

This led to an out-of-bounds array access. Only xscale_sched_adjust_cost
uses the shift
attribute, so the segfault only happens for xscale tuning. In the future
we might want
to use a more general pattern-matching approach to find the shifted
operand in an rtx...

In any case, this patch fixes the value of 'shift' for the offending
pattern and also
updates 'shift'  for the *<arith_shift_insn>_shiftsi pattern to point to
the correct
operand that is being shifted.

Tested arm-none-eabi and bootstrapped with -mtune=xscale in BOOT_CFLAGS.

Ok for trunk?

Thanks,
Kyrill

2014-01-12  Kyrylo Tkachov  <kyrylo.tkachov@arm.com>

      PR target/64460
      * config/arm/arm.md (*<arith_shift_insn>_multsi): Set 'shift' attr
      to 2.
      (*<arith_shift_insn>_shiftsi): Set 'shift' attr to 3.

2014-01-12  Kyrylo Tkachov  <kyrylo.tkachov@arm.com>

      PR target/64460
      * gcc.target/arm/pr64460_1.c: New test.


commit c89087db2f16eda521d6c938d342570c1d69a7a2
Author: Kyrylo Tkachov <kyrylo.tkachov@arm.com>
Date:   Fri Jan 9 16:41:44 2015 +0000

    [ARM] PR target/64460 ICE with -mtune=xscale in shift attr

diff --git a/gcc/config/arm/arm.md b/gcc/config/arm/arm.md
index c61057f..bbefb93 100644
--- a/gcc/config/arm/arm.md
+++ b/gcc/config/arm/arm.md
@@ -8255,36 +8255,36 @@ (define_insn "trap"
 (define_insn "*<arith_shift_insn>_multsi"
   [(set (match_operand:SI 0 "s_register_operand" "=r,r")
 	(shiftable_ops:SI
 	 (mult:SI (match_operand:SI 2 "s_register_operand" "r,r")
 		  (match_operand:SI 3 "power_of_two_operand" ""))
 	 (match_operand:SI 1 "s_register_operand" "rk,<t2_binop0>")))]
   "TARGET_32BIT"
   "<arith_shift_insn>%?\\t%0, %1, %2, lsl %b3"
   [(set_attr "predicable" "yes")
    (set_attr "predicable_short_it" "no")
-   (set_attr "shift" "4")
+   (set_attr "shift" "2")
    (set_attr "arch" "a,t2")
    (set_attr "type" "alu_shift_imm")])
 
 (define_insn "*<arith_shift_insn>_shiftsi"
   [(set (match_operand:SI 0 "s_register_operand" "=r,r,r")
 	(shiftable_ops:SI
 	 (match_operator:SI 2 "shift_nomul_operator"
 	  [(match_operand:SI 3 "s_register_operand" "r,r,r")
 	   (match_operand:SI 4 "shift_amount_operand" "M,M,r")])
 	 (match_operand:SI 1 "s_register_operand" "rk,<t2_binop0>,rk")))]
   "TARGET_32BIT && GET_CODE (operands[2]) != MULT"
   "<arith_shift_insn>%?\\t%0, %1, %3%S2"
   [(set_attr "predicable" "yes")
    (set_attr "predicable_short_it" "no")
-   (set_attr "shift" "4")
+   (set_attr "shift" "3")
    (set_attr "arch" "a,t2,a")
    (set_attr "type" "alu_shift_imm,alu_shift_imm,alu_shift_reg")])
 
 (define_split
   [(set (match_operand:SI 0 "s_register_operand" "")
 	(match_operator:SI 1 "shiftable_operator"
 	 [(match_operator:SI 2 "shiftable_operator"
 	   [(match_operator:SI 3 "shift_operator"
 	     [(match_operand:SI 4 "s_register_operand" "")
 	      (match_operand:SI 5 "reg_or_int_operand" "")])
diff --git a/gcc/testsuite/gcc.target/arm/pr64460_1.c b/gcc/testsuite/gcc.target/arm/pr64460_1.c
new file mode 100644
index 0000000..ee6ad4a
--- /dev/null
+++ b/gcc/testsuite/gcc.target/arm/pr64460_1.c
@@ -0,0 +1,69 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -mtune=xscale" } */
+
+typedef unsigned int size_t;
+typedef short unsigned int __uint16_t;
+typedef long unsigned int __uint32_t;
+typedef unsigned int __uintptr_t;
+typedef __uint16_t uint16_t ;
+typedef __uint32_t uint32_t ;
+typedef __uintptr_t uintptr_t;
+typedef uint32_t Objects_Id;
+typedef uint16_t Objects_Maximum;
+typedef struct { } Objects_Control;
+
+static __inline__ void *_Addresses_Align_up (void *address, size_t alignment)
+{
+	uintptr_t mask = alignment - (uintptr_t)1;
+	return (void*)(((uintptr_t)address + mask) & ~mask);
+}
+
+typedef struct {
+	Objects_Id minimum_id;
+	Objects_Maximum maximum;
+	_Bool
+		auto_extend;
+	Objects_Maximum allocation_size;
+	void **object_blocks;
+} Objects_Information;
+
+extern uint32_t _Objects_Get_index (Objects_Id);
+extern void** _Workspace_Allocate (size_t);
+
+void _Objects_Extend_information (Objects_Information *information)
+{
+	uint32_t block_count;
+	uint32_t minimum_index;
+	uint32_t maximum;
+	size_t block_size;
+	_Bool
+		do_extend =
+		minimum_index = _Objects_Get_index( information->minimum_id );
+	if ( information->object_blocks ==
+			((void *)0)
+	   )
+		block_count = 0;
+	else {
+		block_count = information->maximum / information->allocation_size;
+	}
+	if ( do_extend ) {
+		void **object_blocks;
+		uintptr_t object_blocks_size;
+		uintptr_t inactive_per_block_size;
+		object_blocks_size = (uintptr_t)_Addresses_Align_up(
+				(void*)(block_count * sizeof(void*)),
+				8
+				);
+		inactive_per_block_size =
+			(uintptr_t)_Addresses_Align_up(
+					(void*)(block_count * sizeof(uint32_t)),
+					8
+					);
+		block_size = object_blocks_size + inactive_per_block_size +
+			((maximum + minimum_index) * sizeof(Objects_Control *));
+		if ( information->auto_extend ) {
+			object_blocks = _Workspace_Allocate( block_size );
+		} else {
+		}
+	}
+}

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