📄 ip2k.md
字号:
OUT_AS2 (mov, ipl, w); OUT_AS1 (pop, iph); return \"\"; case 1: OUT_AS2 (mov, w, (IP)); OUT_AS2 (mov, %H0, w); OUT_AS1 (inc, ipl); OUT_AS2 (mov, w, (IP)); OUT_AS2 (mov, %L0, w); if (!find_regno_note (insn, REG_DEAD, REG_IP)) OUT_AS1 (dec, ipl); return \"\"; default: abort (); } }")(define_insn "*movhi_from_ip_plus_offs" [(set (match_operand:HI 0 "nonimmediate_operand" "=f,bqdo") (mem:HI (plus:HI (reg:HI 4) (match_operand 1 "const_int_operand" "P, P"))))] "reload_completed && (INTVAL (operands[1]) < 0x100)" "*{ switch (which_alternative) { case 0: OUT_AS2 (mov, w, %1); OUT_AS2 (add, ipl, w); OUT_AS1 (push, (IP)); OUT_AS1 (inc, ipl); OUT_AS2 (mov, w, (IP)); OUT_AS2 (mov, ipl, w); OUT_AS1 (pop, iph); return \"\"; case 1: if (INTVAL (operands[1]) == 1) OUT_AS1 (inc, ipl); else { OUT_AS2 (mov, w, %1); OUT_AS2 (add, ipl, w); } OUT_AS1 (push, (IP)%<); OUT_AS1 (pop, %H0%>); OUT_AS1 (inc, ipl); OUT_AS1 (push, (IP)%<); OUT_AS1 (pop, %L0%>); if (!find_regno_note (insn, REG_DEAD, REG_IP)) { OUT_AS1 (dec, ipl); if (INTVAL (operands[1]) == 1) OUT_AS1 (dec, ipl); else OUT_AS2 (sub, ipl, w); } return \"\"; default: abort (); } }")(define_insn_and_split "*movhi" [(set (match_operand:HI 0 "ip2k_split_dest_operand" "=<,<,uo,b, uS,uo,uo, q,u") (match_operand:HI 1 "general_operand" "ron,i, n,T,uoi,uS,ui,ui,q"))] "" "@ push\\t%L1%<\;push\\t%H1%> push\\t%L1%<\;push\\t%H1%> mov\\tw,%H1\;mov\\t%H0,w\;mov\\tw,%L1\;mov\\t%L0,w loadl\\t%x1\;loadh\\t%x1 mov\\tw,%H1\;push\\t%L1%<\;pop\\t%L0%>\;mov\\t%H0,w mov\\tw,%H1\;push\\t%L1%<\;pop\\t%L0%>\;mov\\t%H0,w mov\\tw,%H1\;push\\t%L1%<\;pop\\t%L0%>\;mov\\t%H0,w mov\\tw,%H1\;mov\\t%H0,w\;mov\\tw,%L1\;mov\\t%L0,w mov\\tw,%H1\;mov\\t%H0,w\;mov\\tw,%L1\;mov\\t%L0,w" "(ip2k_reorg_split_himode && (GET_CODE (operands[1]) == CONST_INT || (push_operand (operands[0], HImode) && GET_CODE (operands[1]) == REG) || (register_operand (operands[0], HImode) && REGNO (operands[0]) >= 0x80 && ip2k_gen_operand (operands[1], HImode))))" [(set (match_dup 2) (match_dup 3)) (set (match_dup 4) (match_dup 5))] "{ ip2k_split_words (QImode, HImode, operands); /* Split into 2=3,4=5 */ }" [(set_attr "clobberw" "no,no,yes,no,yes,yes,yes,yes,yes")]);; We don't generally use IP for HImode indirections because it's not;; offsettable, however if we're accessing something that's already pointed;; to by IP and would otherwise require a reload of DP then we can win by;; simulating HImode accesses via IP instead.(define_peephole2 [(set (reg:HI 12) (reg:HI 4)) (set (mem:HI (reg:HI 12)) (match_operand:HI 0 "general_operand" ""))] "((ip2k_reorg_in_progress || ip2k_reorg_completed) && ip2k_xexp_not_uses_reg_p (operands[0], REG_DP, 2) && peep2_regno_dead_p (2, REG_DP))" [(set (mem:HI (reg:HI 4)) (match_dup 0))] "")(define_peephole2 [(set (reg:HI 12) (reg:HI 4)) (set (match_operand:HI 0 "nonimmediate_operand" "") (mem:HI (reg:HI 12)))] "((ip2k_reorg_in_progress || ip2k_reorg_completed) && ip2k_xexp_not_uses_reg_p (operands[0], REG_DP, 2) && peep2_regno_dead_p (2, REG_DP))" [(set (match_dup 0) (mem:HI (reg:HI 4)))] "")(define_peephole2 [(set (reg:HI 12) (reg:HI 4)) (set (match_operand:HI 0 "nonimmediate_operand" "") (mem:HI (plus:HI (reg:HI 12) (match_operand 1 "const_int_operand" ""))))] ; ; We only match here if IP and DP both go dead because emulating ; offsets in conjunction with IP doesn't win unless IP goes ; dead too. ; "((ip2k_reorg_in_progress || ip2k_reorg_completed) && peep2_regno_dead_p (2, REG_DP) && peep2_regno_dead_p (2, REG_IP) && (INTVAL (operands[1]) < 0x100))" [(set (match_dup 0) (mem:HI (plus:HI (reg:HI 4) (match_dup 1))))] "")(define_peephole2 [(set (reg:HI 12) (reg:HI 4)) (set (reg:HI 4) (mem:HI (plus:HI (reg:HI 12) (match_operand 0 "const_int_operand" ""))))] "((ip2k_reorg_in_progress || ip2k_reorg_completed) && peep2_regno_dead_p (2, REG_DP) && (INTVAL (operands[0]) < 0x100))" [(set (reg:HI 4) (mem:HI (plus:HI (reg:HI 4) (match_dup 0))))] "")(define_peephole2 [(set (match_operand:HI 0 "register_operand" "") (mem:HI (reg:HI 4))) (set (match_operand:HI 2 "nonimmediate_operand" "") (match_dup 0))] "((ip2k_reorg_in_progress || ip2k_reorg_completed) && peep2_reg_dead_p (2, operands[0]))" [(set (match_dup 2) (mem:HI (reg:HI 4)))] "")(define_peephole2 [(set (match_operand:HI 0 "register_operand" "") (mem:HI (plus:HI (reg:HI 4) (match_operand 1 "const_int_operand" "")))) (set (match_operand:HI 2 "nonimmediate_operand" "") (match_dup 0))] "((ip2k_reorg_in_progress || ip2k_reorg_completed) && peep2_reg_dead_p (2, operands[0]) && (INTVAL (operands[1]) < 0x100))" [(set (match_dup 2) (mem:HI (plus:HI (reg:HI 4) (match_dup 1))))] "")(define_peephole2 [(set (match_operand:HI 0 "ip2k_nonsp_reg_operand" "") (match_operand:HI 1 "ip2k_short_operand" "")) (set (reg:HI 12) (reg:HI 4)) (set (mem:HI (reg:HI 12)) (match_dup 0))] "(peep2_reg_dead_p (3, operands[0]) && ip2k_xexp_not_uses_reg_p (operands[0], REG_DP, 2) && peep2_regno_dead_p (3, REG_DP))" [(set (mem:HI (reg:HI 4)) (match_dup 1))] "");; We sometimes want to copy a value twice, usually when we copy a value into;; both a structure slot and into a temporary register. We can win here;; because gcc doesn't know about ways of reusing w while we're copying.;;(define_insn "*movhi_twice" [(set (match_operand:HI 0 "ip2k_gen_operand" "=&uS,uS") (match_operand:HI 1 "ip2k_gen_operand" "uS,uS")) (set (match_operand:HI 2 "ip2k_gen_operand" "=&uS,uS") (match_dup 1))] "ip2k_reorg_split_simode" "*{ switch (which_alternative) { case 0: return AS2 (mov, w, %L1) CR_TAB AS2 (mov, %L0, w) CR_TAB AS2 (mov, %L2, w) CR_TAB AS2 (mov, w, %H1) CR_TAB AS2 (mov, %H0, w) CR_TAB AS2 (mov, %H2, w); case 1: return AS2 (mov, w, %L1) CR_TAB AS1 (push, %H1%<) CR_TAB AS1 (push, %H1%<) CR_TAB AS1 (pop, %H0%>) CR_TAB AS2 (mov, %L0, w) CR_TAB AS1 (pop, %H2%>) CR_TAB AS2 (mov, %L2, w); default: abort (); } }");; We have to be *very* careful with this one to use predicates that do not;; allow this to match if there are any register dependencies between the;; operands.;; Don't try to match until we've removed redundant reloads. Often this;; simplification will remove the need to do two moves!;;(define_peephole2 [(set (match_operand:HI 0 "ip2k_gen_operand" "") (match_operand:HI 1 "ip2k_gen_operand" "")) (set (match_operand:HI 2 "ip2k_gen_operand" "") (match_dup 0))] "(ip2k_reorg_split_simode)" [(parallel [(set (match_dup 0) (match_dup 1)) (set (match_dup 2) (match_dup 1))])] "");; We have to be *very* careful with this one to use predicates that do not;; allow this to match if there are any register dependencies between the;; operands.;; Don't try to match until we've removed redundant reloads. Often this;; simplification will remove the need to do two moves!;;(define_peephole2 [(set (match_operand:HI 0 "ip2k_gen_operand" "") (match_operand:HI 1 "ip2k_gen_operand" "")) (set (match_operand:HI 2 "ip2k_gen_operand" "") (match_dup 1))] "(ip2k_reorg_split_simode && (!REG_P (operands[0]) || ip2k_xexp_not_uses_reg_p (operands[1], REGNO (operands[0]), 2)))" [(parallel [(set (match_dup 0) (match_dup 1)) (set (match_dup 2) (match_dup 1))])] "");;;; Move 32-bit integers.;;(define_expand "movsi" [(set (match_operand:SI 0 "" "") (match_operand:SI 1 "" ""))] "" "")(define_insn_and_split "*movsi" [(set (match_operand:SI 0 "ip2k_split_dest_operand" "=<, ro, S") (match_operand:SI 1 "general_operand" "roSi,rSi,roi"))] "" "#" "ip2k_reorg_split_simode" [(set (match_dup 2) (match_dup 3)) (set (match_dup 4) (match_dup 5))] "{ ip2k_split_words (HImode, SImode, operands); /* Split into 2=3,4=5 */ }");; We sometimes want to copy a value twice, usually when we copy a value into;; both a structure slot and into a temporary register. We can win here;; because gcc doesn't know about ways of reusing w while we're copying.;;(define_insn "*movsi_twice" [(set (match_operand:SI 0 "ip2k_gen_operand" "=&uS,uS") (match_operand:SI 1 "ip2k_gen_operand" "uS,uS")) (set (match_operand:SI 2 "ip2k_gen_operand" "=&uS,uS") (match_dup 1))] "ip2k_reorg_split_dimode" "*{ switch (which_alternative) { case 0: return AS2 (mov, w, %A1) CR_TAB AS2 (mov, %A0, w) CR_TAB AS2 (mov, %A2, w) CR_TAB AS2 (mov, w, %B1) CR_TAB AS2 (mov, %B0, w) CR_TAB AS2 (mov, %B2, w) CR_TAB AS2 (mov, w, %C1) CR_TAB AS2 (mov, %C0, w) CR_TAB AS2 (mov, %C2, w) CR_TAB AS2 (mov, w, %D1) CR_TAB AS2 (mov, %D0, w) CR_TAB AS2 (mov, %D2, w); case 1: return AS2 (mov, w, %D1) CR_TAB AS1 (push, %C1%<) CR_TAB AS1 (push, %B1%<) CR_TAB AS1 (push, %A1%<) CR_TAB AS1 (push, %C1%<) CR_TAB AS1 (push, %B1%<) CR_TAB AS1 (push, %A1%<) CR_TAB AS1 (pop, %A0%>) CR_TAB AS1 (pop, %B0%>) CR_TAB AS1 (pop, %C0%>) CR_TAB AS2 (mov, %D0, w) CR_TAB AS1 (pop, %A2%>) CR_TAB AS1 (pop, %B2%>) CR_TAB AS1 (pop, %C2%>) CR_TAB AS2 (mov, %D2, w); default: abort (); } }");; We have to be *very* careful with this one to use predicates that do not ;; allow this to match if there are any register dependencies between the;; operands.;; Don't try to match until we've removed redundant reloads. Often this;; simplification will remove the need to do two moves!;;(define_peephole2 [(set (match_operand:SI 0 "ip2k_gen_operand" "") (match_operand:SI 1 "ip2k_gen_operand" "")) (set (match_operand:SI 2 "ip2k_gen_operand" "") (match_dup 0))] "(ip2k_reorg_split_dimode && (!REG_P (operands[0]) || (ip2k_xexp_not_uses_reg_p (operands[1], REGNO (operands[0]), 4) && ip2k_xexp_not_uses_reg_p (operands[2], REGNO (operands[0]), 4))) && (!REG_P (operands[1]) || (ip2k_xexp_not_uses_reg_p (operands[0], REGNO (operands[1]), 4) && ip2k_xexp_not_uses_reg_p (operands[2], REGNO (operands[1]), 4))) && (!REG_P (operands[2]) || (ip2k_xexp_not_uses_reg_p (operands[0], REGNO (operands[2]), 4) && ip2k_xexp_not_uses_reg_p (operands[1], REGNO (operands[2]), 4))))" [(parallel [(set (match_dup 0) (match_dup 1)) (set (match_dup 2) (match_dup 1))])] "");; We have to be *very* careful with this one to use predicates that do not;; allow this to match if there are any register dependencies between the;; operands.;; Don't try to match until we've removed redundant reloads. Often this;; simplification will remove the need to do two moves!;;(define_peephole2 [(set (match_operand:SI 0 "ip2k_gen_operand" "") (match_operand:SI 1 "ip2k_gen_operand" "")) (set (match_operand:SI 2 "ip2k_gen_operand" "") (match_dup 1))] "(ip2k_reorg_split_dimode && (!REG_P (operands[0]) || (ip2k_xexp_not_uses_reg_p (operands[1], REGNO (operands[0]), 4) && ip2k_xexp_not_uses_reg_p (operands[2], REGNO (operands[0]), 4))) && (!REG_P (operands[1]) || (ip2k_xexp_not_uses_reg_p (operands[0], REGNO (operands[1]), 4) && ip2k_xexp_not_uses_reg_p (operands[2], REGNO (operands[1]), 4))) && (!REG_P (operands[2]) || (ip2k_xexp_not_uses_reg_p (operands[0], REGNO (operands[2]), 4) && ip2k_xexp_not_uses_reg_p (operands[1], REGNO (operands[2]), 4))))" [(parallel [(set (match_dup 0) (match_dup 1)) (set (match_dup 2) (match_dup 1))])] "");;;; Move 64-bit integers.;;(define_expand "movdi" [(set (match_operand:DI 0 "" "") (match_operand:DI 1 "" ""))] "" "")(define_insn_and_split "*movdi" [(set (match_operand:DI 0 "ip2k_split_dest_operand" "=<, ro, S") (match_operand:DI 1 "general_operand" "roSi,rSi,roi"))]
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -