(valstr): Replace member val_as.off by val_as.sym, which contains
offset and index. This is for the new dumps; conditions can't use it, yet. (nstr_comp_val): Zero index. (nstr_exec_val): Implement index. (nstr_exec_val): Simplify coercion to WANT.
This commit is contained in:
parent
d1bf11a015
commit
612f2dadb8
2 changed files with 47 additions and 40 deletions
|
@ -78,11 +78,12 @@ typedef unsigned char nsc_flags;
|
|||
/*
|
||||
* Value, possibly symbolic.
|
||||
* If type is NSC_NOTYPE, it's an error value.
|
||||
* If category is NSC_OFF, the value is at offset val_as.off in the
|
||||
* context object.
|
||||
* If category is NSC_OFF, the value is in a context object at offset
|
||||
* val_as.sym.off + val_as.sym.idx * S, where S is the size of the
|
||||
* value.
|
||||
* If category is NSC_VAL, the value is in val_as, and the type is a
|
||||
* promoted type.
|
||||
* Some values can also be interpreted as an object type. The values
|
||||
* Some values can also be interpreted as an object type. The value's
|
||||
* consumer chooses how to interpret it, depending on context.
|
||||
*/
|
||||
struct valstr {
|
||||
|
@ -90,8 +91,11 @@ struct valstr {
|
|||
packed_nsc_cat val_cat; /* category of value */
|
||||
signed char val_as_type; /* value interpreted as object type */
|
||||
union {
|
||||
ptrdiff_t off; /* cat NSC_OFF */
|
||||
double dbl; /* cat NSC_VAL, types NSC_DOUBLE */
|
||||
struct { /* cat NSC_OFF */
|
||||
ptrdiff_t off;
|
||||
int idx;
|
||||
} sym;
|
||||
double dbl; /* cat NSC_VAL, type NSC_DOUBLE */
|
||||
char *str; /* cat NSC_VAL, type NSC_STRING */
|
||||
long lng; /* cat NSC_VAL, type NSC_LONG */
|
||||
} val_as;
|
||||
|
|
|
@ -187,6 +187,8 @@ nstr_exec(struct nscstr *np, int ncond, void *ptr)
|
|||
* Return a pointer to the first character after the value on success,
|
||||
* NULL on error.
|
||||
* TYPE is the context type, a file type.
|
||||
* If STR names an array, VAL simply refers to the element with index
|
||||
* zero.
|
||||
*/
|
||||
char *
|
||||
nstr_comp_val(char *str, struct valstr*val, int type)
|
||||
|
@ -232,7 +234,8 @@ nstr_comp_val(char *str, struct valstr*val, int type)
|
|||
else {
|
||||
val->val_type = cap[j].ca_type;
|
||||
val->val_cat = NSC_OFF;
|
||||
val->val_as.off = cap[j].ca_off;
|
||||
val->val_as.sym.off = cap[j].ca_off;
|
||||
val->val_as.sym.idx = 0;
|
||||
}
|
||||
}
|
||||
} else
|
||||
|
@ -391,8 +394,8 @@ nstr_coerce_val(struct valstr *val, nsc_type to, char *str)
|
|||
* Use coordinate system of country CNUM.
|
||||
* PTR points to a context object of the type that was used to compile
|
||||
* the value.
|
||||
* If WANT is not zero, coerce the value to promoted value type WANT.
|
||||
* VAL must be coercible. That's the case if a previous
|
||||
* Unless WANT is NSC_NOTYPE, coerce the value to promoted value type
|
||||
* WANT. VAL must be coercible. That's the case if a previous
|
||||
* nstr_coerce_val(VAL, WANT, STR) succeeded.
|
||||
*/
|
||||
void
|
||||
|
@ -400,6 +403,7 @@ nstr_exec_val(struct valstr *val, natid cnum, void *ptr, nsc_type want)
|
|||
{
|
||||
char *memb_ptr;
|
||||
nsc_type valtype = NSC_LONG;
|
||||
int idx;
|
||||
|
||||
switch (val->val_cat) {
|
||||
default:
|
||||
|
@ -410,38 +414,39 @@ nstr_exec_val(struct valstr *val, natid cnum, void *ptr, nsc_type want)
|
|||
break;
|
||||
case NSC_OFF:
|
||||
memb_ptr = ptr;
|
||||
memb_ptr += val->val_as.off;
|
||||
memb_ptr += val->val_as.sym.off;
|
||||
idx = val->val_as.sym.idx;
|
||||
switch (val->val_type) {
|
||||
case NSC_CHAR:
|
||||
val->val_as.lng = *(signed char *)memb_ptr;
|
||||
val->val_as.lng = ((signed char *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_UCHAR:
|
||||
val->val_as.lng = *(unsigned char *)memb_ptr;
|
||||
val->val_as.lng = ((unsigned char *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_SHORT:
|
||||
val->val_as.lng = *(short *)memb_ptr;
|
||||
val->val_as.lng = ((short *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_USHORT:
|
||||
val->val_as.lng = *(unsigned short *)memb_ptr;
|
||||
val->val_as.lng = ((unsigned short *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_INT:
|
||||
val->val_as.lng = *(int *)memb_ptr;
|
||||
val->val_as.lng = ((int *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_LONG:
|
||||
val->val_as.lng = *(long *)memb_ptr;
|
||||
val->val_as.lng = ((long *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_XCOORD:
|
||||
val->val_as.lng = xrel(getnatp(cnum), *(short *)memb_ptr);
|
||||
val->val_as.lng = xrel(getnatp(cnum), ((short *)memb_ptr)[idx]);
|
||||
break;
|
||||
case NSC_YCOORD:
|
||||
val->val_as.lng = yrel(getnatp(cnum), *(short *)memb_ptr);
|
||||
val->val_as.lng = yrel(getnatp(cnum), ((short *)memb_ptr)[idx]);
|
||||
break;
|
||||
case NSC_FLOAT:
|
||||
val->val_as.dbl = *(float *)memb_ptr;
|
||||
val->val_as.dbl = ((float *)memb_ptr)[idx];
|
||||
valtype = NSC_DOUBLE;
|
||||
break;
|
||||
case NSC_DOUBLE:
|
||||
val->val_as.dbl = *(double *)memb_ptr;
|
||||
val->val_as.dbl = ((double *)memb_ptr)[idx];
|
||||
valtype = NSC_DOUBLE;
|
||||
break;
|
||||
case NSC_STRING:
|
||||
|
@ -449,10 +454,10 @@ nstr_exec_val(struct valstr *val, natid cnum, void *ptr, nsc_type want)
|
|||
valtype = NSC_STRING;
|
||||
break;
|
||||
case NSC_TIME:
|
||||
val->val_as.lng = *(time_t *)memb_ptr;
|
||||
val->val_as.lng = ((time_t *)memb_ptr)[idx];
|
||||
break;
|
||||
case NSC_TYPEID:
|
||||
val->val_as.lng = *(signed char *)memb_ptr;
|
||||
val->val_as.lng = ((signed char *)memb_ptr)[idx];
|
||||
valtype = NSC_TYPEID;
|
||||
break;
|
||||
default:
|
||||
|
@ -461,7 +466,6 @@ nstr_exec_val(struct valstr *val, natid cnum, void *ptr, nsc_type want)
|
|||
}
|
||||
}
|
||||
|
||||
if (want) {
|
||||
if (valtype == want)
|
||||
;
|
||||
else if (want == NSC_DOUBLE) {
|
||||
|
@ -471,7 +475,7 @@ nstr_exec_val(struct valstr *val, natid cnum, void *ptr, nsc_type want)
|
|||
}
|
||||
} else if (want == NSC_STRING)
|
||||
CANT_HAPPEN("unimplemented WANT"); /* FIXME */
|
||||
if (CANT_HAPPEN(valtype != want)) {
|
||||
if (CANT_HAPPEN(valtype != want && want != NSC_NOTYPE)) {
|
||||
valtype = want;
|
||||
switch (want) {
|
||||
case NSC_TYPEID:
|
||||
|
@ -482,7 +486,6 @@ nstr_exec_val(struct valstr *val, natid cnum, void *ptr, nsc_type want)
|
|||
CANT_HAPPEN("bad WANT argument");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
val->val_type = valtype;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue