arm.md (unaligned_loaddi, [...]): New unspec insn patterns.
authorBernd Edlinger <bernd.edlinger@hotmail.de>
Fri, 30 Aug 2019 10:38:37 +0000 (10:38 +0000)
committerBernd Edlinger <edlinger@gcc.gnu.org>
Fri, 30 Aug 2019 10:38:37 +0000 (10:38 +0000)
2019-08-30  Bernd Edlinger  <bernd.edlinger@hotmail.de>

        * config/arm/arm.md (unaligned_loaddi,
        unaligned_storedi): New unspec insn patterns.
        * config/arm/neon.md (unaligned_storev8qi): Likewise.
        * config/arm/arm.c (gen_cpymem_ldrd_strd): Use unaligned_loaddi
        and unaligned_storedi for 4-byte aligned memory.
        (arm_block_set_aligned_vect): Use unaligned_storev8qi for
        4-byte aligned memory.

From-SVN: r275063

gcc/ChangeLog
gcc/config/arm/arm.c
gcc/config/arm/arm.md
gcc/config/arm/neon.md

index 57811a5f94618295c0b0dfc50ede5500cd147716..f902b554286d307337834153226cd9181b17c1e7 100644 (file)
@@ -1,3 +1,13 @@
+2019-08-30  Bernd Edlinger  <bernd.edlinger@hotmail.de>
+
+       * config/arm/arm.md (unaligned_loaddi,
+       unaligned_storedi): New unspec insn patterns.
+       * config/arm/neon.md (unaligned_storev8qi): Likewise.
+       * config/arm/arm.c (gen_cpymem_ldrd_strd): Use unaligned_loaddi
+       and unaligned_storedi for 4-byte aligned memory.
+       (arm_block_set_aligned_vect): Use unaligned_storev8qi for
+       4-byte aligned memory.
+
 2019-08-30  Martin Jambor  <mjambor@suse.cz>
 
        tree-optimization/91579
index a34cb7495f0d7303ab121f7cf9e11c71d9378423..eb8bf13414fdf5f411deed9110cc28921153f7d4 100644 (file)
@@ -14578,8 +14578,10 @@ gen_cpymem_ldrd_strd (rtx *operands)
          low_reg = gen_lowpart (SImode, reg0);
          hi_reg = gen_highpart_mode (SImode, DImode, reg0);
        }
-      if (src_aligned)
-        emit_move_insn (reg0, src);
+      if (MEM_ALIGN (src) >= 2 * BITS_PER_WORD)
+       emit_move_insn (reg0, src);
+      else if (src_aligned)
+       emit_insn (gen_unaligned_loaddi (reg0, src));
       else
        {
          emit_insn (gen_unaligned_loadsi (low_reg, src));
@@ -14587,8 +14589,10 @@ gen_cpymem_ldrd_strd (rtx *operands)
          emit_insn (gen_unaligned_loadsi (hi_reg, src));
        }
 
-      if (dst_aligned)
-        emit_move_insn (dst, reg0);
+      if (MEM_ALIGN (dst) >= 2 * BITS_PER_WORD)
+       emit_move_insn (dst, reg0);
+      else if (dst_aligned)
+       emit_insn (gen_unaligned_storedi (dst, reg0));
       else
        {
          emit_insn (gen_unaligned_storesi (dst, low_reg));
@@ -30197,7 +30201,10 @@ arm_block_set_aligned_vect (rtx dstbase,
     {
       addr = plus_constant (Pmode, dst, i);
       mem = adjust_automodify_address (dstbase, mode, addr, offset + i);
-      emit_move_insn (mem, reg);
+      if (MEM_ALIGN (mem) >= 2 * BITS_PER_WORD)
+       emit_move_insn (mem, reg);
+      else
+       emit_insn (gen_unaligned_storev8qi (mem, reg));
     }
 
   /* Handle single word leftover by shifting 4 bytes back.  We can
@@ -30211,7 +30218,7 @@ arm_block_set_aligned_vect (rtx dstbase,
       if (align > UNITS_PER_WORD)
        set_mem_align (mem, BITS_PER_UNIT * UNITS_PER_WORD);
 
-      emit_move_insn (mem, reg);
+      emit_insn (gen_unaligned_storev8qi (mem, reg));
     }
   /* Handle (0, 4), (4, 8) bytes leftover by shifting bytes back.
      We have to use unaligned access for this case.  */
index 0be7a018eedeea048523f622f99bdd765b8d86ec..e49e0d579c92e0b9452ac1cb8a41035fcd7fff4c 100644 (file)
 
 ; ARMv6+ unaligned load/store instructions (used for packed structure accesses).
 
+(define_insn "unaligned_loaddi"
+  [(set (match_operand:DI 0 "s_register_operand" "=r")
+       (unspec:DI [(match_operand:DI 1 "memory_operand" "m")]
+                  UNSPEC_UNALIGNED_LOAD))]
+  "TARGET_32BIT && TARGET_LDRD"
+  "*
+  return output_move_double (operands, true, NULL);
+  "
+  [(set_attr "length" "8")
+   (set_attr "type" "load_8")])
+
 (define_insn "unaligned_loadsi"
   [(set (match_operand:SI 0 "s_register_operand" "=l,l,r")
        (unspec:SI [(match_operand:SI 1 "memory_operand" "m,Uw,m")]
    (set_attr "predicable_short_it" "no,yes,no")
    (set_attr "type" "load_byte")])
 
+(define_insn "unaligned_storedi"
+  [(set (match_operand:DI 0 "memory_operand" "=m")
+       (unspec:DI [(match_operand:DI 1 "s_register_operand" "r")]
+                  UNSPEC_UNALIGNED_STORE))]
+  "TARGET_32BIT && TARGET_LDRD"
+  "*
+  return output_move_double (operands, true, NULL);
+  "
+  [(set_attr "length" "8")
+   (set_attr "type" "store_8")])
+
 (define_insn "unaligned_storesi"
   [(set (match_operand:SI 0 "memory_operand" "=m,Uw,m")
        (unspec:SI [(match_operand:SI 1 "s_register_operand" "l,l,r")]
index a5aa8d68e62159396f879d54128a364a2261e937..6a0ee28efc9aa9f1fba7b5ae031564f40aa095fe 100644 (file)
 ;; type attribute definitions.
 (define_attr "vqh_mnem" "vadd,vmin,vmax" (const_string "vadd"))
 
+(define_insn "unaligned_storev8qi"
+  [(set (match_operand:V8QI 0 "memory_operand" "=Un")
+       (unspec:V8QI [(match_operand:V8QI 1 "s_register_operand" "w")]
+                    UNSPEC_UNALIGNED_STORE))]
+  "TARGET_NEON"
+  "*
+  return output_move_neon (operands);
+  "
+  [(set_attr "type" "neon_store1_1reg")])
+
 (define_insn "*neon_mov<mode>"
   [(set (match_operand:VDX 0 "nonimmediate_operand"
          "=w,Un,w, w, w,  ?r,?w,?r, ?Us,*r")