On Thu, May 23, 2019 at 11:36 PM Jakub Jelinek <[email protected]> wrote:
>
> Hi!
>
> On Thu, May 23, 2019 at 12:40:51AM +0200, Jakub Jelinek wrote:
> > Incrementally, we should consider handling e.g. *subsi_2{,_zext} and similar
> > patterns and also this stack_protect_test_[sd]i in ix86_macro_fusion_pair_p,
> > not sure if unconditionally, or only when tuning for skylake+ / generic.
>
> Actually, *subsi_2 etc. is already supported, the following patch adds macro
> fusion support for the stack_protect_test_?i.
> Additionally, it fixes a compile time inefficiency, while recog_memoized
> and extract_constrain_insn_cached do caching, get_attr_type uses those two
> plus often calls various predicates which are not cached, so calling
> get_attr_type 4-7 times in a row on the same instruction isn't a very good
> idea.
>
> Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?
>
> 2019-05-23 Jakub Jelinek <[email protected]>
>
> PR target/90568
> * config/i386/x86-tune-sched.c (ix86_macro_funsion_pair_p): Call
> gen_attr_type just once instead of 4-7 times. Formatting fixes.
> Handle stack_protect_test_<mode> codegen similarly to corresponding
> sub instruction.
OK.
Thanks,
Uros.
>
> --- gcc/config/i386/x86-tune-sched.c.jj 2019-01-01 12:37:31.608737849 +0100
> +++ gcc/config/i386/x86-tune-sched.c 2019-05-23 12:28:29.826740473 +0200
> @@ -525,6 +525,7 @@ ix86_macro_fusion_pair_p (rtx_insn *cond
> enum rtx_code ccode;
> rtx compare_set = NULL_RTX, test_if, cond;
> rtx alu_set = NULL_RTX, addr = NULL_RTX;
> + enum attr_type condgen_type;
>
> if (!any_condjump_p (condjmp))
> return false;
> @@ -538,15 +539,26 @@ ix86_macro_fusion_pair_p (rtx_insn *cond
> || !modified_in_p (cc_reg_1, condgen))
> return false;
>
> - if (get_attr_type (condgen) != TYPE_TEST
> - && get_attr_type (condgen) != TYPE_ICMP
> - && get_attr_type (condgen) != TYPE_INCDEC
> - && get_attr_type (condgen) != TYPE_ALU)
> + condgen_type = get_attr_type (condgen);
> + if (condgen_type == TYPE_MULTI
> + && (INSN_CODE (condgen) == CODE_FOR_stack_protect_test_di
> + || INSN_CODE (condgen) == CODE_FOR_stack_protect_test_si)
> + && TARGET_FUSE_ALU_AND_BRANCH)
> + {
> + /* stack_protect_test_<mode> ends with a sub, which subtracts
> + a non-rip special memory operand from a GPR. */
> + src = NULL_RTX;
> + alu_set = XVECEXP (PATTERN (condgen), 0, 1);
> + goto handle_stack_protect_test;
> + }
> + else if (condgen_type != TYPE_TEST
> + && condgen_type != TYPE_ICMP
> + && condgen_type != TYPE_INCDEC
> + && condgen_type != TYPE_ALU)
> return false;
>
> compare_set = single_set (condgen);
> - if (compare_set == NULL_RTX
> - && !TARGET_FUSE_ALU_AND_BRANCH)
> + if (compare_set == NULL_RTX && !TARGET_FUSE_ALU_AND_BRANCH)
> return false;
>
> if (compare_set == NULL_RTX)
> @@ -571,10 +583,8 @@ ix86_macro_fusion_pair_p (rtx_insn *cond
>
> /* Macro-fusion for cmp/test MEM-IMM + conditional jmp is not
> supported. */
> - if ((MEM_P (XEXP (src, 0))
> - && CONST_INT_P (XEXP (src, 1)))
> - || (MEM_P (XEXP (src, 1))
> - && CONST_INT_P (XEXP (src, 0))))
> + if ((MEM_P (XEXP (src, 0)) && CONST_INT_P (XEXP (src, 1)))
> + || (MEM_P (XEXP (src, 1)) && CONST_INT_P (XEXP (src, 0))))
> return false;
>
> /* No fusion for RIP-relative address. */
> @@ -583,29 +593,27 @@ ix86_macro_fusion_pair_p (rtx_insn *cond
> else if (MEM_P (XEXP (src, 1)))
> addr = XEXP (XEXP (src, 1), 0);
>
> - if (addr) {
> - ix86_address parts;
> - int ok = ix86_decompose_address (addr, &parts);
> - gcc_assert (ok);
> -
> - if (ix86_rip_relative_addr_p (&parts))
> - return false;
> - }
> + if (addr)
> + {
> + ix86_address parts;
> + int ok = ix86_decompose_address (addr, &parts);
> + gcc_assert (ok);
> +
> + if (ix86_rip_relative_addr_p (&parts))
> + return false;
> + }
>
> + handle_stack_protect_test:
> test_if = SET_SRC (pc_set (condjmp));
> cond = XEXP (test_if, 0);
> ccode = GET_CODE (cond);
> /* Check whether conditional jump use Sign or Overflow Flags. */
> if (!TARGET_FUSE_CMP_AND_BRANCH_SOFLAGS
> - && (ccode == GE
> - || ccode == GT
> - || ccode == LE
> - || ccode == LT))
> + && (ccode == GE || ccode == GT || ccode == LE || ccode == LT))
> return false;
>
> /* Return true for TYPE_TEST and TYPE_ICMP. */
> - if (get_attr_type (condgen) == TYPE_TEST
> - || get_attr_type (condgen) == TYPE_ICMP)
> + if (condgen_type == TYPE_TEST || condgen_type == TYPE_ICMP)
> return true;
>
> /* The following is the case that macro-fusion for alu + jmp. */
> @@ -619,11 +627,8 @@ ix86_macro_fusion_pair_p (rtx_insn *cond
>
> /* Macro-fusion for inc/dec + unsigned conditional jump is not
> supported. */
> - if (get_attr_type (condgen) == TYPE_INCDEC
> - && (ccode == GEU
> - || ccode == GTU
> - || ccode == LEU
> - || ccode == LTU))
> + if (condgen_type == TYPE_INCDEC
> + && (ccode == GEU || ccode == GTU || ccode == LEU || ccode == LTU))
> return false;
>
> return true;
>
>
> Jakub