⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 m68hc11.c

📁 linux下的gcc编译器
💻 C
📖 第 1 页 / 共 5 页
字号:
	{	  printf ("Class = %s for: ", reg_class_names[class]);	  fflush (stdout);	  debug_rtx (operand);	}    }  if (debug_m6811)    {      printf (" => class=%s\n", reg_class_names[class]);      fflush (stdout);      debug_rtx (operand);    }  return class;}/* Return 1 if the operand is a valid indexed addressing mode.   For 68hc11:  n,r    with n in [0..255] and r in A_REGS class   For 68hc12:  n,r    no constraint on the constant, r in A_REGS class.  */static intregister_indirect_p (operand, mode, strict)     rtx operand;     enum machine_mode mode;     int strict;{  rtx base, offset;  switch (GET_CODE (operand))    {    case POST_INC:    case PRE_INC:    case POST_DEC:    case PRE_DEC:      if (TARGET_M6812 && TARGET_AUTO_INC_DEC)	return register_indirect_p (XEXP (operand, 0), mode, strict);      return 0;    case PLUS:      base = XEXP (operand, 0);      if (GET_CODE (base) == MEM)	return 0;      offset = XEXP (operand, 1);      if (GET_CODE (offset) == MEM)	return 0;      if (GET_CODE (base) == REG)	{	  if (!VALID_CONSTANT_OFFSET_P (offset, mode))	    return 0;	  if (strict == 0)	    return 1;	  return REGNO_OK_FOR_BASE_P2 (REGNO (base), strict);	}      if (GET_CODE (offset) == REG)	{	  if (!VALID_CONSTANT_OFFSET_P (base, mode))	    return 0;	  if (strict == 0)	    return 1;	  return REGNO_OK_FOR_BASE_P2 (REGNO (offset), strict);	}      return 0;    case REG:      return REGNO_OK_FOR_BASE_P2 (REGNO (operand), strict);    case CONST_INT:      if (TARGET_M6811)        return 0;      return VALID_CONSTANT_OFFSET_P (operand, mode);    default:      return 0;    }}/* Returns 1 if the operand fits in a 68HC11 indirect mode or in   a 68HC12 1-byte index addressing mode.  */intm68hc11_small_indexed_indirect_p (operand, mode)     rtx operand;     enum machine_mode mode;{  rtx base, offset;  if (GET_CODE (operand) == REG && reload_in_progress      && REGNO (operand) >= FIRST_PSEUDO_REGISTER      && reg_equiv_memory_loc[REGNO (operand)])    {      operand = reg_equiv_memory_loc[REGNO (operand)];      operand = eliminate_regs (operand, 0, NULL_RTX);    }  if (GET_CODE (operand) != MEM)    return 0;  operand = XEXP (operand, 0);  if (CONSTANT_ADDRESS_P (operand))    return 1;  if (PUSH_POP_ADDRESS_P (operand))    return 1;  if (!register_indirect_p (operand, mode, reload_completed))    return 0;  if (TARGET_M6812 && GET_CODE (operand) == PLUS      && (reload_completed | reload_in_progress))    {      base = XEXP (operand, 0);      offset = XEXP (operand, 1);      /* The offset can be a symbol address and this is too big         for the operand constraint.  */      if (GET_CODE (base) != CONST_INT && GET_CODE (offset) != CONST_INT)        return 0;      if (GET_CODE (base) == CONST_INT)	offset = base;      switch (GET_MODE_SIZE (mode))	{	case 8:	  if (INTVAL (offset) < -16 + 6 || INTVAL (offset) > 15 - 6)	    return 0;	  break;	case 4:	  if (INTVAL (offset) < -16 + 2 || INTVAL (offset) > 15 - 2)	    return 0;	  break;	default:	  if (INTVAL (offset) < -16 || INTVAL (offset) > 15)	    return 0;	  break;	}    }  return 1;}intm68hc11_register_indirect_p (operand, mode)     rtx operand;     enum machine_mode mode;{  if (GET_CODE (operand) != MEM)    return 0;  operand = XEXP (operand, 0);  return register_indirect_p (operand, mode,                              (reload_completed | reload_in_progress));}static intgo_if_legitimate_address_internal (operand, mode, strict)     rtx operand;     enum machine_mode mode;     int strict;{  if (CONSTANT_ADDRESS_P (operand) && TARGET_M6812)    {      /* Reject the global variables if they are too wide.  This forces         a load of their address in a register and generates smaller code.  */      if (GET_MODE_SIZE (mode) == 8)	return 0;      return 1;    }  if (register_indirect_p (operand, mode, strict))    {      return 1;    }  if (PUSH_POP_ADDRESS_P (operand))    {      return 1;    }  if (symbolic_memory_operand (operand, mode))    {      return 1;    }  return 0;}intm68hc11_go_if_legitimate_address (operand, mode, strict)     rtx operand;     enum machine_mode mode;     int strict;{  int result;  if (debug_m6811)    {      printf ("Checking: ");      fflush (stdout);      debug_rtx (operand);    }  result = go_if_legitimate_address_internal (operand, mode, strict);  if (debug_m6811)    {      printf (" -> %s\n", result == 0 ? "NO" : "YES");    }  if (result == 0)    {      if (debug_m6811)	{	  printf ("go_if_legitimate%s, ret 0: %d:",		  (strict ? "_strict" : ""), mode);	  fflush (stdout);	  debug_rtx (operand);	}    }  return result;}intm68hc11_legitimize_address (operand, old_operand, mode)     rtx *operand ATTRIBUTE_UNUSED;     rtx old_operand ATTRIBUTE_UNUSED;     enum machine_mode mode ATTRIBUTE_UNUSED;{  return 0;}intm68hc11_reload_operands (operands)     rtx operands[];{  enum machine_mode mode;  if (regs_inited == 0)    create_regs_rtx ();  mode = GET_MODE (operands[1]);  /* Input reload of indirect addressing (MEM (PLUS (REG) (CONST))).  */  if (A_REG_P (operands[0]) && memory_reload_operand (operands[1], mode))    {      rtx big_offset = XEXP (XEXP (operands[1], 0), 1);      rtx base = XEXP (XEXP (operands[1], 0), 0);      if (GET_CODE (base) != REG)	{	  rtx tmp = base;	  base = big_offset;	  big_offset = tmp;	}      /* If the offset is out of range, we have to compute the address         with a separate add instruction.  We try to do with with an 8-bit         add on the A register.  This is possible only if the lowest part         of the offset (ie, big_offset % 256) is a valid constant offset         with respect to the mode.  If it's not, we have to generate a         16-bit add on the D register.  From:                (SET (REG X (MEM (PLUS (REG X) (CONST_INT 1000)))))                we generate:                 [(SET (REG D) (REG X)) (SET (REG X) (REG D))]         (SET (REG A) (PLUS (REG A) (CONST_INT 1000 / 256)))         [(SET (REG D) (REG X)) (SET (REG X) (REG D))]         (SET (REG X) (MEM (PLUS (REG X) (CONST_INT 1000 % 256)))                (SET (REG X) (PLUS (REG X) (CONST_INT 1000 / 256 * 256)))         (SET (REG X) (MEM (PLUS (REG X) (CONST_INT 1000 % 256))))       */      if (!VALID_CONSTANT_OFFSET_P (big_offset, mode))	{	  int vh, vl;	  rtx reg = operands[0];	  rtx offset;	  int val = INTVAL (big_offset);	  /* We use the 'operands[0]' as a scratch register to compute the	     address. Make sure 'base' is in that register.  */	  if (!rtx_equal_p (base, operands[0]))	    {	      emit_move_insn (reg, base);	    }	  if (val > 0)	    {	      vh = val >> 8;	      vl = val & 0x0FF;	    }	  else	    {	      vh = (val >> 8) & 0x0FF;	      vl = val & 0x0FF;	    }	  /* Create the lowest part offset that still remains to be added.	     If it's not a valid offset, do a 16-bit add.  */	  offset = GEN_INT (vl);	  if (!VALID_CONSTANT_OFFSET_P (offset, mode))	    {	      emit_insn (gen_rtx (SET, VOIDmode, reg,				  gen_rtx (PLUS, HImode, reg, big_offset)));	      offset = const0_rtx;	    }	  else	    {	      emit_insn (gen_rtx (SET, VOIDmode, reg,				  gen_rtx (PLUS, HImode, reg,					   GEN_INT (vh << 8))));	    }	  emit_move_insn (operands[0],			  gen_rtx (MEM, GET_MODE (operands[1]),				   gen_rtx (PLUS, Pmode, reg, offset)));	  return 1;	}    }  /* Use the normal gen_movhi pattern.  */  return 0;}voidm68hc11_emit_libcall (name, code, dmode, smode, noperands, operands)     const char *name;     enum rtx_code code;     enum machine_mode dmode;     enum machine_mode smode;     int noperands;     rtx *operands;{  rtx ret;  rtx insns;  rtx libcall;  rtx equiv;  start_sequence ();  libcall = gen_rtx_SYMBOL_REF (Pmode, name);  switch (noperands)    {    case 2:      ret = emit_library_call_value (libcall, NULL_RTX, LCT_CONST,                                     dmode, 1, operands[1], smode);      equiv = gen_rtx (code, dmode, operands[1]);      break;    case 3:      ret = emit_library_call_value (libcall, NULL_RTX,                                     LCT_CONST, dmode, 2,                                     operands[1], smode, operands[2],                                     smode);      equiv = gen_rtx (code, dmode, operands[1], operands[2]);      break;    default:      abort ();    }  insns = get_insns ();  end_sequence ();  emit_libcall_block (insns, operands[0], ret, equiv);}/* Returns true if X is a PRE/POST increment decrement   (same as auto_inc_p() in rtlanal.c but do not take into   account the stack).  */static intm68hc11_auto_inc_p (x)     rtx x;{  return GET_CODE (x) == PRE_DEC    || GET_CODE (x) == POST_INC    || GET_CODE (x) == POST_DEC || GET_CODE (x) == PRE_INC;}/* Predicates for machine description.  */intmemory_reload_operand (operand, mode)     rtx operand;     enum machine_mode mode ATTRIBUTE_UNUSED;{  return GET_CODE (operand) == MEM    && GET_CODE (XEXP (operand, 0)) == PLUS    && ((GET_CODE (XEXP (XEXP (operand, 0), 0)) == REG	 && GET_CODE (XEXP (XEXP (operand, 0), 1)) == CONST_INT)	|| (GET_CODE (XEXP (XEXP (operand, 0), 1)) == REG	    && GET_CODE (XEXP (XEXP (operand, 0), 0)) == CONST_INT));}inttst_operand (operand, mode)     rtx operand;     enum machine_mode mode;{  if (GET_CODE (operand) == MEM && reload_completed == 0)    {      rtx addr = XEXP (operand, 0);      if (m68hc11_auto_inc_p (addr))	return 0;    }  return nonimmediate_operand (operand, mode);}intcmp_operand (operand, mode)     rtx operand;     enum machine_mode mode;{  if (GET_CODE (operand) == MEM)    {      rtx addr = XEXP (operand, 0);      if (m68hc11_auto_inc_p (addr))	return 0;    }  return general_operand (operand, mode);}intnon_push_operand (operand, mode)     rtx operand;     enum machine_mode mode;{  if (general_operand (operand, mode) == 0)    return 0;  if (push_operand (operand, mode) == 1)    return 0;  return 1;}intreg_or_some_mem_operand (operand, mode)     rtx operand;     enum machine_mode mode;{  if (GET_CODE (operand) == MEM)    {      rtx op = XEXP (operand, 0);      if (symbolic_memory_operand (op, mode))	return 1;      if (IS_STACK_PUSH (operand))	return 1;      if (m68hc11_register_indirect_p (operand, mode))	return 1;      return 0;    }  return register_operand (operand, mode);}intm68hc11_symbolic_p (operand, mode)     rtx operand;     enum machine_mode mode;{  if (GET_CODE (operand) == MEM)    {      rtx op = XEXP (operand, 0);      if (symbolic_memory_operand (op, mode))	return 1;    }  return 0;}intm68hc11_indirect_p (operand, mode)     rtx operand;     enum machine_mode mode;{  if (GET_CODE (operand) == MEM)    {      rtx op = XEXP (operand, 0);      if (symbolic_memory_operand (op, mode))	return 0;      if (reload_in_progress)        return 1;      operand = XEXP (operand, 0);      return register_indirect_p (operand, mode, reload_completed);    }  return 0;}int

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -