📄 m68hc11.md
字号:
(define_split /* "bitcmpqi" */ [(set (cc0) (and:QI (match_operand:QI 0 "tst_operand" "") (match_operand:QI 1 "hard_addr_reg_operand" "")))] "z_replacement_completed == 2" [(set (match_dup 3) (match_dup 2)) (set (cc0) (and:QI (match_dup 0) (match_dup 4)))] "operands[2] = gen_rtx (REG, HImode, REGNO (operands[1])); operands[3] = gen_rtx (REG, HImode, SOFT_TMP_REGNUM); operands[4] = gen_rtx (REG, QImode, SOFT_TMP_REGNUM);")(define_insn "bitcmpqi_z_used" [(set (cc0) (and:QI (match_operand:QI 0 "tst_operand" "d,m") (match_operand:QI 1 "cmp_operand" "m,d"))) (use (match_operand:HI 2 "hard_reg_operand" "xy,xy")) (use (reg:HI SOFT_Z_REGNUM))] "" "#") (define_split /* "bitcmpqi_z_used" */ [(set (cc0) (and:QI (match_operand:QI 0 "tst_operand" "") (match_operand:QI 1 "cmp_operand" ""))) (use (match_operand:HI 2 "hard_reg_operand" "")) (use (reg:HI SOFT_Z_REGNUM))] "z_replacement_completed == 2" [(set (mem:HI (pre_dec:HI (reg:HI SP_REGNUM))) (match_dup 2)) (set (match_dup 2) (match_dup 3)) (set (cc0) (and:QI (match_dup 0) (match_dup 1))) (set (match_dup 2) (mem:HI (post_inc:HI (reg:HI SP_REGNUM))))] "operands[3] = gen_rtx (REG, HImode, SOFT_Z_REGNUM);")(define_insn "bitcmphi" [(set (cc0) (and:HI (match_operand:HI 0 "tst_operand" "d") (match_operand:HI 1 "const_int_operand" "i")))] "(INTVAL (operands[1]) & 0x0ff) == 0 || (INTVAL (operands[1]) & 0x0ff00) == 0" "*{ if ((INTVAL (operands[1]) & 0x0ff) == 0) return \"bita\\t%h1\"; else return \"bitb\\t%1\";}")(define_insn "bitcmpqi_12" [(set (cc0) (zero_extract (match_operand:HI 0 "tst_operand" "d") (match_operand:HI 1 "const_int_operand" "i") (match_operand:HI 2 "const_int_operand" "i")))] "(unsigned) (INTVAL (operands[2]) + INTVAL (operands[1])) <= 8 || (((unsigned) (INTVAL (operands[2]) + INTVAL (operands[1])) <= 16) && (unsigned) INTVAL (operands[2]) >= 8)" "*{ rtx ops[1]; int mask; int startpos = INTVAL (operands[2]); int bitsize = INTVAL (operands[1]); if (startpos >= 8) { startpos -= 8; mask = (1 << (startpos + bitsize)) - 1; mask &= ~((1 << startpos) - 1); ops[0] = GEN_INT (mask); output_asm_insn (\"bita\\t%0\", ops); } else { mask = (1 << (startpos + bitsize)) - 1; mask &= ~((1 << startpos) - 1); ops[0] = GEN_INT (mask); output_asm_insn (\"bitb\\t%0\", ops); } return \"\";}")(define_insn "cmpqi_1" [(set (cc0) (compare (match_operand:QI 0 "tst_operand" "d,m,d,!u,*B,d*B") (match_operand:QI 1 "cmp_operand" "im,d,!u,d,dim*A,*u")))] "" "*{ if (A_REG_P (operands[0]) || A_REG_P (operands[1])) { return \"#\"; } else if (D_REG_P (operands[0])) { return \"cmpb\\t%b1\"; } cc_status.flags |= CC_REVERSED; return \"cmpb\\t%b0\";}")(define_insn "cmpqi_z_used" [(set (cc0) (compare (match_operand:QI 0 "tst_operand" "dxy,m") (match_operand:QI 1 "cmp_operand" "m,dxy"))) (use (match_operand:HI 2 "hard_reg_operand" "dxy,dxy")) (use (reg:HI SOFT_Z_REGNUM))] "" "#") (define_split /* cmpqi_z_used */ [(set (cc0) (compare (match_operand:QI 0 "tst_operand" "") (match_operand:QI 1 "cmp_operand" ""))) (use (match_operand:HI 2 "hard_reg_operand" "")) (use (reg:HI SOFT_Z_REGNUM))] "z_replacement_completed == 2" [(set (mem:HI (pre_dec:HI (reg:HI SP_REGNUM))) (match_dup 2)) (set (match_dup 2) (match_dup 3)) (set (cc0) (compare (match_dup 0) (match_dup 1))) (set (match_dup 2) (mem:HI (post_inc:HI (reg:HI SP_REGNUM))))] "operands[3] = gen_rtx (REG, HImode, SOFT_Z_REGNUM);");;--------------------------------------------------------------------;;- Move strict_low_part;;--------------------------------------------------------------------;;;; The (strict_low_part ...) patterns are replaced by normal (set) patterns.;; The replacement must be made at the very end because we loose the;; (strict_low_part ...) information. This is correct for our machine;; description but not for GCC optimization passes.;;(define_insn "movstrictsi" [(set (strict_low_part (match_operand:SI 0 "non_push_operand" "+um,D,D")) (match_operand:SI 1 "general_operand" "D,Dim,uD"))] "" "#")(define_split [(set (strict_low_part (match_operand:SI 0 "non_push_operand" "")) (match_operand:SI 1 "general_operand" ""))] "z_replacement_completed == 2" [(set (match_dup 0) (match_dup 1))] "")(define_insn "movstricthi" [(set (strict_low_part (match_operand:HI 0 "non_push_operand" "+um,dA,dA")) (match_operand:HI 1 "general_operand" "dA,dAim,u"))] "" "#")(define_split [(set (strict_low_part (match_operand:HI 0 "non_push_operand" "")) (match_operand:HI 1 "general_operand" ""))] "z_replacement_completed == 2" [(set (match_dup 0) (match_dup 1))] "")(define_insn "movstrictqi" [(set (strict_low_part (match_operand:QI 0 "non_push_operand" "+mu,!dA")) (match_operand:QI 1 "general_operand" "d,imudA"))] "" "#")(define_split [(set (strict_low_part (match_operand:QI 0 "non_push_operand" "")) (match_operand:QI 1 "general_operand" ""))] "z_replacement_completed == 2" [(set (match_dup 0) (match_dup 1))] "");;--------------------------------------------------------------------;;- 64-bit Move Operations.;; The movdi and movdf patterns are identical except for the mode.;; They are also very similar to those for movsi and movsf.;;;; For 68HC11, we need a scratch register (either D, X, Y) ;; because there is no memory->memory moves. It must be defined with;; earlyclobber (&) so that it does not appear in the source or destination ;; address. Providing patterns for movdi/movdf allows GCC to generate;; better code. [Until now, the scratch register is limited to D because;; otherwise we can run out of registers in the A_REGS class for reload].;;;; For 68HC12, the scratch register is not necessary. To use the same;; pattern and same split, we use the 'v' constraint. This tells the;; reload to use the _.tmp register (which is not used at all).;; The insn will be split in one or several memory moves (movw).;; [SCz: this does not work ?? So, I switched temporary to 'd' reg];;--------------------------------------------------------------------(define_expand "movdi" [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "") (match_operand:DI 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))])] "" " /* For push/pop, emit a REG_INC note to make sure the reload inheritance and reload CSE pass notice the change of the stack pointer. */ if (IS_STACK_PUSH (operands[0]) || IS_STACK_POP (operands[1])) { rtx insn; insn = emit_insn (gen_movdi_internal (operands[0], operands[1])); REG_NOTES (insn) = alloc_EXPR_LIST (REG_INC, stack_pointer_rtx, REG_NOTES (insn)); DONE; }")(define_insn "movdi_internal" [(set (match_operand:DI 0 "nonimmediate_operand" "=ou,U,!u,U,m,m,!u") (match_operand:DI 1 "general_operand" "K,iU,iU,!u,mi,!u,!mu")) (clobber (match_scratch:HI 2 "=X,&d,&d,&d,&d,&d,&d"))] "" "#")(define_split [(set (match_operand:DI 0 "nonimmediate_operand" "") (match_operand:DI 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))] "reload_completed" [(const_int 0)] "m68hc11_split_move (operands[0], operands[1], operands[2]); DONE;")(define_expand "movdf" [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "") (match_operand:DF 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))])] "" "/* For push/pop, emit a REG_INC note to make sure the reload inheritance and reload CSE pass notice the change of the stack pointer. */ if (IS_STACK_PUSH (operands[0]) || IS_STACK_POP (operands[1])) { rtx insn; insn = emit_insn (gen_movdf_internal (operands[0], operands[1])); REG_NOTES (insn) = alloc_EXPR_LIST (REG_INC, stack_pointer_rtx, REG_NOTES (insn)); DONE; }")(define_insn "movdf_internal" [(set (match_operand:DF 0 "nonimmediate_operand" "=ou,U,!u,U,m,m,!u") (match_operand:DF 1 "general_operand" "G,iU,iU,!u,mi,!u,!mu")) (clobber (match_scratch:HI 2 "=X,&d,&d,&d,&d,&d,&d"))] "" "#")(define_split [(set (match_operand:DF 0 "nonimmediate_operand" "") (match_operand:DF 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))] "reload_completed" [(const_int 0)] "m68hc11_split_move (operands[0], operands[1], operands[2]); DONE;");;--------------------------------------------------------------------;;- 32-bit Move Operations.;; The movsi and movsf patterns are identical except for the mode.;; When we move to/from a hard register (d+x), we don't need a scratch.;; Otherwise, a scratch register is used as intermediate register for;; the move. The '&' constraint is necessary to make sure the reload;; pass does not give us a register that dies in the insn and is used;; for input/output operands.;;--------------------------------------------------------------------(define_expand "movsi" [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "") (match_operand:SI 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))])] "" "/* For push/pop, emit a REG_INC note to make sure the reload inheritance and reload CSE pass notice the change of the stack pointer. */ if (IS_STACK_PUSH (operands[0]) || IS_STACK_POP (operands[1])) { rtx insn; insn = emit_insn (gen_movsi_internal (operands[0], operands[1])); REG_NOTES (insn) = alloc_EXPR_LIST (REG_INC, stack_pointer_rtx, REG_NOTES (insn)); DONE; }")(define_insn "movsi_internal" [(set (match_operand:SI 0 "nonimmediate_operand" "=ou,mu,?D,m,?D,?u,?u,!u,D") (match_operand:SI 1 "general_operand" "K,imu,im,?D,!u,?D,mi,!u,!D")) (clobber (match_scratch:HI 2 "=X,&d,X,X,X,X,&d,&d,X"))] "" "#")(define_split [(set (match_operand:SI 0 "nonimmediate_operand" "") (match_operand:SI 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))] "reload_completed" [(const_int 0)] "m68hc11_split_move (operands[0], operands[1], operands[2]); DONE;")(define_expand "movsf" [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "") (match_operand:SF 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))])] "" "/* For push/pop, emit a REG_INC note to make sure the reload inheritance and reload CSE pass notice the change of the stack pointer. */ if (IS_STACK_PUSH (operands[0]) || IS_STACK_POP (operands[1])) { rtx insn; insn = emit_insn (gen_movsf_internal (operands[0], operands[1])); REG_NOTES (insn) = alloc_EXPR_LIST (REG_INC, stack_pointer_rtx, REG_NOTES (insn)); DONE; }")(define_insn "movsf_internal" [(set (match_operand:SF 0 "nonimmediate_operand" "=o!u,m,D,m,D,!u,!u,!u,D") (match_operand:SF 1 "general_operand" "G,im,im,D,!u,D,mi,!u,!D")) (clobber (match_scratch:HI 2 "=X,&d,X,X,X,X,&d,&d,X"))] "" "#")(define_split [(set (match_operand:SF 0 "nonimmediate_operand" "") (match_operand:SF 1 "general_operand" "")) (clobber (match_scratch:HI 2 ""))] "reload_completed" [(const_int 0)] "m68hc11_split_move (operands[0], operands[1], operands[2]); DONE;");;--------------------------------------------------------------------;;- 16-bit Move Operations.;; We don't need a scratch register.;;--------------------------------------------------------------------(define_insn "*movhi2_push" [(set (match_operand:HI 0 "push_operand" "=<,<,<") (match_operand:HI 1 "general_operand" "xy,?d,!z"))] "TARGET_M6811 && !TARGET_M6812" "*{ cc_status = cc_prev_status; if (D_REG_P (operands[1])) { output_asm_insn (\"pshb\", operands); return \"psha\"; } else if (X_REG_P (operands[1])) { return \"pshx\"; } else if (Y_REG_P (operands[1])) { return \"pshy\"; } fatal_insn (\"Invalid register in the instruction\", insn);}")(define_insn "*movhi2_pop" [(set (match_operand:HI 0 "nonimmediate_operand" "=xy,d") (match_operand:HI 1 "pop_operand" ">,>"))] "TARGET_M6811" "*{ cc_status = cc_prev_status; if (D_REG_P (operands[0])) { output_asm_insn (\"pula\", operands); return \"pulb\"; } else if (X_REG_P (operands[0])) { return \"pulx\"; } else if (Y_REG_P (operands[0])) { return \"puly\"; } fatal_insn (\"Invalid register in the instruction\", insn);}")(define_expand "movhi" [(set (match_operand:HI 0 "nonimmediate_operand" "") (match_operand:HI 1 "general_operand" ""))] "" "{ if (reload_in_progress) { if (m68hc11_reload_operands (operands)) { DONE; } } if (TARGET_M6811 && (reload_in_progress | reload_completed) == 0) { if (GET_CODE (operands[0]) == MEM && (GET_CODE (operands[1]) == MEM || GET_CODE (operands[1]) == CONST_INT)) { operands[1] = force_reg (HImode, operands[1]); } else if (IS_STACK_PUSH (operands[0]) && GET_CODE (operands[1]) != REG) { operands[1] = force_reg (HImode, operands[1]); } } /* For push/pop, emit a REG_INC note to make sure the reload inheritance and reload CSE pass notice the change of the stack pointer. */ if (IS_STACK_PUSH (operands[0]) || IS_STACK_POP (operands[1])) { rtx insn; insn = emit_insn (gen_rtx (SET, VOIDmode, operands[0], operands[1])); REG_NOTES (insn) = alloc_EXPR_LIST (REG_INC, stack_pointer_rtx, REG_NOTES (insn)); DONE; }}")(define_insn "movhi_const0" [(set (match_operand:HI 0 "non_push_operand" "=d,A,um") (const_int 0))] ""
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -