--- gcc/config/arm/arm.md 2018/04/24 18:16:12 1.1.1.2 +++ gcc/config/arm/arm.md 2018/04/24 18:22:25 1.1.1.3 @@ -1,5 +1,5 @@ -;;- Machine description Acorn RISC Machine for GNU compiler -;; Copyright (C) 1991, 1993 Free Software Foundation, Inc. +;;- Machine description for Advanced RISC Machines' ARM for GNU compiler +;; Copyright (C) 1991, 1993, 1994 Free Software Foundation, Inc. ;; Contributed by Pieter `Tiggr' Schoenmakers (rcpieter@win.tue.nl) ;; and Martin Simmons (@harleqn.co.uk). ;; More major hacks by Richard Earnshaw (rwe11@cl.cam.ac.uk) @@ -22,14 +22,8 @@ ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al. -;; Every template must be output by arm_output_asm_insn, since this keeps -;; track of the offset of labels within the text segment. This is needed to -;; to be able to (correctly) output instructions for loading a value from a -;; function's constant pool, since different instructions are needed when the -;; constant pool is more than 4095 bytes away from the PC. - ;; There are patterns in this file to support XFmode arithmetic. -;; Unfortunately RISCiX doesn't work well with these so they are disabled. +;; Unfortunately RISC iX doesn't work well with these so they are disabled. ;; (See arm.h) ;; UNSPEC Usage: @@ -37,6 +31,8 @@ ;; the mode is MODE_FLOAT ;; 1 `cos' operation: operand 0 is the result, operand 1 the parameter, ;; the mode is MODE_FLOAT +;; 2 `push multiple' operation: operand 0 is the first register. Subsequent +;; registers are in parallel (use...) expressions. ;; Attributes @@ -70,13 +66,19 @@ (define_attr "cpu" "arm2,arm3,arm6" (const (symbol_ref "arm_cpu_attr"))) -; LENGTH, all instructions are 4 bytes -(define_attr "length" "" (const_int 1)) +; Floating Point Unit. If we only have floating point emulation, then there +; is no point in scheduling the floating point insns. (Well, for best +; performance we should try and group them together). + +(define_attr "fpu" "fpa,fpe" (const (symbol_ref "arm_fpu_attr"))) + +; LENGTH of an instruction (in bytes) +(define_attr "length" "" (const_int 4)) ; An assembler sequence may clobber the condition codes without us knowing (define_asm_attributes [(set_attr "conds" "clob") - (set_attr "length" "1")]) + (set_attr "length" "4")]) ; TYPE attribute is used to detect floating point instructions which, if ; running on a co-processor can run in parallel with other, basic instructions @@ -87,7 +89,15 @@ ; normal any data instruction that doesn't hit memory or fp regs ; block blockage insn, this blocks all functional units ; float a floating point arithmetic operation (subject to expansion) +; fdivx XFmode floating point division +; fdivd DFmode floating point division +; fdivs SFmode floating point division +; fmul Floating point multiply +; ffmul Fast floating point multiply +; farith Floating point arithmetic (4 cycle) +; ffarith Fast floating point arithmetic (2 cycle) ; float_em a floating point arithmetic operation that is normally emulated +; even on a machine with an fpa. ; f_load a floating point load from memory ; f_store a floating point store to memory ; f_mem_r a transfer of a floating point register to a real reg via mem @@ -102,7 +112,7 @@ ; store4 store 4 words ; (define_attr "type" - "normal,block,float,float_em,f_load,f_store,f_mem_r,r_mem_f,f_2_r,r_2_f,call,load,store1,store2,store3,store4" + "normal,block,float,fdivx,fdivd,fdivs,fmul,ffmul,farith,ffarith,float_em,f_load,f_store,f_mem_r,r_mem_f,f_2_r,r_2_f,call,load,store1,store2,store3,store4" (const_string "normal")) (define_attr "write_conflict" "no,yes" @@ -123,8 +133,40 @@ ;; (define_function_unit {name} {num-units} {n-users} {test} ;; {ready-delay} {issue-delay} [{conflict-list}]) -;; This is not well tuned, but I don't have all the details. -(define_function_unit "fpa" 1 1 (eq_attr "type" "float") 5 0) +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "fdivx")) 71 69) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "fdivd")) 59 57) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "fdivs")) 31 29) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "fmul")) 9 7) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "ffmul")) 6 4) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "farith")) 4 2) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "ffarith")) 2 2) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "r_2_f")) 5 3) + +(define_function_unit "fpa" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "f_2_r")) 1 2) + +;; The fpa10 doesn't really have a memory read unit, but it can start to +;; speculatively execute the instruction in the pipeline, provided the data +;; is already loaded, so pretend reads have a delay of 2 (and that the +;; pipeline is infinite. + +(define_function_unit "fpa_mem" 1 0 (and (eq_attr "fpu" "fpa") + (eq_attr "type" "f_load")) 3 1) (define_function_unit "write_buf" 1 2 (eq_attr "type" "store1") 3 3 [(eq_attr "write_conflict" "yes")]) @@ -149,12 +191,9 @@ (match_operand:DI 2 "s_register_operand" "r,0"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"adds\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"adc\\t%R0, %R1, %R2\", operands)); -" + "adds\\t%0, %1, %2\;adc\\t%R0, %R1, %R2" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -163,12 +202,9 @@ (match_operand:DI 2 "s_register_operand" "r,0"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"adds\\t%0, %2, %1\", operands); - return (arm_output_asm_insn (\"adc\\t%R0, %R2, %1, asr #31\", operands)); -" + "adds\\t%0, %2, %1\;adc\\t%R0, %R2, %1, asr #31" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -177,63 +213,74 @@ (match_operand:DI 2 "s_register_operand" "r,0"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"adds\\t%0, %2, %1\", operands); - return (arm_output_asm_insn (\"adc\\t%R0, %R2, #0\", operands)); -" + "adds\\t%0, %2, %1\;adc\\t%R0, %R2, #0" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) -(define_insn "addsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (plus:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_add_operand" "rL")))] +(define_expand "addsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (plus:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "reg_or_int_operand" "")))] "" - "* - if (GET_CODE (operands[2]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[2]))) + " + if (GET_CODE (operands[2]) == CONST_INT) { - operands[2] = gen_rtx (CONST_INT, VOIDmode, -INTVAL (operands[2])); - return arm_output_asm_insn (\"sub\\t%0, %1, %2\", operands); + arm_split_constant (PLUS, SImode, INTVAL (operands[2]), operands[0], + operands[1], + (reload_in_progress || reload_completed ? 0 + : preserve_subexpressions_p ())); + DONE; } - return arm_output_asm_insn (\"add\\t%0, %1, %2\", operands); ") +(define_split + [(set (match_operand:SI 0 "s_register_operand" "") + (plus:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "const_int_operand" "")))] + "! (const_ok_for_arm (INTVAL (operands[2])) + || const_ok_for_arm (-INTVAL (operands[2])))" + [(clobber (const_int 0))] + " + arm_split_constant (PLUS, SImode, INTVAL (operands[2]), operands[0], + operands[1], 0); + DONE; +") + +(define_insn "" + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") + (plus:SI (match_operand:SI 1 "s_register_operand" "r,r,r") + (match_operand:SI 2 "reg_or_int_operand" "rI,L,?n")))] + "" + "@ + add%?\\t%0, %1, %2 + sub%?\\t%0, %1, #%n2 + #" +[(set_attr "length" "4,4,16")]) + (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (plus:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_add_operand" "rL")) - (const_int 0))) - (set (match_operand:SI 0 "s_register_operand" "=r") + (compare:CC_NOOV + (plus:SI (match_operand:SI 1 "s_register_operand" "r,r") + (match_operand:SI 2 "arm_add_operand" "rI,L")) + (const_int 0))) + (set (match_operand:SI 0 "s_register_operand" "=r,r") (plus:SI (match_dup 1) (match_dup 2)))] "" - "* - if (GET_CODE (operands[2]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[2]))) - { - operands[2] = gen_rtx (CONST_INT, VOIDmode, -INTVAL (operands[2])); - return arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - } - return (arm_output_asm_insn (\"adds\\t%0, %1, %2\", operands)); -" + "@ + add%?s\\t%0, %1, %2 + sub%?s\\t%0, %1, #%n2" [(set_attr "conds" "set")]) (define_insn "" [(set (reg:CC 24) - (compare:CC (match_operand:SI 1 "s_register_operand" "r") - (neg:SI (match_operand:SI 2 "arm_add_operand" "rL")))) - (set (match_operand:SI 0 "s_register_operand" "=r") + (compare:CC (match_operand:SI 1 "s_register_operand" "r,r") + (neg:SI (match_operand:SI 2 "arm_add_operand" "rI,L")))) + (set (match_operand:SI 0 "s_register_operand" "=r,r") (plus:SI (match_dup 1) (match_dup 2)))] "" - "* - if (GET_CODE (operands[2]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[2]))) - { - operands[2] = gen_rtx (CONST_INT, VOIDmode, -INTVAL (operands[2])); - return arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - } - return (arm_output_asm_insn (\"adds\\t%0, %1, %2\", operands)); -" + "@ + add%?s\\t%0, %1, %2 + sub%?s\\t%0, %1, #%n2" [(set_attr "conds" "set")]) (define_insn "incscc" @@ -242,13 +289,11 @@ [(reg 24) (const_int 0)]) (match_operand:SI 1 "s_register_operand" "0,?r")))] "" - "* - if (which_alternative == 1) - arm_output_asm_insn (\"mov%D2\\t%0, %1\", operands); - return arm_output_asm_insn (\"add%d2\\t%0, %1, #1\", operands); -" + "@ + add%d2\\t%0, %1, #1 + mov%D2\\t%0, %1\;add%d2\\t%0, %1, #1" [(set_attr "conds" "use") - (set_attr "length" "*,2")]) + (set_attr "length" "4,8")]) ; If a constant is too big to fit in a single instruction then the constant ; will be pre-loaded into a register taking at least two insns, we might be @@ -311,46 +356,20 @@ (plus:SF (match_operand:SF 1 "s_register_operand" "f,f") (match_operand:SF 2 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"adfs\\t%0, %1, %2\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[2]); - r = REAL_VALUE_NEGATE (r); - operands[2] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[2])); - return arm_output_asm_insn (\"sufs\\t%0, %1, %2\", operands); - } -} -" -[(set_attr "type" "float")]) + "@ + adf%?s\\t%0, %1, %2 + suf%?s\\t%0, %1, #%N2" +[(set_attr "type" "farith")]) (define_insn "adddf3" [(set (match_operand:DF 0 "s_register_operand" "=f,f") (plus:DF (match_operand:DF 1 "s_register_operand" "f,f") (match_operand:DF 2 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"adfd\\t%0, %1, %2\", operands)); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[2]); - r = REAL_VALUE_NEGATE (r); - operands[2] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[2])); - return arm_output_asm_insn (\"sufd\\t%0, %1, %2\", operands); - } -} -" -[(set_attr "type" "float")]) + "@ + adf%?d\\t%0, %1, %2 + suf%?d\\t%0, %1, #%N2" +[(set_attr "type" "farith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f,f") @@ -358,23 +377,10 @@ (match_operand:SF 1 "s_register_operand" "f,f")) (match_operand:DF 2 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"adfd\\t%0, %1, %2\", operands)); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[2]); - r = REAL_VALUE_NEGATE (r); - operands[2] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[2])); - return arm_output_asm_insn (\"sufd\\t%0, %1, %2\", operands); - } -} -" -[(set_attr "type" "float")]) + "@ + adf%?d\\t%0, %1, %2 + suf%?d\\t%0, %1, #%N2" +[(set_attr "type" "farith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -382,10 +388,8 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"adfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "adf%?d\\t%0, %1, %2" +[(set_attr "type" "farith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -394,33 +398,18 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"adfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "adf%?d\\t%0, %1, %2" +[(set_attr "type" "farith")]) (define_insn "addxf3" [(set (match_operand:XF 0 "s_register_operand" "=f,f") (plus:XF (match_operand:XF 1 "s_register_operand" "f,f") (match_operand:XF 2 "fpu_add_operand" "fG,H")))] "ENABLE_XF_PATTERNS" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"adfe\\t%0, %1, %2\", operands)); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[2]); - r = REAL_VALUE_NEGATE (r); - operands[2] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[2])); - return arm_output_asm_insn (\"sufe\\t%0, %1, %2\", operands); - } -} -" -[(set_attr "type" "float")]) + "@ + adf%?e\\t%0, %1, %2 + suf%?e\\t%0, %1, #%N2" +[(set_attr "type" "farith")]) (define_insn "subdi3" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r,&r") @@ -428,12 +417,9 @@ (match_operand:DI 2 "s_register_operand" "r,0,0"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"sbc\\t%R0, %R1, %R2\", operands)); -" + "subs\\t%0, %1, %2\;sbc\\t%R0, %R1, %R2" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -442,12 +428,9 @@ (match_operand:SI 2 "s_register_operand" "r,r")))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"sbc\\t%R0, %R1, #0\", operands)); -" + "subs\\t%0, %1, %2\;sbc\\t%R0, %R1, #0" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -456,12 +439,9 @@ (match_operand:SI 2 "s_register_operand" "r,r")))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"sbc\\t%R0, %R1, %2, asr #31\", operands)); -" + "subs\\t%0, %1, %2\;sbc\\t%R0, %R1, %2, asr #31" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -470,12 +450,9 @@ (match_operand:DI 1 "s_register_operand" "?r,0"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"rsbs\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"rsc\\t%R0, %R1, #0\", operands)); -" + "rsbs\\t%0, %1, %2\;rsc\\t%R0, %R1, #0" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -484,12 +461,9 @@ (match_operand:DI 1 "s_register_operand" "?r,0"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"rsbs\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"rsc\\t%R0, %R1, %2, asr #31\", operands)); -" + "rsbs\\t%0, %1, %2\;rsc\\t%R0, %R1, %2, asr #31" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=r") @@ -499,30 +473,49 @@ (match_operand:SI 2 "s_register_operand" "r")))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"rsc\\t%R0, %1, %1 @ extend carry\", - operands)); -" + "subs\\t%0, %1, %2\;rsc\\t%R0, %1, %1" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) -(define_insn "subsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (minus:SI (match_operand:SI 1 "arm_rhs_operand" "r,I") - (match_operand:SI 2 "arm_rhs_operand" "rI,r")))] +(define_expand "subsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (minus:SI (match_operand:SI 1 "reg_or_int_operand" "") + (match_operand:SI 2 "s_register_operand" "")))] "" - "* - switch (which_alternative) + " + if (GET_CODE (operands[1]) == CONST_INT) { - case 0: - return (arm_output_asm_insn (\"sub\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rsb\\t%0, %2, %1\", operands)); + arm_split_constant (MINUS, SImode, INTVAL (operands[1]), operands[0], + operands[2], + (reload_in_progress || reload_completed ? 0 + : preserve_subexpressions_p ())); + DONE; } ") (define_insn "" + [(set (match_operand:SI 0 "s_register_operand" "=r,r") + (minus:SI (match_operand:SI 1 "reg_or_int_operand" "rI,?n") + (match_operand:SI 2 "s_register_operand" "r,r")))] + "" + "@ + rsb%?\\t%0, %2, %1 + #" +[(set_attr "length" "4,16")]) + +(define_split + [(set (match_operand:SI 0 "s_register_operand" "") + (minus:SI (match_operand:SI 1 "const_int_operand" "") + (match_operand:SI 2 "s_register_operand" "")))] + "! const_ok_for_arm (INTVAL (operands[1]))" + [(clobber (const_int 0))] + " + arm_split_constant (MINUS, SImode, INTVAL (operands[1]), operands[0], + operands[2], 0); + DONE; +") + +(define_insn "" [(set (reg:CC_NOOV 24) (compare:CC_NOOV (minus:SI (match_operand:SI 1 "arm_rhs_operand" "r,I") (match_operand:SI 2 "arm_rhs_operand" "rI,r")) @@ -530,15 +523,9 @@ (set (match_operand:SI 0 "s_register_operand" "=r,r") (minus:SI (match_dup 1) (match_dup 2)))] "" - "* - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - case 1: - return arm_output_asm_insn (\"rsbs\\t%0, %2, %1\", operands); - } -" + "@ + sub%?s\\t%0, %1, %2 + rsb%?s\\t%0, %2, %1" [(set_attr "conds" "set")]) (define_insn "decscc" @@ -547,45 +534,31 @@ (match_operator:SI 2 "comparison_operator" [(reg 24) (const_int 0)])))] "" - "* - if (which_alternative == 1) - arm_output_asm_insn (\"mov%D2\\t%0, %1\", operands); - return arm_output_asm_insn (\"sub%d2\\t%0, %1, #1\", operands); -" + "@ + sub%d2\\t%0, %1, #1 + mov%D2\\t%0, %1\;sub%d2\\t%0, %1, #1" [(set_attr "conds" "use") - (set_attr "length" "*,2")]) + (set_attr "length" "*,8")]) (define_insn "subsf3" [(set (match_operand:SF 0 "s_register_operand" "=f,f") (minus:SF (match_operand:SF 1 "fpu_rhs_operand" "f,G") (match_operand:SF 2 "fpu_rhs_operand" "fG,f")))] "" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"sufs\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rsfs\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + suf%?s\\t%0, %1, %2 + rsf%?s\\t%0, %2, %1" +[(set_attr "type" "farith")]) (define_insn "subdf3" [(set (match_operand:DF 0 "s_register_operand" "=f,f") (minus:DF (match_operand:DF 1 "fpu_rhs_operand" "f,G") (match_operand:DF 2 "fpu_rhs_operand" "fG,f")))] "" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"sufd\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rsfd\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + suf%?d\\t%0, %1, %2 + rsf%?d\\t%0, %2, %1" +[(set_attr "type" "farith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -593,10 +566,8 @@ (match_operand:SF 1 "s_register_operand" "f")) (match_operand:DF 2 "fpu_rhs_operand" "fG")))] "" - "* - return arm_output_asm_insn (\"sufd\\t%0, %1, %2\", operands); -" -[(set_attr "type" "float")]) + "suf%?d\\t%0, %1, %2" +[(set_attr "type" "farith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f,f") @@ -604,16 +575,10 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f,f"))))] "" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"sufd\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rsfd\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + suf%?d\\t%0, %1, %2 + rsf%?d\\t%0, %2, %1" +[(set_attr "type" "farith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -622,26 +587,18 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return arm_output_asm_insn (\"sufd\\t%0, %1, %2\", operands); -" -[(set_attr "type" "float")]) + "suf%?d\\t%0, %1, %2" +[(set_attr "type" "farith")]) (define_insn "subxf3" [(set (match_operand:XF 0 "s_register_operand" "=f,f") (minus:XF (match_operand:XF 1 "fpu_rhs_operand" "f,G") (match_operand:XF 2 "fpu_rhs_operand" "fG,f")))] "ENABLE_XF_PATTERNS" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"sufe\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rsfe\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + suf%?e\\t%0, %1, %2 + rsf%?e\\t%0, %2, %1" +[(set_attr "type" "farith")]) ;; Multiplication insns @@ -651,9 +608,7 @@ (mult:SI (match_operand:SI 2 "s_register_operand" "r,r") (match_operand:SI 1 "s_register_operand" "%?r,0")))] "" - "* - return (arm_output_asm_insn (\"mul\\t%0, %2, %1\", operands)); -") + "mul%?\\t%0, %2, %1") (define_insn "" [(set (reg:CC_NOOV 24) @@ -664,9 +619,7 @@ (set (match_operand:SI 0 "s_register_operand" "=&r,&r") (mult:SI (match_dup 2) (match_dup 1)))] "" - "* - return (arm_output_asm_insn (\"muls\\t%0, %2, %1\", operands)); -" + "mul%?s\\t%0, %2, %1" [(set_attr "conds" "set")]) (define_insn "" @@ -677,9 +630,7 @@ (const_int 0))) (clobber (match_scratch:SI 0 "=&r,&r"))] "" - "* - return (arm_output_asm_insn (\"muls\\t%0, %2, %1\", operands)); -" + "mul%?s\\t%0, %2, %1" [(set_attr "conds" "set")]) ;; Unnamed templates to match MLA instruction. @@ -691,9 +642,7 @@ (match_operand:SI 1 "s_register_operand" "%r,0,r,0")) (match_operand:SI 3 "s_register_operand" "?r,r,0,0")))] "" - "* - return (arm_output_asm_insn (\"mla\\t%0, %2, %1, %3\", operands)); -") + "mla%?\\t%0, %2, %1, %3") (define_insn "" [(set (reg:CC_NOOV 24) @@ -707,9 +656,7 @@ (plus:SI (mult:SI (match_dup 2) (match_dup 1)) (match_dup 3)))] "" - "* - return (arm_output_asm_insn (\"mlas\\t%0, %2, %1, %3\", operands)); -" + "mla%?s\\t%0, %2, %1, %3" [(set_attr "conds" "set")]) (define_insn "" @@ -722,9 +669,7 @@ (const_int 0))) (clobber (match_scratch:SI 0 "=&r,&r,&r,&r"))] "" - "* - return (arm_output_asm_insn (\"mlas\\t%0, %2, %1, %3\", operands)); -" + "mla%?s\\t%0, %2, %1, %3" [(set_attr "conds" "set")]) (define_insn "mulsf3" @@ -732,20 +677,16 @@ (mult:SF (match_operand:SF 1 "s_register_operand" "f") (match_operand:SF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"fmls\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "fml%?s\\t%0, %1, %2" +[(set_attr "type" "ffmul")]) (define_insn "muldf3" [(set (match_operand:DF 0 "s_register_operand" "=f") (mult:DF (match_operand:DF 1 "s_register_operand" "f") (match_operand:DF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"mufd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "muf%?d\\t%0, %1, %2" +[(set_attr "type" "fmul")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -753,10 +694,8 @@ (match_operand:SF 1 "s_register_operand" "f")) (match_operand:DF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"mufd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "muf%?d\\t%0, %1, %2" +[(set_attr "type" "fmul")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -764,10 +703,8 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"mufd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "muf%?d\\t%0, %1, %2" +[(set_attr "type" "fmul")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -776,20 +713,16 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"mufd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "muf%?d\\t%0, %1, %2" +[(set_attr "type" "fmul")]) (define_insn "mulxf3" [(set (match_operand:XF 0 "s_register_operand" "=f") (mult:XF (match_operand:XF 1 "s_register_operand" "f") (match_operand:XF 2 "fpu_rhs_operand" "fG")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"mufe\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "muf%?e\\t%0, %1, %2" +[(set_attr "type" "fmul")]) ;; Division insns @@ -798,32 +731,20 @@ (div:SF (match_operand:SF 1 "fpu_rhs_operand" "f,G") (match_operand:SF 2 "fpu_rhs_operand" "fG,f")))] "" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"fdvs\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"frds\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + fdv%?s\\t%0, %1, %2 + frd%?s\\t%0, %2, %1" +[(set_attr "type" "fdivs")]) (define_insn "divdf3" [(set (match_operand:DF 0 "s_register_operand" "=f,f") (div:DF (match_operand:DF 1 "fpu_rhs_operand" "f,G") (match_operand:DF 2 "fpu_rhs_operand" "fG,f")))] "" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"dvfd\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rdfd\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + dvf%?d\\t%0, %1, %2 + rdf%?d\\t%0, %2, %1" +[(set_attr "type" "fdivd")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -831,10 +752,8 @@ (match_operand:SF 1 "s_register_operand" "f")) (match_operand:DF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"dvfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "dvf%?d\\t%0, %1, %2" +[(set_attr "type" "fdivd")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -842,10 +761,8 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"rdfd\\t%0, %2, %1\", operands)); -" -[(set_attr "type" "float")]) + "rdf%?d\\t%0, %2, %1" +[(set_attr "type" "fdivd")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -854,26 +771,18 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"dvfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "dvf%?d\\t%0, %1, %2" +[(set_attr "type" "fdivd")]) (define_insn "divxf3" [(set (match_operand:XF 0 "s_register_operand" "=f,f") (div:XF (match_operand:XF 1 "fpu_rhs_operand" "f,G") (match_operand:XF 2 "fpu_rhs_operand" "fG,f")))] "ENABLE_XF_PATTERNS" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"dvfe\\t%0, %1, %2\", operands)); - case 1: - return (arm_output_asm_insn (\"rdfe\\t%0, %2, %1\", operands)); - } -" -[(set_attr "type" "float")]) + "@ + dvf%?e\\t%0, %1, %2 + rdf%?e\\t%0, %2, %1" +[(set_attr "type" "fdivx")]) ;; Modulo insns @@ -882,20 +791,16 @@ (mod:SF (match_operand:SF 1 "s_register_operand" "f") (match_operand:SF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"rmfs\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "rmf%?s\\t%0, %1, %2" +[(set_attr "type" "fdivs")]) (define_insn "moddf3" [(set (match_operand:DF 0 "s_register_operand" "=f") (mod:DF (match_operand:DF 1 "s_register_operand" "f") (match_operand:DF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"rmfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "rmf%?d\\t%0, %1, %2" +[(set_attr "type" "fdivd")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -903,10 +808,8 @@ (match_operand:SF 1 "s_register_operand" "f")) (match_operand:DF 2 "fpu_rhs_operand" "fG")))] "" - "* - return (arm_output_asm_insn (\"rmfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "rmf%?d\\t%0, %1, %2" +[(set_attr "type" "fdivd")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -914,10 +817,8 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"rmfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "rmf%?d\\t%0, %1, %2" +[(set_attr "type" "fdivd")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") @@ -926,20 +827,16 @@ (float_extend:DF (match_operand:SF 2 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"rmfd\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "rmf%?d\\t%0, %1, %2" +[(set_attr "type" "fdivd")]) (define_insn "modxf3" [(set (match_operand:XF 0 "s_register_operand" "=f") (mod:XF (match_operand:XF 1 "s_register_operand" "f") (match_operand:XF 2 "fpu_rhs_operand" "fG")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"rmfe\\t%0, %1, %2\", operands)); -" -[(set_attr "type" "float")]) + "rmf%?e\\t%0, %1, %2" +[(set_attr "type" "fdivx")]) ;; Boolean and,ior,xor insns @@ -948,11 +845,8 @@ (and:DI (match_operand:DI 1 "s_register_operand" "%0,0") (match_operand:DI 2 "s_register_operand" "r,0")))] "" - "* - arm_output_asm_insn (\"and\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"and\\t%R0, %R1, %R2\", operands)); -" -[(set_attr "length" "2")]) + "and%?\\t%0, %1, %2\;and%?\\t%R0, %R1, %R2" +[(set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -960,11 +854,8 @@ (match_operand:SI 2 "s_register_operand" "r,r")) (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"and\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"mov\\t%R0, #0\", operands); -" -[(set_attr "length" "2")]) + "and%?\\t%0, %1, %2\;mov%?\\t%R0, #0" +[(set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -972,68 +863,74 @@ (match_operand:SI 2 "s_register_operand" "r,r")) (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"and\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"and\\t%R0, %R1, %2, asr #31\", operands); -" -[(set_attr "length" "2")]) + "and%?\\t%0, %1, %2\;and%?\\t%R0, %R1, %2, asr #31" +[(set_attr "length" "8")]) -(define_insn "andsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (and:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_not_operand" "rK")))] +(define_expand "andsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (and:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "reg_or_int_operand" "")))] "" - "* - if (GET_CODE (operands[2]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[2]))) + " + if (GET_CODE (operands[2]) == CONST_INT) { - operands[2] = gen_rtx (CONST_INT, VOIDmode, ~INTVAL (operands[2])); - return arm_output_asm_insn (\"bic\\t%0, %1, %2\", operands); + arm_split_constant (AND, SImode, INTVAL (operands[2]), operands[0], + operands[1], + (reload_in_progress || reload_completed + ? 0 : preserve_subexpressions_p ())); + DONE; } - return arm_output_asm_insn (\"and\\t%0, %1, %2\", operands); ") (define_insn "" - [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (and:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_not_operand" "rK")) - (const_int 0))) - (set (match_operand:SI 0 "s_register_operand" "=r") - (and:SI (match_dup 1) (match_dup 2)))] + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") + (and:SI (match_operand:SI 1 "s_register_operand" "r,r,r") + (match_operand:SI 2 "reg_or_int_operand" "rI,K,?n")))] "" - "* - if (GET_CODE (operands[2]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[2]))) - { - operands[2] = gen_rtx (CONST_INT, VOIDmode, ~INTVAL (operands[2])); - return arm_output_asm_insn (\"bics\\t%0, %1, %2\", operands); - } - return arm_output_asm_insn (\"ands\\t%0, %1, %2\", operands); -" -[(set_attr "conds" "set")]) + "@ + and%?\\t%0, %1, %2 + bic%?\\t%0, %1, #%B2 + #" +[(set_attr "length" "4,4,16")]) + +(define_split + [(set (match_operand:SI 0 "s_register_operand" "") + (and:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "const_int_operand" "")))] + "! (const_ok_for_arm (INTVAL (operands[2])) + || const_ok_for_arm (~ INTVAL (operands[2])))" + [(clobber (const_int 0))] + " + arm_split_constant (AND, SImode, INTVAL (operands[2]), operands[0], + operands[1], 0); + DONE; +") (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (and:SI (match_operand:SI 0 "s_register_operand" "r") - (match_operand:SI 1 "arm_rhs_operand" "rI")) - (const_int 0)))] + (compare:CC_NOOV + (and:SI (match_operand:SI 1 "s_register_operand" "r,r") + (match_operand:SI 2 "arm_not_operand" "rI,K")) + (const_int 0))) + (set (match_operand:SI 0 "s_register_operand" "=r,r") + (and:SI (match_dup 1) (match_dup 2)))] "" - "* - return arm_output_asm_insn (\"tst\\t%0, %1\", operands); -" + "@ + and%?s\\t%0, %1, %2 + bic%?s\\t%0, %1, #%B2" [(set_attr "conds" "set")]) (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (and:SI (match_operand:SI 0 "s_register_operand" "r") - (match_operand:SI 1 "immediate_operand" "K")) - (const_int 0))) - (clobber (match_scratch:SI 3 "=r"))] - "const_ok_for_arm (~INTVAL (operands[1]))" - "* - operands[1] = GEN_INT (~INTVAL (operands[1])); - return arm_output_asm_insn (\"bics\\t%3, %0, %1\", operands); -" + (compare:CC_NOOV + (and:SI (match_operand:SI 0 "s_register_operand" "r,r") + (match_operand:SI 1 "arm_not_operand" "rI,K")) + (const_int 0))) + (clobber (match_scratch:SI 3 "=X,r"))] + "" + "@ + tst%?\\t%0, %1 + bic%?s\\t%3, %0, #%B1" [(set_attr "conds" "set")]) (define_insn "" @@ -1054,8 +951,9 @@ while (cnt--) mask = (mask << 1) | 1; - operands[1] = gen_rtx (CONST_INT, VOIDmode, mask << INTVAL (operands[2])); - return arm_output_asm_insn (\"tst\\t%0, %1\", operands); + operands[1] = GEN_INT (mask << INTVAL (operands[2])); + output_asm_insn (\"tst%?\\t%0, %1\", operands); + return \"\"; } " [(set_attr "conds" "set")]) @@ -1077,13 +975,14 @@ while (cnt--) mask = (mask << 1) | 1; - operands[1] = gen_rtx (CONST_INT, VOIDmode, mask << INTVAL (operands[2])); - arm_output_asm_insn (\"ldrb\\t%3, %0\", operands); - return arm_output_asm_insn (\"tst\\t%3, %1\", operands); + operands[1] = GEN_INT (mask << INTVAL (operands[2])); + output_asm_insn (\"ldr%?b\\t%3, %0\", operands); + output_asm_insn (\"tst%?\\t%3, %1\", operands); + return \"\"; } " [(set_attr "conds" "set") - (set_attr "length" "2")]) + (set_attr "length" "8")]) ;; constants for op 2 will never be given to these patterns. (define_insn "" @@ -1091,25 +990,19 @@ (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "r,0")) (match_operand:DI 1 "s_register_operand" "0,r")))] "" - "* - arm_output_asm_insn (\"bic\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"bic\\t%R0, %R1, %R2\", operands); -" -[(set_attr "length" "2")]) + "bic%?\\t%0, %1, %2\;bic%?\\t%R0, %R1, %R2" +[(set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") (and:DI (not:DI (zero_extend:DI (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "?r,0")))] + (match_operand:DI 1 "s_register_operand" "0,?r")))] "" - "* - arm_output_asm_insn (\"bic\\t%0, %1, %2\", operands); - if (REGNO (operands[1]) != REGNO (operands[0])) - return arm_output_asm_insn (\"mov\\t%R0, %R1\", operands); - return \"\"; -" -[(set_attr "length" "2,1")]) + "@ + bic%?\\t%0, %1, %2 + bic%?\\t%0, %1, %2\;mov%?\\t%R0, %R1" +[(set_attr "length" "4,8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -1117,46 +1010,37 @@ (match_operand:SI 2 "s_register_operand" "r,r"))) (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"bic\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"bic\\t%R0, %R1, %2, asr #31\", operands); -" -[(set_attr "length" "2")]) + "bic%?\\t%0, %1, %2\;bic%?\\t%R0, %R1, %2, asr #31" +[(set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) (match_operand:SI 1 "s_register_operand" "r")))] "" - "* - return (arm_output_asm_insn (\"bic\\t%0, %1, %2\", operands)); -") + "bic%?\\t%0, %1, %2") (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (and:SI - (not:SI (match_operand:SI 2 "s_register_operand" "r")) - (match_operand:SI 1 "s_register_operand" "r")) - (const_int 0))) + (compare:CC_NOOV + (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) + (match_operand:SI 1 "s_register_operand" "r")) + (const_int 0))) (set (match_operand:SI 0 "s_register_operand" "=r") (and:SI (not:SI (match_dup 2)) (match_dup 1)))] "" - "* - return (arm_output_asm_insn (\"bics\\t%0, %1, %2\", operands)); -" + "bic%?s\\t%0, %1, %2" [(set_attr "conds" "set")]) (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (and:SI - (not:SI (match_operand:SI 2 "s_register_operand" "r")) - (match_operand:SI 1 "s_register_operand" "r")) - (const_int 0))) + (compare:CC_NOOV + (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) + (match_operand:SI 1 "s_register_operand" "r")) + (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* - return (arm_output_asm_insn (\"bics\\t%0, %1, %2\", operands)); -" + "bic%?s\\t%0, %1, %2" [(set_attr "conds" "set")]) (define_insn "iordi3" @@ -1164,25 +1048,19 @@ (ior:DI (match_operand:DI 1 "s_register_operand" "%0") (match_operand:DI 2 "s_register_operand" "r")))] "" - "* - arm_output_asm_insn (\"orr\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"orr\\t%R0, %R1, %R2\", operands)); -" -[(set_attr "length" "2")]) + "orr%?\\t%0, %1, %2\;orr%?\\t%R0, %R1, %R2" +[(set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") (ior:DI (zero_extend:DI (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "?r,0")))] + (match_operand:DI 1 "s_register_operand" "0,?r")))] "" - "* - arm_output_asm_insn (\"orr\\t%0, %1, %2\", operands); - if (REGNO (operands[0]) != REGNO (operands[1])) - return (arm_output_asm_insn (\"mov\\t%R0, %R1\", operands)); - return \"\"; -" -[(set_attr "length" "2,1")]) + "@ + orr%?\\t%0, %1, %2 + orr%?\\t%0, %1, %2\;mov%?\\t%R0, %R1" +[(set_attr "length" "4,8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -1190,22 +1068,48 @@ (match_operand:SI 2 "s_register_operand" "r,r")) (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"orr\\t%0, %1, %2\", operands); - return (arm_output_asm_insn (\"orr\\t%R0, %R1, %2, asr #31\", operands)); -" -[(set_attr "length" "2")]) + "orr%?\\t%0, %1, %2\;orr%?\\t%R0, %R1, %2, asr #31" +[(set_attr "length" "8")]) -(define_insn "iorsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (ior:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rI")))] +(define_expand "iorsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (ior:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "reg_or_int_operand" "")))] "" - "* - return (arm_output_asm_insn (\"orr\\t%0, %1, %2\", operands)); + " + if (GET_CODE (operands[2]) == CONST_INT) + { + arm_split_constant (IOR, SImode, INTVAL (operands[2]), operands[0], + operands[1], + (reload_in_progress || reload_completed + ? 0 : preserve_subexpressions_p ())); + DONE; + } ") (define_insn "" + [(set (match_operand:SI 0 "s_register_operand" "=r,r") + (ior:SI (match_operand:SI 1 "s_register_operand" "r,r") + (match_operand:SI 2 "reg_or_int_operand" "rI,?n")))] + "" + "@ + orr%?\\t%0, %1, %2 + #" +[(set_attr "length" "4,16")]) + +(define_split + [(set (match_operand:SI 0 "s_register_operand" "") + (ior:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "const_int_operand" "")))] + "! const_ok_for_arm (INTVAL (operands[2]))" + [(clobber (const_int 0))] + " + arm_split_constant (IOR, SImode, INTVAL (operands[2]), operands[0], + operands[1], 0); + DONE; +") + +(define_insn "" [(set (reg:CC_NOOV 24) (compare:CC_NOOV (ior:SI (match_operand:SI 1 "s_register_operand" "%r") (match_operand:SI 2 "arm_rhs_operand" "rI")) @@ -1213,9 +1117,7 @@ (set (match_operand:SI 0 "s_register_operand" "=r") (ior:SI (match_dup 1) (match_dup 2)))] "" - "* - return arm_output_asm_insn (\"orrs\\t%0, %1, %2\", operands); -" + "orr%?s\\t%0, %1, %2" [(set_attr "conds" "set")]) (define_insn "" @@ -1225,9 +1127,7 @@ (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* - return arm_output_asm_insn (\"orrs\\t%0, %1, %2\", operands); -" + "orr%?s\\t%0, %1, %2" [(set_attr "conds" "set")]) (define_insn "xordi3" @@ -1235,25 +1135,19 @@ (xor:DI (match_operand:DI 1 "s_register_operand" "%0,0") (match_operand:DI 2 "s_register_operand" "r,0")))] "" - "* - arm_output_asm_insn (\"eor\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"eor\\t%R0, %R1, %R2\", operands); -" -[(set_attr "length" "2")]) + "eor%?\\t%0, %1, %2\;eor%?\\t%R0, %R1, %R2" +[(set_attr "length" "8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") (xor:DI (zero_extend:DI (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "?r,0")))] + (match_operand:DI 1 "s_register_operand" "0,?r")))] "" - "* - arm_output_asm_insn (\"eor\\t%0, %1, %2\", operands); - if (REGNO (operands[0]) != REGNO (operands[1])) - return arm_output_asm_insn (\"mov\\t%R0, %R1\", operands); - return \"\"; -" -[(set_attr "length" "2,1")]) + "@ + eor%?\\t%0, %1, %2 + eor%?\\t%0, %1, %2\;mov%?\\t%R0, %R1" +[(set_attr "length" "4,8")]) (define_insn "" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") @@ -1261,20 +1155,15 @@ (match_operand:SI 2 "s_register_operand" "r,r")) (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"eor\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"eor\\t%R0, %R1, %2, asr #31\", operands); -" -[(set_attr "length" "2")]) + "eor%?\\t%0, %1, %2\;eor%?\\t%R0, %R1, %2, asr #31" +[(set_attr "length" "8")]) (define_insn "xorsi3" [(set (match_operand:SI 0 "s_register_operand" "=r") (xor:SI (match_operand:SI 1 "s_register_operand" "r") (match_operand:SI 2 "arm_rhs_operand" "rI")))] "" - "* - return (arm_output_asm_insn (\"eor\\t%0, %1, %2\", operands)); -") + "eor%?\\t%0, %1, %2") (define_insn "" [(set (reg:CC_NOOV 24) @@ -1284,9 +1173,7 @@ (set (match_operand:SI 0 "s_register_operand" "=r") (xor:SI (match_dup 1) (match_dup 2)))] "" - "* - return arm_output_asm_insn (\"eors\\t%0, %1, %2\", operands); -" + "eor%?s\\t%0, %1, %2" [(set_attr "conds" "set")]) (define_insn "" @@ -1295,9 +1182,7 @@ (match_operand:SI 1 "arm_rhs_operand" "rI")) (const_int 0)))] "" - "* - return arm_output_asm_insn (\"teq\\t%0, %1\", operands); -" + "teq%?\\t%0, %1" [(set_attr "conds" "set")]) ;; by splitting (IOR (AND (NOT A) (NOT B)) C) as D = AND (IOR A B) (NOT C), @@ -1323,11 +1208,8 @@ (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI")) (not:SI (match_operand:SI 3 "arm_rhs_operand" "rI,rI,rI"))))] "" - "* - arm_output_asm_insn (\"orr\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"bic\\t%0, %0, %3\", operands); -" -[(set_attr "length" "2")]) + "orr%?\\t%0, %1, %2\;bic%?\\t%0, %0, %3" +[(set_attr "length" "8")]) @@ -1339,16 +1221,12 @@ (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"cmp\\t%1, %2\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"movge\\t%0, %1\", operands); - if (which_alternative != 1) - return arm_output_asm_insn (\"movlt\\t%0, %2\", operands); - return \"\"; -" + "@ + cmp\\t%1, %2\;movlt\\t%0, %2 + cmp\\t%1, %2\;movge\\t%0, %1 + cmp\\t%1, %2\;movge\\t%0, %1\;movlt\\t%0, %2" [(set_attr "conds" "clob") - (set_attr "length" "2,2,3")]) + (set_attr "length" "8,8,12")]) (define_insn "sminsi3" [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") @@ -1356,16 +1234,12 @@ (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"cmp\\t%1, %2\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"movle\\t%0, %1\", operands); - if (which_alternative != 1) - return arm_output_asm_insn (\"movgt\\t%0, %2\", operands); - return \"\"; -" + "@ + cmp\\t%1, %2\;movge\\t%0, %2 + cmp\\t%1, %2\;movlt\\t%0, %1 + cmp\\t%1, %2\;movlt\\t%0, %1\;movge\\t%0, %2" [(set_attr "conds" "clob") - (set_attr "length" "2,2,3")]) + (set_attr "length" "8,8,12")]) (define_insn "umaxsi3" [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") @@ -1373,16 +1247,12 @@ (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"cmp\\t%1, %2\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"movcs\\t%0, %1\", operands); - if (which_alternative != 1) - return arm_output_asm_insn (\"movcc\\t%0, %2\", operands); - return \"\"; -" + "@ + cmp\\t%1, %2\;movcc\\t%0, %2 + cmp\\t%1, %2\;movcs\\t%0, %1 + cmp\\t%1, %2\;movcs\\t%0, %1\;movcc\\t%0, %2" [(set_attr "conds" "clob") - (set_attr "length" "2,2,3")]) + (set_attr "length" "8,8,12")]) (define_insn "uminsi3" [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") @@ -1390,16 +1260,12 @@ (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI"))) (clobber (reg:CC 24))] "" - "* - arm_output_asm_insn (\"cmp\\t%1, %2\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"movcc\\t%0, %1\", operands); - if (which_alternative != 1) - return arm_output_asm_insn (\"movcs\\t%0, %2\", operands); - return \"\"; -" + "@ + cmp\\t%1, %2\;movcs\\t%0, %2 + cmp\\t%1, %2\;movcc\\t%0, %1 + cmp\\t%1, %2\;movcc\\t%0, %1\;movcs\\t%0, %2" [(set_attr "conds" "clob") - (set_attr "length" "2,2,3")]) + (set_attr "length" "8,8,12")]) (define_insn "" [(set (match_operand:SI 0 "memory_operand" "=m") @@ -1411,12 +1277,13 @@ "* operands[3] = gen_rtx (minmax_code (operands[3]), SImode, operands[1], operands[2]); - arm_output_asm_insn (\"cmp\\t%1, %2\", operands); - arm_output_asm_insn (\"str%d3\\t%1, %0\", operands); - return arm_output_asm_insn (\"str%D3\\t%2, %0\", operands); + output_asm_insn (\"cmp\\t%1, %2\", operands); + output_asm_insn (\"str%d3\\t%1, %0\", operands); + output_asm_insn (\"str%D3\\t%2, %0\", operands); + return \"\"; " [(set_attr "conds" "clob") - (set_attr "length" "3") + (set_attr "length" "12") (set_attr "type" "store1")]) (define_insn "" @@ -1430,177 +1297,150 @@ "" "* { - char buf[100]; enum rtx_code code = GET_CODE (operands[4]); - char *inst = arithmetic_instr (operands[4], TRUE); operands[5] = gen_rtx (minmax_code (operands[5]), SImode, operands[2], operands[3]); - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); - sprintf (buf, \"%s%%d5\\t%%0, %%1, %%2\", inst); - arm_output_asm_insn (buf, operands); + output_asm_insn (\"cmp\\t%2, %3\", operands); + output_asm_insn (\"%i4%d5\\t%0, %1, %2\", operands); if (which_alternative != 0 || operands[3] != const0_rtx || (code != PLUS && code != MINUS && code != IOR && code != XOR)) - { - sprintf (buf, \"%s%%D5\\t%%0, %%1, %%3\", inst); - return arm_output_asm_insn (buf, operands); - } + output_asm_insn (\"%i4%D5\\t%0, %1, %3\", operands); return \"\"; } " [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) ;; Shift and rotation insns -(define_insn "ashlsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (ashift:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rn")))] +(define_expand "ashlsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (ashift:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "arm_rhs_operand" "")))] "" - "* - return (output_shifted_move (ASHIFT, operands)); + " + if (GET_CODE (operands[2]) == CONST_INT + && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) > 31) + { + emit_insn (gen_movsi (operands[0], const0_rtx)); + DONE; + } ") -(define_insn "ashrsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (ashiftrt:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rn")))] +(define_expand "ashrsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (ashiftrt:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "arm_rhs_operand" "")))] "" - "* - return (output_shifted_move (ASHIFTRT, operands)); + " + if (GET_CODE (operands[2]) == CONST_INT + && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) > 31) + operands[2] = GEN_INT (31); ") -;; lshlsi3 is not defined because shift counts cannot be negative -;; An unnamed pattern is needed for expansion of zero_extend. - -(define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (lshift:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rn")))] +(define_expand "lshrsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (lshiftrt:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "arm_rhs_operand" "")))] "" - "* - return (output_shifted_move (LSHIFT, operands)); + " + if (GET_CODE (operands[2]) == CONST_INT + && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) > 31) + { + emit_insn (gen_movsi (operands[0], const0_rtx)); + DONE; + } ") -(define_insn "lshrsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (lshiftrt:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rn")))] +(define_expand "rotlsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (rotatert:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "reg_or_int_operand" "")))] "" - "* - return (output_shifted_move (LSHIFTRT, operands)); + " + if (GET_CODE (operands[2]) == CONST_INT) + operands[2] = GEN_INT ((32 - INTVAL (operands[2])) % 32); + else + { + rtx reg = gen_reg_rtx (SImode); + emit_insn (gen_subsi3 (reg, GEN_INT (32), operands[2])); + operands[2] = reg; + } ") -;; rotlsi3 is not defined yet to see what happens - -(define_insn "rotrsi3" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (rotatert:SI (match_operand:SI 1 "s_register_operand" "r,r") - (match_operand:SI 2 "arm_rhs_operand" "r,n")))] +(define_expand "rotrsi3" + [(set (match_operand:SI 0 "s_register_operand" "") + (rotatert:SI (match_operand:SI 1 "s_register_operand" "") + (match_operand:SI 2 "arm_rhs_operand" "")))] "" - "* - switch (which_alternative) - { - case 0: - return (arm_output_asm_insn (\"mov\\t%0, %1, ror %2\", operands)); - case 1: - if (INTVAL(operands[2]) > 31) - operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) % 32); - return (arm_output_asm_insn (\"mov\\t%0, %1, ror %2\", operands)); - } + " + if (GET_CODE (operands[2]) == CONST_INT + && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) > 31) + operands[2] = GEN_INT (INTVAL (operands[2]) % 32); ") (define_insn "" + [(set (match_operand:SI 0 "s_register_operand" "=r") + (match_operator:SI 3 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r") + (match_operand:SI 2 "reg_or_int_operand" "rM")]))] + "" + "mov%?\\t%0, %1%S3") + +(define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (match_operator:SI 1 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rn")]) + (compare:CC_NOOV (match_operator:SI 3 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r") + (match_operand:SI 2 "arm_rhs_operand" "rM")]) (const_int 0))) (set (match_operand:SI 0 "s_register_operand" "=r") - (match_op_dup 1 [(match_dup 2) (match_dup 3)]))] + (match_op_dup 3 [(match_dup 1) (match_dup 2)]))] "" - "* -{ - char buf[100]; - - sprintf (buf, \"movs\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[1]), &operands[3])); - return arm_output_asm_insn (buf, operands); -} -" + "mov%?s\\t%0, %1%S3" [(set_attr "conds" "set")]) (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (match_operator:SI 1 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rn")]) + (compare:CC_NOOV (match_operator:SI 3 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r") + (match_operand:SI 2 "arm_rhs_operand" "rM")]) (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* -{ - char buf[100]; - - sprintf (buf, \"movs\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[1]), &operands[3])); - return arm_output_asm_insn (buf, operands); -} -" + "mov%?s\\t%0, %1%S3" [(set_attr "conds" "set")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") - (not:SI (match_operator:SI 1 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rn")])))] + (not:SI (match_operator:SI 3 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r") + (match_operand:SI 2 "arm_rhs_operand" "rM")])))] "" - "* -{ - char buf[100]; - sprintf (buf, \"mvn\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[1]), &operands[3])); - return arm_output_asm_insn (buf, operands); -} -") + "mvn%?\\t%0, %1%S3") (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (not:SI (match_operator:SI 1 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rn")])) + (compare:CC_NOOV (not:SI (match_operator:SI 3 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r") + (match_operand:SI 2 "arm_rhs_operand" "rM")])) (const_int 0))) (set (match_operand:SI 0 "s_register_operand" "=r") - (not:SI (match_op_dup 1 [(match_dup 2) (match_dup 3)])))] + (not:SI (match_op_dup 3 [(match_dup 1) (match_dup 2)])))] "" - "* -{ - char buf[100]; - sprintf (buf, \"mvns\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[1]), &operands[3])); - return arm_output_asm_insn (buf, operands); -} -" + "mvn%?s\\t%0, %1%S3" [(set_attr "conds" "set")]) (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (not:SI (match_operator:SI 1 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rn")])) + (compare:CC_NOOV (not:SI (match_operator:SI 3 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r") + (match_operand:SI 2 "arm_rhs_operand" "rM")])) (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* -{ - char buf[100]; - sprintf (buf, \"mvns\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[1]), &operands[3])); - return arm_output_asm_insn (buf, operands); -} -" + "mvn%?s\\t%0, %1%S3" [(set_attr "conds" "set")]) @@ -1610,57 +1450,44 @@ [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") (neg:DI (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"rsbs\\t%0, %1, #0\", operands); - return (arm_output_asm_insn (\"rsc\\t%R0, %R1, #0\", operands)); -" + "rsbs\\t%0, %1, #0\;rsc\\t%R0, %R1, #0" [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "negsi2" [(set (match_operand:SI 0 "s_register_operand" "=r") (neg:SI (match_operand:SI 1 "s_register_operand" "r")))] "" - "* - return (arm_output_asm_insn (\"rsb\\t%0, %1, #0\", operands)); -") + "rsb%?\\t%0, %1, #0") (define_insn "negsf2" [(set (match_operand:SF 0 "s_register_operand" "=f") (neg:SF (match_operand:SF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"mnfs\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mnf%?s\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "negdf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (neg:DF (match_operand:DF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"mnfd\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mnf%?d\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") (neg:DF (float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"mnfd\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mnf%?d\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "negxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (neg:XF (match_operand:XF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"mnfe\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mnf%?e\\t%0, %1" +[(set_attr "type" "ffarith")]) ;; abssi2 doesn't really clobber the condition codes if a different register ;; is being set. To keep things simple, assume during rtl manipulations that @@ -1672,92 +1499,64 @@ (abs:SI (match_operand:SI 1 "s_register_operand" "0,r"))) (clobber (reg 24))] "" - "* - switch (which_alternative) - { - case 0: - arm_output_asm_insn (\"cmp\\t%0, #0\", operands); - return arm_output_asm_insn (\"rsblt\\t%0, %0, #0\", operands); - case 1: - arm_output_asm_insn (\"eor\\t%0, %1, %1, asr #31\", operands); - return arm_output_asm_insn (\"sub\\t%0, %0, %1, asr #31\", operands); - } -" + "@ + cmp\\t%0, #0\;rsblt\\t%0, %0, #0 + eor%?\\t%0, %1, %1, asr #31\;sub%?\\t%0, %0, %1, asr #31" [(set_attr "conds" "clob,*") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,&r") (neg:SI (abs:SI (match_operand:SI 1 "s_register_operand" "0,r")))) (clobber (reg 24))] "" - "* - switch (which_alternative) - { - case 0: - arm_output_asm_insn (\"cmp\\t%0, #0\", operands); - return arm_output_asm_insn (\"rsbgt\\t%0, %0, #0\", operands); - case 1: - arm_output_asm_insn (\"eor\\t%0, %1, %1, asr #31\", operands); - return arm_output_asm_insn (\"rsb\\t%0, %0, %1, asr #31\", operands); - } -" + "@ + cmp\\t%0, #0\;rsbgt\\t%0, %0, #0 + eor%?\\t%0, %1, %1, asr #31\;rsb%?\\t%0, %0, %1, asr #31" [(set_attr "conds" "clob,*") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "abssf2" [(set (match_operand:SF 0 "s_register_operand" "=f") (abs:SF (match_operand:SF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"abss\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "abs%?s\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "absdf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (abs:DF (match_operand:DF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"absd\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "abs%?d\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "" [(set (match_operand:DF 0 "s_register_operand" "=f") (abs:DF (float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"absd\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "abs%?d\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "absxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (abs:XF (match_operand:XF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"abse\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "abs%?e\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "sqrtsf2" [(set (match_operand:SF 0 "s_register_operand" "=f") (sqrt:SF (match_operand:SF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"sqts\\t%0, %1\", operands)); -" + "sqt%?s\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "sqrtdf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (sqrt:DF (match_operand:DF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"sqtd\\t%0, %1\", operands)); -" + "sqt%?d\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "" @@ -1765,36 +1564,28 @@ (sqrt:DF (float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))))] "" - "* - return (arm_output_asm_insn (\"sqtd\\t%0, %1\", operands)); -" + "sqt%?d\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "sqrtxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (sqrt:XF (match_operand:XF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"sqte\\t%0, %1\", operands)); -" + "sqt%?e\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "sinsf2" [(set (match_operand:SF 0 "s_register_operand" "=f") (unspec:SF [(match_operand:SF 1 "s_register_operand" "f")] 0))] "" - "* - return arm_output_asm_insn (\"sins\\t%0, %1\", operands); -" + "sin%?s\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "sindf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (unspec:DF [(match_operand:DF 1 "s_register_operand" "f")] 0))] "" - "* - return arm_output_asm_insn (\"sind\\t%0, %1\", operands); -" + "sin%?d\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "" @@ -1802,36 +1593,28 @@ (unspec:DF [(float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))] 0))] "" - "* - return arm_output_asm_insn (\"sind\\t%0, %1\", operands); -" + "sin%?d\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "sinxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (unspec:XF [(match_operand:XF 1 "s_register_operand" "f")] 0))] "ENABLE_XF_PATTERNS" - "* - return arm_output_asm_insn (\"sine\\t%0, %1\", operands); -" + "sin%?e\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "cossf2" [(set (match_operand:SF 0 "s_register_operand" "=f") (unspec:SF [(match_operand:SF 1 "s_register_operand" "f")] 1))] "" - "* - return arm_output_asm_insn (\"coss\\t%0, %1\", operands); -" + "cos%?s\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "cosdf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (unspec:DF [(match_operand:DF 1 "s_register_operand" "f")] 1))] "" - "* - return arm_output_asm_insn (\"cosd\\t%0, %1\", operands); -" + "cos%?d\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "" @@ -1839,37 +1622,28 @@ (unspec:DF [(float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))] 1))] "" - "* - return arm_output_asm_insn (\"cosd\\t%0, %1\", operands); -" + "cos%?d\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "cosxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (unspec:XF [(match_operand:XF 1 "s_register_operand" "f")] 1))] "ENABLE_XF_PATTERNS" - "* - return arm_output_asm_insn (\"cose\\t%0, %1\", operands); -" + "cos%?e\\t%0, %1" [(set_attr "type" "float_em")]) (define_insn "one_cmpldi2" [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") (not:DI (match_operand:DI 1 "s_register_operand" "?r,0")))] "" - "* - arm_output_asm_insn (\"mvn\\t%0, %1\", operands); - return arm_output_asm_insn (\"mvn\\t%R0, %R1\", operands); -" -[(set_attr "length" "2")]) + "mvn%?\\t%0, %1\;mvn%?\\t%R0, %R1" +[(set_attr "length" "8")]) (define_insn "one_cmplsi2" [(set (match_operand:SI 0 "s_register_operand" "=r") (not:SI (match_operand:SI 1 "s_register_operand" "r")))] "" - "* - return (arm_output_asm_insn (\"mvn\\t%0, %1\", operands)); -") + "mvn%?\\t%0, %1") (define_insn "" [(set (reg:CC_NOOV 24) @@ -1878,9 +1652,7 @@ (set (match_operand:SI 0 "s_register_operand" "=r") (not:SI (match_dup 1)))] "" - "* - return (arm_output_asm_insn (\"mvns\\t%0, %1\", operands)); -" + "mvn%?s\\t%0, %1" [(set_attr "conds" "set")]) (define_insn "" @@ -1889,9 +1661,7 @@ (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* - return (arm_output_asm_insn (\"mvns\\t%0, %1\", operands)); -" + "mvn%?s\\t%0, %1" [(set_attr "conds" "set")]) ;; Fixed <--> Floating conversion insns @@ -1900,54 +1670,42 @@ [(set (match_operand:SF 0 "s_register_operand" "=f") (float:SF (match_operand:SI 1 "s_register_operand" "r")))] "" - "* - return (arm_output_asm_insn (\"flts\\t%0, %1\", operands)); -" + "flt%?s\\t%0, %1" [(set_attr "type" "r_2_f")]) (define_insn "floatsidf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (float:DF (match_operand:SI 1 "s_register_operand" "r")))] "" - "* - return (arm_output_asm_insn (\"fltd\\t%0, %1\", operands)); -" + "flt%?d\\t%0, %1" [(set_attr "type" "r_2_f")]) (define_insn "floatsixf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (float:XF (match_operand:SI 1 "s_register_operand" "r")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"flte\\t%0, %1\", operands)); -" + "flt%?e\\t%0, %1" [(set_attr "type" "r_2_f")]) (define_insn "fix_truncsfsi2" [(set (match_operand:SI 0 "s_register_operand" "=r") (fix:SI (match_operand:SF 1 "s_register_operand" "f")))] "" - "* - return arm_output_asm_insn (\"fixz\\t%0, %1\", operands); -" + "fix%?z\\t%0, %1" [(set_attr "type" "f_2_r")]) (define_insn "fix_truncdfsi2" [(set (match_operand:SI 0 "s_register_operand" "=r") (fix:SI (match_operand:DF 1 "s_register_operand" "f")))] "" - "* - return arm_output_asm_insn (\"fixz\\t%0, %1\", operands); -" + "fix%?z\\t%0, %1" [(set_attr "type" "f_2_r")]) (define_insn "fix_truncxfsi2" [(set (match_operand:SI 0 "s_register_operand" "=r") (fix:SI (match_operand:XF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return arm_output_asm_insn (\"fixz\\t%0, %1\", operands); -" + "fix%?z\\t%0, %1" [(set_attr "type" "f_2_r")]) ;; Truncation insns @@ -1957,30 +1715,24 @@ (float_truncate:SF (match_operand:DF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"mvfs\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mvf%?s\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "truncxfsf2" [(set (match_operand:SF 0 "s_register_operand" "=f") (float_truncate:SF (match_operand:XF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"mvfs\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mvf%?s\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "truncxfdf2" [(set (match_operand:DF 0 "s_register_operand" "=f") (float_truncate:DF (match_operand:XF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"mvfd\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mvf%?d\\t%0, %1" +[(set_attr "type" "ffarith")]) ;; Zero and sign extension instructions. @@ -1990,28 +1742,19 @@ "" "* if (REGNO (operands[1]) != REGNO (operands[0])) - arm_output_asm_insn (\"mov\\t%0, %1\", operands); - return arm_output_asm_insn (\"mov\\t%R0, #0\", operands); + output_asm_insn (\"mov%?\\t%0, %1\", operands); + return \"mov%?\\t%R0, #0\"; " -[(set_attr "length" "2")]) +[(set_attr "length" "8")]) (define_insn "zero_extendqidi2" [(set (match_operand:DI 0 "s_register_operand" "=r,r") (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "r,m")))] "" - "* - switch (which_alternative) - { - case 0: - arm_output_asm_insn (\"and\\t%0, %1, #255\", operands); - break; - case 1: - arm_output_asm_insn (\"ldrb\\t%0, %1\",operands); - break; - } - return arm_output_asm_insn (\"mov\\t%R0, #0\", operands); -" -[(set_attr "length" "2") + "@ + and%?\\t%0, %1, #255\;mov%?\\t%R0, #0 + ldr%?b\\t%0, %1\;mov%?\\t%R0, #0" +[(set_attr "length" "8") (set_attr "type" "*,load")]) (define_insn "extendsidi2" @@ -2020,105 +1763,115 @@ "" "* if (REGNO (operands[1]) != REGNO (operands[0])) - arm_output_asm_insn (\"mov\\t%0, %1\", operands); - return arm_output_asm_insn (\"mov\\t%R0, %0, asr #31\", operands); + output_asm_insn (\"mov%?\\t%0, %1\", operands); + return \"mov%?\\t%R0, %0, asr #31\"; " -[(set_attr "length" "2")]) +[(set_attr "length" "8")]) (define_expand "zero_extendhisi2" - [(set (match_dup 2) - (ashift:SI (match_operand:HI 1 "s_register_operand" "") - (const_int 16))) + [(set (match_dup 2) (ashift:SI (match_operand:HI 1 "nonimmediate_operand" "") + (const_int 16))) (set (match_operand:SI 0 "s_register_operand" "") - (lshiftrt:SI (match_dup 2) - (const_int 16)))] + (lshiftrt:SI (match_dup 2) (const_int 16)))] "" " -{ operands[1] = gen_lowpart (SImode, operands[1]); - operands[2] = gen_reg_rtx (SImode); }") - -(define_insn "zero_extendqihi2" - [(set (match_operand:HI 0 "s_register_operand" "=r") - (zero_extend:HI - (match_operand:QI 1 "s_register_operand" "r")))] - "" - "* - return (arm_output_asm_insn (\"and\\t%0, %1, #255\\t@ zero_extendqihi2\", operands)); -") - -(define_insn "" - [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (match_operand:QI 1 "s_register_operand" "r") - (const_int 0))) - (set (match_operand:SI 0 "s_register_operand" "=r") - (zero_extend:HI (match_dup 1)))] - "" - "* - return arm_output_asm_insn (\"ands\\t%0, %1, #255\", operands); -" -[(set_attr "conds" "set")]) - -(define_insn "" - [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (match_operand:QI 0 "s_register_operand" "r") - (const_int 0)))] - "" - "* - return arm_output_asm_insn (\"tst\\t%0, #255\", operands); -" -[(set_attr "conds" "set")]) +{ + if (TARGET_SHORT_BY_BYTES && GET_CODE (operands[1]) == MEM) + { + emit_insn (gen_movhi_bytes (operands[0], operands[1])); + DONE; + } + if (! s_register_operand (operands[1], HImode)) + operands[1] = copy_to_mode_reg (HImode, operands[1]); + operands[1] = gen_lowpart (SImode, operands[1]); + operands[2] = gen_reg_rtx (SImode); +}") -(define_insn "zero_extendqisi2" +(define_expand "zero_extendqisi2" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "r,m")))] "" - "* - switch (which_alternative) + " + if (GET_CODE (operands[1]) != MEM) { - case 0: - return (arm_output_asm_insn (\"and\\t%0, %1, #255\\t@ zero_extendqisi2\", operands)); - case 1: - return (arm_output_asm_insn (\"ldrb\\t%0, %1\\t@ zero_extendqisi2\", operands)); + emit_insn (gen_andsi3 (operands[0], gen_lowpart (SImode, operands[1]), + GEN_INT (255))); + DONE; } -" -[(set_attr "type" "*,load")]) +") (define_insn "" - [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (match_operand:QI 1 "s_register_operand" "r") - (const_int 0))) - (set (match_operand:SI 0 "s_register_operand" "=r") - (zero_extend:SI (match_dup 1)))] + [(set (match_operand:SI 0 "s_register_operand" "=r") + (zero_extend:SI (match_operand:QI 1 "memory_operand" "m")))] "" - "* - return arm_output_asm_insn (\"ands\\t%0, %1, #255\", operands); -" -[(set_attr "conds" "set")]) + "ldr%?b\\t%0, %1\\t%@ zero_extendqisi2" +[(set_attr "type" "load")]) + +(define_split + [(set (match_operand:SI 0 "s_register_operand" "") + (zero_extend:SI (subreg:QI (match_operand:SI 1 "" "") 0))) + (clobber (match_operand:SI 2 "s_register_operand" ""))] + "GET_CODE (operands[1]) != MEM" + [(set (match_dup 2) (match_dup 1)) + (set (match_dup 0) (and:SI (match_dup 2) (const_int 255)))] + "") (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (match_operand:QI 1 "s_register_operand" "r") - (const_int 0))) - (set (match_operand:QI 0 "s_register_operand" "=r") - (match_dup 1))] + (compare:CC_NOOV (match_operand:QI 0 "s_register_operand" "r") + (const_int 0)))] "" - "* - return arm_output_asm_insn (\"ands\\t%0, %1, #255\", operands); -" + "tst\\t%0, #255" [(set_attr "conds" "set")]) (define_expand "extendhisi2" [(set (match_dup 2) - (ashift:SI (match_operand:HI 1 "s_register_operand" "") + (ashift:SI (match_operand:HI 1 "nonimmediate_operand" "") (const_int 16))) (set (match_operand:SI 0 "s_register_operand" "") (ashiftrt:SI (match_dup 2) (const_int 16)))] "" " -{ operands[1] = gen_lowpart (SImode, operands[1]); - operands[2] = gen_reg_rtx (SImode); }") +{ + if (TARGET_SHORT_BY_BYTES && GET_CODE (operands[1]) == MEM) + { + emit_insn (gen_extendhisi2_mem (operands[0], operands[1])); + DONE; + } + if (! s_register_operand (operands[1], HImode)) + operands[1] = copy_to_mode_reg (HImode, operands[1]); + operands[1] = gen_lowpart (SImode, operands[1]); + operands[2] = gen_reg_rtx (SImode); +}") + +(define_expand "extendhisi2_mem" + [(set (match_dup 2) (zero_extend:SI (mem:QI (match_operand:HI 1 "" "")))) + (set (match_dup 3) + (zero_extend:SI (mem:QI (plus:SI (match_dup 1) (const_int 1))))) + (set (match_dup 6) (ashift:SI (match_dup 4) (const_int 24))) + (set (match_operand:SI 0 "" "") + (ior:SI (ashiftrt:SI (match_dup 6) (const_int 16)) (match_dup 5)))] + "" + " + operands[0] = gen_lowpart (SImode, operands[0]); + operands[1] = copy_to_mode_reg (SImode, XEXP (operands[1], 0)); + operands[2] = gen_reg_rtx (SImode); + operands[3] = gen_reg_rtx (SImode); + operands[6] = gen_reg_rtx (SImode); + + if (BYTES_BIG_ENDIAN) + { + operands[4] = operands[2]; + operands[5] = operands[3]; + } + else + { + operands[4] = operands[3]; + operands[5] = operands[2]; + } +") (define_expand "extendqihi2" [(set (match_dup 2) @@ -2149,27 +1902,22 @@ [(set (match_operand:DF 0 "s_register_operand" "=f") (float_extend:DF (match_operand:SF 1 "s_register_operand" "f")))] "" - "* - return (arm_output_asm_insn (\"mvfd\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mvf%?d\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "extendsfxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (float_extend:XF (match_operand:SF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"mvfe\\t%0, %1\", operands)); -") + "mvf%?e\\t%0, %1" +[(set_attr "type" "ffarith")]) (define_insn "extenddfxf2" [(set (match_operand:XF 0 "s_register_operand" "=f") (float_extend:XF (match_operand:DF 1 "s_register_operand" "f")))] "ENABLE_XF_PATTERNS" - "* - return (arm_output_asm_insn (\"mvfe\\t%0, %1\", operands)); -" -[(set_attr "type" "float")]) + "mvf%?e\\t%0, %1" +[(set_attr "type" "ffarith")]) ;; Move insns (including loads and stores) @@ -2229,18 +1977,19 @@ ;; case 4: template = \"stmia\\t%0!, %M1\"; break; ;; case 5: template = \"stmia\\t%0, %M1\"; break; ;; } -;; return (arm_output_asm_insn (template, operands)); +;; output_asm_insn (template, operands); +;; return \"\"; ;; }") (define_insn "movdi" [(set (match_operand:DI 0 "di_operand" "=r,r,r,o<>,r") - (match_operand:DI 1 "di_operand" "rK,n,o<>,r,F"))] + (match_operand:DI 1 "di_operand" "rIK,n,o<>,r,F"))] "" "* return (output_move_double (operands)); " -[(set_attr "length" "2,8,2,2,8") +[(set_attr "length" "8,32,8,8,32") (set_attr "type" "*,*,load,store2,*")]) (define_expand "movsi" @@ -2255,159 +2004,99 @@ && !(const_ok_for_arm (INTVAL (operands[1])) || const_ok_for_arm (~INTVAL (operands[1])))) { - int n = INTVAL (operands[1]); - rtx tmpreg, tmpreg2; - int i, n_ones = 0, first = 1, last = 0; - - if (GET_CODE (operands[0]) != REG - && GET_CODE (operands[0]) != SUBREG) - abort (); - for (i = 0; i < 32; i++) - if (n & 1 << i) - n_ones++; - /* These loops go the opposite way around to those in arm.c so that - the last constant may be more likely to be eliminted into the - next instruction */ - - if (n_ones > 16) - { - n = (~n) & 0xffffffff; - for (i = 30; i >= 0; i -= 2) - { - if (n & (3 << i)) - { - i -= 6; - if (i < 0) - i = 0; - if ((n & (255 << i)) == n) - last = 1; - if (first) - { - rtx equal; - rtx insn = - emit_insn (gen_movsi (tmpreg = (reload_in_progress - || reload_completed) - ? operands[0] - : gen_reg_rtx (SImode), - equal = gen_rtx (CONST_INT, VOIDmode, - ~(n & (255 << i))))); - first = 0; - } - else - { - rtx constant; - rtx insn = - emit_insn (gen_subsi3 (tmpreg2 = (reload_in_progress - || reload_completed - || last) - ? operands[0] - : gen_reg_rtx (SImode), - tmpreg, - constant = gen_rtx (CONST_INT, VOIDmode, - n & (255 << i)))); - tmpreg = tmpreg2; - } - n &= ~(255 << i); - } - } - } - else - { - for (i = 30; i >= 0; i -= 2) - { - if (n & (3 << i)) - { - i -= 6; - if (i < 0) - i = 0; - if ((n & (255 << i)) == n) - last = 1; - if (first) - { - rtx equal; - rtx insn = - emit_insn (gen_movsi (tmpreg = (reload_in_progress - || reload_completed) - ? operands[0] - : gen_reg_rtx (SImode), - equal = gen_rtx (CONST_INT, VOIDmode, - n & (255 << i)))); - first = 0; - } - else - { - rtx constant; - rtx insn = - emit_insn (gen_addsi3 (tmpreg2 = (reload_in_progress - || reload_completed - || last) - ? operands[0] - : gen_reg_rtx (SImode), - tmpreg, - constant = gen_rtx (CONST_INT, VOIDmode, - n & (255 << i)))); - tmpreg = tmpreg2; - } - n &= ~(255 << i); - } - } - } + arm_split_constant (SET, SImode, INTVAL (operands[1]), operands[0], + NULL_RTX, + (reload_in_progress || reload_completed ? 0 + : preserve_subexpressions_p ())); DONE; } ") (define_insn "" - [(set (match_operand:SI 0 "general_operand" "=r,r,r,m,r") - (match_operand:SI 1 "general_operand" "m,K,r,r,S"))] + [(set (match_operand:SI 0 "general_operand" "=r,r,r,r,m,r,r") + (match_operand:SI 1 "general_operand" "R,m,K,rI,r,S,?n"))] "(register_operand (operands[0], SImode) - && (GET_CODE (operands[1]) != CONST_INT - || const_ok_for_arm (INTVAL (operands[1])) - || const_ok_for_arm (~INTVAL (operands[1]))) && (GET_CODE (operands[1]) != SYMBOL_REF || CONSTANT_ADDRESS_P (operands[1]))) || register_operand (operands[1], SImode)" "* switch (which_alternative) { - case 2: - return (arm_output_asm_insn (\"mov\\t%0, %1\", operands)); - case 1: - if (!const_ok_for_arm (INTVAL (operands[1]))) + case 0: + /* NB Calling get_attr_length may cause the insn to be re-extracted... */ + if (get_attr_length (insn) == 8) + { + /* ... so modify the operands here. */ + operands[1] = XEXP (operands[1], 0); + output_asm_insn (\"sub%?\\t%0, %|pc, #(8 + . - %a1) & ~4095\", + operands); + output_asm_insn (\"ldr%?\\t%0, [%0, #- ((4 + . - %a1) & 4095)]\", + operands); + } + else { - operands[1] = gen_rtx (CONST_INT, VOIDmode, ~INTVAL (operands[1])); - return arm_output_asm_insn (\"mvn\\t%0, %1\", operands); + /* ... and here. */ + operands[1] = XEXP (operands[1], 0); + output_asm_insn (\"ldr%?\\t%0, [%|pc, %1 - . - 8]\", operands); } - return arm_output_asm_insn (\"mov\\t%0, %1\", operands); - case 0: + return \"\"; + + case 1: if (GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))) - return (arm_output_llc (operands)); - else - return (arm_output_asm_insn (\"ldr\\t%0, %1\", operands)); + abort (); + return \"ldr%?\\t%0, %1\"; + case 3: - return (arm_output_asm_insn (\"str\\t%1, %0\", operands)); + return \"mov%?\\t%0, %1\"; + case 2: + return \"mvn%?\\t%0, #%B1\"; case 4: - return output_load_symbol (operands); + return \"str%?\\t%1, %0\"; + case 5: + return output_load_symbol (insn, operands); + case 6: + return \"#\"; } " -[(set_attr "length" "2,*,*,*,4") - (set_attr "type" "load,*,*,store1,*")]) +[(set (attr "length") + (cond [(eq_attr "alternative" "0") + (if_then_else + (gt (minus + (pc) + (symbol_ref "const_pool_offset (XEXP (operands[1], 0))")) + (const_int 4087)) + (const_int 8) + (const_int 4)) + (ior (eq_attr "alternative" "5") + (eq_attr "alternative" "6")) (const_int 16)] + (const_int 4))) + (set_attr "type" "load,load,*,*,store1,*,*")]) + +(define_split + [(set (match_operand:SI 0 "s_register_operand" "") + (match_operand:SI 1 "const_int_operand" ""))] + "! (const_ok_for_arm (INTVAL (operands[1])) + || const_ok_for_arm (~INTVAL (operands[1])))" + [(clobber (const_int 0))] + " + arm_split_constant (SET, SImode, INTVAL (operands[1]), operands[0], + NULL_RTX, 0); + DONE; +") ;; If copying one reg to another we can set the condition codes according to ;; its value. Such a move is common after a return from subroutine and the ;; result is being tested against zero. (define_insn "" - [(set (reg:CC 24) (compare (match_operand:SI 1 "s_register_operand" "r") + [(set (reg:CC 24) (compare (match_operand:SI 1 "s_register_operand" "0,r") (const_int 0))) - (set (match_operand:SI 0 "s_register_operand" "=r") (match_dup 1))] + (set (match_operand:SI 0 "s_register_operand" "=r,r") (match_dup 1))] "" - "* - if (GET_CODE (operands[0]) == REG && GET_CODE (operands[1]) == REG - && REGNO (operands[0]) == REGNO (operands[1])) - return arm_output_asm_insn (\"cmp\\t%0, #0\", operands); - return arm_output_asm_insn (\"subs\\t%0, %1, #0\", operands); -" + "@ + cmp%?\\t%0, #0 + sub%?s\\t%0, %1, #0" [(set_attr "conds" "set")]) ;; Subroutine to store a half word from a register into memory. @@ -2443,30 +2132,69 @@ } ") -;; Subroutine to store a half word integer constant into memory. -;; Operand 0 is the constant -;; Operand 1 is the destination address in a register (SImode) - -(define_expand "storeinthi" - [;; store the low byte - (set (mem:QI (match_operand:SI 1 "" "")) (match_operand 0 "" "")) - ;; store the high byte - (set (mem:QI (match_dup 3)) (match_dup 2))] +(define_expand "storehi_bigend" + [(set (mem:QI (match_dup 4)) (match_dup 3)) + (set (match_dup 2) + (ashiftrt:SI (match_operand 0 "" "") (const_int 8))) + (set (mem:QI (match_operand 1 "" "")) + (subreg:QI (match_dup 2) 0))] "" " { - int value = INTVAL (operands[0]); enum rtx_code code = GET_CODE (operands[1]); - if ((code == PLUS || code == MINUS) && (GET_CODE (XEXP (operands[1], 1)) == REG || GET_CODE (XEXP (operands[1], 0)) != REG)) - operands[1] = force_reg (SImode, operands[1]); + operands[1] = force_reg (SImode, operands[1]); - operands[0] = force_reg (QImode, gen_rtx (CONST_INT, VOIDmode, value & 255)); - operands[2] = force_reg (QImode, - gen_rtx (CONST_INT, VOIDmode,(value>>8) & 255)); - operands[3] = plus_constant (operands[1], 1); + operands[4] = plus_constant (operands[1], 1); + operands[3] = gen_lowpart (QImode, operands[0]); + operands[0] = gen_lowpart (SImode, operands[0]); + operands[2] = gen_reg_rtx (SImode); +} +") + +;; Subroutine to store a half word integer constant into memory. +(define_expand "storeinthi" + [(set (mem:QI (match_operand:SI 0 "" "")) + (subreg:QI (match_operand 1 "" "") 0)) + (set (mem:QI (match_dup 3)) (subreg:QI (match_dup 2) 0))] + "" + " +{ + HOST_WIDE_INT value = INTVAL (operands[1]); + enum rtx_code code = GET_CODE (operands[0]); + + if ((code == PLUS || code == MINUS) + && (GET_CODE (XEXP (operands[0], 1)) == REG + || GET_CODE (XEXP (operands[0], 0)) != REG)) + operands[0] = force_reg (SImode, operands[0]); + + operands[1] = gen_reg_rtx (SImode); + if (BYTES_BIG_ENDIAN) + { + emit_insn (gen_movsi (operands[1], GEN_INT ((value >> 8) & 255))); + if ((value & 255) == ((value >> 8) & 255)) + operands[2] = operands[1]; + else + { + operands[2] = gen_reg_rtx (SImode); + emit_insn (gen_movsi (operands[2], GEN_INT (value & 255))); + } + } + else + { + emit_insn (gen_movsi (operands[1], GEN_INT (value & 255))); + if ((value & 255) == ((value >> 8) & 255)) + operands[2] = operands[1]; + else + { + operands[2] = gen_reg_rtx (SImode); + emit_insn (gen_movsi (operands[2], GEN_INT ((value >> 8) & 255))); + } + } + + operands[3] = plus_constant (operands[0], 1); } ") @@ -2478,87 +2206,148 @@ { rtx insn; - if (reload_in_progress || reload_completed) - insn = gen_rtx (SET, VOIDmode, operands[0], operands[1]); - else + if (! (reload_in_progress || reload_completed)) { if (GET_CODE (operands[0]) == MEM) { if (GET_CODE (operands[1]) == CONST_INT) - { - insn = gen_storeinthi (operands[1], XEXP (operands[0],0)); - } + emit_insn (gen_storeinthi (XEXP (operands[0], 0), operands[1])); else { if (GET_CODE (operands[1]) == MEM) operands[1] = force_reg (HImode, operands[1]); - insn = gen_storehi (operands[1], XEXP (operands[0], 0)); + if (BYTES_BIG_ENDIAN) + emit_insn (gen_storehi_bigend (operands[1], + XEXP (operands[0], 0))); + else + emit_insn (gen_storehi (operands[1], XEXP (operands[0], 0))); } + DONE; } - else if (GET_CODE (operands[1]) == CONST_INT - && !(const_ok_for_arm (INTVAL (operands[1])) - || const_ok_for_arm (~INTVAL (operands[1])))) + /* Sign extend a constant, and keep it in an SImode reg. */ + else if (GET_CODE (operands[1]) == CONST_INT) { - rtx reg, reg2; + rtx reg = gen_reg_rtx (SImode); + HOST_WIDE_INT val = INTVAL (operands[1]) & 0xffff; - /* no need to be clever, this will always take two insns. - The top sixteen bits should be all zeros or all ones. */ - if (INTVAL (operands[1]) < 0) - { - emit_insn (gen_movsi (reg = gen_reg_rtx (SImode), - GEN_INT (INTVAL (operands[1]) - | ~(0x0ff00)))); - emit_insn (gen_addsi3 (reg2 = gen_reg_rtx (SImode), reg, - GEN_INT (-((~INTVAL (operands[1])) - & 0xff)))); - } - else + /* If the constant is already valid, leave it alone. */ + if (! const_ok_for_arm (val)) { - emit_insn (gen_movsi (reg = gen_reg_rtx (SImode), - GEN_INT (INTVAL (operands[1]) & 0xff00))); - emit_insn (gen_addsi3 (reg2 = gen_reg_rtx (SImode), reg, - GEN_INT (INTVAL (operands[1]) & 0x00ff))); + /* If setting all the top bits will make the constant + loadable in a single instruction, then set them. + Otherwise, sign extend the number. */ + + if (const_ok_for_arm (~ (val | ~0xffff))) + val |= ~0xffff; + else if (val & 0x8000) + val |= ~0xffff; } - insn = gen_rtx (SET, HImode, operands[0], - gen_rtx (SUBREG, HImode, reg2, 0)); + + emit_insn (gen_movsi (reg, GEN_INT (val))); + operands[1] = gen_rtx (SUBREG, HImode, reg, 0); + } + else if (TARGET_SHORT_BY_BYTES && GET_CODE (operands[1]) == MEM) + { + rtx reg = gen_reg_rtx (SImode); + emit_insn (gen_movhi_bytes (reg, operands[1])); + operands[1] = gen_lowpart (HImode, reg); + } + else if (BYTES_BIG_ENDIAN && GET_CODE (operands[1]) == MEM) + { + emit_insn (gen_movhi_bigend (operands[0], operands[1])); + DONE; } - else - insn = gen_rtx (SET, VOIDmode, operands[0], operands[1]); } +} +") - emit_insn (insn); - DONE; -}") +(define_expand "movhi_bytes" + [(set (match_dup 2) (zero_extend:SI (mem:QI (match_operand:HI 1 "" "")))) + (set (match_dup 3) + (zero_extend:SI (mem:QI (plus:SI (match_dup 1) (const_int 1))))) + (set (match_operand:SI 0 "" "") + (ior:SI (ashift:SI (match_dup 4) (const_int 8)) (match_dup 5)))] + "" + " + operands[0] = gen_lowpart (SImode, operands[0]); + operands[1] = copy_to_mode_reg (SImode, XEXP (operands[1], 0)); + operands[2] = gen_reg_rtx (SImode); + operands[3] = gen_reg_rtx (SImode); + + if (BYTES_BIG_ENDIAN) + { + operands[4] = operands[2]; + operands[5] = operands[3]; + } + else + { + operands[4] = operands[3]; + operands[5] = operands[2]; + } +") + +(define_expand "movhi_bigend" + [(set (match_dup 2) + (rotate:SI (subreg:SI (match_operand:HI 1 "memory_operand" "") 0) + (const_int 16))) + (set (match_dup 3) + (ashiftrt:SI (match_dup 2) (const_int 16))) + (set (match_operand:HI 0 "s_register_operand" "") + (subreg:HI (match_dup 3) 0))] + "" + " + operands[2] = gen_reg_rtx (SImode); + operands[3] = gen_reg_rtx (SImode); +") ;; Pattern to recognise insn generated default case above (define_insn "" - [(set (match_operand:HI 0 "general_operand" "=r,r,r,m") - (match_operand:HI 1 "general_operand" "r,K,m,r"))] - "(register_operand (operands[0], HImode) - && (GET_CODE (operands[1]) != CONST_INT - || const_ok_for_arm (INTVAL (operands[1])) - || const_ok_for_arm (~INTVAL (operands[1])))) - || register_operand (operands[1], HImode)" - "* - switch (which_alternative) - { - case 1: - if (!const_ok_for_arm (INTVAL (operands[1]))) - { - operands[1] = GEN_INT (~INTVAL (operands[1])); - return arm_output_asm_insn (\"mvn\\t%0, %1\", operands); - } - /* fall through */ - case 0: - return arm_output_asm_insn (\"mov\\t%0, %1\\t@movhi\", operands); - case 2: - return arm_output_asm_insn (\"ldr\\t%0, %1\\t@movhi\", operands); - case 3: - return arm_output_asm_insn (\"str\\t%1, %0\\t@movhi\", operands); - } -" -[(set_attr "type" "*,*,load,store1")]) + [(set (match_operand:HI 0 "general_operand" "=r,r,r") + (match_operand:HI 1 "general_operand" "rI,K,m"))] + "! BYTES_BIG_ENDIAN + && ! TARGET_SHORT_BY_BYTES + && (GET_CODE (operands[1]) != CONST_INT + || const_ok_for_arm (INTVAL (operands[1])) + || const_ok_for_arm (~INTVAL (operands[1])))" + "@ + mov%?\\t%0, %1\\t%@ movhi + mvn%?\\t%0, #%B1\\t%@ movhi + ldr%?\\t%0, %1\\t%@ movhi" +[(set_attr "type" "*,*,load")]) + +(define_insn "" + [(set (match_operand:HI 0 "s_register_operand" "=r,r,r") + (match_operand:HI 1 "general_operand" "rI,K,m"))] + "BYTES_BIG_ENDIAN + && ! TARGET_SHORT_BY_BYTES + && (GET_CODE (operands[1]) != CONST_INT + || const_ok_for_arm (INTVAL (operands[1])) + || const_ok_for_arm (~INTVAL (operands[1])))" + "@ + mov%?\\t%0, %1\\t%@ movhi + mvn%?\\t%0, #%B1\\t%@ movhi + ldr%?\\t%0, %1\\t%@ movhi_bigend\;mov%?\\t%0, %0, asr #16" +[(set_attr "type" "*,*,load") + (set_attr "length" "4,4,8")]) + +(define_insn "" + [(set (match_operand:SI 0 "s_register_operand" "=r") + (rotate:SI (subreg:SI (match_operand:HI 1 "memory_operand" "m") 0) + (const_int 16)))] + "BYTES_BIG_ENDIAN + && ! TARGET_SHORT_BY_BYTES" + "ldr%?\\t%0, %1\\t%@ movhi_bigend" +[(set_attr "type" "load")]) + +(define_insn "" + [(set (match_operand:HI 0 "s_register_operand" "=r,r") + (match_operand:HI 1 "arm_rhs_operand" "rI,K"))] + "TARGET_SHORT_BY_BYTES" + "@ + mov%?\\t%0, %1\\t%@ movhi + mvn%?\\t%0, #%B1\\t%@ movhi") + (define_expand "reload_outhi" [(parallel [(match_operand:HI 0 "reload_memory_operand" "=o") @@ -2570,6 +2359,16 @@ DONE; ") +(define_expand "reload_inhi" + [(parallel [(match_operand:HI 0 "s_register_operand" "=r") + (match_operand:HI 1 "reload_memory_operand" "o") + (match_operand:SI 2 "s_register_operand" "=&r")])] + "TARGET_SHORT_BY_BYTES" + " + arm_reload_in_hi (operands); + DONE; +") + (define_expand "movqi" [(set (match_operand:QI 0 "general_operand" "") (match_operand:QI 1 "general_operand" ""))] @@ -2579,87 +2378,109 @@ if (!(reload_in_progress || reload_completed)) { - rtx reg; if (GET_CODE (operands[1]) == CONST_INT) { - emit_insn (gen_movsi (reg = gen_reg_rtx (SImode), operands[1])); + rtx reg = gen_reg_rtx (SImode); + + emit_insn (gen_movsi (reg, operands[1])); operands[1] = gen_rtx (SUBREG, QImode, reg, 0); } + if (GET_CODE (operands[0]) == MEM) + operands[1] = force_reg (QImode, operands[1]); } - if (GET_CODE (operands[0]) == MEM) - operands[1] = force_reg (QImode, operands[1]); ") (define_insn "" [(set (match_operand:QI 0 "general_operand" "=r,r,r,m") - (match_operand:QI 1 "general_operand" "r,K,m,r"))] + (match_operand:QI 1 "general_operand" "rI,K,m,r"))] "register_operand (operands[0], QImode) || register_operand (operands[1], QImode)" - "* - switch (which_alternative) - { - case 1: - if (INTVAL (operands[1]) < 0) + "@ + mov%?\\t%0, %1 + mvn%?\\t%0, #%B1 + ldr%?b\\t%0, %1 + str%?b\\t%1, %0" +[(set_attr "type" "*,*,load,store1")]) + +(define_expand "movsf" + [(set (match_operand:SF 0 "general_operand" "") + (match_operand:SF 1 "general_operand" ""))] + "" + " + if (GET_CODE (operands[1]) == CONST_DOUBLE + && ((GET_CODE (operands[0]) == REG + && REGNO (operands[0]) < 16) + || ! (const_double_rtx_ok_for_fpu (operands[1]) + || neg_const_double_rtx_ok_for_fpu (operands[1])))) + { + extern int optimize; + rtx mem = force_const_mem (SFmode, operands[1]); + rtx addr; + + if (reload_in_progress || reload_completed) + addr = gen_rtx (REG, SImode, REGNO (operands[0])); + else + addr = gen_reg_rtx (SImode); + if (optimize == 0) { - operands[1] = GEN_INT (~INTVAL (operands[1])); - return arm_output_asm_insn (\"mvn\\t%0, %1\", operands); + rtx ptr = force_const_mem (SImode, XEXP (mem, 0)); + emit_insn (gen_movsi (addr, ptr)); } - case 0: - return (arm_output_asm_insn (\"mov\\t%0, %1\", operands)); - case 2: - return (arm_output_asm_insn (\"ldrb\\t%0, %1\", operands)); - case 3: - return (arm_output_asm_insn (\"strb\\t%1, %0\", operands)); + else + emit_insn (gen_movsi (addr, XEXP (mem, 0))); + operands[1] = gen_rtx (MEM, SFmode, addr); } -" -[(set_attr "type" "*,*,load,store1")]) + if (GET_CODE (operands[0]) == MEM) + operands[1] = force_reg (SFmode, operands[1]); +") -(define_insn "movsf" +(define_insn "" [(set (match_operand:SF 0 "general_operand" "=f,f,f,m,f,r,r,r,m") (match_operand:SF 1 "general_operand" "fG,H,m,f,r,f,r,m,r"))] - "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"mvfs\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"mnfs\\t%0, %1\", operands); - case 2: - return arm_output_asm_insn (\"ldfs\\t%0, %1\", operands); - case 3: - return arm_output_asm_insn (\"stfs\\t%1, %0\", operands); - case 4: - arm_output_asm_insn(\"stmfd\\tsp!, {%1}\", operands); - return arm_output_asm_insn (\"ldfs\\t%0, [sp],#4\", operands); - case 5: - arm_output_asm_insn(\"stfs\\t%1, [sp,#-4]!\", operands); - return arm_output_asm_insn (\"ldmfd\\tsp!, {%0}\", operands); - case 6: - return arm_output_asm_insn (\"mov\\t%0, %1\", operands); - case 7: - return arm_output_asm_insn (\"ldr\\t%0, %1\\t@ float\", operands); - case 8: - return arm_output_asm_insn (\"str\\t%1, %0\\t@ float\", operands); - } -} -" -[(set_attr "length" "1,1,1,1,2,2,1,1,1") - (set_attr "type" "float,float,f_load,f_store,r_mem_f,f_mem_r,*,load,store1")]) + "GET_CODE (operands[0]) != MEM || register_operand (operands[1], SFmode)" + "@ + mvf%?s\\t%0, %1 + mnf%?s\\t%0, #%N1 + ldf%?s\\t%0, %1 + stf%?s\\t%1, %0 + str%?\\t%1, [%|sp, #-4]!\;ldf%?s\\t%0, [%|sp], #4 + stf%?s\\t%1, [%|sp, #-4]!\;ldr%?\\t%0, [%|sp], #4 + mov%?\\t%0, %1 + ldr%?\\t%0, %1\\t%@ float + str%?\\t%1, %0\\t%@ float" +[(set_attr "length" "4,4,4,4,8,8,4,4,4") + (set_attr "type" + "ffarith,ffarith,f_load,f_store,r_mem_f,f_mem_r,*,load,store1")]) (define_expand "movdf" - [(parallel [(set (match_operand:DF 0 "general_operand" "") - (match_operand:DF 1 "general_operand" "")) - (clobber (match_scratch:SI 2 ""))])] + [(set (match_operand:DF 0 "general_operand" "") + (match_operand:DF 1 "general_operand" ""))] "" " + if (GET_CODE (operands[1]) == CONST_DOUBLE + && ((GET_CODE (operands[0]) == REG + && REGNO (operands[0]) < 16) + || ! (const_double_rtx_ok_for_fpu (operands[1]) + || neg_const_double_rtx_ok_for_fpu (operands[1])))) + { + extern int optimize; + rtx mem = force_const_mem (DFmode, operands[1]); + rtx addr; + + if (reload_in_progress || reload_completed) + addr = gen_rtx (REG, SImode, REGNO (operands[0])); + else + addr = gen_reg_rtx (SImode); + if (optimize == 0) + { + rtx ptr = force_const_mem (SImode, XEXP (mem, 0)); + emit_insn (gen_movsi (addr, ptr)); + } + else + emit_insn (gen_movsi (addr, XEXP (mem, 0))); + operands[1] = gen_rtx (MEM, DFmode, addr); + } if (GET_CODE (operands[0]) == MEM) operands[1] = force_reg (DFmode, operands[1]); ") @@ -2667,100 +2488,92 @@ ;; Reloading a df mode value stored in integer regs to memory can require a ;; scratch reg. (define_expand "reload_outdf" - [(parallel [(set (match_operand:DF 0 "reload_memory_operand" "=o") - (match_operand:DF 1 "s_register_operand" "r")) - (clobber (match_operand:SI 2 "s_register_operand" "=&r"))])] + [(match_operand:DF 0 "reload_memory_operand" "=o") + (match_operand:DF 1 "s_register_operand" "r") + (match_operand:SI 2 "s_register_operand" "=&r")] "" - "") + " + if (GET_CODE (XEXP (operands[0], 0)) == REG) + operands[2] = XEXP (operands[0], 0); + else + emit_insn (gen_addsi3 (operands[2], XEXP (XEXP (operands[0], 0), 0), + XEXP (XEXP (operands[0], 0), 1))); + emit_insn (gen_rtx (SET, VOIDmode, gen_rtx (MEM, DFmode, operands[2]), + operands[1])); + DONE; +") (define_insn "" - [(set (match_operand:DF 0 "general_operand" "=r,Q,r,o,f,f,f,f,m,!f,!r,r") + [(set (match_operand:DF 0 "general_operand" "=r,Q#m,r,f,f,f,f,m,!f,!r,r") (match_operand:DF 1 "general_operand" - "Q,r,?o,?r,?f,!G,!H,m,f,r,f,??r")) - (clobber (match_scratch:SI 2 "=X,X,X,&r,X,X,X,X,X,X,X,X"))] + "Q,r,?o,?f,!G,!H,m,f,r,f,??r"))] "GET_CODE (operands[0]) != MEM || register_operand (operands[1], DFmode)" "* { - REAL_VALUE_TYPE r; rtx ops[3]; switch (which_alternative) { case 0: - operands[1] = XEXP (operands[1], 0); - return arm_output_asm_insn (\"ldmia\\t%1, {%0, %R0}\\t@ double\", - operands); + return \"ldm%?ia\\t%m1, {%0, %R0}\\t%@ double\"; + case 1: - operands[0] = XEXP (operands[0], 0); - return arm_output_asm_insn (\"stmia\\t%0, {%1, %R1}\\t@ double\", - operands); + return \"stm%?ia\\t%m0, {%1, %R1}\\t%@ double\"; + case 2: ops[0] = operands[0]; ops[1] = XEXP (XEXP (operands[1], 0), 0); ops[2] = XEXP (XEXP (operands[1], 0), 1); if (!INTVAL (ops[2]) || const_ok_for_arm (INTVAL (ops[2]))) - arm_output_asm_insn (\"add\\t%0, %1, %2\", ops); + output_asm_insn (\"add%?\\t%0, %1, %2\", ops); else - arm_output_asm_insn (\"sub\\t%0, %1, #%n2\", ops); - return arm_output_asm_insn (\"ldmia\\t%0, {%0, %R0}\\t@ double\", - operands); - case 3: + output_asm_insn (\"sub%?\\t%0, %1, #%n2\", ops); + return \"ldm%?ia\\t%0, {%0, %R0}\\t%@ double\"; - ops[0] = operands[2]; - ops[1] = XEXP (XEXP (operands[0], 0), 0); - ops[2] = XEXP (XEXP (operands[0], 0), 1); - if (!INTVAL (ops[2]) || const_ok_for_arm (INTVAL (ops[2]))) - arm_output_asm_insn (\"add\\t%0, %1, %2\", ops); - else - arm_output_asm_insn (\"sub\\t%0, %1, #%n2\", ops); - return arm_output_asm_insn (\"stmia\\t%2, {%1, %R1}\\t@ double\", - operands); + case 3: case 4: - case 5: - return arm_output_asm_insn (\"mvfd\\t%0, %1\", operands); - case 6: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"mnfd\\t%0, %1\", operands); - case 7: return arm_output_asm_insn (\"ldfd\\t%0, %1\", operands); - case 8: return arm_output_asm_insn (\"stfd\\t%1, %0\", operands); - case 9: return output_mov_double_fpu_from_arm (operands); - case 10: return output_mov_double_arm_from_fpu (operands); - case 11: return output_move_double (operands); + return \"mvf%?d\\t%0, %1\"; + + case 5: return \"mnf%?d\\t%0, #%N1\"; + case 6: return \"ldf%?d\\t%0, %1\"; + case 7: return \"stf%?d\\t%1, %0\"; + case 8: return output_mov_double_fpu_from_arm (operands); + case 9: return output_mov_double_arm_from_fpu (operands); + case 10: return output_move_double (operands); } } " -[(set_attr "length" "1,1,2,2,1,1,1,1,1,2,2,2") +[(set_attr "length" "4,4,8,4,4,4,4,4,8,8,8") (set_attr "type" -"load,store2,load,store2,float,float,float,f_load,f_store,r_mem_f,f_mem_r,*")]) +"load,store2,load,ffarith,ffarith,ffarith,f_load,f_store,r_mem_f,f_mem_r,*")]) -(define_insn "movxf" +(define_expand "movxf" + [(set (match_operand:XF 0 "general_operand" "") + (match_operand:XF 1 "general_operand" ""))] + "ENABLE_XF_PATTERNS" + "") + +;; Even when the XFmode patterns aren't enabled, we enable this after +;; reloading so that we can push floating point registers in the prologue. + +(define_insn "" [(set (match_operand:XF 0 "general_operand" "=f,f,f,m,f,r,r") (match_operand:XF 1 "general_operand" "fG,H,m,f,r,f,r"))] - "ENABLE_XF_PATTERNS" + "ENABLE_XF_PATTERNS || reload_completed" "* -{ - REAL_VALUE_TYPE r; - switch (which_alternative) { - case 0: return arm_output_asm_insn (\"mvfe\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"mnfe\\t%0, %1\", operands); - case 2: return arm_output_asm_insn (\"ldfe\\t%0, %1\", operands); - case 3: return arm_output_asm_insn (\"stfe\\t%1, %0\", operands); + case 0: return \"mvf%?e\\t%0, %1\"; + case 1: return \"mnf%?e\\t%0, #%N1\"; + case 2: return \"ldf%?e\\t%0, %1\"; + case 3: return \"stf%?e\\t%1, %0\"; case 4: return output_mov_long_double_fpu_from_arm (operands); case 5: return output_mov_long_double_arm_from_fpu (operands); case 6: return output_mov_long_double_arm_from_arm (operands); } -} " -[(set_attr "length" "1,1,1,1,2,2,3") - (set_attr "type" "float,float,f_load,f_store,r_mem_f,f_mem_r,*")]) +[(set_attr "length" "4,4,4,4,8,8,12") + (set_attr "type" "ffarith,ffarith,f_load,f_store,r_mem_f,f_mem_r,*")]) ;; load- and store-multiple insns @@ -2808,7 +2621,8 @@ ops[1] = SET_DEST (XVECEXP (operands[0], 0, 1)); ops[2] = SET_DEST (XVECEXP (operands[0], 0, count - 2)); - return arm_output_asm_insn (\"ldmia\\t%0!, {%1-%2}\\t@ load multiple\", ops); + output_asm_insn (\"ldm%?ia\\t%0!, {%1-%2}\\t%@ load multiple\", ops); + return \"\"; } " [(set_attr "type" "load")]) @@ -2829,7 +2643,8 @@ ops[1] = SET_DEST (XVECEXP (operands[0], 0, 0)); ops[2] = SET_DEST (XVECEXP (operands[0], 0, count - 1)); - return arm_output_asm_insn (\"ldmia\\t%0, {%1-%2}\\t@ load multiple\", ops); + output_asm_insn (\"ldm%?ia\\t%0, {%1-%2}\\t%@ load multiple\", ops); + return \"\"; } " [(set_attr "type" "load")]) @@ -2875,7 +2690,8 @@ ops[1] = SET_SRC (XVECEXP (operands[0], 0, 1)); ops[2] = SET_SRC (XVECEXP (operands[0], 0, count - 2)); - return arm_output_asm_insn (\"stmia\\t%0!, {%1-%2}\\t@ str multiple\", ops); + output_asm_insn (\"stm%?ia\\t%0!, {%1-%2}\\t%@ str multiple\", ops); + return \"\"; } " [(set (attr "type") @@ -2901,7 +2717,8 @@ ops[1] = SET_SRC (XVECEXP (operands[0], 0, 0)); ops[2] = SET_SRC (XVECEXP (operands[0], 0, count - 1)); - return arm_output_asm_insn (\"stmia\\t%0, {%1-%2}\\t@ str multiple\", ops); + output_asm_insn (\"stm%?ia\\t%0, {%1-%2}\\t%@ str multiple\", ops); + return \"\"; } " [(set (attr "type") @@ -2915,93 +2732,16 @@ ;; We could let this apply for blocks of less than this, but it clobbers so ;; many registers that there is then probably a better way. -;; If optimizing, output redundant moves with REG_NOTES on them, this -;; produces better code. - -(define_expand "movstrsi" - [(set (match_operand:BLK 0 "general_operand" "=m") - (match_operand:BLK 1 "general_operand" "m")) - (use (match_operand:SI 2 "immediate_operand" "n")) - (use (match_operand:SI 3 "immediate_operand" "n")) - (clobber (reg:SI 0)) - (clobber (reg:SI 1)) - (clobber (reg:SI 2)) - (clobber (reg:SI 3)) - (clobber (match_scratch:SI 4 "=+r")) - (clobber (match_scratch:SI 5 "=+r"))] +(define_expand "movstrqi" + [(match_operand:BLK 0 "general_operand" "") + (match_operand:BLK 1 "general_operand" "") + (match_operand:SI 2 "const_int_operand" "") + (match_operand:SI 3 "const_int_operand" "")] "" " -{ - int words_to_go; - int i, r; - rtx const_sxteen = gen_rtx (CONST_INT, SImode, 16); - rtx src = gen_reg_rtx (SImode); - rtx dst = gen_reg_rtx (SImode); - rtx st_src, st_dst, end_src, end_dst, fin_src, fin_dst; - extern int optimize; - - if (GET_CODE (operands[2]) != CONST_INT - || GET_CODE (operands[3]) != CONST_INT - || INTVAL (operands[2]) % 4 != 0 - || INTVAL (operands[2]) < 4 - || INTVAL (operands[2]) > 64 - || INTVAL (operands[3]) < 4 - || INTVAL (operands[3]) % 4 != 0) - FAIL; - emit_move_insn (dst, st_dst = force_reg (SImode, XEXP (operands[0], 0))); - emit_move_insn (src, st_src = force_reg (SImode, XEXP (operands[1], 0))); - fin_src = src; - fin_dst = dst; - - for (i = 0, words_to_go = INTVAL (operands[2]) / 4; words_to_go >= 2; i+=4) - { - emit_insn (arm_gen_load_multiple (0, words_to_go > 4 ? 4 : words_to_go, - src, TRUE, TRUE)); - emit_insn (arm_gen_store_multiple (0, words_to_go > 4 ? 4 : words_to_go, - dst, TRUE, TRUE)); - if (optimize) - for (r = (words_to_go > 4) ? 3 : words_to_go - 1; r >= 0; r--) - { - rtx note; - note = emit_move_insn (gen_reg_rtx (SImode), - gen_rtx (REG, SImode, r)); - REG_NOTES (note) = gen_rtx (EXPR_LIST, REG_EQUIV, - gen_rtx (MEM, SImode, - plus_constant (st_src, 4*(i+r))), - REG_NOTES (note)); - REG_NOTES (note) = gen_rtx (EXPR_LIST, REG_EQUIV, - gen_rtx (MEM, SImode, - plus_constant (st_dst, 4*(i+r))), - REG_NOTES (note)); - } - words_to_go -= words_to_go < 4 ? words_to_go : 4; - } - if (words_to_go) - { - rtx sreg; - - emit_move_insn (sreg = gen_reg_rtx (SImode), gen_rtx (MEM, SImode, src)); - emit_move_insn (fin_src = gen_reg_rtx (SImode), plus_constant (src, 4)); - emit_move_insn (gen_rtx (MEM, SImode, dst), sreg); - emit_move_insn (fin_dst = gen_reg_rtx (SImode), plus_constant (dst, 4)); - } - if (optimize) - { - /* Insns for the REG_NOTES: These notes tell the optimiser where the - index registers have got to so that consecutive block moves of - contiguous data work efficiently */ - - end_src = emit_move_insn (fin_src, fin_src); - REG_NOTES (end_src) = gen_rtx(EXPR_LIST, REG_EQUAL, - plus_constant (st_src, INTVAL (operands[2])), - REG_NOTES (end_src)); - end_dst = emit_move_insn (fin_dst, fin_dst); - REG_NOTES (end_dst) = gen_rtx(EXPR_LIST, REG_EQUAL, - plus_constant (st_dst, INTVAL (operands[2])), - REG_NOTES (end_dst)); - } - DONE; -} + if (arm_gen_movstrqi (operands)) + DONE; + FAIL; ") @@ -3065,15 +2805,12 @@ (define_insn "" [(set (match_operand 0 "cc_register" "") - (compare (match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_add_operand" "rL")))] + (compare (match_operand:SI 1 "s_register_operand" "r,r") + (match_operand:SI 2 "arm_add_operand" "rI,L")))] "" - "* - if (GET_CODE (operands[2]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[2]))) - return arm_output_asm_insn (\"cmn\\t%1, #%n2\", operands); - return arm_output_asm_insn (\"cmp\\t%1, %2\", operands); -" + "@ + cmp%?\\t%1, %2 + cmn%?\\t%1, #%n2" [(set_attr "conds" "set")]) (define_insn "" @@ -3081,9 +2818,7 @@ (compare (match_operand:SI 1 "s_register_operand" "r") (neg:SI (match_operand:SI 2 "s_register_operand" "r"))))] "" - "* - return arm_output_asm_insn (\"cmn\\t%1, %2\", operands); -" + "cmn%?\\t%1, %2" [(set_attr "conds" "set")]) (define_insn "" @@ -3091,11 +2826,9 @@ (compare (match_operand:SI 1 "s_register_operand" "r") (match_operator:SI 2 "shift_operator" [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "arm_rhs_operand" "rn")])))] + (match_operand:SI 4 "arm_rhs_operand" "rM")])))] "" - "* - return output_shift_compare (operands, FALSE); -" + "cmp%?\\t%1, %3%S2" [(set_attr "conds" "set")]) (define_insn "" @@ -3103,11 +2836,9 @@ (compare (match_operand:SI 1 "s_register_operand" "r") (neg:SI (match_operator:SI 2 "shift_operator" [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "arm_rhs_operand" "rn")]))))] + (match_operand:SI 4 "arm_rhs_operand" "rM")]))))] "" - "* - return output_shift_compare (operands, TRUE); -" + "cmn%?\\t%1, %3%S2" [(set_attr "conds" "set")]) (define_insn "" @@ -3115,22 +2846,9 @@ (compare:CCFP (match_operand:SF 0 "s_register_operand" "f,f") (match_operand:SF 1 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmf\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnf\\t%0, %1\", operands); - } -} -" + "@ + cmf%?\\t%0, %1 + cnf%?\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3139,22 +2857,9 @@ (compare:CCFP (match_operand:DF 0 "s_register_operand" "f,f") (match_operand:DF 1 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmf\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnf\\t%0, %1\", operands); - } -} -" + "@ + cmf%?\\t%0, %1 + cnf%?\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3164,22 +2869,9 @@ (match_operand:SF 0 "s_register_operand" "f,f")) (match_operand:DF 1 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmf\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnf\\t%0, %1\", operands); - } -} -" + "@ + cmf%?\\t%0, %1 + cnf%?\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3189,9 +2881,7 @@ (float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))))] "" - "* - return arm_output_asm_insn (\"cmf\\t%0, %1\", operands); -" + "cmf%?\\t%0, %1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3200,22 +2890,9 @@ (compare:CCFP (match_operand:XF 0 "s_register_operand" "f,f") (match_operand:XF 1 "fpu_add_operand" "fG,H")))] "ENABLE_XF_PATTERNS" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmf\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnf\\t%0, %1\", operands); - } -} -" + "@ + cmf%?\\t%0, %1 + cnf%?\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3224,22 +2901,9 @@ (compare:CCFPE (match_operand:SF 0 "s_register_operand" "f,f") (match_operand:SF 1 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmfe\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnfe\\t%0, %1\", operands); - } -} -" + "@ + cmf%?e\\t%0, %1 + cnf%?e\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3248,22 +2912,9 @@ (compare:CCFPE (match_operand:DF 0 "s_register_operand" "f,f") (match_operand:DF 1 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmfe\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnfe\\t%0, %1\", operands); - } -} -" + "@ + cmf%?e\\t%0, %1 + cnf%?e\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3273,22 +2924,9 @@ (match_operand:SF 0 "s_register_operand" "f,f")) (match_operand:DF 1 "fpu_add_operand" "fG,H")))] "" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmfe\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnfe\\t%0, %1\", operands); - } -} -" + "@ + cmf%?e\\t%0, %1 + cnf%?e\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3298,9 +2936,7 @@ (float_extend:DF (match_operand:SF 1 "s_register_operand" "f"))))] "" - "* - return arm_output_asm_insn (\"cmfe\\t%0, %1\", operands); -" + "cmf%?e\\t%0, %1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3309,22 +2945,9 @@ (compare:CCFPE (match_operand:XF 0 "s_register_operand" "f,f") (match_operand:XF 1 "fpu_add_operand" "fG,H")))] "ENABLE_XF_PATTERNS" - "* -{ - REAL_VALUE_TYPE r; - - switch (which_alternative) - { - case 0: - return arm_output_asm_insn (\"cmfe\\t%0, %1\", operands); - case 1: - REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]); - r = REAL_VALUE_NEGATE (r); - operands[1] = CONST_DOUBLE_FROM_REAL_VALUE (r, GET_MODE (operands[1])); - return arm_output_asm_insn (\"cnfe\\t%0, %1\", operands); - } -} -" + "@ + cmf%?e\\t%0, %1 + cnf%?e\\t%0, #%N1" [(set_attr "conds" "set") (set_attr "type" "f_2_r")]) @@ -3337,7 +2960,7 @@ (define_insn "" [(set (match_operand 0 "cc_register" "") (match_dup 0))] "" - "\\t@ deleted compare" + "\\t%@ deleted compare" [(set_attr "conds" "set") (set_attr "length" "0")]) @@ -3492,7 +3115,7 @@ arm_ccfsm_state += 2; return \"\"; } - return (arm_output_asm_insn (\"b%d1\\t%l0\", operands)); + return \"b%d1\\t%l0\"; }" [(set_attr "conds" "use")]) @@ -3502,7 +3125,7 @@ [(reg 24) (const_int 0)]) (pc) (label_ref (match_operand 0 "" ""))))] - "" + "REVERSIBLE_CC_MODE (GET_MODE (XEXP (operands[1], 0)))" "* { extern int arm_ccfsm_state; @@ -3512,7 +3135,7 @@ arm_ccfsm_state += 2; return \"\"; } - return (arm_output_asm_insn (\"b%D1\\t%l0\", operands)); + return \"b%D1\\t%l0\"; }" [(set_attr "conds" "use")]) @@ -3633,36 +3256,27 @@ [(set (match_operand:SI 0 "s_register_operand" "=r") (match_operator:SI 1 "comparison_operator" [(reg 24) (const_int 0)]))] "" - "* - arm_output_asm_insn (\"mov%d1\\t%0, #1\", operands); - return arm_output_asm_insn (\"mov%D1\\t%0, #0\", operands); -" + "mov%D1\\t%0, #0\;mov%d1\\t%0, #1" [(set_attr "conds" "use") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") (neg:SI (match_operator:SI 1 "comparison_operator" [(reg 24) (const_int 0)])))] "" - "* - arm_output_asm_insn (\"mvn%d1\\t%0, #0\", operands); - return arm_output_asm_insn (\"mov%D1\\t%0, #0\", operands); -" + "mov%D1\\t%0, #0\;mvn%d1\\t%0, #0" [(set_attr "conds" "use") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") (not:SI (match_operator:SI 1 "comparison_operator" [(reg 24) (const_int 0)])))] "" - "* - arm_output_asm_insn (\"mvn%d1\\t%0, #1\", operands); - return arm_output_asm_insn (\"mov%D1\\t%0, #0\", operands); -" + "mov%D1\\t%0, #0\;mvn%d1\\t%0, #1" [(set_attr "conds" "use") - (set_attr "length" "2")]) + (set_attr "length" "8")]) ;; Jump and linkage insns @@ -3680,7 +3294,7 @@ arm_ccfsm_state += 2; return \"\"; } - return (arm_output_asm_insn (\"b\\t%l0\", operands)); + return \"b%?\\t%l0\"; }") (define_expand "call" @@ -3696,14 +3310,14 @@ (clobber (reg:SI 14))] "" "* - return (output_call (operands)); + return output_call (operands); " [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) ;; length is worst case, normally it is only two - (set_attr "length" "3") + (set_attr "length" "12") (set_attr "type" "call")]) (define_insn "" @@ -3712,13 +3326,13 @@ (clobber (reg:SI 14))] "" "* - return (output_call_mem (operands)); + return output_call_mem (operands); " [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) - (set_attr "length" "3") + (set_attr "length" "12") (set_attr "type" "call")]) (define_expand "call_value" @@ -3736,13 +3350,13 @@ (clobber (reg:SI 14))] "" "* - return (output_call (&operands[1])); + return output_call (&operands[1]); " [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) - (set_attr "length" "3") + (set_attr "length" "12") (set_attr "type" "call")]) (define_insn "" @@ -3752,13 +3366,13 @@ (clobber (reg:SI 14))] "! CONSTANT_ADDRESS_P (XEXP (operands[1], 0))" "* - return (output_call_mem (&operands[1])); + return output_call_mem (&operands[1]); " [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) - (set_attr "length" "3") + (set_attr "length" "12") (set_attr "type" "call")]) ;; Allow calls to SYMBOL_REFs specially as they are not valid general addresses @@ -3769,9 +3383,7 @@ (match_operand:SI 1 "general_operand" "g")) (clobber (reg:SI 14))] "GET_CODE (operands[0]) == SYMBOL_REF" - "* - return (arm_output_asm_insn (\"bl\\t%a0\", operands)); -" + "bl%?\\t%a0" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") @@ -3784,9 +3396,7 @@ (match_operand:SI 2 "general_operand" "g"))) (clobber (reg:SI 14))] "GET_CODE(operands[1]) == SYMBOL_REF" - "* - return (arm_output_asm_insn (\"bl\\t%a1\", operands)); -" + "bl%?\\t%a1" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") @@ -3900,37 +3510,27 @@ (match_operand:SI 0 "s_register_operand" "r")) (use (label_ref (match_operand 1 "" "")))] "" - "* - return arm_output_asm_insn (\"mov\\tpc, %0\\t@ table jump, label %l1\", - operands); -") + "mov%?\\t%|pc, %0\\t%@ table jump, label %l1") (define_insn "" [(set (pc) (match_operand:SI 0 "memory_operand" "m")) (use (label_ref (match_operand 1 "" "")))] "" - "* - return arm_output_asm_insn (\"ldr\\tpc, %0\\t@ table jump, label %l1\", - operands); -" + "ldr%?\\t%|pc, %0\\t%@ table jump, label %l1" [(set_attr "type" "load")]) (define_insn "indirect_jump" [(set (pc) (match_operand:SI 0 "s_register_operand" "r"))] "" - "* - return arm_output_asm_insn (\"mov\\tpc, %0\\t@ indirect jump\", operands); -") + "mov%?\\t%|pc, %0\\t%@ indirect jump") (define_insn "" [(set (pc) (match_operand:SI 0 "memory_operand" "m"))] "" - "* - return arm_output_asm_insn (\"ldr\\tpc, %0\\t@ indirect jump\", operands); -" + "ldr%?\\t%|pc, %0\\t%@ indirect jump" [(set_attr "type" "load")]) ;; Misc insns @@ -3938,9 +3538,7 @@ (define_insn "nop" [(const_int 0)] "" - "* - return arm_output_asm_insn (\"mov\\tr0, r0\\t@ nop\", operands); -") + "mov%?\\tr0, r0\\t%@ nop") ;; Patterns to allow combination of arithmetic, cond code and shifts @@ -3949,28 +3547,24 @@ (match_operator:SI 1 "shiftable_operator" [(match_operator:SI 3 "shift_operator" [(match_operand:SI 4 "s_register_operand" "r") - (match_operand:SI 5 "nonmemory_operand" "rI")]) + (match_operand:SI 5 "reg_or_int_operand" "rI")]) (match_operand:SI 2 "s_register_operand" "r")]))] "" - "* - return (output_arithmetic_with_shift (operands, TRUE, FALSE)); -") + "%i1%?\\t%0, %2, %4%S3") (define_insn "" [(set (reg:CC_NOOV 24) (compare:CC_NOOV (match_operator:SI 1 "shiftable_operator" [(match_operator:SI 3 "shift_operator" [(match_operand:SI 4 "s_register_operand" "r") - (match_operand:SI 5 "nonmemory_operand" "rI")]) + (match_operand:SI 5 "reg_or_int_operand" "rI")]) (match_operand:SI 2 "s_register_operand" "r")]) (const_int 0))) (set (match_operand:SI 0 "s_register_operand" "=r") (match_op_dup 1 [(match_op_dup 3 [(match_dup 4) (match_dup 5)]) (match_dup 2)]))] "" - "* - return (output_arithmetic_with_shift (operands, TRUE, TRUE)); -" + "%i1%?s\\t%0, %2, %4%S3" [(set_attr "conds" "set")]) (define_insn "" @@ -3978,14 +3572,12 @@ (compare:CC_NOOV (match_operator:SI 1 "shiftable_operator" [(match_operator:SI 3 "shift_operator" [(match_operand:SI 4 "s_register_operand" "r") - (match_operand:SI 5 "nonmemory_operand" "rI")]) + (match_operand:SI 5 "reg_or_int_operand" "rI")]) (match_operand:SI 2 "s_register_operand" "r")]) (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* - return (output_arithmetic_with_shift (operands, TRUE, TRUE)); -" + "%i1%?s\\t%0, %2, %4%S3" [(set_attr "conds" "set")]) (define_insn "" @@ -3993,70 +3585,36 @@ (minus:SI (match_operand:SI 1 "s_register_operand" "r") (match_operator:SI 2 "shift_operator" [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "nonmemory_operand" "rn")])))] + (match_operand:SI 4 "reg_or_int_operand" "rM")])))] "" - "* -{ - rtx ops[6]; - - ops[0] = operands[0]; - ops[1] = gen_rtx (MINUS, SImode, operands[1], operands[2]); - ops[2] = operands[1]; - ops[3] = operands[2]; - ops[4] = operands[3]; - ops[5] = operands[4]; - return output_arithmetic_with_shift (ops, FALSE, FALSE); -} -") + "sub%?\\t%0, %1, %3%S2") (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (minus:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operator:SI 2 "shift_operator" - [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "nonmemory_operand" "rn")])) - (const_int 0))) + (compare:CC_NOOV + (minus:SI (match_operand:SI 1 "s_register_operand" "r") + (match_operator:SI 2 "shift_operator" + [(match_operand:SI 3 "s_register_operand" "r") + (match_operand:SI 4 "reg_or_int_operand" "rM")])) + (const_int 0))) (set (match_operand:SI 0 "s_register_operand" "=r") (minus:SI (match_dup 1) (match_op_dup 2 [(match_dup 3) (match_dup 4)])))] "" - "* -{ - rtx ops[6]; - - ops[0] = operands[0]; - ops[1] = gen_rtx (MINUS, SImode, operands[1], operands[2]); - ops[2] = operands[1]; - ops[3] = operands[2]; - ops[4] = operands[3]; - ops[5] = operands[4]; - return output_arithmetic_with_shift (ops, FALSE, TRUE); -} -" + "sub%?s\\t%0, %1, %3%S2" [(set_attr "conds" "set")]) (define_insn "" [(set (reg:CC_NOOV 24) - (compare:CC_NOOV (minus:SI (match_operand:SI 1 "s_register_operand" "r") - (match_operator:SI 2 "shift_operator" - [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "nonmemory_operand" "rn")])) - (const_int 0))) + (compare:CC_NOOV + (minus:SI (match_operand:SI 1 "s_register_operand" "r") + (match_operator:SI 2 "shift_operator" + [(match_operand:SI 3 "s_register_operand" "r") + (match_operand:SI 4 "reg_or_int_operand" "rM")])) + (const_int 0))) (clobber (match_scratch:SI 0 "=r"))] "" - "* -{ - rtx ops[6]; - - ops[0] = operands[0]; - ops[1] = gen_rtx (MINUS, SImode, operands[1], operands[2]); - ops[2] = operands[1]; - ops[3] = operands[2]; - ops[4] = operands[3]; - ops[5] = operands[4]; - return output_arithmetic_with_shift (ops, FALSE, TRUE); -} -" + "sub%?s\\t%0, %1, %3%S2" [(set_attr "conds" "set")]) ;; These variants of the above insns can occur if the first operand is the @@ -4071,22 +3629,18 @@ [(set (match_operand:SI 0 "" "=&r") (plus:SI (plus:SI (match_operator:SI 5 "shift_operator" [(match_operand:SI 3 "" "r") - (match_operand:SI 4 "" "rn")]) + (match_operand:SI 4 "" "rM")]) (match_operand:SI 2 "" "r")) (match_operand:SI 1 "const_int_operand" "n")))] "reload_in_progress" "* -{ - char instr[100]; - sprintf (instr, \"add\\t%%0, %%2, %%3, %s %%4\", - shift_instr (GET_CODE (operands[5]), &operands[4])); - arm_output_asm_insn (instr, operands); + output_asm_insn (\"add%?\\t%0, %2, %3%S5\", operands); operands[2] = operands[1]; operands[1] = operands[0]; return output_add_immediate (operands); -}" +" ; we have no idea how long the add_immediate is, it could be up to 4. -[(set_attr "length" "5")]) +[(set_attr "length" "20")]) (define_insn "" [(set (reg:CC_NOOV 24) @@ -4094,7 +3648,7 @@ (plus:SI (match_operator:SI 5 "shift_operator" [(match_operand:SI 3 "" "r") - (match_operand:SI 4 "" "rn")]) + (match_operand:SI 4 "" "rM")]) (match_operand:SI 1 "" "r")) (match_operand:SI 2 "const_int_operand" "n")) (const_int 0))) @@ -4104,15 +3658,11 @@ (match_dup 2)))] "reload_in_progress" "* -{ - char instr[100]; - sprintf (instr, \"adds\\t%%0, %%0, %%3, %s %%4\", - shift_instr (GET_CODE (operands[5]), &operands[4])); output_add_immediate (operands); - return arm_output_asm_insn (instr, operands); -}" + return \"add%?s\\t%0, %0, %3%S5\"; +" [(set_attr "conds" "set") - (set_attr "length" "5")]) + (set_attr "length" "20")]) (define_insn "" [(set (reg:CC_NOOV 24) @@ -4120,22 +3670,18 @@ (plus:SI (match_operator:SI 5 "shift_operator" [(match_operand:SI 3 "" "r") - (match_operand:SI 4 "" "rn")]) + (match_operand:SI 4 "" "rM")]) (match_operand:SI 1 "" "r")) (match_operand:SI 2 "const_int_operand" "n")) (const_int 0))) (clobber (match_scratch:SI 0 "=&r"))] "reload_in_progress" "* -{ - char instr[100]; - sprintf (instr, \"adds\\t%%0, %%0, %%3, %s %%4\", - shift_instr (GET_CODE (operands[5]), &operands[4])); output_add_immediate (operands); - return arm_output_asm_insn (instr, operands); -}" + return \"add%?s\\t%0, %0, %3%S5\"; +" [(set_attr "conds" "set") - (set_attr "length" "5")]) + (set_attr "length" "20")]) ;; These are similar, but are needed when the mla pattern contains the ;; eliminated register as operand 3. @@ -4148,12 +3694,12 @@ (match_operand:SI 4 "const_int_operand" "n,n")))] "reload_in_progress" "* - arm_output_asm_insn (\"mla\\t%0, %2, %1, %3\", operands); + output_asm_insn (\"mla%?\\t%0, %2, %1, %3\", operands); operands[2] = operands[4]; operands[1] = operands[0]; return output_add_immediate (operands); " -[(set_attr "length" "5")]) +[(set_attr "length" "20")]) (define_insn "" [(set (reg:CC_NOOV 24) @@ -4169,9 +3715,10 @@ "reload_in_progress" "* output_add_immediate (operands); - return arm_output_asm_insn (\"mlas\\t%0, %3, %4, %0\", operands); + output_asm_insn (\"mla%?s\\t%0, %3, %4, %0\", operands); + return \"\"; " -[(set_attr "length" "5") +[(set_attr "length" "20") (set_attr "conds" "set")]) (define_insn "" @@ -4186,9 +3733,9 @@ "reload_in_progress" "* output_add_immediate (operands); - return arm_output_asm_insn (\"mlas\\t%0, %3, %4, %0\", operands); + return \"mla%?s\\t%0, %3, %4, %0\"; " -[(set_attr "length" "5") +[(set_attr "length" "20") (set_attr "conds" "set")]) @@ -4197,15 +3744,12 @@ (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") (and:SI (match_operator 1 "comparison_operator" - [(reg 24) (const_int 0)]) + [(match_operand 3 "reversible_cc_register" "") (const_int 0)]) (match_operand:SI 2 "s_register_operand" "r")))] "" - "* - arm_output_asm_insn (\"mov%D1\\t%0, #0\", operands); - return arm_output_asm_insn (\"and%d1\\t%0, %2, #1\", operands); -" + "mov%D1\\t%0, #0\;and%d1\\t%0, %2, #1" [(set_attr "conds" "use") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") @@ -4213,48 +3757,40 @@ [(reg 24) (const_int 0)]) (match_operand:SI 1 "s_register_operand" "0,?r")))] "" - "* - if (which_alternative != 0) - arm_output_asm_insn (\"mov%D2\\t%0, %1\", operands); - return arm_output_asm_insn (\"orr%d2\\t%0, %1, #1\", operands); -" + "@ + orr%d2\\t%0, %1, #1 + mov%D2\\t%0, %1\;orr%d2\\t%0, %1, #1" [(set_attr "conds" "use") - (set_attr "length" "1,2")]) + (set_attr "length" "4,8")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r") + [(set (match_operand:SI 0 "s_register_operand" "=r,r") (match_operator 1 "comparison_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_add_operand" "rL")])) + [(match_operand:SI 2 "s_register_operand" "r,r") + (match_operand:SI 3 "arm_add_operand" "rI,L")])) (clobber (reg 24))] "" "* if (GET_CODE (operands[1]) == LT && operands[3] == const0_rtx) - return arm_output_asm_insn (\"mov\\t%0, %2, lsr #31\", operands); + return \"mov\\t%0, %2, lsr #31\"; + if (GET_CODE (operands[1]) == GE && operands[3] == const0_rtx) - { - arm_output_asm_insn (\"mvn\\t%0, %2\", operands); - return arm_output_asm_insn (\"mov\\t%0, %0, lsr #31\", operands); - } + return \"mvn\\t%0, %2\;mov\\t%0, %0, lsr #31\"; + if (GET_CODE (operands[1]) == NE) { - if (GET_CODE (operands[3]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"adds\\t%0, %2, #%n3\", operands); - else - arm_output_asm_insn (\"subs\\t%0, %2, %3\", operands); - return arm_output_asm_insn (\"movne\\t%0, #1\", operands); + if (which_alternative == 1) + return \"adds\\t%0, %2, #%n3\;movne\\t%0, #1\"; + return \"subs\\t%0, %2, %3\;movne\\t%0, #1\"; } - if (GET_CODE (operands[3]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"cmn\\t%2, #%n3\", operands); + if (which_alternative == 1) + output_asm_insn (\"cmn\\t%2, #%n3\", operands); else - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); - arm_output_asm_insn (\"mov%D1\\t%0, #0\", operands); - return arm_output_asm_insn (\"mov%d1\\t%0, #1\", operands); + output_asm_insn (\"cmp\\t%2, %3\", operands); + return \"mov%D1\\t%0, #0\;mov%d1\\t%0, #1\"; " [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=&r") @@ -4271,42 +3807,37 @@ int dominant = comparison_dominates_p (GET_CODE (operands[4]), GET_CODE (operands[1])); - arm_output_asm_insn (dominant ? \"cmp\\t%5, %6\" : \"cmp\\t%2, %3\", - operands); - arm_output_asm_insn (\"mov\\t%0, #0\", operands); + output_asm_insn (dominant ? \"cmp\\t%5, %6\" : \"cmp\\t%2, %3\", + operands); + output_asm_insn (\"mov\\t%0, #0\", operands); if (GET_CODE (operands[1]) == GET_CODE (operands[4]) || comparison_dominates_p (GET_CODE (operands[1]), GET_CODE (operands[4])) || dominant) - { - arm_output_asm_insn (dominant ? \"cmp%D4\\t%2, %3\" : \"cmp%D1\\t%5,%6\", - operands); - } + output_asm_insn (dominant ? \"cmp%D4\\t%2, %3\" : \"cmp%D1\\t%5,%6\", + operands); else - { - arm_output_asm_insn (\"mov%d1\\t%0, #1\", operands); - arm_output_asm_insn (\"cmp\\t%5, %6\", operands); - } - return arm_output_asm_insn (dominant ? \"mov%d1\\t%0, #1\" - : \"mov%d4\\t%0, #1\", operands); + output_asm_insn (\"mov%d1\\t%0, #1\;cmp\\t%5, %6\", operands); + return dominant ? \"mov%d1\\t%0, #1\" : \"mov%d4\\t%0, #1\"; } " [(set_attr "conds" "clob") ; worst case length - (set_attr "length" "5")]) + (set_attr "length" "20")]) (define_split [(set (pc) - (if_then_else (match_operator 5 "equality_operator" - [(ior:SI (match_operator 6 "comparison_operator" - [(match_operand:SI 0 "s_register_operand" "r") - (match_operand:SI 1 "arm_add_operand" "rL")]) - (match_operator 7 "comparison_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_add_operand" "rL")])) - (const_int 0)]) - (label_ref (match_operand 4 "" "")) - (pc))) + (if_then_else + (match_operator 5 "equality_operator" + [(ior:SI (match_operator 6 "comparison_operator" + [(match_operand:SI 0 "s_register_operand" "") + (match_operand:SI 1 "arm_add_operand" "")]) + (match_operator 7 "comparison_operator" + [(match_operand:SI 2 "s_register_operand" "") + (match_operand:SI 3 "arm_add_operand" "")])) + (const_int 0)]) + (label_ref (match_operand 4 "" "")) + (pc))) (clobber (reg 24))] "(GET_CODE (operands[6]) == GET_CODE (operands[7]) || comparison_dominates_p (GET_CODE (operands[6]), GET_CODE (operands[7])) @@ -4342,16 +3873,16 @@ (define_insn "" [(set (pc) - (if_then_else (ne - (ior:SI (match_operator 5 "comparison_operator" - [(match_operand:SI 0 "s_register_operand" "r") - (match_operand:SI 1 "arm_add_operand" "rL")]) - (match_operator 6 "comparison_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rL")])) - (const_int 0)) - (label_ref (match_operand 4 "" "")) - (pc))) + (if_then_else + (ne (ior:SI (match_operator 5 "comparison_operator" + [(match_operand:SI 0 "s_register_operand" "r,r,r,r") + (match_operand:SI 1 "arm_add_operand" "rI,L,rI,L")]) + (match_operator 6 "comparison_operator" + [(match_operand:SI 2 "s_register_operand" "r,r,r,r") + (match_operand:SI 3 "arm_rhs_operand" "rI,rI,L,L")])) + (const_int 0)) + (label_ref (match_operand 4 "" "")) + (pc))) (clobber (reg 24))] "!(GET_CODE (operands[5]) == GET_CODE (operands[6]) || comparison_dominates_p (GET_CODE (operands[5]), GET_CODE (operands[6])) @@ -4360,64 +3891,63 @@ { extern int arm_ccfsm_state; - if (GET_CODE (operands[1]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[1]))) - arm_output_asm_insn (\"cmn\\t%0, #%n1\", operands); + if (which_alternative & 1) + output_asm_insn (\"cmn\\t%0, #%n1\;b%d5\\t%l4\", operands); else - arm_output_asm_insn (\"cmp\\t%0, %1\", operands); - arm_output_asm_insn (\"b%d5\\t%l4\", operands); - if (GET_CODE (operands[3]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"cmn\\t%2, #%n3\", operands); + output_asm_insn (\"cmp\\t%0, %1\;b%d5\\t%l4\", operands); + + if (which_alternative >= 2) + output_asm_insn (\"cmn\\t%2, #%n3\", operands); else - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); + output_asm_insn (\"cmp\\t%2, %3\", operands); + if (arm_ccfsm_state == 1 || arm_ccfsm_state == 2) { arm_ccfsm_state += 2; return \"\"; } - return arm_output_asm_insn (\"b%d6\\t%l4\", operands); + return \"b%d6\\t%l4\"; }" [(set_attr "conds" "jump_clob") - (set_attr "length" "4")]) + (set_attr "length" "16")]) (define_insn "" [(set (reg:CC 24) - (compare:CC (ior:CC (match_operator 4 "comparison_operator" - [(match_operand:SI 0 "s_register_operand" "r") - (match_operand:SI 1 "arm_add_operand" "rL")]) - (match_operator 5 "comparison_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_add_operand" "rL")])) - (const_int 0)))] + (compare:CC + (ior:CC (match_operator 4 "comparison_operator" + [(match_operand:SI 0 "s_register_operand" "r,r,r,r") + (match_operand:SI 1 "arm_add_operand" "rI,L,rI,L")]) + (match_operator 5 "comparison_operator" + [(match_operand:SI 2 "s_register_operand" "r,r,r,r") + (match_operand:SI 3 "arm_add_operand" "rI,rI,L,L")])) + (const_int 0)))] "(GET_CODE (operands[4]) == GET_CODE (operands[5]) || comparison_dominates_p (GET_CODE (operands[4]), GET_CODE (operands[5])) || comparison_dominates_p (GET_CODE (operands[5]), GET_CODE (operands[4])))" "* if (comparison_dominates_p (GET_CODE (operands[5]), GET_CODE (operands[4]))) { - if (GET_CODE (operands[3]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"cmn\\t%2, #%n3\", operands); + if (which_alternative >= 2) + output_asm_insn (\"cmn\\t%2, #%n3\", operands); else - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); - if (GET_CODE (operands[1]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[1]))) - return arm_output_asm_insn (\"cmn%D5\\t%0, #%n1\", operands); - return arm_output_asm_insn (\"cmp%D5\\t%0, %1\", operands); + output_asm_insn (\"cmp\\t%2, %3\", operands); + + if (which_alternative & 1) + return \"cmn%D5\\t%0, #%n1\"; + return \"cmp%D5\\t%0, %1\"; } - if (GET_CODE (operands[1]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[1]))) - arm_output_asm_insn (\"cmn\\t%0, #%n1\", operands); + + if (which_alternative & 1) + output_asm_insn (\"cmn\\t%0, #%n1\", operands); else - arm_output_asm_insn (\"cmp\\t%0, %1\", operands); - if (GET_CODE (operands[3]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[3]))) - return arm_output_asm_insn (\"cmn%D4\\t%2, #%n3\", operands); - return arm_output_asm_insn (\"cmp%D4\\t%2, %3\", operands); + output_asm_insn (\"cmp\\t%0, %1\", operands); + + if (which_alternative >= 2) + return \"cmn%D4\\t%2, #%n3\"; + return \"cmp%D4\\t%2, %3\"; " [(set_attr "conds" "set") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") @@ -4431,20 +3961,20 @@ "* if (GET_CODE (operands[3]) == NE) { - if (which_alternative != 0) - arm_output_asm_insn (\"mov%d4\\t%0, %1\", operands); if (which_alternative != 1) - arm_output_asm_insn (\"mov%D4\\t%0, %2\", operands); + output_asm_insn (\"mov%D4\\t%0, %2\", operands); + if (which_alternative != 0) + output_asm_insn (\"mov%d4\\t%0, %1\", operands); return \"\"; } if (which_alternative != 0) - arm_output_asm_insn (\"mov%D4\\t%0, %1\", operands); + output_asm_insn (\"mov%D4\\t%0, %1\", operands); if (which_alternative != 1) - arm_output_asm_insn (\"mov%d4\\t%0, %2\", operands); + output_asm_insn (\"mov%d4\\t%0, %2\", operands); return \"\"; " [(set_attr "conds" "use") - (set_attr "length" "1,1,2")]) + (set_attr "length" "4,4,8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") @@ -4456,26 +3986,18 @@ (clobber (reg 24))] "" "* -{ - char *instr = arithmetic_instr (operands[5], TRUE); - char pattern[100]; - if (GET_CODE (operands[4]) == LT && operands[3] == const0_rtx) - { - sprintf (pattern, \"%s\\t%%0, %%1, %%2, lsr #31\", instr); - return arm_output_asm_insn (pattern, operands); - } - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); + return \"%i5\\t%0, %1, %2, lsr #31\"; + + output_asm_insn (\"cmp\\t%2, %3\", operands); if (GET_CODE (operands[5]) == AND) - arm_output_asm_insn (\"mov%D4\\t%0, #0\", operands); + output_asm_insn (\"mov%D4\\t%0, #0\", operands); else if (which_alternative != 0) - arm_output_asm_insn (\"mov%D4\\t%0, %1\", operands); - sprintf (pattern, \"%s%%d4\\t%%0, %%1, #1\", instr); - return arm_output_asm_insn (pattern, operands); -} + output_asm_insn (\"mov%D4\\t%0, %1\", operands); + return \"%i5%d4\\t%0, %1, #1\"; " [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") @@ -4486,13 +4008,13 @@ (clobber (reg 24))] "" "* - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); + output_asm_insn (\"cmp\\t%2, %3\", operands); if (which_alternative != 0) - arm_output_asm_insn (\"mov%D4\\t%0, %1\", operands); - return arm_output_asm_insn (\"sub%d4\\t%0, %1, #1\", operands); + output_asm_insn (\"mov%D4\\t%0, %1\", operands); + return \"sub%d4\\t%0, %1, #1\"; " [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=&r") @@ -4513,35 +4035,34 @@ : comparison_dominates_p (reverse_condition (GET_CODE (operands[4])), reverse_condition (GET_CODE (operands[1]))) ? 2 : 0; - arm_output_asm_insn (dominant == 2 ? \"cmp\\t%5, %6\" : \"cmp\\t%2, %3\", + output_asm_insn (dominant == 2 ? \"cmp\\t%5, %6\" : \"cmp\\t%2, %3\", operands); - arm_output_asm_insn (\"mov\\t%0, #1\", operands); + output_asm_insn (\"mov\\t%0, #1\", operands); if (GET_CODE (operands[1]) == GET_CODE (operands[4]) || dominant) { - arm_output_asm_insn (dominant == 2 ? \"cmp%d4\\t%2, %3\" + output_asm_insn (dominant == 2 ? \"cmp%d4\\t%2, %3\" : \"cmp%d1\\t%5, %6\", operands); } else { - arm_output_asm_insn (\"mov%D1\\t%0, #0\", operands); - arm_output_asm_insn (\"cmp\\t%5, %6\", operands); + output_asm_insn (\"mov%D1\\t%0, #0\", operands); + output_asm_insn (\"cmp\\t%5, %6\", operands); } - return arm_output_asm_insn (dominant == 2 ? \"mov%D1\\t%0, #0\" - : \"mov%D4\\t%0, #0\", operands); + return dominant == 2 ? \"mov%D1\\t%0, #0\" : \"mov%D4\\t%0, #0\"; } " [(set_attr "conds" "clob") - (set_attr "length" "5")]) + (set_attr "length" "20")]) (define_split [(set (pc) (if_then_else (match_operator 1 "equality_operator" [(and:SI (match_operator 2 "comparison_operator" - [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "arm_add_operand" "rL")]) + [(match_operand:SI 3 "s_register_operand" "") + (match_operand:SI 4 "arm_add_operand" "")]) (match_operator 0 "comparison_operator" - [(match_operand:SI 5 "s_register_operand" "r") - (match_operand:SI 6 "arm_add_operand" "rL")])) + [(match_operand:SI 5 "s_register_operand" "") + (match_operand:SI 6 "arm_add_operand" "")])) (const_int 0)]) (label_ref (match_operand 7 "" "")) (pc))) @@ -4589,16 +4110,16 @@ (define_insn "" [(set (pc) - (if_then_else (eq - (and:SI (match_operator 1 "comparison_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_add_operand" "rL")]) - (match_operator 4 "comparison_operator" - [(match_operand:SI 5 "s_register_operand" "r") - (match_operand:SI 6 "arm_rhs_operand" "rL")])) - (const_int 0)) - (label_ref (match_operand 0 "" "")) - (pc))) + (if_then_else + (eq (and:SI (match_operator 1 "comparison_operator" + [(match_operand:SI 2 "s_register_operand" "r,r,r,r") + (match_operand:SI 3 "arm_add_operand" "rI,L,rI,L")]) + (match_operator 4 "comparison_operator" + [(match_operand:SI 5 "s_register_operand" "r,r,r,r") + (match_operand:SI 6 "arm_rhs_operand" "rI,rI,L,L")])) + (const_int 0)) + (label_ref (match_operand 0 "" "")) + (pc))) (clobber (reg 24))] "!(GET_CODE (operands[1]) == GET_CODE (operands[4]) || comparison_dominates_p (reverse_condition (GET_CODE (operands[1])), @@ -4609,26 +4130,25 @@ { extern int arm_ccfsm_state; - if (GET_CODE (operands[3]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"cmn\\t%2, #%n3\", operands); + if (which_alternative & 1) + output_asm_insn (\"cmn\\t%2, #%n3\;b%D1\\t%l0\", operands); else - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); - arm_output_asm_insn (\"b%D1\\t%l0\", operands); - if (GET_CODE (operands[6]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[6]))) - arm_output_asm_insn (\"cmn\\t%5, #%n6\", operands); + output_asm_insn (\"cmp\\t%2, %3\;b%D1\\t%l0\", operands); + + if (which_alternative >= 2) + output_asm_insn (\"cmn\\t%5, #%n6\", operands); else - arm_output_asm_insn (\"cmp\\t%5, %6\", operands); + output_asm_insn (\"cmp\\t%5, %6\", operands); + if (arm_ccfsm_state == 1 || arm_ccfsm_state == 2) { arm_ccfsm_state += 2; return \"\"; } - return arm_output_asm_insn (\"b%D4\\t%l0\", operands); + return \"b%D4\\t%l0\"; }" [(set_attr "conds" "jump_clob") - (set_attr "length" "4")]) + (set_attr "length" "16")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") @@ -4639,126 +4159,107 @@ "" "* if (GET_CODE (operands[3]) == LT && operands[3] == const0_rtx) - return arm_output_asm_insn (\"mov\\t%0, %1, asr #31\", operands); + return \"mov\\t%0, %1, asr #31\"; + if (GET_CODE (operands[3]) == NE) - { - arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"mvnne\\t%0, #0\", operands); - } + return \"subs\\t%0, %1, %2\;mvnne\\t%0, #0\"; + if (GET_CODE (operands[3]) == GT) - { - arm_output_asm_insn (\"subs\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"mvnne\\t%0, %0, asr #31\", operands); - } - arm_output_asm_insn (\"cmp\\t%1, %2\", operands); - arm_output_asm_insn (\"mov%D3\\t%0, #0\", operands); - return arm_output_asm_insn (\"mvn%d3\\t%0, #0\", operands); + return \"subs\\t%0, %1, %2\;mvnne\\t%0, %0, asr #31\"; + + output_asm_insn (\"cmp\\t%1, %2\", operands); + output_asm_insn (\"mov%D3\\t%0, #0\", operands); + return \"mvn%d3\\t%0, #0\"; " [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "movcond" [(set (match_operand:SI 0 "s_register_operand" "=r,r,r") - (if_then_else:SI (match_operator 5 "comparison_operator" - [(match_operand:SI 3 "s_register_operand" "r,r,r") - (match_operand:SI 4 "arm_add_operand" "rL,rL,rL")]) - (match_operand:SI 1 "arm_rhs_operand" "0,rI,?rI") - (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI"))) + (if_then_else:SI + (match_operator 5 "comparison_operator" + [(match_operand:SI 3 "s_register_operand" "r,r,r") + (match_operand:SI 4 "arm_add_operand" "rIL,rIL,rIL")]) + (match_operand:SI 1 "arm_rhs_operand" "0,rI,?rI") + (match_operand:SI 2 "arm_rhs_operand" "rI,0,rI"))) (clobber (reg 24))] "" "* if (GET_CODE (operands[5]) == LT && (operands[4] == const0_rtx)) { - if (which_alternative != 1 && GET_CODE (operands[4]) == REG) + if (which_alternative != 1 && GET_CODE (operands[1]) == REG) { - arm_output_asm_insn (\"ands\\t%0, %1, %3, asr #32\", operands); if (operands[2] == const0_rtx) - return \"\"; - return arm_output_asm_insn (\"movcc\\t%0, %2\", operands); + return \"and\\t%0, %1, %3, asr #31\"; + return \"ands\\t%0, %1, %3, asr #32\;movcc\\t%0, %2\"; } else if (which_alternative != 0 && GET_CODE (operands[2]) == REG) { - arm_output_asm_insn (\"bics\\t%0, %2, %3, asr #32\", operands); if (operands[1] == const0_rtx) - return \"\"; - return arm_output_asm_insn (\"movcs\\t%0, %1\", operands); + return \"bic\\t%0, %2, %3, asr #31\"; + return \"bics\\t%0, %2, %3, asr #32\;movcs\\t%0, %1\"; } /* The only case that falls through to here is when both ops 1 & 2 are constants */ } + if (GET_CODE (operands[5]) == GE && (operands[4] == const0_rtx)) { if (which_alternative != 1 && GET_CODE (operands[1]) == REG) { - arm_output_asm_insn (\"bics\\t%0, %1, %3, asr #32\", operands); if (operands[2] == const0_rtx) - return \"\"; - return arm_output_asm_insn (\"movcs\\t%0, %2\", operands); + return \"bic\\t%0, %1, %3, asr #31\"; + return \"bics\\t%0, %1, %3, asr #32\;movcs\\t%0, %2\"; } else if (which_alternative != 0 && GET_CODE (operands[2]) == REG) { - arm_output_asm_insn (\"ands\\t%0, %2, %3, asr #32\", operands); if (operands[1] == const0_rtx) - return \"\"; - return arm_output_asm_insn (\"movcc\\t%0, %1\", operands); + return \"and\\t%0, %2, %3, asr #31\"; + return \"ands\\t%0, %2, %3, asr #32\;movcc\\t%0, %1\"; } /* The only case that falls through to here is when both ops 1 & 2 are constants */ } if (GET_CODE (operands[4]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[4]))) - arm_output_asm_insn (\"cmn\\t%3, #%n4\", operands); + output_asm_insn (\"cmn\\t%3, #%n4\", operands); else - arm_output_asm_insn (\"cmp\\t%3, %4\", operands); + output_asm_insn (\"cmp\\t%3, %4\", operands); if (which_alternative != 0) - arm_output_asm_insn (\"mov%d5\\t%0, %1\", operands); + output_asm_insn (\"mov%d5\\t%0, %1\", operands); if (which_alternative != 1) - arm_output_asm_insn (\"mov%D5\\t%0, %2\", operands); + output_asm_insn (\"mov%D5\\t%0, %2\", operands); return \"\"; " [(set_attr "conds" "clob") - (set_attr "length" "2,2,3")]) + (set_attr "length" "8,8,12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r") + [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 9 "comparison_operator" - [(match_operand:SI 5 "s_register_operand" "r") - (match_operand:SI 6 "arm_add_operand" "rL")]) + [(match_operand:SI 5 "s_register_operand" "r,r") + (match_operand:SI 6 "arm_add_operand" "rI,L")]) (match_operator:SI 8 "shiftable_operator" - [(match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rI")]) + [(match_operand:SI 1 "s_register_operand" "r,r") + (match_operand:SI 2 "arm_rhs_operand" "rI,rI")]) (match_operator:SI 7 "shiftable_operator" - [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "arm_rhs_operand" "rI")]))) + [(match_operand:SI 3 "s_register_operand" "r,r") + (match_operand:SI 4 "arm_rhs_operand" "rI,rI")]))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[6]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[6]))) - arm_output_asm_insn (\"cmn\\t%5, #%n6\", operands); - else - arm_output_asm_insn (\"cmp\\t%5, %6\", operands); - sprintf (pattern, \"%s%%d9\\t%%0, %%1, %%2\", arithmetic_instr (operands[8], - FALSE)); - arm_output_asm_insn (pattern, operands); - sprintf (pattern, \"%s%%D9\\t%%0, %%3, %%4\", arithmetic_instr (operands[7], - FALSE)); - return arm_output_asm_insn (pattern, operands); -} -" + "@ + cmp\\t%5, %6\;%I8%d9\\t%0, %1, %2\;%I7%D9\\t%0, %3, %4 + cmn\\t%5, #%n6\;%I8%d9\\t%0, %1, %2\;%I7%D9\\t%0, %3, %4" [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 6 "comparison_operator" [(match_operand:SI 2 "s_register_operand" "r,r") - (match_operand:SI 3 "arm_add_operand" "rL,rL")]) + (match_operand:SI 3 "arm_add_operand" "rIL,rIL")]) (match_operator:SI 7 "shiftable_operator" [(match_operand:SI 4 "s_register_operand" "r,r") (match_operand:SI 5 "arm_rhs_operand" "rI,rI")]) @@ -4766,9 +4267,6 @@ (clobber (reg 24))] "" "* -{ - char pattern[100]; - /* If we have an operation where (op x 0) is the identity operation and the condtional operator is LT or GE and we are comparing against zero and everything is in registers then we can do this in two instructions */ @@ -4780,46 +4278,33 @@ && REGNO (operands[4]) != REGNO (operands[0])) { if (GET_CODE (operands[6]) == LT) - { - arm_output_asm_insn (\"and\\t%0, %5, %2, asr #31\", operands); - sprintf (pattern, \"%s\\t%%0, %%4, %%0\", - arithmetic_instr (operands[7], FALSE)); - return arm_output_asm_insn (pattern, operands); - } + return \"and\\t%0, %5, %2, asr #31\;%I7\\t%0, %4, %0\"; else if (GET_CODE (operands[6]) == GE) - { - arm_output_asm_insn (\"bic\\t%0, %5, %2, asr #31\", operands); - sprintf (pattern, \"%s\\t%%0, %%4, %%0\", - arithmetic_instr (operands[7], FALSE)); - return arm_output_asm_insn (pattern, operands); - } + return \"bic\\t%0, %5, %2, asr #31\;%I7\\t%0, %4, %0\"; } if (GET_CODE (operands[3]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"cmn\\t%2, #%n3\", operands); + output_asm_insn (\"cmn\\t%2, #%n3\", operands); else - arm_output_asm_insn (\"cmp\\t%2, %3\", operands); - sprintf (pattern, \"%s%%d6\\t%%0, %%4, %%5\", arithmetic_instr (operands[7], - FALSE)); - arm_output_asm_insn (pattern, operands); + output_asm_insn (\"cmp\\t%2, %3\", operands); + output_asm_insn (\"%I7%d6\\t%0, %4, %5\", operands); if (which_alternative != 0) { if (GET_CODE (operands[1]) == MEM) - arm_output_asm_insn (\"ldr%D6\\t%0, %1\", operands); + return \"ldr%D6\\t%0, %1\"; else - arm_output_asm_insn (\"mov%D6\\t%0, %1\", operands); + return \"mov%D6\\t%0, %1\"; } return \"\"; -} " [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 6 "comparison_operator" [(match_operand:SI 4 "s_register_operand" "r,r") - (match_operand:SI 5 "arm_add_operand" "rL,rL")]) + (match_operand:SI 5 "arm_add_operand" "rIL,rIL")]) (match_operand:SI 1 "arm_rhsm_operand" "0,?rIm") (match_operator:SI 7 "shiftable_operator" [(match_operand:SI 2 "s_register_operand" "r,r") @@ -4827,9 +4312,6 @@ (clobber (reg 24))] "" "* -{ - char pattern[100]; - /* If we have an operation where (op x 0) is the identity operation and the condtional operator is LT or GE and we are comparing against zero and everything is in registers then we can do this in two instructions */ @@ -4841,45 +4323,34 @@ && REGNO (operands[2]) != REGNO (operands[0])) { if (GET_CODE (operands[6]) == GE) - { - arm_output_asm_insn (\"and\\t%0, %3, %4, asr #31\", operands); - sprintf (pattern, \"%s\\t%%0, %%2, %%0\", - arithmetic_instr (operands[7], FALSE)); - return arm_output_asm_insn (pattern, operands); - } + return \"and\\t%0, %3, %4, asr #31\;%I7\\t%0, %2, %0\"; else if (GET_CODE (operands[6]) == LT) - { - arm_output_asm_insn (\"bic\\t%0, %3, %4, asr #31\", operands); - sprintf (pattern, \"%s\\t%%0, %%2, %%0\", - arithmetic_instr (operands[7], FALSE)); - return arm_output_asm_insn (pattern, operands); - } + return \"bic\\t%0, %3, %4, asr #31\;%I7\\t%0, %2, %0\"; } + if (GET_CODE (operands[5]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); + output_asm_insn (\"cmn\\t%4, #%n5\", operands); else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); + output_asm_insn (\"cmp\\t%4, %5\", operands); + if (which_alternative != 0) { if (GET_CODE (operands[1]) == MEM) - arm_output_asm_insn (\"ldr%d6\\t%0, %1\", operands); + output_asm_insn (\"ldr%d6\\t%0, %1\", operands); else - arm_output_asm_insn (\"mov%d6\\t%0, %1\", operands); + output_asm_insn (\"mov%d6\\t%0, %1\", operands); } - sprintf (pattern, \"%s%%D6\\t%%0, %%2, %%3\", arithmetic_instr (operands[7], - FALSE)); - return arm_output_asm_insn (pattern, operands); -} + return \"%I7%D6\\t%0, %2, %3\"; " [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 6 "comparison_operator" [(match_operand:SI 4 "s_register_operand" "r,r") - (match_operand:SI 5 "arm_add_operand" "rL,rL")]) + (match_operand:SI 5 "arm_add_operand" "rIL,rIL")]) (plus:SI (match_operand:SI 2 "s_register_operand" "r,r") (match_operand:SI 3 "arm_add_operand" "rL,rL")) @@ -4890,68 +4361,68 @@ { if (GET_CODE (operands[5]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); + output_asm_insn (\"cmn\\t%4, #%n5\", operands); else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); + output_asm_insn (\"cmp\\t%4, %5\", operands); if (GET_CODE (operands[3]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"sub%d6\\t%0, %2, #%n3\", operands); + output_asm_insn (\"sub%d6\\t%0, %2, #%n3\", operands); else - arm_output_asm_insn (\"add%d6\\t%0, %2, %3\", operands); + output_asm_insn (\"add%d6\\t%0, %2, %3\", operands); if (which_alternative != 0) { if (GET_CODE (operands[1]) == MEM) - arm_output_asm_insn (\"ldr%D6\\t%0, %1\", operands); + output_asm_insn (\"ldr%D6\\t%0, %1\", operands); else - arm_output_asm_insn (\"mov%D6\\t%0, %1\", operands); + output_asm_insn (\"mov%D6\\t%0, %1\", operands); } return \"\"; } " [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 6 "comparison_operator" [(match_operand:SI 4 "s_register_operand" "r,r") - (match_operand:SI 5 "arm_add_operand" "rL,rL")]) + (match_operand:SI 5 "arm_add_operand" "rIL,rIL")]) (match_operand:SI 1 "arm_rhsm_operand" "0,?rIm") (plus:SI (match_operand:SI 2 "s_register_operand" "r,r") - (match_operand:SI 3 "arm_add_operand" "rL,rL")))) + (match_operand:SI 3 "arm_add_operand" "rIL,rIL")))) (clobber (reg 24))] "" "* { if (GET_CODE (operands[5]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); + output_asm_insn (\"cmn\\t%4, #%n5\", operands); else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); + output_asm_insn (\"cmp\\t%4, %5\", operands); if (GET_CODE (operands[3]) == CONST_INT && !const_ok_for_arm (INTVAL (operands[3]))) - arm_output_asm_insn (\"sub%D6\\t%0, %2, #%n3\", operands); + output_asm_insn (\"sub%D6\\t%0, %2, #%n3\", operands); else - arm_output_asm_insn (\"add%D6\\t%0, %2, %3\", operands); + output_asm_insn (\"add%D6\\t%0, %2, %3\", operands); if (which_alternative != 0) { if (GET_CODE (operands[6]) == MEM) - arm_output_asm_insn (\"ldr%d6\\t%0, %1\", operands); + output_asm_insn (\"ldr%d6\\t%0, %1\", operands); else - arm_output_asm_insn (\"mov%d6\\t%0, %1\", operands); + output_asm_insn (\"mov%d6\\t%0, %1\", operands); } return \"\"; } " [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 5 "comparison_operator" [(match_operand:SI 3 "s_register_operand" "r,r") - (match_operand:SI 4 "arm_add_operand" "rL,rL")]) + (match_operand:SI 4 "arm_add_operand" "rIL,rIL")]) (match_operand:SI 1 "arm_rhs_operand" "0,?rI") (not:SI (match_operand:SI 2 "s_register_operand" "r,r")))) @@ -4959,241 +4430,158 @@ "" "#" [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) - -;; if (GET_CODE (operands[3]) == CONST_INT -;; && !const_ok_for_arm (INTVAL (operands[3]))) -;; arm_output_asm_insn (\"cmn\\t%2, #%n3\", operands); -;; else -;; arm_output_asm_insn (\"cmp\\t%2, %3\", operands); -;; if (which_alternative != 0) -;; arm_output_asm_insn (\"mov%d1\\t%0, %4\", operands); -;; return arm_output_asm_insn (\"mvn%D1\\t%0, %5\", operands); + (set_attr "length" "8,12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (if_then_else:SI (match_operator 5 "comparison_operator" - [(match_operand:SI 3 "s_register_operand" "r,r") - (match_operand:SI 4 "arm_add_operand" "rL,rL")]) - (not:SI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:SI 1 "arm_rhs_operand" "0,?rI"))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r,r") + (if_then_else:SI + (match_operator 5 "comparison_operator" + [(match_operand:SI 3 "s_register_operand" "r,r,r,r") + (match_operand:SI 4 "arm_add_operand" "rI,L,rI,L")]) + (not:SI + (match_operand:SI 2 "s_register_operand" "r,r,r,r")) + (match_operand:SI 1 "arm_rhs_operand" "0,0,?rI,?rI"))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[30]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[4]))) - arm_output_asm_insn (\"cmn\\t%3, #%n4\", operands); - else - arm_output_asm_insn (\"cmp\\t%3, %4\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"mov%D5\\t%0, %1\", operands); - return arm_output_asm_insn (\"mvn%d5\\t%0, %2\", operands); - -} -" + "@ + cmp\\t%3, %4\;mvn%d5\\t%0, %2 + cmn\\t%3, #%n4\;mvn%d5\\t%0, %2 + cmp\\t%3, %4\;mov%D5\\t%0, %1\;mvn%d5\\t%0, %2 + cmn\\t%3, #%n4\;mov%D5\\t%0, %1\;mvn%d5\\t%0, %2" [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,8,12,12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (if_then_else:SI (match_operator 6 "comparison_operator" - [(match_operand:SI 4 "s_register_operand" "r,r") - (match_operand:SI 5 "arm_add_operand" "rL,rL")]) - (match_operator:SI 7 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r,r") - (match_operand:SI 3 "arm_rhs_operand" "rn,rn")]) - (match_operand:SI 1 "arm_rhs_operand" "0,?rI"))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r,r") + (if_then_else:SI + (match_operator 6 "comparison_operator" + [(match_operand:SI 4 "s_register_operand" "r,r,r,r") + (match_operand:SI 5 "arm_add_operand" "rI,L,rI,L")]) + (match_operator:SI 7 "shift_operator" + [(match_operand:SI 2 "s_register_operand" "r,r,r,r") + (match_operand:SI 3 "arm_rhs_operand" "rM,rM,rM,rM")]) + (match_operand:SI 1 "arm_rhs_operand" "0,0,?rI,?rI"))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[5]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); - else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"mov%D6\\t%0, %1\", operands); - sprintf (pattern, \"mov%%d6\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[7]), &operands[3])); - return arm_output_asm_insn (pattern, operands); -} -" + "@ + cmp\\t%4, %5\;mov%d6\\t%0, %2%S7 + cmn\\t%4, #%n5\;mov%d6\\t%0, %2%S7 + cmp\\t%4, %5\;mov%D6\\t%0, %1\;mov%d6\\t%0, %2%S7 + cmn\\t%4, #%n5\;mov%D6\\t%0, %1\;mov%d6\\t%0, %2%S7" [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,8,12,12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (if_then_else:SI (match_operator 6 "comparison_operator" - [(match_operand:SI 4 "s_register_operand" "r,r") - (match_operand:SI 5 "arm_add_operand" "rL,rL")]) - (match_operand:SI 1 "arm_rhs_operand" "0,?rI") - (match_operator:SI 7 "shift_operator" - [(match_operand:SI 2 "s_register_operand" "r,r") - (match_operand:SI 3 "arm_rhs_operand" "rn,rn")]))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r,r") + (if_then_else:SI + (match_operator 6 "comparison_operator" + [(match_operand:SI 4 "s_register_operand" "r,r,r,r") + (match_operand:SI 5 "arm_add_operand" "rI,L,rI,L")]) + (match_operand:SI 1 "arm_rhs_operand" "0,0,?rI,?rI") + (match_operator:SI 7 "shift_operator" + [(match_operand:SI 2 "s_register_operand" "r,r,r,r") + (match_operand:SI 3 "arm_rhs_operand" "rM,rM,rM,rM")]))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[5]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); - else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"mov%d6\\t%0, %1\", operands); - sprintf (pattern, \"mov%%D6\\t%%0, %%2, %s %%3\", - shift_instr (GET_CODE (operands[7]), &operands[3])); - return arm_output_asm_insn (pattern, operands); -} -" + "@ + cmp\\t%4, %5\;mov%D6\\t%0, %2%S7 + cmn\\t%4, #%n5\;mov%D6\\t%0, %2%S7 + cmp\\t%4, %5\;mov%d6\\t%0, %1\;mov%D6\\t%0, %2%S7 + cmn\\t%4, #%n5\;mov%d6\\t%0, %1\;mov%D6\\t%0, %2%S7" [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,8,12,12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (if_then_else:SI (match_operator 7 "comparison_operator" - [(match_operand:SI 5 "s_register_operand" "r") - (match_operand:SI 6 "arm_add_operand" "rL")]) - (match_operator:SI 8 "shift_operator" - [(match_operand:SI 1 "s_register_operand" "r") - (match_operand:SI 2 "arm_rhs_operand" "rn")]) - (match_operator:SI 9 "shift_operator" - [(match_operand:SI 3 "s_register_operand" "r") - (match_operand:SI 4 "arm_rhs_operand" "rI")]))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r") + (if_then_else:SI + (match_operator 7 "comparison_operator" + [(match_operand:SI 5 "s_register_operand" "r,r") + (match_operand:SI 6 "arm_add_operand" "rI,L")]) + (match_operator:SI 8 "shift_operator" + [(match_operand:SI 1 "s_register_operand" "r,r") + (match_operand:SI 2 "arm_rhs_operand" "rM,rM")]) + (match_operator:SI 9 "shift_operator" + [(match_operand:SI 3 "s_register_operand" "r,r") + (match_operand:SI 4 "arm_rhs_operand" "rI,rI")]))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[6]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[6]))) - arm_output_asm_insn (\"cmn\\t%5, #%n6\", operands); - else - arm_output_asm_insn (\"cmp\\t%5, %6\", operands); - sprintf (pattern, \"mov%%d7\\t%%0, %%1, %s %%2\", - shift_instr (GET_CODE (operands[8]), &operands[2])); - arm_output_asm_insn (pattern, operands); - sprintf (pattern, \"mov%%D7\\t%%0, %%3, %s %%4\", - shift_instr (GET_CODE (operands[9]), &operands[4])); - return arm_output_asm_insn (pattern, operands); -} -" + "@ + cmp\\t%5, %6\;mov%d7\\t%0, %1%S8\;mov%D7\\t%0, %3%S9 + cmn\\t%5, #%n6\;mov%d7\\t%0, %1%S8\;mov%D7\\t%0, %3%S9" [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (if_then_else:SI (match_operator 6 "comparison_operator" - [(match_operand:SI 4 "s_register_operand" "r") - (match_operand:SI 5 "arm_add_operand" "rL")]) - (not:SI (match_operand:SI 1 "s_register_operand" "r")) - (match_operator:SI 7 "shiftable_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rI")]))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r") + (if_then_else:SI + (match_operator 6 "comparison_operator" + [(match_operand:SI 4 "s_register_operand" "r,r") + (match_operand:SI 5 "arm_add_operand" "rI,L")]) + (not:SI (match_operand:SI 1 "s_register_operand" "r,r")) + (match_operator:SI 7 "shiftable_operator" + [(match_operand:SI 2 "s_register_operand" "r,r") + (match_operand:SI 3 "arm_rhs_operand" "rI,rI")]))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[5]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); - else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); - arm_output_asm_insn (\"mvn%d6\\t%0, %1\", operands); - sprintf (pattern, \"%s%%D6\\t%%0, %%2, %%3\", arithmetic_instr (operands[7], - FALSE)); - return arm_output_asm_insn (pattern, operands); -} -" + "@ + cmp\\t%4, %5\;mvn%d6\\t%0, %1\;%I7%D6\\t%0, %2, %3 + cmn\\t%4, #%n5\;mvn%d6\\t%0, %1\;%I7%D6\\t%0, %2, %3" [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r") - (if_then_else:SI (match_operator 6 "comparison_operator" - [(match_operand:SI 4 "s_register_operand" "r") - (match_operand:SI 5 "arm_add_operand" "rL")]) - (match_operator:SI 7 "shiftable_operator" - [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "arm_rhs_operand" "rI")]) - (not:SI (match_operand:SI 1 "s_register_operand" "r")))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r") + (if_then_else:SI + (match_operator 6 "comparison_operator" + [(match_operand:SI 4 "s_register_operand" "r,r") + (match_operand:SI 5 "arm_add_operand" "rI,L")]) + (match_operator:SI 7 "shiftable_operator" + [(match_operand:SI 2 "s_register_operand" "r,r") + (match_operand:SI 3 "arm_rhs_operand" "rI,rI")]) + (not:SI (match_operand:SI 1 "s_register_operand" "r,r")))) (clobber (reg 24))] "" - "* -{ - char pattern[100]; - - if (GET_CODE (operands[5]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[5]))) - arm_output_asm_insn (\"cmn\\t%4, #%n5\", operands); - else - arm_output_asm_insn (\"cmp\\t%4, %5\", operands); - arm_output_asm_insn (\"mvn%D6\\t%0, %1\", operands); - sprintf (pattern, \"%s%%d6\\t%%0, %%2, %%3\", arithmetic_instr (operands[7], - FALSE)); - return arm_output_asm_insn (pattern, operands); -} -" + "@ + cmp\\t%4, %5\;mvn%D6\\t%0, %1\;%I7%d6\\t%0, %2, %3 + cmn\\t%4, #%n5\;mvn%D6\\t%0, %1\;%I7%d6\\t%0, %2, %3" [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (if_then_else:SI (match_operator 5 "comparison_operator" - [(match_operand:SI 3 "s_register_operand" "r,r") - (match_operand:SI 4 "arm_add_operand" "rL,rL")]) - (neg:SI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:SI 1 "arm_rhs_operand" "0,?rI"))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r,r") + (if_then_else:SI + (match_operator 5 "comparison_operator" + [(match_operand:SI 3 "s_register_operand" "r,r,r,r") + (match_operand:SI 4 "arm_add_operand" "rI,L,rI,L")]) + (neg:SI (match_operand:SI 2 "s_register_operand" "r,r,r,r")) + (match_operand:SI 1 "arm_rhs_operand" "0,0,?rI,?rI"))) (clobber (reg:CC 24))] "" - "* - if (GET_CODE (operands[4]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[4]))) - arm_output_asm_insn (\"cmn\\t%3, #%n4\", operands); - else - arm_output_asm_insn (\"cmp\\t%3, %4\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"mov%D5\\t%0, %1\", operands); - return arm_output_asm_insn (\"rsb%d5\\t%0, %2, #0\", operands); -" + "@ + cmp\\t%3, %4\;rsb%d5\\t%0, %2, #0 + cmn\\t%3, #%n4\;rsb%d5\\t%0, %2, #0 + cmp\\t%3, %4\;mov%D5\\t%0, %1\;rsb%d5\\t%0, %2, #0 + cmn\\t%3, #%n4\;mov%D5\\t%0, %1\;rsb%d5\\t%0, %2, #0" [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,8,12,12")]) (define_insn "" - [(set (match_operand:SI 0 "s_register_operand" "=r,r") - (if_then_else:SI (match_operator 5 "comparison_operator" - [(match_operand:SI 3 "s_register_operand" "r,r") - (match_operand:SI 4 "arm_add_operand" "rL,rL")]) - (match_operand:SI 1 "arm_rhs_operand" "0,?rI") - (neg:SI - (match_operand:SI 2 "s_register_operand" "r,r")))) + [(set (match_operand:SI 0 "s_register_operand" "=r,r,r,r") + (if_then_else:SI + (match_operator 5 "comparison_operator" + [(match_operand:SI 3 "s_register_operand" "r,r,r,r") + (match_operand:SI 4 "arm_add_operand" "rI,L,rI,L")]) + (match_operand:SI 1 "arm_rhs_operand" "0,0,?rI,?rI") + (neg:SI (match_operand:SI 2 "s_register_operand" "r,r,r,r")))) (clobber (reg:CC 24))] "" - "* - if (GET_CODE (operands[4]) == CONST_INT - && !const_ok_for_arm (INTVAL (operands[4]))) - arm_output_asm_insn (\"cmn\\t%3, #%n4\", operands); - else - arm_output_asm_insn (\"cmp\\t%3, %4\", operands); - if (which_alternative != 0) - arm_output_asm_insn (\"mov%d5\\t%0, %1\", operands); - return arm_output_asm_insn (\"rsb%D5\\t%0, %2, #0\", operands); -" + "@ + cmp\\t%3, %4\;rsb%D5\\t%0, %2, #0 + cmn\\t%3, #%n4\;rsb%D5\\t%0, %2, #0 + cmp\\t%3, %4\;mov%d5\\t%0, %1\;rsb%D5\\t%0, %2, #0 + cmn\\t%3, #%n4\;mov%d5\\t%0, %1\;rsb%D5\\t%0, %2, #0" [(set_attr "conds" "clob") - (set_attr "length" "2,3")]) + (set_attr "length" "8,8,12,12")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") @@ -5205,12 +4593,9 @@ "* { rtx ldm[3]; - rtx arith[3]; - char pattern[100]; + rtx arith[4]; int val1 = 0, val2 = 0; - sprintf (pattern, \"%s\\t%%0, %%1, %%2\", - arithmetic_instr (operands[1], FALSE)); if (REGNO (operands[0]) > REGNO (operands[4])) { ldm[1] = operands[4]; @@ -5226,6 +4611,7 @@ if (GET_CODE (XEXP (operands[3], 0)) != REG) val2 = INTVAL (XEXP (XEXP (operands[3], 0), 1)); arith[0] = operands[0]; + arith[3] = operands[1]; if (val1 < val2) { arith[1] = ldm[1]; @@ -5244,30 +4630,31 @@ ops[2] = XEXP (XEXP (operands[2], 0), 1); output_add_immediate (ops); if (val1 < val2) - arm_output_asm_insn (\"ldmia\\t%0, {%1, %2}\", ldm); + output_asm_insn (\"ldm%?ia\\t%0, {%1, %2}\", ldm); else - arm_output_asm_insn (\"ldmda\\t%0, {%1, %2}\", ldm); + output_asm_insn (\"ldm%?da\\t%0, {%1, %2}\", ldm); } else if (val1) { ldm[0] = XEXP (operands[3], 0); if (val1 < val2) - arm_output_asm_insn (\"ldmda\\t%0, {%1, %2}\", ldm); + output_asm_insn (\"ldm%?da\\t%0, {%1, %2}\", ldm); else - arm_output_asm_insn (\"ldmia\\t%0, {%1, %2}\", ldm); + output_asm_insn (\"ldm%?ia\\t%0, {%1, %2}\", ldm); } else { ldm[0] = XEXP (operands[2], 0); if (val1 < val2) - arm_output_asm_insn (\"ldmia\\t%0, {%1, %2}\", ldm); + output_asm_insn (\"ldm%?ia\\t%0, {%1, %2}\", ldm); else - arm_output_asm_insn (\"ldmda\\t%0, {%1, %2}\", ldm); + output_asm_insn (\"ldm%?da\\t%0, {%1, %2}\", ldm); } - return arm_output_asm_insn (pattern, arith); + output_asm_insn (\"%I3%?\\t%0, %1, %2\", arith); + return \"\"; } " -[(set_attr "length" "3") +[(set_attr "length" "12") (set_attr "type" "load")]) ;; the arm can support extended pre-inc instructions @@ -5290,9 +4677,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"strb\\t%3, [%0, %2]!\", operands); -" + "str%?b\\t%3, [%0, %2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5305,9 +4690,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"strb\\t%3, [%0, -%2]!\", operands); -" + "str%?b\\t%3, [%0, -%2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5320,9 +4703,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldrb\\t%3, [%0, %2]!\", operands); -" + "ldr%?b\\t%3, [%0, %2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5335,9 +4716,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldrb\\t%3, [%0, -%2]!\", operands); -" + "ldr%?b\\t%3, [%0, -%2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5351,10 +4730,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldrb\\t%3, [%0, %2]!\\t@ z_extendqisi\", - operands); -" + "ldr%?b\\t%3, [%0, %2]!\\t%@ z_extendqisi" [(set_attr "type" "load")]) (define_insn "" @@ -5368,10 +4744,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldrb\\t%3, [%0, -%2]!\\t@ z_extendqisi\", - operands); -" + "ldr%?b\\t%3, [%0, -%2]!\\t%@ z_extendqisi" [(set_attr "type" "load")]) (define_insn "" @@ -5384,9 +4757,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"str\\t%3, [%0, %2]!\", operands); -" + "str%?\\t%3, [%0, %2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5399,9 +4770,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"str\\t%3, [%0, -%2]!\", operands); -" + "str%?\\t%3, [%0, -%2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5414,9 +4783,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldr\\t%3, [%0, %2]!\", operands); -" + "ldr%?\\t%3, [%0, %2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5429,9 +4796,7 @@ && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldr\\t%3, [%0, -%2]!\", operands); -" + "ldr%?\\t%3, [%0, -%2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5440,13 +4805,13 @@ (match_operand:SI 2 "index_operand" "rJ")))) (set (match_operand:SI 0 "s_register_operand" "=r") (plus:SI (match_dup 1) (match_dup 2)))] - "REGNO (operands[0]) != FRAME_POINTER_REGNUM + "(! BYTES_BIG_ENDIAN) + && ! TARGET_SHORT_BY_BYTES + && REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldr\\t%3, [%0, %2]!\\t@ loadhi\", operands); -" + "ldr%?\\t%3, [%0, %2]!\\t%@ loadhi" [(set_attr "type" "load")]) (define_insn "" @@ -5455,13 +4820,13 @@ (match_operand:SI 2 "s_register_operand" "r")))) (set (match_operand:SI 0 "s_register_operand" "=r") (minus:SI (match_dup 1) (match_dup 2)))] - "REGNO (operands[0]) != FRAME_POINTER_REGNUM + "(!BYTES_BIG_ENDIAN) + && ! TARGET_SHORT_BY_BYTES + && REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != FRAME_POINTER_REGNUM)" - "* - return arm_output_asm_insn (\"ldr\\t%3, [%0, -%2]!\\t@ loadhi\", operands); -" + "ldr%?\\t%3, [%0, -%2]!\\t%@ loadhi" [(set_attr "type" "load")]) (define_insn "" @@ -5476,15 +4841,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"strb\\t%%5, [%%0, %%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "str%?b\\t%5, [%0, %3%S2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5499,15 +4856,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"strb\\t%%5, [%%0, -%%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "str%?b\\t%5, [%0, -%3%S2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5522,15 +4871,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"ldrb\\t%%5, [%%0, %%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "ldr%?b\\t%5, [%0, %3%S2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5545,15 +4886,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"ldrb\\t%%5, [%%0, -%%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "ldr%?b\\t%5, [%0, -%3%S2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5568,15 +4901,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"str\\t%%5, [%%0, %%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "str%?\\t%5, [%0, %3%S2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5591,15 +4916,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"str\\t%%5, [%%0, -%%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "str%?\\t%5, [%0, -%3%S2]!" [(set_attr "type" "store1")]) (define_insn "" @@ -5614,15 +4931,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"ldr\\t%%5, [%%0, %%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "ldr%?\\t%5, [%0, %3%S2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5637,15 +4946,7 @@ "REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"ldr\\t%%5, [%%0, -%%3, %s %%4]!\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "ldr%?\\t%5, [%0, -%3%S2]!" [(set_attr "type" "load")]) (define_insn "" @@ -5657,18 +4958,12 @@ (set (match_operand:SI 0 "s_register_operand" "=r") (plus:SI (match_op_dup 2 [(match_dup 3) (match_dup 4)]) (match_dup 1)))] - "REGNO (operands[0]) != FRAME_POINTER_REGNUM + "(! BYTES_BIG_ENDIAN) + && ! TARGET_SHORT_BY_BYTES + && REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"ldr\\t%%5, [%%0, %%3, %s %%4]!\\t@ loadhi\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "ldr%?\\t%5, [%0, %3%S2]!\\t%@ loadhi" [(set_attr "type" "load")]) (define_insn "" @@ -5680,18 +4975,12 @@ (set (match_operand:SI 0 "s_register_operand" "=r") (minus:SI (match_dup 1) (match_op_dup 2 [(match_dup 3) (match_dup 4)])))] - "REGNO (operands[0]) != FRAME_POINTER_REGNUM + "(! BYTES_BIG_ENDIAN) + && ! TARGET_SHORT_BY_BYTES + && REGNO (operands[0]) != FRAME_POINTER_REGNUM && REGNO (operands[1]) != FRAME_POINTER_REGNUM && REGNO (operands[3]) != FRAME_POINTER_REGNUM" - "* -{ - char instr[100]; - - sprintf (instr, \"ldr\\t%%5, [%%0, -%%3, %s %%4]!\\t@ loadhi\", - shift_instr (GET_CODE (operands[2]), &operands[4])); - return arm_output_asm_insn (instr, operands); -} -" + "ldr%?\\t%5, [%0, -%3%S2]!\\t%@ loadhi" [(set_attr "type" "load")]) ; It can also support extended post-inc expressions, but combine doesn't @@ -5708,9 +4997,7 @@ (set (match_dup 0) (plus:SI (match_dup 0) (match_operand:SI 1 "index_operand" "rJ")))] "" - "* - return arm_output_asm_insn (\"strb\\t%2, [%0], %1\", operands); -") + "str%?b\\t%2, [%0], %1") (define_peephole [(set (match_operand:QI 0 "s_register_operand" "=r") @@ -5720,9 +5007,7 @@ "REGNO(operands[0]) != REGNO(operands[1]) && (GET_CODE (operands[2]) != REG || REGNO(operands[0]) != REGNO (operands[2]))" - "* - return arm_output_asm_insn (\"ldrb\\t%0, [%1], %2\", operands); -") + "ldr%?b\\t%0, [%1], %2") (define_peephole [(set (mem:SI (match_operand:SI 0 "s_register_operand" "+r")) @@ -5730,21 +5015,19 @@ (set (match_dup 0) (plus:SI (match_dup 0) (match_operand:SI 1 "index_operand" "rJ")))] "" - "* - return arm_output_asm_insn (\"str\\t%2, [%0], %1\", operands); -") + "str%?\\t%2, [%0], %1") (define_peephole [(set (match_operand:HI 0 "s_register_operand" "=r") (mem:HI (match_operand:SI 1 "s_register_operand" "+r"))) (set (match_dup 1) (plus:SI (match_dup 1) (match_operand:SI 2 "index_operand" "rJ")))] - "REGNO(operands[0]) != REGNO(operands[1]) + "(! BYTES_BIG_ENDIAN) + && ! TARGET_SHORT_BY_BYTES + && REGNO(operands[0]) != REGNO(operands[1]) && (GET_CODE (operands[2]) != REG || REGNO(operands[0]) != REGNO (operands[2]))" - "* - return arm_output_asm_insn (\"ldr\\t%0, [%1], %2\\t@ loadhi\", operands); -") + "ldr%?\\t%0, [%1], %2\\t%@ loadhi") (define_peephole [(set (match_operand:SI 0 "s_register_operand" "=r") @@ -5754,9 +5037,26 @@ "REGNO(operands[0]) != REGNO(operands[1]) && (GET_CODE (operands[2]) != REG || REGNO(operands[0]) != REGNO (operands[2]))" - "* - return arm_output_asm_insn (\"ldr\\t%0, [%1], %2\", operands); -") + "ldr%?\\t%0, [%1], %2") + +(define_peephole + [(set (mem:QI (plus:SI (match_operand:SI 0 "s_register_operand" "+r") + (match_operand:SI 1 "index_operand" "rJ"))) + (match_operand:QI 2 "s_register_operand" "r")) + (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))] + "" + "str%?b\\t%2, [%0, %1]!") + +(define_peephole + [(set (mem:QI (plus:SI (match_operator:SI 4 "shift_operator" + [(match_operand:SI 0 "s_register_operand" "r") + (match_operand:SI 1 "const_int_operand" "n")]) + (match_operand:SI 2 "s_register_operand" "+r"))) + (match_operand:QI 3 "s_register_operand" "r")) + (set (match_dup 2) (plus:SI (match_op_dup 4 [(match_dup 0) (match_dup 1)]) + (match_dup 2)))] + "" + "str%?b\\t%3, [%2, %0%S4]!") ; This pattern is never tried by combine, so do it as a peephole @@ -5766,9 +5066,7 @@ (set (match_operand 2 "cc_register" "") (compare (match_dup 1) (const_int 0)))] "" - "* - return arm_output_asm_insn (\"subs\\t%0, %1, #0\", operands); -" + "sub%?s\\t%0, %1, #0" [(set_attr "conds" "set")]) ; Peepholes to spot possible load- and store-multiples, if the ordering is @@ -5798,10 +5096,7 @@ && !MEM_VOLATILE_P (SET_SRC (PATTERN (prev_nonnote_insn (prev_nonnote_insn (prev_nonnote_insn (insn))))))" - "* - return arm_output_asm_insn (\"ldmia\\t%1, {%4, %3, %2, %0}\\t@ phole ldm\", - operands); -") + "ldm%?ia\\t%1, {%4, %3, %2, %0}\\t%@ phole ldm") (define_peephole [(set (match_operand:SI 0 "s_register_operand" "=r") @@ -5820,10 +5115,7 @@ && !MEM_VOLATILE_P (SET_SRC (PATTERN (prev_nonnote_insn (insn)))) && !MEM_VOLATILE_P (SET_SRC (PATTERN (prev_nonnote_insn (prev_nonnote_insn (insn)))))" - "* - return arm_output_asm_insn (\"ldmia\\t%1, {%3, %2, %0}\\t@ phole ldm\", - operands); -") + "ldm%?ia\\t%1, {%3, %2, %0}\\t%@ phole ldm") (define_peephole [(set (match_operand:SI 0 "s_register_operand" "=r") @@ -5836,10 +5128,7 @@ || REGNO (operands[1]) == REGNO (operands[2])) && !MEM_VOLATILE_P (SET_SRC (PATTERN (insn))) && !MEM_VOLATILE_P (SET_SRC (PATTERN (prev_nonnote_insn (insn))))" - "* - return arm_output_asm_insn (\"ldmia\\t%1, {%2, %0}\\t@ phole ldm\", - operands); -") + "ldm%?ia\\t%1, {%2, %0}\\t%@ phole ldm") (define_peephole [(set (mem:SI (plus:SI (match_operand:SI 1 "s_register_operand" "r") @@ -5861,10 +5150,7 @@ && !MEM_VOLATILE_P (SET_DEST (PATTERN (prev_nonnote_insn (prev_nonnote_insn (prev_nonnote_insn (insn))))))" - "* - return arm_output_asm_insn (\"stmia\\t%1, {%4, %3, %2, %0}\\t@ phole stm\", - operands); -") + "stm%?ia\\t%1, {%4, %3, %2, %0}\\t%@ phole stm") (define_peephole [(set (mem:SI (plus:SI (match_operand:SI 1 "s_register_operand" "r") @@ -5880,10 +5166,7 @@ && !MEM_VOLATILE_P (SET_DEST (PATTERN (prev_nonnote_insn (insn)))) && !MEM_VOLATILE_P (SET_DEST (PATTERN (prev_nonnote_insn (prev_nonnote_insn (insn)))))" - "* - return arm_output_asm_insn (\"stmia\\t%1, {%3, %2, %0}\\t@ phole stm\", - operands); -") + "stm%?ia\\t%1, {%3, %2, %0}\\t%@ phole stm") (define_peephole [(set (mem:SI (plus:SI (match_operand:SI 1 "s_register_operand" "r") @@ -5894,10 +5177,7 @@ "REGNO (operands[0]) > REGNO (operands[2]) && !MEM_VOLATILE_P (SET_DEST (PATTERN (insn))) && !MEM_VOLATILE_P (SET_DEST (PATTERN (prev_nonnote_insn (insn))))" - "* - return arm_output_asm_insn (\"stmia\\t%1, {%2, %0}\\t@ phole stm\", - operands); -") + "stm%?ia\\t%1, {%2, %0}\\t%@ phole stm") ;; A call followed by return can be replaced by restoring the regs and ;; jumping to the subroutine, provided we aren't passing the address of @@ -5935,13 +5215,13 @@ } output_return_instruction (NULL, FALSE); - return (arm_output_asm_insn (\"b\\t%a0\", operands)); + return \"b%?\\t%a0\"; }" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_peephole [(parallel [(set (match_operand 0 "s_register_operand" "=rf") @@ -5966,13 +5246,13 @@ } output_return_instruction (NULL, FALSE); - return (arm_output_asm_insn (\"b\\t%a1\", operands)); + return \"b%?\\t%a1\"; }" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) - (set_attr "length" "2")]) + (set_attr "length" "8")]) ;; As above but when this function is not void, we must be returning the ;; result of the called subroutine. @@ -6001,13 +5281,13 @@ } output_return_instruction (NULL, FALSE); - return (arm_output_asm_insn (\"b\\t%a1\", operands)); + return \"b%?\\t%a1\"; }" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") (const_string "clob") (const_string "nocond"))) - (set_attr "length" "2")]) + (set_attr "length" "8")]) ;; If calling a subroutine and then jumping back to somewhere else, but not ;; too far away, then we can set the link register with the branch address @@ -6022,7 +5302,7 @@ (clobber (reg:SI 14))]) (set (pc) (label_ref (match_operand 2 "" "")))] - "GET_CODE (operands[0]) == SYMBOL_REF + "0 && GET_CODE (operands[0]) == SYMBOL_REF && short_branch (INSN_UID (insn), INSN_UID (operands[2])) && arm_insn_not_targeted (insn)" "* @@ -6037,20 +5317,20 @@ if (TARGET_6) { if (backward) - arm_output_asm_insn (\"sub\\tlr, pc, #(8 + . -%l2)\", operands); + output_asm_insn (\"sub%?\\t%|lr, %|pc, #(8 + . -%l2)\", operands); else - arm_output_asm_insn (\"add\\tlr, pc, #(%l2 - . -8)\", operands); + output_asm_insn (\"add%?\\t%|lr, %|pc, #(%l2 - . -8)\", operands); } else #endif { - arm_output_asm_insn (\"mov\\tlr, pc\\t@ protect cc\"); + output_asm_insn (\"mov%?\\t%|lr, %|pc\\t%@ protect cc\", operands); if (backward) - arm_output_asm_insn (\"sub\\tlr, lr, #(4 + . -%l2)\", operands); + output_asm_insn (\"sub%?\\t%|lr, %|lr, #(4 + . -%l2)\", operands); else - arm_output_asm_insn (\"add\\tlr, lr, #(%l2 - . -4)\", operands); + output_asm_insn (\"add%?\\t%|lr, %|lr, #(%l2 - . -4)\", operands); } - return arm_output_asm_insn (\"b\\t%a0\", operands); + return \"b%?\\t%a0\"; }" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") @@ -6058,8 +5338,8 @@ (const_string "nocond"))) (set (attr "length") (if_then_else (eq_attr "cpu" "arm6") - (const_int 2) - (const_int 3)))]) + (const_int 8) + (const_int 12)))]) (define_peephole [(parallel[(set (match_operand:SI 0 "s_register_operand" "=r") @@ -6068,7 +5348,7 @@ (clobber (reg:SI 14))]) (set (pc) (label_ref (match_operand 3 "" "")))] - "GET_CODE (operands[0]) == SYMBOL_REF + "0 && GET_CODE (operands[0]) == SYMBOL_REF && short_branch (INSN_UID (insn), INSN_UID (operands[3])) && arm_insn_not_targeted (insn)" "* @@ -6083,20 +5363,20 @@ if (TARGET_6) { if (backward) - arm_output_asm_insn (\"sub\\tlr, pc, #(8 + . -%l3)\", operands); + output_asm_insn (\"sub%?\\t%|lr, %|pc, #(8 + . -%l3)\", operands); else - arm_output_asm_insn (\"add\\tlr, pc, #(%l3 - . -8)\", operands); + output_asm_insn (\"add%?\\t%|lr, %|pc, #(%l3 - . -8)\", operands); } else #endif { - arm_output_asm_insn (\"mov\\tlr, pc\\t@ protect cc\"); + output_asm_insn (\"mov%?\\t%|lr, %|pc\\t%@ protect cc\", operands); if (backward) - arm_output_asm_insn (\"sub\\tlr, lr, #(4 + . -%l3)\", operands); + output_asm_insn (\"sub%?\\t%|lr, %|lr, #(4 + . -%l3)\", operands); else - arm_output_asm_insn (\"add\\tlr, lr, #(%l3 - . -4)\", operands); + output_asm_insn (\"add%?\\t%|lr, %|lr, #(%l3 - . -4)\", operands); } - return arm_output_asm_insn (\"b\\t%a1\", operands); + return \"b%?\\t%a1\"; }" [(set (attr "conds") (if_then_else (eq_attr "cpu" "arm6") @@ -6104,15 +5384,15 @@ (const_string "nocond"))) (set (attr "length") (if_then_else (eq_attr "cpu" "arm6") - (const_int 2) - (const_int 3)))]) + (const_int 8) + (const_int 12)))]) (define_split [(set (pc) (if_then_else (match_operator 0 "comparison_operator" [(match_operator:SI 1 "shift_operator" [(match_operand:SI 2 "s_register_operand" "r") - (match_operand:SI 3 "nonmemory_operand" "rn")]) + (match_operand:SI 3 "reg_or_int_operand" "rM")]) (match_operand:SI 4 "s_register_operand" "r")]) (label_ref (match_operand 5 "" "")) (pc))) @@ -6160,38 +5440,21 @@ == (((unsigned long) INTVAL (operands[1])) >> 24) << 24" "* operands[1] = GEN_INT (((unsigned long) INTVAL (operands[1])) >> 24); - arm_output_asm_insn (\"ldrb\\t%2, %0\", operands); - return arm_output_asm_insn (\"cmp\\t%2, %1\", operands); + output_asm_insn (\"ldr%?b\\t%2, %0\", operands); + output_asm_insn (\"cmp%?\\t%2, %1\", operands); + return \"\"; " [(set_attr "conds" "set") - (set_attr "length" "2") + (set_attr "length" "8") (set_attr "type" "load")]) -(define_expand "save_stack_nonlocal" - [(match_operand:DI 0 "memory_operand" "") - (match_operand:SI 1 "s_register_operand" "")] - "" - " -{ - /* We also need to save the frame pointer for non-local gotos */ - emit_move_insn (operand_subword (operands[0], 0, 0, DImode), - hard_frame_pointer_rtx); - emit_move_insn (operand_subword (operands[0], 1, 0, DImode), operands[1]); - DONE; -}") - -(define_expand "restore_stack_nonlocal" - [(match_operand:SI 0 "s_register_operand" "") - (match_operand:DI 1 "memory_operand" "")] +(define_expand "prologue" + [(clobber (const_int 0))] "" " -{ - /* Restore the frame pointer first, the stack pointer second. */ - emit_move_insn (operands[0], operand_subword (operands[1], 1, 0, DImode)); - emit_move_insn (hard_frame_pointer_rtx, operand_subword (operands[1], 0, 0, - DImode)); + arm_expand_prologue (); DONE; -}") +") ;; This split is only used during output to reduce the number of patterns ;; that need assembler instructions adding to them. We allowed the setting @@ -6227,18 +5490,17 @@ (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r,r") (if_then_else:SI (match_operator 4 "comparison_operator" - [(match_operand 3 "cc_register" "") (const_int 0)]) + [(match_operand 3 "reversible_cc_register" "") + (const_int 0)]) (match_operand:SI 1 "arm_rhs_operand" "0,?rI") (not:SI (match_operand:SI 2 "s_register_operand" "r,r"))))] "" - "* - if (which_alternative != 0) - arm_output_asm_insn (\"mov%d4\\t%0, %1\", operands); - return arm_output_asm_insn (\"mvn%D4\\t%0, %2\", operands); -" + "@ + mvn%D4\\t%0, %2 + mov%d4\\t%0, %1\;mvn%D4\\t%0, %2" [(set_attr "conds" "use") - (set_attr "length" "1,2")]) + (set_attr "length" "4,8")]) ;; The next two patterns occur when an AND operation is followed by a ;; scc insn sequence @@ -6251,11 +5513,11 @@ "" "* operands[2] = GEN_INT (1 << INTVAL (operands[2])); - arm_output_asm_insn (\"ands\\t%0, %1, %2\", operands); - return arm_output_asm_insn (\"mvnne\\t%0, #0\", operands); + output_asm_insn (\"ands\\t%0, %1, %2\", operands); + return \"mvnne\\t%0, #0\"; " [(set_attr "conds" "clob") - (set_attr "length" "2")]) + (set_attr "length" "8")]) (define_insn "" [(set (match_operand:SI 0 "s_register_operand" "=r") @@ -6266,9 +5528,42 @@ "" "* operands[2] = GEN_INT (1 << INTVAL (operands[2])); - arm_output_asm_insn (\"tst\\t%1, %2\", operands); - arm_output_asm_insn (\"mvneq\\t%0, #0\", operands); - return arm_output_asm_insn (\"movne\\t%0, #0\", operands); + output_asm_insn (\"tst\\t%1, %2\", operands); + output_asm_insn (\"mvneq\\t%0, #0\", operands); + return \"movne\\t%0, #0\"; " [(set_attr "conds" "clob") - (set_attr "length" "3")]) + (set_attr "length" "12")]) + +;; Push multiple registers to the stack. The first register is in the +;; unspec part of the insn; subsequent registers are in parallel (use ...) +;; expressions. +(define_insn "" + [(match_parallel 2 "multi_register_push" + [(set (match_operand:BLK 0 "memory_operand" "=m") + (unspec:BLK [(match_operand:SI 1 "s_register_operand" "r")] 2))])] + "" + "* +{ + char pattern[100]; + int i; + extern int lr_save_eliminated; + + if (lr_save_eliminated) + { + if (XVECLEN (operands[2], 0) > 1) + abort (); + return \"\"; + } + strcpy (pattern, \"stmfd\\t%m0!, {%|%1\"); + for (i = 1; i < XVECLEN (operands[2], 0); i++) + { + strcat (pattern, \", %|\"); + strcat (pattern, reg_names[REGNO (XEXP (XVECEXP (operands[2], 0, i), + 0))]); + } + strcat (pattern, \"}\"); + output_asm_insn (pattern, operands); + return \"\"; +}" +[(set_attr "type" "store4")])