📄 pa.md
字号:
;; of the base register.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (mem:SI (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r") (const_int 4)) (match_operand:SI 2 "register_operand" "r"))))] "! TARGET_DISABLE_INDEXING" "ldwx,s %1(0,%2),%0" [(set_attr "type" "load") (set_attr "length" "4")]);; This variant of the above insn can occur if the second operand;; is the frame pointer. This is a kludge, but there doesn't;; seem to be a way around it. Only recognize it while reloading.;; Note how operand 3 uses a predicate of "const_int_operand", but ;; has constraints allowing a register. I don't know how this works,;; but it somehow makes sure that out-of-range constants are placed;; in a register which somehow magically is a "const_int_operand".;; (this was stolen from alpha.md, I'm not going to try and change it.)(define_insn "" [(set (match_operand:SI 0 "register_operand" "&=r") (mem:SI (plus:SI (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r") (const_int 4)) (match_operand:SI 2 "register_operand" "r")) (match_operand:SI 3 "const_int_operand" "rI"))))] "! TARGET_DISABLE_INDEXING && reload_in_progress" "*{ if (GET_CODE (operands[3]) == CONST_INT) return \"sh2addl %1,%2,%0\;ldw %3(0,%0),%0\"; else return \"sh2addl %1,%2,%0\;ldwx %3(0,%0),%0\";}" [(set_attr "type" "load") (set_attr "length" "8")]);; Load or store with base-register modification.(define_insn "pre_ldwm" [(set (match_operand:SI 3 "register_operand" "=r") (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "0") (match_operand:SI 2 "pre_cint_operand" "")))) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_dup 2)))] "" "*{ if (INTVAL (operands[2]) < 0) return \"ldwm %2(0,%0),%3\"; return \"ldws,mb %2(0,%0),%3\";}" [(set_attr "type" "load") (set_attr "length" "4")])(define_insn "pre_stwm" [(set (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "0") (match_operand:SI 2 "pre_cint_operand" ""))) (match_operand:SI 3 "reg_or_0_operand" "rM")) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_dup 2)))] "" "*{ if (INTVAL (operands[2]) < 0) return \"stwm %r3,%2(0,%0)\"; return \"stws,mb %r3,%2(0,%0)\";}" [(set_attr "type" "store") (set_attr "length" "4")])(define_insn "post_ldwm" [(set (match_operand:SI 3 "register_operand" "r") (mem:SI (match_operand:SI 1 "register_operand" "0"))) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_operand:SI 2 "post_cint_operand" "")))] "" "*{ if (INTVAL (operands[2]) > 0) return \"ldwm %2(0,%0),%3\"; return \"ldws,ma %2(0,%0),%3\";}" [(set_attr "type" "load") (set_attr "length" "4")])(define_insn "post_stwm" [(set (mem:SI (match_operand:SI 1 "register_operand" "0")) (match_operand:SI 3 "reg_or_0_operand" "rM")) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_operand:SI 2 "post_cint_operand" "")))] "" "*{ if (INTVAL (operands[2]) > 0) return \"stwm %r3,%2(0,%0)\"; return \"stws,ma %r3,%2(0,%0)\";}" [(set_attr "type" "store") (set_attr "length" "4")]);; For pic;; Note since this pattern can be created at reload time (via movsi), all;; the same rules for movsi apply here. (no new pseudos, no temporaries).(define_insn "pic_load_label" [(set (match_operand:SI 0 "register_operand" "=a") (match_operand:SI 1 "pic_label_operand" ""))] "" "*{ rtx label_rtx = gen_label_rtx (); rtx xoperands[3]; extern FILE *asm_out_file; xoperands[0] = operands[0]; xoperands[1] = operands[1]; xoperands[2] = label_rtx; output_asm_insn (\"bl .+8,%0\", xoperands); output_asm_insn (\"depi 0,31,2,%0\", xoperands); ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\", CODE_LABEL_NUMBER (label_rtx)); /* If we're trying to load the address of a label that happens to be close, then we can use a shorter sequence. */ if (GET_CODE (operands[1]) == LABEL_REF && insn_addresses && abs (insn_addresses[INSN_UID (XEXP (operands[1], 0))] - insn_current_address) < 8100) { /* Prefixing with R% here is wrong, it extracts just 11 bits and is always non-negative. */ output_asm_insn (\"ldo %1-%2(%0),%0\", xoperands); } else { output_asm_insn (\"addil L%%%1-%2,%0\", xoperands); output_asm_insn (\"ldo R%%%1-%2(%0),%0\", xoperands); } return \"\";}" [(set_attr "type" "multi") (set_attr "length" "16")]) ; 12 or 16(define_insn "pic2_highpart" [(set (match_operand:SI 0 "register_operand" "=a") (plus:SI (match_operand:SI 1 "register_operand" "r") (high:SI (match_operand 2 "" ""))))] "symbolic_operand (operands[2], Pmode) && ! function_label_operand (operands[2]) && flag_pic == 2" "addil LT'%G2,%1" [(set_attr "type" "binary") (set_attr "length" "4")]); We need this to make sure CSE doesn't simplify a memory load with a; symbolic address, whose content it think it knows. For PIC, what CSE; think is the real value will be the address of that value.(define_insn "pic2_lo_sum" [(set (match_operand:SI 0 "register_operand" "=r") (mem:SI (lo_sum:SI (match_operand:SI 1 "register_operand" "r") (unspec:SI [(match_operand:SI 2 "symbolic_operand" "")] 0))))] "" "*{ if (flag_pic != 2) abort (); return \"ldw RT'%G2(%1),%0\";}" [(set_attr "type" "load") (set_attr "length" "4")]);; Always use addil rather than ldil;add sequences. This allows the;; HP linker to eliminate the dp relocation if the symbolic operand;; lives in the TEXT space.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=a") (high:SI (match_operand 1 "" "")))] "symbolic_operand (operands[1], Pmode) && ! function_label_operand (operands[1]) && ! read_only_operand (operands[1]) && ! flag_pic" "addil LR'%G1,%%r27" [(set_attr "type" "binary") (set_attr "length" "4")]);; This is for use in the prologue/epilogue code. We need it;; to add large constants to a stack pointer or frame pointer.;; Because of the additional %r1 pressure, we probably do not;; want to use this in general code, so make it available;; only after reload.(define_insn "add_high_const" [(set (match_operand:SI 0 "register_operand" "=!a,*r") (plus:SI (match_operand:SI 1 "register_operand" "r,r") (high:SI (match_operand 2 "const_int_operand" ""))))] "reload_completed" "@ addil L'%G2,%1 ldil L'%G2,%0\;addl %0,%1,%0" [(set_attr "type" "binary,binary") (set_attr "length" "4,8")]);; For function addresses.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (high:SI (match_operand:SI 1 "function_label_operand" "")))] "!TARGET_PORTABLE_RUNTIME" "ldil LP'%G1,%0" [(set_attr "type" "move") (set_attr "length" "4")]);; This version is used only for the portable runtime conventions model;; (it does not use/support plabels)(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (high:SI (match_operand:SI 1 "function_label_operand" "")))] "TARGET_PORTABLE_RUNTIME" "ldil L'%G1,%0" [(set_attr "type" "move") (set_attr "length" "4")])(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (high:SI (match_operand 1 "" "")))] "(!flag_pic || !symbolic_operand (operands[1]), Pmode) && !is_function_label_plus_const (operands[1])" "*{ if (symbolic_operand (operands[1], Pmode)) return \"ldil LR'%G1,%0\"; else return \"ldil L'%G1,%0\";}" [(set_attr "type" "move") (set_attr "length" "4")]);; lo_sum of a function address.;;;; Note since we are not supporting MPE style external calls we can;; use the short ldil;ldo sequence. If one wanted to support;; MPE external calls you would want to generate something like;; ldil;ldo;extru;ldw;add. See the HP compiler's output for details.(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (lo_sum:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "function_label_operand" "")))] "!TARGET_PORTABLE_RUNTIME" "ldo RP'%G2(%1),%0" [(set_attr "type" "move") (set_attr "length" "4")]);; This version is used only for the portable runtime conventions model;; (it does not use/support plabels)(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (lo_sum:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "function_label_operand" "")))] "TARGET_PORTABLE_RUNTIME" "ldo R'%G2(%1),%0" [(set_attr "type" "move") (set_attr "length" "4")])(define_insn "" [(set (match_operand:SI 0 "register_operand" "=r") (lo_sum:SI (match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "immediate_operand" "i")))] "!is_function_label_plus_const (operands[2])" "*{ if (flag_pic && symbolic_operand (operands[2], Pmode)) abort (); else if (symbolic_operand (operands[2], Pmode)) return \"ldo RR'%G2(%1),%0\"; else return \"ldo R'%G2(%1),%0\";}" [(set_attr "type" "move") (set_attr "length" "4")]);; Now that a symbolic_address plus a constant is broken up early;; in the compilation phase (for better CSE) we need a special;; combiner pattern to load the symbolic address plus the constant;; in only 2 instructions. (For cases where the symbolic address;; was not a common subexpression.)(define_split [(set (match_operand:SI 0 "register_operand" "") (match_operand:SI 1 "symbolic_operand" "")) (clobber (match_operand:SI 2 "register_operand" ""))] "! (flag_pic && pic_label_operand (operands[1], SImode))" [(set (match_dup 2) (high:SI (match_dup 1))) (set (match_dup 0) (lo_sum:SI (match_dup 2) (match_dup 1)))] "")(define_expand "movhi" [(set (match_operand:HI 0 "general_operand" "") (match_operand:HI 1 "general_operand" ""))] "" "{ if (emit_move_sequence (operands, HImode, 0)) DONE;}")(define_insn "" [(set (match_operand:HI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,Q,*q,!f") (match_operand:HI 1 "move_operand" "r,J,N,K,Q,rM,rM,!fM"))] "register_operand (operands[0], HImode) || reg_or_0_operand (operands[1], HImode)" "@ copy %1,%0 ldi %1,%0 ldil L'%1,%0 zdepi %Z1,%0 ldh%M1 %1,%0 sth%M0 %r1,%0 mtsar %r1 fcpy,sgl %r1,%0" [(set_attr "type" "move,move,move,shift,load,store,move,fpalu") (set_attr "length" "4,4,4,4,4,4,4,4")])(define_insn "" [(set (match_operand:HI 0 "register_operand" "=r") (mem:HI (plus:SI (mult:SI (match_operand:SI 2 "register_operand" "r") (const_int 2)) (match_operand:SI 1 "register_operand" "r"))))] "! TARGET_DISABLE_INDEXING" "ldhx,s %2(0,%1),%0" [(set_attr "type" "load") (set_attr "length" "4")]);; This variant of the above insn can occur if the second operand;; is the frame pointer. This is a kludge, but there doesn't;; seem to be a way around it. Only recognize it while reloading.;; Note how operand 3 uses a predicate of "const_int_operand", but ;; has constraints allowing a register. I don't know how this works,;; but it somehow makes sure that out-of-range constants are placed;; in a register which somehow magically is a "const_int_operand".;; (this was stolen from alpha.md, I'm not going to try and change it.(define_insn "" [(set (match_operand:HI 0 "register_operand" "=&r") (mem:HI (plus:SI (plus:SI (mult:SI (match_operand:SI 2 "register_operand" "r") (const_int 2)) (match_operand:SI 1 "register_operand" "r")) (match_operand:SI 3 "const_int_operand" "rI"))))] "! TARGET_DISABLE_INDEXING && reload_in_progress" "*{ if (GET_CODE (operands[3]) == CONST_INT) return \"sh1addl %2,%1,%0\;ldh %3(0,%0),%0\"; else return \"sh1addl %2,%1,%0\;ldhx %3(0,%0),%0\";}" [(set_attr "type" "load") (set_attr "length" "8")])(define_insn "" [(set (match_operand:HI 3 "register_operand" "=r") (mem:HI (plus:SI (match_operand:SI 1 "register_operand" "0") (match_operand:SI 2 "int5_operand" "L")))) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_dup 2)))] "" "ldhs,mb %2(0,%0),%3" [(set_attr "type" "load") (set_attr "length" "4")])(define_insn "" [(set (mem:HI (plus:SI (match_operand:SI 1 "register_operand" "0") (match_operand:SI 2 "int5_operand" "L"))) (match_operand:HI 3 "reg_or_0_operand" "rM")) (set (match_operand:SI 0 "register_operand" "=r") (plus:SI (match_dup 1) (match_dup 2)))] "" "sths,mb %r3,%2(0,%0)" [(set_attr "type" "store") (set_attr "length" "4")])(define_insn "" [(set (match_operand:HI 0 "register_operand" "=r") (high:HI (match_operand 1 "const_int_operand" "")))] "" "ldil L'%G1,%0" [(set_attr "type" "move") (set_attr "length" "4")])(define_insn "" [(set (match_operand:HI 0 "register_operand" "=r") (lo_sum:HI (match_operand:HI 1 "register_operand" "r") (match_operand 2 "const_int_operand" "")))] "" "ldo R'%G2(%1),%0" [(set_attr "type" "move") (set_attr "length" "4")])(define_expand "movqi" [(set (match_operand:QI 0 "general_operand" "") (match_operand:QI 1 "general_operand" ""))] "" "{ if (emit_move_sequence (operands, QImode, 0)) DONE;}")(define_insn "" [(set (match_operand:QI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,Q,*q,!f") (match_operand:QI 1 "move_operand" "r,J,N,K,Q,rM,rM,!fM"))] "register_operand (operands[0], QImode) || reg_or_0_operand (operands[1], QImode)" "@ copy %1,%0 ldi %1,%0 ldil L'%1,%0 zdepi %Z1,%0 ldb%M1 %1,%0 stb%M0 %r1,%0 mtsar %r1 fcpy,sgl %r1,%0"
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -