📄 sparc.md
字号:
[(set (match_operand:SI 0 "register_operand" "") (zero_extend:SI (match_operand:QI 1 "register_operand" "")))] "" "")(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r,r,r") (zero_extend:SI (match_operand:QI 1 "sparc_operand" "r,I,Q")))] "GET_CODE (operands[1]) != CONST_INT" "@ and %1,0xff,%0 mov (%1 & 0xff),%0 ldub %1,%0" [(set_attr "type" "unary,move,load") (set_attr "length" "1")])(define_insn "" [(set (reg:CC 0) (compare:CC (zero_extend:SI (match_operand:QI 0 "register_operand" "r")) (const_int 0)))] "" "andcc %0,0xff,%%g0" [(set_attr "type" "compare")])(define_insn "" [(set (reg:CC 0) (compare:CC (zero_extend:SI (match_operand:QI 1 "register_operand" "r")) (const_int 0))) (set (match_operand:SI 0 "register_operand" "=r") (zero_extend:SI (match_dup 1)))] "" "andcc %1,0xff,%0" [(set_attr "type" "unary")]);;- sign extension instructions;; These patterns originally accepted general_operands, however, slightly;; better code is generated by only accepting register_operands, and then;; letting combine generate the lds[hb] insns.(define_expand "extendhisi2" [(set (match_operand:SI 0 "register_operand" "") (sign_extend:SI (match_operand:HI 1 "register_operand" "")))] "" "{ rtx temp = gen_reg_rtx (SImode); rtx shift_16 = gen_rtx (CONST_INT, VOIDmode, 16); if (GET_CODE (operand1) == SUBREG) operand1 = XEXP (operand1, 0); emit_insn (gen_ashlsi3 (temp, gen_rtx (SUBREG, SImode, operand1, 0), shift_16)); emit_insn (gen_ashrsi3 (operand0, temp, shift_16)); DONE;}")(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (sign_extend:SI (match_operand:HI 1 "memory_operand" "m")))] "" "ldsh %1,%0" [(set_attr "type" "load")])(define_expand "extendqihi2" [(set (match_operand:HI 0 "register_operand" "") (sign_extend:HI (match_operand:QI 1 "register_operand" "")))] "" "{ rtx temp = gen_reg_rtx (SImode); rtx shift_24 = gen_rtx (CONST_INT, VOIDmode, 24); if (GET_CODE (operand1) == SUBREG) operand1 = XEXP (operand1, 0); if (GET_CODE (operand0) == SUBREG) operand0 = XEXP (operand0, 0); emit_insn (gen_ashlsi3 (temp, gen_rtx (SUBREG, SImode, operand1, 0), shift_24)); if (GET_MODE (operand0) != SImode) operand0 = gen_rtx (SUBREG, SImode, operand0, 0); emit_insn (gen_ashrsi3 (operand0, temp, shift_24)); DONE;}")(define_insn "" [(set (match_operand:HI 0 "register_operand" "=r") (sign_extend:HI (match_operand:QI 1 "memory_operand" "m")))] "" "ldsb %1,%0" [(set_attr "type" "load")])(define_expand "extendqisi2" [(set (match_operand:SI 0 "register_operand" "") (sign_extend:SI (match_operand:QI 1 "register_operand" "")))] "" "{ rtx temp = gen_reg_rtx (SImode); rtx shift_24 = gen_rtx (CONST_INT, VOIDmode, 24); if (GET_CODE (operand1) == SUBREG) operand1 = XEXP (operand1, 0); emit_insn (gen_ashlsi3 (temp, gen_rtx (SUBREG, SImode, operand1, 0), shift_24)); emit_insn (gen_ashrsi3 (operand0, temp, shift_24)); DONE;}")(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (sign_extend:SI (match_operand:QI 1 "memory_operand" "m")))] "" "ldsb %1,%0" [(set_attr "type" "load")]);; Special pattern for optimizing bit-field compares. This is needed;; because combine uses this as a canonical form.(define_insn "" [(set (reg:CC 0) (compare:CC (zero_extract:SI (match_operand:SI 0 "register_operand" "r") (match_operand:SI 1 "small_int" "n") (match_operand:SI 2 "small_int" "n")) (const_int 0)))] "INTVAL (operands[2]) > 19" "*{ int len = INTVAL (operands[1]); int pos = 32 - INTVAL (operands[2]) - len; unsigned mask = ((1 << len) - 1) << pos; operands[1] = gen_rtx (CONST_INT, VOIDmode, mask); return \"andcc %0,%1,%%g0\";}");; Conversions between float, double and long double.(define_insn "extendsfdf2" [(set (match_operand:DF 0 "register_operand" "=f") (float_extend:DF (match_operand:SF 1 "register_operand" "f")))] "" "fstod %1,%0" [(set_attr "type" "fp")])(define_insn "extendsftf2" [(set (match_operand:TF 0 "register_operand" "=f") (float_extend:TF (match_operand:SF 1 "register_operand" "f")))] "" "fstoq %1,%0" [(set_attr "type" "fp")])(define_insn "extenddftf2" [(set (match_operand:TF 0 "register_operand" "=f") (float_extend:TF (match_operand:DF 1 "register_operand" "f")))] "" "fdtoq %1,%0" [(set_attr "type" "fp")])(define_insn "truncdfsf2" [(set (match_operand:SF 0 "register_operand" "=f") (float_truncate:SF (match_operand:DF 1 "register_operand" "f")))] "" "fdtos %1,%0" [(set_attr "type" "fp")])(define_insn "trunctfsf2" [(set (match_operand:SF 0 "register_operand" "=f") (float_truncate:SF (match_operand:TF 1 "register_operand" "f")))] "" "fqtos %1,%0" [(set_attr "type" "fp")])(define_insn "trunctfdf2" [(set (match_operand:DF 0 "register_operand" "=f") (float_truncate:DF (match_operand:TF 1 "register_operand" "f")))] "" "fqtod %1,%0" [(set_attr "type" "fp")]);; Conversion between fixed point and floating point.(define_insn "floatsisf2" [(set (match_operand:SF 0 "register_operand" "=f") (float:SF (match_operand:SI 1 "register_operand" "f")))] "" "fitos %1,%0" [(set_attr "type" "fp")])(define_insn "floatsidf2" [(set (match_operand:DF 0 "register_operand" "=f") (float:DF (match_operand:SI 1 "register_operand" "f")))] "" "fitod %1,%0" [(set_attr "type" "fp")])(define_insn "floatsitf2" [(set (match_operand:TF 0 "register_operand" "=f") (float:TF (match_operand:SI 1 "register_operand" "f")))] "" "fitox %1,%0" [(set_attr "type" "fp")]);; Convert a float to an actual integer.;; Truncation is performed as part of the conversion.(define_insn "fix_truncsfsi2" [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))] "" "fstoi %1,%0" [(set_attr "type" "fp")])(define_insn "fix_truncdfsi2" [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))] "" "fdtoi %1,%0" [(set_attr "type" "fp")])(define_insn "fix_trunctfsi2" [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (fix:TF (match_operand:TF 1 "register_operand" "f"))))] "" "fqtoi %1,%0" [(set_attr "type" "fp")]);;- arithmetic instructions(define_insn "adddi3" [(set (match_operand:DI 0 "register_operand" "=r") (plus:DI (match_operand:DI 1 "arith_double_operand" "%r") (match_operand:DI 2 "arith_double_operand" "rHI"))) (clobber (reg:SI 0))] "" "*{ rtx op2 = operands[2]; /* If constant is positive, upper bits zeroed, otherwise unchanged. Give the assembler a chance to pick the move instruction. */ if (GET_CODE (op2) == CONST_INT) { int sign = INTVAL (op2); if (sign < 0) return \"addcc %R1,%2,%R0\;addx %1,-1,%0\"; return \"addcc %R1,%2,%R0\;addx %1,0,%0\"; } else if (GET_CODE (op2) == CONST_DOUBLE) { int sign = CONST_DOUBLE_HIGH (op2); operands[2] = gen_rtx (CONST_INT, VOIDmode, CONST_DOUBLE_LOW (operands[1])); if (sign < 0) return \"addcc %R1,%2,%R0\;addx %1,-1,%0\"; return \"addcc %R1,%2,%R0\;addx %1,0,%0\"; } return \"addcc %R1,%R2,%R0\;addx %1,%2,%0\";}" [(set_attr "length" "2")])(define_insn "addsi3" [(set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_operand:SI 1 "arith_operand" "%r") (match_operand:SI 2 "arith_operand" "rI")))] "" "add %1,%2,%0")(define_insn "" [(set (reg:CC_NOOV 0) (compare:CC_NOOV (plus:SI (match_operand:SI 0 "arith_operand" "%r") (match_operand:SI 1 "arith_operand" "rI")) (const_int 0)))] "" "addcc %0,%1,%%g0" [(set_attr "type" "compare")])(define_insn "" [(set (reg:CC_NOOV 0) (compare:CC_NOOV (plus:SI (match_operand:SI 1 "arith_operand" "%r") (match_operand:SI 2 "arith_operand" "rI")) (const_int 0))) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_dup 2)))] "" "addcc %1,%2,%0")(define_insn "subdi3" [(set (match_operand:DI 0 "register_operand" "=r") (minus:DI (match_operand:DI 1 "register_operand" "r") (match_operand:DI 2 "arith_double_operand" "rHI"))) (clobber (reg:SI 0))] "" "*{ rtx op2 = operands[2]; /* If constant is positive, upper bits zeroed, otherwise unchanged. Give the assembler a chance to pick the move instruction. */ if (GET_CODE (op2) == CONST_INT) { int sign = INTVAL (op2); if (sign < 0) return \"subcc %R1,%2,%R0\;subx %1,-1,%0\"; return \"subcc %R1,%2,%R0\;subx %1,0,%0\"; } else if (GET_CODE (op2) == CONST_DOUBLE) { int sign = CONST_DOUBLE_HIGH (op2); operands[2] = gen_rtx (CONST_INT, VOIDmode, CONST_DOUBLE_LOW (operands[1])); if (sign < 0) return \"subcc %R1,%2,%R0\;subx %1,-1,%0\"; return \"subcc %R1,%2,%R0\;subx %1,0,%0\"; } return \"subcc %R1,%R2,%R0\;subx %1,%2,%0\";}" [(set_attr "length" "2")])(define_insn "subsi3" [(set (match_operand:SI 0 "register_operand" "=r") (minus:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "arith_operand" "rI")))] "" "sub %1,%2,%0")(define_insn "" [(set (reg:CC_NOOV 0) (compare:CC_NOOV (minus:SI (match_operand:SI 0 "register_operand" "r") (match_operand:SI 1 "arith_operand" "rI")) (const_int 0)))] "" "subcc %0,%1,%%g0" [(set_attr "type" "compare")])(define_insn "" [(set (reg:CC_NOOV 0) (compare:CC_NOOV (minus:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "arith_operand" "rI")) (const_int 0))) (set (match_operand:SI 0 "register_operand" "=r") (minus:SI (match_dup 1) (match_dup 2)))] "" "subcc %1,%2,%0")(define_insn "mulsi3" [(set (match_operand:SI 0 "register_operand" "=r") (mult:SI (match_operand:SI 1 "arith_operand" "%r") (match_operand:SI 2 "arith_operand" "rI")))] "TARGET_V8 || TARGET_SPARCLITE" "smul %1,%2,%0");; It is not known whether this will match.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (mult:SI (match_operand:SI 1 "arith_operand" "%r") (match_operand:SI 2 "arith_operand" "rI"))) (set (reg:CC_NOOV 0) (compare:CC_NOOV (mult:SI (match_dup 1) (match_dup 2)) (const_int 0)))] "TARGET_V8 || TARGET_SPARCLITE" "smulcc %1,%2,%0")(define_insn "mulsidi3" [(set (match_operand:DI 0 "register_operand" "=r") (mult:DI (sign_extend:DI (match_operand:SI 1 "arith_operand" "%r")) (sign_extend:DI (match_operand:SI 2 "arith_operand" "rI"))))] "TARGET_V8 || TARGET_SPARCLITE" "smul %1,%2,%R0\;rd %y,%0" [(set_attr "length" "2")])(define_insn "umulsidi3" [(set (match_operand:DI 0 "register_operand" "=r") (mult:DI (zero_extend:DI (match_operand:SI 1 "arith_operand" "%r")) (zero_extend:DI (match_operand:SI 2 "arith_operand" "rI"))))] "TARGET_V8 || TARGET_SPARCLITE" "umul %1,%2,%R0\;rd %y,%0" [(set_attr "length" "2")]);; The architecture specifies that there must be 3 instructions between;; a y register write and a use of it for correct results.(define_insn "divsi3" [(set (match_operand:SI 0 "register_operand" "=r") (div:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "arith_operand" "rI"))) (clobber (match_scratch:SI 3 "=&r"))] "TARGET_V8" "sra %1,31,%3\;wr %%g0,%3,%%y\;nop\;nop\;nop\;sdiv %1,%2,%0" [(set_attr "length" "3")]);; It is not known whether this will match.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (div:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "arith_operand" "rI"))) (set (reg:CC 0) (compare:CC (div:SI (match_dup 1) (match_dup 2)) (const_int 0))) (clobber (match_scratch:SI 3 "=&r"))] "TARGET_V8" "sra %1,31,%3\;wr %%g0,%3,%%y\;nop\;nop\;nop\;sdivcc %1,%2,%0" [(set_attr "length" "3")])(define_insn "udivsi3" [(set (match_operand:SI 0 "register_operand" "=r") (udiv:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "arith_operand" "rI")))] "TARGET_V8" "wr %%g0,%%g0,%%y\;nop\;nop\;nop\;udiv %1,%2,%0" [(set_attr "length" "2")]);; It is not known whether this will match.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (udiv:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "arith_operand" "rI"))) (set (reg:CC 0) (compare:CC (udiv:SI (match_dup 1) (match_dup 2)) (const_int 0)))] "TARGET_V8" "wr %%g0,%%g0,%%y\;nop\;nop\;nop\;udivcc %1,%2,%0" [(set_attr "length" "2")]);;- and instructions;; We define DImode `and` so with DImode `not` we can get;; DImode `andn`. Other combinations are possible.(define_expand "anddi3" [(set (match_operand:DI 0 "register_operand" "") (and:DI (match_operand:DI 1 "arith_double_operand" "") (match_operand:DI 2 "arith_double_operand" "")))] "" "")
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -