diff --git a/gnu/gcc/gcc/config/m88k/m88k-protos.h b/gnu/gcc/gcc/config/m88k/m88k-protos.h index c153210b212..d686ad55f56 100644 --- a/gnu/gcc/gcc/config/m88k/m88k-protos.h +++ b/gnu/gcc/gcc/config/m88k/m88k-protos.h @@ -24,7 +24,7 @@ Boston, MA 02110-1301, USA. */ #ifdef RTX_CODE extern void m88k_emit_bcnd (enum rtx_code, rtx); extern void m88k_emit_trailing_label (rtx); -extern void expand_block_move (rtx *); +extern int expand_block_move (rtx *); extern void print_operand (FILE *, rtx, int); extern void print_operand_address (FILE *, rtx); extern const char *output_load_const_int (enum machine_mode, rtx *); diff --git a/gnu/gcc/gcc/config/m88k/m88k.c b/gnu/gcc/gcc/config/m88k/m88k.c index f859c6b8d02..7c0a4059649 100644 --- a/gnu/gcc/gcc/config/m88k/m88k.c +++ b/gnu/gcc/gcc/config/m88k/m88k.c @@ -689,14 +689,15 @@ static const enum machine_mode mode_from_align[] = static void block_move_sequence (rtx, rtx, int, int); -/* Emit code to perform a block move. Choose the best method. +/* Emit code to perform a block move, and return 1 if successful. + Return 0 if we should let the compiler generate a call to memcpy(). OPERANDS[0] is the destination. OPERANDS[1] is the source. OPERANDS[2] is the size. OPERANDS[3] is the alignment safe to use. */ -void +int expand_block_move (rtx *operands) { rtx dest, src; @@ -704,8 +705,11 @@ expand_block_move (rtx *operands) int constp = CONST_INT_P (operands[2]); int bytes = constp ? INTVAL (operands[2]) : 0; - if (constp && bytes <= 0) - return; + if (!constp) + return 0; + + if (bytes <= 0) + return 1; /* nothing to do. */ /* Determine machine mode to do move with. */ if (align > 4 && !TARGET_88110) @@ -716,19 +720,11 @@ expand_block_move (rtx *operands) dest = operands[0]; src = operands[1]; - if (constp && bytes <= (optimize_size ? 3 : 6) * align) - { - block_move_sequence (dest, src, bytes, align); - return; - } + if (bytes > (optimize_size ? 3 : 6) * align) + return 0; - emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "memcpy"), 0, - VOIDmode, 3, - dest, Pmode, - src, Pmode, - convert_to_mode (TYPE_MODE (sizetype), operands[2], - TYPE_UNSIGNED (sizetype)), - TYPE_MODE (sizetype)); + block_move_sequence (dest, src, bytes, align); + return 1; } /* Emit code to perform a block move with an offset sequence of ld/st @@ -741,13 +737,13 @@ block_move_sequence (rtx dest_mem, rtx src_mem, int size, int align) rtx temp[2]; enum machine_mode mode[2]; int amount[2]; - int active[2]; + bool active[2]; int phase = 0; int next; int offset_ld = 0; int offset_st = 0; - active[0] = active[1] = FALSE; + active[0] = active[1] = false; /* Establish parameters for the first load and for the second load if it is known to be the same mode as the first. */ @@ -763,7 +759,7 @@ block_move_sequence (rtx dest_mem, rtx src_mem, int size, int align) do { next = phase; - phase = !phase; + phase ^= 1; if (size > 0) { @@ -2021,7 +2017,7 @@ m88k_emit_bcnd (enum rtx_code op, rtx label) value = INTVAL (constant); /* Perform an arithmetic computation to make the compared-to value - zero, but avoid loosing if the bcnd is later changed into sxx. */ + zero, but avoid losing if the bcnd is later changed into sxx. */ if (SMALL_INTVAL (value)) emit_jump_insn (gen_bxx (m88k_emit_test (op, VOIDmode), label)); else diff --git a/gnu/gcc/gcc/config/m88k/m88k.md b/gnu/gcc/gcc/config/m88k/m88k.md index 969888c7746..35f951e8bcb 100644 --- a/gnu/gcc/gcc/config/m88k/m88k.md +++ b/gnu/gcc/gcc/config/m88k/m88k.md @@ -466,9 +466,8 @@ ;; Improve logical operations on compare words ;; ;; We define all logical operations on CCmode values to preserve the pairwise -;; relationship of the compare bits. This allows a future branch prediction +;; relationship of the compare bits. This allows the future branch prediction ;; pass the degree of freedom needed to change and/bb0-le into or/bb1-gt. -;; THIS IS CURRENTLY FALSE! ;; ;; Opportunities arise when conditional expressions using && and || are made ;; unconditional. When these are used to branch, the sequence is @@ -2123,16 +2122,18 @@ ;; String/block move insn. See m88k.c for details. -(define_expand "movstrsi" - [(parallel [(set (mem:BLK (match_operand:BLK 0 "" "")) - (mem:BLK (match_operand:BLK 1 "" ""))) +(define_expand "movmemsi" + [(parallel [(set (match_operand:BLK 0 "memory_operand" "") + (match_operand:BLK 1 "memory_operand" "")) (use (match_operand:SI 2 "arith32_operand" "")) (use (match_operand:SI 3 "immediate_operand" ""))])] "" " { - expand_block_move (operands); - DONE; + if (expand_block_move (operands)) + DONE; + else + FAIL; }") ;;- zero extension instructions @@ -3756,13 +3757,15 @@ (clobber (reg:SI 1))] "" { + /* This is safe as this insn is of type "weird" and thus not considered + to have a delay slot of its own. */ if (flag_delayed_branch) return "bsr.n %0e\;lda %#r1,%#r1[%1]"; - m88k_case_index = REGNO (operands[1]); + m88k_case_index = REGNO (operands[1]); /* for ASM_OUTPUT_CASE_END */ return "bsr %0e"; } [(set_attr "type" "weird") - (set_attr "length" "12")]) ; Including the "jmp r1". + (set_attr "length" "12")]) ; includes ASM_OUTPUT_CASE_END output ;;- jump to subroutine (define_expand "call"