Make xundump reject numbers that don't fit into integral field
Numbers are read into a double, then cast to the field type. The cast may change the value. Flag that as error, except for floating-point fields.
This commit is contained in:
parent
029d929b1b
commit
50070a8f9a
1 changed files with 18 additions and 11 deletions
|
@ -514,7 +514,7 @@ setnum(int fldno, double dbl)
|
||||||
struct castr *ca;
|
struct castr *ca;
|
||||||
int idx;
|
int idx;
|
||||||
char *memb_ptr;
|
char *memb_ptr;
|
||||||
double old;
|
double old, new;
|
||||||
|
|
||||||
ca = getfld(fldno, &idx);
|
ca = getfld(fldno, &idx);
|
||||||
if (!ca)
|
if (!ca)
|
||||||
|
@ -531,58 +531,63 @@ setnum(int fldno, double dbl)
|
||||||
return -1;
|
return -1;
|
||||||
memb_ptr += ca->ca_off;
|
memb_ptr += ca->ca_off;
|
||||||
|
|
||||||
/* FIXME check assignment preserves value */
|
|
||||||
switch (ca->ca_type) {
|
switch (ca->ca_type) {
|
||||||
case NSC_CHAR:
|
case NSC_CHAR:
|
||||||
old = ((signed char *)memb_ptr)[idx];
|
old = ((signed char *)memb_ptr)[idx];
|
||||||
((signed char *)memb_ptr)[idx] = (signed char)dbl;
|
new = ((signed char *)memb_ptr)[idx] = (signed char)dbl;
|
||||||
break;
|
break;
|
||||||
case NSC_UCHAR:
|
case NSC_UCHAR:
|
||||||
case NSC_HIDDEN:
|
case NSC_HIDDEN:
|
||||||
old = ((unsigned char *)memb_ptr)[idx];
|
old = ((unsigned char *)memb_ptr)[idx];
|
||||||
((unsigned char *)memb_ptr)[idx] = (unsigned char)dbl;
|
new = ((unsigned char *)memb_ptr)[idx] = (unsigned char)dbl;
|
||||||
break;
|
break;
|
||||||
case NSC_SHORT:
|
case NSC_SHORT:
|
||||||
old = ((short *)memb_ptr)[idx];
|
old = ((short *)memb_ptr)[idx];
|
||||||
((short *)memb_ptr)[idx] = (short)dbl;
|
new = ((short *)memb_ptr)[idx] = (short)dbl;
|
||||||
break;
|
break;
|
||||||
case NSC_USHORT:
|
case NSC_USHORT:
|
||||||
old = ((unsigned short *)memb_ptr)[idx];
|
old = ((unsigned short *)memb_ptr)[idx];
|
||||||
((unsigned short *)memb_ptr)[idx] = (unsigned short)dbl;
|
new = ((unsigned short *)memb_ptr)[idx] = (unsigned short)dbl;
|
||||||
break;
|
break;
|
||||||
case NSC_INT:
|
case NSC_INT:
|
||||||
old = ((int *)memb_ptr)[idx];
|
old = ((int *)memb_ptr)[idx];
|
||||||
((int *)memb_ptr)[idx] = (int)dbl;
|
new = ((int *)memb_ptr)[idx] = (int)dbl;
|
||||||
break;
|
break;
|
||||||
case NSC_LONG:
|
case NSC_LONG:
|
||||||
old = ((long *)memb_ptr)[idx];
|
old = ((long *)memb_ptr)[idx];
|
||||||
((long *)memb_ptr)[idx] = (long)dbl;
|
new = ((long *)memb_ptr)[idx] = (long)dbl;
|
||||||
break;
|
break;
|
||||||
case NSC_XCOORD:
|
case NSC_XCOORD:
|
||||||
old = ((coord *)memb_ptr)[idx];
|
old = ((coord *)memb_ptr)[idx];
|
||||||
/* FIXME use variant of xrel() that takes orig instead of nation */
|
/* FIXME use variant of xrel() that takes orig instead of nation */
|
||||||
if (old >= WORLD_X / 2)
|
if (old >= WORLD_X / 2)
|
||||||
old -= WORLD_X;
|
old -= WORLD_X;
|
||||||
((coord *)memb_ptr)[idx] = XNORM((coord)dbl);
|
new = ((coord *)memb_ptr)[idx] = XNORM((coord)dbl);
|
||||||
|
if (new >= WORLD_X / 2)
|
||||||
|
new -= WORLD_X;
|
||||||
break;
|
break;
|
||||||
case NSC_YCOORD:
|
case NSC_YCOORD:
|
||||||
old = ((coord *)memb_ptr)[idx];
|
old = ((coord *)memb_ptr)[idx];
|
||||||
/* FIXME use variant of yrel() that takes orig instead of nation */
|
/* FIXME use variant of yrel() that takes orig instead of nation */
|
||||||
if (old >= WORLD_Y / 2)
|
if (old >= WORLD_Y / 2)
|
||||||
old -= WORLD_Y;
|
old -= WORLD_Y;
|
||||||
((coord *)memb_ptr)[idx] = YNORM((coord)dbl);
|
new = ((coord *)memb_ptr)[idx] = YNORM((coord)dbl);
|
||||||
|
if (new >= WORLD_Y / 2)
|
||||||
|
new -= WORLD_Y;
|
||||||
break;
|
break;
|
||||||
case NSC_FLOAT:
|
case NSC_FLOAT:
|
||||||
old = ((float *)memb_ptr)[idx];
|
old = ((float *)memb_ptr)[idx];
|
||||||
((float *)memb_ptr)[idx] = (float)dbl;
|
((float *)memb_ptr)[idx] = (float)dbl;
|
||||||
|
new = dbl; /* suppress new != dbl check */
|
||||||
break;
|
break;
|
||||||
case NSC_DOUBLE:
|
case NSC_DOUBLE:
|
||||||
old = ((double *)memb_ptr)[idx];
|
old = ((double *)memb_ptr)[idx];
|
||||||
((double *)memb_ptr)[idx] = dbl;
|
((double *)memb_ptr)[idx] = dbl;
|
||||||
|
new = dbl; /* suppress new != dbl check */
|
||||||
break;
|
break;
|
||||||
case NSC_TIME:
|
case NSC_TIME:
|
||||||
old = ((time_t *)memb_ptr)[idx];
|
old = ((time_t *)memb_ptr)[idx];
|
||||||
((time_t *)memb_ptr)[idx] = (time_t)dbl;
|
new = ((time_t *)memb_ptr)[idx] = (time_t)dbl;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return gripe("Field %d doesn't take numbers", fldno + 1);
|
return gripe("Field %d doesn't take numbers", fldno + 1);
|
||||||
|
@ -590,6 +595,8 @@ setnum(int fldno, double dbl)
|
||||||
|
|
||||||
if (fldval_must_match(fldno) && old != dbl)
|
if (fldval_must_match(fldno) && old != dbl)
|
||||||
return gripe("Value for field %d must be %g", fldno + 1, old);
|
return gripe("Value for field %d must be %g", fldno + 1, old);
|
||||||
|
if (new != dbl)
|
||||||
|
return gripe("Field %d can't hold this value", fldno + 1);
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue