📄 pa.c
字号:
if (op == CONST0_RTX (mode)) return 1; if (memory_operand (op, mode) && ! symbolic_memory_operand (op, mode)) return 1; return 0;}/* Return 1 if the operand is a register operand or a non-symbolic memory operand after reload. This predicate is used for branch patterns that internally handle register reloading. We need to accept non-symbolic memory operands after reload to ensure that the pattern is still valid if reload didn't find a hard register for the operand. */intreg_before_reload_operand (op, mode) register rtx op; enum machine_mode mode;{ /* Don't accept a SUBREG since it will need a reload. */ if (GET_CODE (op) == SUBREG) return 0; if (register_operand (op, mode)) return 1; if (reload_completed && memory_operand (op, mode) && ! symbolic_memory_operand (op, mode)) return 1; return 0;}/* Accept any constant that can be moved in one instruction into a general register. */intcint_ok_for_move (intval) HOST_WIDE_INT intval;{ /* OK if ldo, ldil, or zdepi, can be used. */ return (CONST_OK_FOR_LETTER_P (intval, 'J') || CONST_OK_FOR_LETTER_P (intval, 'N') || CONST_OK_FOR_LETTER_P (intval, 'K'));}/* Accept anything that can be moved in one instruction into a general register. */intmove_operand (op, mode) rtx op; enum machine_mode mode;{ if (register_operand (op, mode)) return 1; if (GET_CODE (op) == CONSTANT_P_RTX) return 1; if (GET_CODE (op) == CONST_INT) return cint_ok_for_move (INTVAL (op)); if (GET_CODE (op) == SUBREG) op = SUBREG_REG (op); if (GET_CODE (op) != MEM) return 0; op = XEXP (op, 0); /* We consider a LO_SUM DLT reference a move_operand now since it has been merged into the normal movsi/movdi patterns. */ if (GET_CODE (op) == LO_SUM && GET_CODE (XEXP (op, 0)) == REG && REG_OK_FOR_BASE_P (XEXP (op, 0)) && GET_CODE (XEXP (op, 1)) == UNSPEC && GET_MODE (op) == Pmode) return 1; /* Since move_operand is only used for source operands, we can always allow scaled indexing! */ if (! TARGET_DISABLE_INDEXING && GET_CODE (op) == PLUS && ((GET_CODE (XEXP (op, 0)) == MULT && GET_CODE (XEXP (XEXP (op, 0), 0)) == REG && GET_CODE (XEXP (XEXP (op, 0), 1)) == CONST_INT && INTVAL (XEXP (XEXP (op, 0), 1)) == (HOST_WIDE_INT) GET_MODE_SIZE (mode) && GET_CODE (XEXP (op, 1)) == REG) || (GET_CODE (XEXP (op, 1)) == MULT &&GET_CODE (XEXP (XEXP (op, 1), 0)) == REG && GET_CODE (XEXP (XEXP (op, 1), 1)) == CONST_INT && INTVAL (XEXP (XEXP (op, 1), 1)) == (HOST_WIDE_INT) GET_MODE_SIZE (mode) && GET_CODE (XEXP (op, 0)) == REG))) return 1; return memory_address_p (mode, op);}/* Accept REG and any CONST_INT that can be moved in one instruction into a general register. */intreg_or_cint_move_operand (op, mode) rtx op; enum machine_mode mode;{ if (register_operand (op, mode)) return 1; if (GET_CODE (op) == CONST_INT) return cint_ok_for_move (INTVAL (op)); return 0;}intpic_label_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ if (!flag_pic) return 0; switch (GET_CODE (op)) { case LABEL_REF: return 1; case CONST: op = XEXP (op, 0); return (GET_CODE (XEXP (op, 0)) == LABEL_REF && GET_CODE (XEXP (op, 1)) == CONST_INT); default: return 0; }}intfp_reg_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return reg_renumber && FP_REG_P (op);}/* Return truth value of whether OP can be used as an operand in a three operand arithmetic insn that accepts registers of mode MODE or 14-bit signed integers. */intarith_operand (op, mode) rtx op; enum machine_mode mode;{ return (register_operand (op, mode) || (GET_CODE (op) == CONST_INT && INT_14_BITS (op)));}/* Return truth value of whether OP can be used as an operand in a three operand arithmetic insn that accepts registers of mode MODE or 11-bit signed integers. */intarith11_operand (op, mode) rtx op; enum machine_mode mode;{ return (register_operand (op, mode) || (GET_CODE (op) == CONST_INT && INT_11_BITS (op)));}/* Return truth value of whether OP can be used as an operand in a adddi3 insn. */intadddi3_operand (op, mode) rtx op; enum machine_mode mode;{ return (register_operand (op, mode) || (GET_CODE (op) == CONST_INT && (TARGET_64BIT ? INT_14_BITS (op) : INT_11_BITS (op))));}/* A constant integer suitable for use in a PRE_MODIFY memory reference. */intpre_cint_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == CONST_INT && INTVAL (op) >= -0x2000 && INTVAL (op) < 0x10);}/* A constant integer suitable for use in a POST_MODIFY memory reference. */intpost_cint_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == CONST_INT && INTVAL (op) < 0x2000 && INTVAL (op) >= -0x10);}intarith_double_operand (op, mode) rtx op; enum machine_mode mode;{ return (register_operand (op, mode) || (GET_CODE (op) == CONST_DOUBLE && GET_MODE (op) == mode && VAL_14_BITS_P (CONST_DOUBLE_LOW (op)) && ((CONST_DOUBLE_HIGH (op) >= 0) == ((CONST_DOUBLE_LOW (op) & 0x1000) == 0))));}/* Return truth value of whether OP is an integer which fits the range constraining immediate operands in three-address insns, or is an integer register. */intireg_or_int5_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return ((GET_CODE (op) == CONST_INT && INT_5_BITS (op)) || (GET_CODE (op) == REG && REGNO (op) > 0 && REGNO (op) < 32));}/* Return nonzero if OP is an integer register, else return zero. */intireg_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == REG && REGNO (op) > 0 && REGNO (op) < 32);}/* Return truth value of whether OP is an integer which fits the range constraining immediate operands in three-address insns. */intint5_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == CONST_INT && INT_5_BITS (op));}intuint5_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == CONST_INT && INT_U5_BITS (op));}intint11_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == CONST_INT && INT_11_BITS (op));}intuint32_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{#if HOST_BITS_PER_WIDE_INT > 32 /* All allowed constants will fit a CONST_INT. */ return (GET_CODE (op) == CONST_INT && (INTVAL (op) >= 0 && INTVAL (op) < (HOST_WIDE_INT) 1 << 32));#else return (GET_CODE (op) == CONST_INT || (GET_CODE (op) == CONST_DOUBLE && CONST_DOUBLE_HIGH (op) == 0));#endif}intarith5_operand (op, mode) rtx op; enum machine_mode mode;{ return register_operand (op, mode) || int5_operand (op, mode);}/* True iff zdepi can be used to generate this CONST_INT. zdepi first sign extends a 5 bit signed number to a given field length, then places this field anywhere in a zero. */intzdepi_cint_p (x) unsigned HOST_WIDE_INT x;{ unsigned HOST_WIDE_INT lsb_mask, t; /* This might not be obvious, but it's at least fast. This function is critical; we don't have the time loops would take. */ lsb_mask = x & -x; t = ((x >> 4) + lsb_mask) & ~(lsb_mask - 1); /* Return true iff t is a power of two. */ return ((t & (t - 1)) == 0);}/* True iff depi or extru can be used to compute (reg & mask). Accept bit pattern like these: 0....01....1 1....10....0 1..10..01..1 */intand_mask_p (mask) unsigned HOST_WIDE_INT mask;{ mask = ~mask; mask += mask & -mask; return (mask & (mask - 1)) == 0;}/* True iff depi or extru can be used to compute (reg & OP). */intand_operand (op, mode) rtx op; enum machine_mode mode;{ return (register_operand (op, mode) || (GET_CODE (op) == CONST_INT && and_mask_p (INTVAL (op))));}/* True iff depi can be used to compute (reg | MASK). */intior_mask_p (mask) unsigned HOST_WIDE_INT mask;{ mask += mask & -mask; return (mask & (mask - 1)) == 0;}/* True iff depi can be used to compute (reg | OP). */intior_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == CONST_INT && ior_mask_p (INTVAL (op)));}intlhs_lshift_operand (op, mode) rtx op; enum machine_mode mode;{ return register_operand (op, mode) || lhs_lshift_cint_operand (op, mode);}/* True iff OP is a CONST_INT of the forms 0...0xxxx or 0...01...1xxxx. Such values can be the left hand side x in (x << r), using the zvdepi instruction. */intlhs_lshift_cint_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ unsigned HOST_WIDE_INT x; if (GET_CODE (op) != CONST_INT) return 0; x = INTVAL (op) >> 4; return (x & (x + 1)) == 0;}intarith32_operand (op, mode) rtx op; enum machine_mode mode;{ return register_operand (op, mode) || GET_CODE (op) == CONST_INT;}intpc_or_label_operand (op, mode) rtx op; enum machine_mode mode ATTRIBUTE_UNUSED;{ return (GET_CODE (op) == PC || GET_CODE (op) == LABEL_REF);}/* Legitimize PIC addresses. If the address is already position-independent, we return ORIG. Newly generated position-independent addresses go to REG. If we need more than one register, we lose. */rtxlegitimize_pic_address (orig, mode, reg) rtx orig, reg; enum machine_mode mode;{ rtx pic_ref = orig; /* Labels need special handling. */ if (pic_label_operand (orig, mode)) { /* We do not want to go through the movXX expanders here since that would create recursion. Nor do we really want to call a generator for a named pattern since that requires multiple patterns if we want to support multiple word sizes. So instead we just emit the raw set, which avoids the movXX expanders completely. */ emit_insn (gen_rtx_SET (VOIDmode, reg, orig)); current_function_uses_pic_offset_table = 1; return reg; } if (GET_CODE (orig) == SYMBOL_REF) { if (reg == 0) abort (); emit_move_insn (reg, gen_rtx_PLUS (word_mode, pic_offset_table_rtx, gen_rtx_HIGH (word_mode, orig))); pic_ref = gen_rtx_MEM (Pmode, gen_rtx_LO_SUM (Pmode, reg, gen_rtx_UNSPEC (Pmode, gen_rtvec (1, orig), 0))); current_function_uses_pic_offset_table = 1; RTX_UNCHANGING_P (pic_ref) = 1; emit_move_insn (reg, pic_ref); return reg; } else if (GET_CODE (orig) == CONST) { rtx base; if (GET_CODE (XEXP (orig, 0)) == PLUS && XEXP (XEXP (orig, 0), 0) == pic_offset_table_rtx)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -