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

📄 valarith.c

📁 早期freebsd实现
💻 C
📖 第 1 页 / 共 2 页
字号:
       TYPE_CODE (VALUE_TYPE (arg1)) != TYPE_CODE_INT)      ||      (TYPE_CODE (VALUE_TYPE (arg2)) != TYPE_CODE_FLT       &&       TYPE_CODE (VALUE_TYPE (arg2)) != TYPE_CODE_INT))    error ("Argument to arithmetic operation not a number.");  if (TYPE_CODE (VALUE_TYPE (arg1)) == TYPE_CODE_FLT      ||      TYPE_CODE (VALUE_TYPE (arg2)) == TYPE_CODE_FLT)    {      double v1, v2, v;      v1 = value_as_double (arg1);      v2 = value_as_double (arg2);      switch (op)	{	case BINOP_ADD:	  v = v1 + v2;	  break;	case BINOP_SUB:	  v = v1 - v2;	  break;	case BINOP_MUL:	  v = v1 * v2;	  break;	case BINOP_DIV:	  v = v1 / v2;	  break;	default:	  error ("Integer-only operation on floating point number.");	}      val = allocate_value (builtin_type_double);      SWAP_TARGET_AND_HOST (&v, sizeof (v));      *(double *) VALUE_CONTENTS_RAW (val) = v;    }  else    /* Integral operations here.  */    {      /* Should we promote to unsigned longest?  */      if ((TYPE_UNSIGNED (VALUE_TYPE (arg1))	   || TYPE_UNSIGNED (VALUE_TYPE (arg2)))	  && (TYPE_LENGTH (VALUE_TYPE (arg1)) >= sizeof (unsigned LONGEST)	      || TYPE_LENGTH (VALUE_TYPE (arg2)) >= sizeof (unsigned LONGEST)))	{	  unsigned LONGEST v1, v2, v;	  v1 = (unsigned LONGEST) value_as_long (arg1);	  v2 = (unsigned LONGEST) value_as_long (arg2);	  	  switch (op)	    {	    case BINOP_ADD:	      v = v1 + v2;	      break;	      	    case BINOP_SUB:	      v = v1 - v2;	      break;	      	    case BINOP_MUL:	      v = v1 * v2;	      break;	      	    case BINOP_DIV:	      v = v1 / v2;	      break;	      	    case BINOP_REM:	      v = v1 % v2;	      break;	      	    case BINOP_LSH:	      v = v1 << v2;	      break;	      	    case BINOP_RSH:	      v = v1 >> v2;	      break;	      	    case BINOP_LOGAND:	      v = v1 & v2;	      break;	      	    case BINOP_LOGIOR:	      v = v1 | v2;	      break;	      	    case BINOP_LOGXOR:	      v = v1 ^ v2;	      break;	      	    case BINOP_AND:	      v = v1 && v2;	      break;	      	    case BINOP_OR:	      v = v1 || v2;	      break;	      	    case BINOP_MIN:	      v = v1 < v2 ? v1 : v2;	      break;	      	    case BINOP_MAX:	      v = v1 > v2 ? v1 : v2;	      break;	      	    default:	      error ("Invalid binary operation on numbers.");	    }	  val = allocate_value (BUILTIN_TYPE_UNSIGNED_LONGEST);	  SWAP_TARGET_AND_HOST (&v, sizeof (v));	  *(unsigned LONGEST *) VALUE_CONTENTS_RAW (val) = v;	}      else	{	  LONGEST v1, v2, v;	  v1 = value_as_long (arg1);	  v2 = value_as_long (arg2);	  	  switch (op)	    {	    case BINOP_ADD:	      v = v1 + v2;	      break;	      	    case BINOP_SUB:	      v = v1 - v2;	      break;	      	    case BINOP_MUL:	      v = v1 * v2;	      break;	      	    case BINOP_DIV:	      v = v1 / v2;	      break;	      	    case BINOP_REM:	      v = v1 % v2;	      break;	      	    case BINOP_LSH:	      v = v1 << v2;	      break;	      	    case BINOP_RSH:	      v = v1 >> v2;	      break;	      	    case BINOP_LOGAND:	      v = v1 & v2;	      break;	      	    case BINOP_LOGIOR:	      v = v1 | v2;	      break;	      	    case BINOP_LOGXOR:	      v = v1 ^ v2;	      break;	      	    case BINOP_AND:	      v = v1 && v2;	      break;	      	    case BINOP_OR:	      v = v1 || v2;	      break;	      	    case BINOP_MIN:	      v = v1 < v2 ? v1 : v2;	      break;	      	    case BINOP_MAX:	      v = v1 > v2 ? v1 : v2;	      break;	      	    default:	      error ("Invalid binary operation on numbers.");	    }	  	  val = allocate_value (BUILTIN_TYPE_LONGEST);	  SWAP_TARGET_AND_HOST (&v, sizeof (v));	  *(LONGEST *) VALUE_CONTENTS_RAW (val) = v;	}    }  return val;}/* Simulate the C operator ! -- return 1 if ARG1 contains zero.  */intvalue_zerop (arg1)     value arg1;{  register int len;  register char *p;  COERCE_ARRAY (arg1);  if (TYPE_CODE (VALUE_TYPE (arg1)) == TYPE_CODE_FLT)    return 0 == value_as_double (arg1);  len = TYPE_LENGTH (VALUE_TYPE (arg1));  p = VALUE_CONTENTS (arg1);  while (--len >= 0)    {      if (*p++)	break;    }  return len < 0;}/* Simulate the C operator == by returning a 1   iff ARG1 and ARG2 have equal contents.  */intvalue_equal (arg1, arg2)     register value arg1, arg2;{  register int len;  register char *p1, *p2;  enum type_code code1;  enum type_code code2;  COERCE_ARRAY (arg1);  COERCE_ARRAY (arg2);  code1 = TYPE_CODE (VALUE_TYPE (arg1));  code2 = TYPE_CODE (VALUE_TYPE (arg2));  if (code1 == TYPE_CODE_INT && code2 == TYPE_CODE_INT)    return value_as_long (arg1) == value_as_long (arg2);  else if ((code1 == TYPE_CODE_FLT || code1 == TYPE_CODE_INT)	   && (code2 == TYPE_CODE_FLT || code2 == TYPE_CODE_INT))    return value_as_double (arg1) == value_as_double (arg2);  /* FIXME: Need to promote to either CORE_ADDR or LONGEST, whichever     is bigger.  */  else if (code1 == TYPE_CODE_PTR && code2 == TYPE_CODE_INT)    return value_as_pointer (arg1) == (CORE_ADDR) value_as_long (arg2);  else if (code2 == TYPE_CODE_PTR && code1 == TYPE_CODE_INT)    return (CORE_ADDR) value_as_long (arg1) == value_as_pointer (arg2);  else if (code1 == code2	   && ((len = TYPE_LENGTH (VALUE_TYPE (arg1)))	       == TYPE_LENGTH (VALUE_TYPE (arg2))))    {      p1 = VALUE_CONTENTS (arg1);      p2 = VALUE_CONTENTS (arg2);      while (--len >= 0)	{	  if (*p1++ != *p2++)	    break;	}      return len < 0;    }  else    {      error ("Invalid type combination in equality test.");      return 0;  /* For lint -- never reached */    }}/* Simulate the C operator < by returning 1   iff ARG1's contents are less than ARG2's.  */intvalue_less (arg1, arg2)     register value arg1, arg2;{  register enum type_code code1;  register enum type_code code2;  COERCE_ARRAY (arg1);  COERCE_ARRAY (arg2);  code1 = TYPE_CODE (VALUE_TYPE (arg1));  code2 = TYPE_CODE (VALUE_TYPE (arg2));  if (code1 == TYPE_CODE_INT && code2 == TYPE_CODE_INT)    {      if (TYPE_UNSIGNED (VALUE_TYPE (arg1))       || TYPE_UNSIGNED (VALUE_TYPE (arg2)))	return ((unsigned LONGEST) value_as_long (arg1)		< (unsigned LONGEST) value_as_long (arg2));      else	return value_as_long (arg1) < value_as_long (arg2);    }  else if ((code1 == TYPE_CODE_FLT || code1 == TYPE_CODE_INT)	   && (code2 == TYPE_CODE_FLT || code2 == TYPE_CODE_INT))    return value_as_double (arg1) < value_as_double (arg2);  else if (code1 == TYPE_CODE_PTR && code2 == TYPE_CODE_PTR)    return value_as_pointer (arg1) < value_as_pointer (arg2);  /* FIXME: Need to promote to either CORE_ADDR or LONGEST, whichever     is bigger.  */  else if (code1 == TYPE_CODE_PTR && code2 == TYPE_CODE_INT)    return value_as_pointer (arg1) < (CORE_ADDR) value_as_long (arg2);  else if (code2 == TYPE_CODE_PTR && code1 == TYPE_CODE_INT)    return (CORE_ADDR) value_as_long (arg1) < value_as_pointer (arg2);  else    {      error ("Invalid type combination in ordering comparison.");      return 0;    }}/* The unary operators - and ~.  Both free the argument ARG1.  */valuevalue_neg (arg1)     register value arg1;{  register struct type *type;  COERCE_ENUM (arg1);  type = VALUE_TYPE (arg1);  if (TYPE_CODE (type) == TYPE_CODE_FLT)    return value_from_double (type, - value_as_double (arg1));  else if (TYPE_CODE (type) == TYPE_CODE_INT)    return value_from_longest (type, - value_as_long (arg1));  else {    error ("Argument to negate operation not a number.");    return 0;  /* For lint -- never reached */  }}valuevalue_lognot (arg1)     register value arg1;{  COERCE_ENUM (arg1);  if (TYPE_CODE (VALUE_TYPE (arg1)) != TYPE_CODE_INT)    error ("Argument to complement operation not an integer.");  return value_from_longest (VALUE_TYPE (arg1), ~ value_as_long (arg1));}

⌨️ 快捷键说明

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