Make values independent objects.

values are now uniquely allocated (for the current object file). With
this, constants in dags will work.
This commit is contained in:
Bill Currie 2012-07-18 23:01:09 +09:00
parent c57df8b5f3
commit 28ce35f1c1
13 changed files with 317 additions and 157 deletions

View file

@ -157,6 +157,7 @@ typedef struct {
} ex_state_t;
typedef struct ex_value_s {
struct ex_value_s *next;
etype_t type;
union {
const char *string_val; ///< string constant
@ -191,7 +192,7 @@ typedef struct expr_s {
ex_expr_t expr; ///< binary or unary expression
struct symbol_s *symbol; ///< symbol reference expression
ex_temp_t temp; ///< temporary variable expression
ex_value_t value; ///< constant value
ex_value_t *value; ///< constant value
} e;
} expr_t;

View file

@ -68,7 +68,7 @@ typedef struct symbol_s {
union {
int offset; ///< st_var (in a struct/union)
struct def_s *def; ///< st_var
struct ex_value_s value; ///< st_const
struct ex_value_s *value; ///< st_const
struct expr_s *expr; ///< st_expr
struct function_s *func; ///< st_func
} s;

View file

@ -31,9 +31,29 @@
#ifndef __value_h
#define __value_h
/** \defgroup qfcc_value Constant values.
\ingroup qfcc_expr
*/
//@{
struct ex_value_s;
struct type_s;
struct ex_value_s *new_string_val (const char *string_val);
struct ex_value_s *new_float_val (float float_val);
struct ex_value_s *new_vector_val (const float *vector_val);
struct ex_value_s *new_entity_val (int entity_val);
struct ex_value_s *new_field_val (int field_val, struct type_s *type,
struct def_s *def);
struct ex_value_s *new_func_val (int func_val);
struct ex_value_s *new_pointer_val (int val, struct type_s *type,
struct def_s *def);
struct ex_value_s *new_quaternion_val (const float *quaternion_val);
struct ex_value_s *new_integer_val (int integer_val);
struct ex_value_s *new_uinteger_val (int uinteger_val);
struct ex_value_s *new_short_val (short short_val);
struct ex_value_s *new_nil_val (struct type_s *type);
void convert_value (struct ex_value_s *value, struct type_s *type);
struct def_s *emit_value (struct ex_value_s *value, struct def_s *def);
@ -41,4 +61,6 @@ int ReuseString (const char *str);
void clear_immediates (void);
//@}
#endif//__value_h

View file

@ -140,7 +140,7 @@ convert_to_float (expr_t *e)
switch (e->type) {
case ex_value:
switch (e->e.value.type) {
switch (e->e.value->type) {
case ev_integer:
convert_int (e);
return e;

View file

@ -284,7 +284,7 @@ init_elements (struct def_s *def, expr_t *eles)
reloc_def_op (c->e.labelref.label, &loc);
continue;
} else if (c->type == ex_value) {
if (c->e.value.type == ev_integer
if (c->e.value->type == ev_integer
&& elements[i].type->type == ev_float)
convert_int (c);
if (get_type (c) != elements[i].type) {
@ -306,11 +306,11 @@ init_elements (struct def_s *def, expr_t *eles)
} else {
if (c->type != ex_value)
internal_error (c, "bogus expression type in init_elements()");
if (c->e.value.type == ev_string) {
if (c->e.value->type == ev_string) {
EMIT_STRING (def->space, g->string_var,
c->e.value.v.string_val);
c->e.value->v.string_val);
} else {
memcpy (g, &c->e.value.v, type_size (get_type (c)) * 4);
memcpy (g, &c->e.value->v, type_size (get_type (c)) * 4);
}
}
}
@ -341,12 +341,12 @@ init_vector_components (symbol_t *vector_sym, int is_field)
expr = sym->s.expr;
if (is_field) {
if (expr->type != ex_value
|| expr->e.value.type != ev_field) {
|| expr->e.value->type != ev_field) {
error (0, "%s redefined", name);
sym = 0;
} else {
expr->e.value.v.pointer.def = vector_sym->s.def;
expr->e.value.v.pointer.val = i;
expr->e.value->v.pointer.def = vector_sym->s.def;
expr->e.value->v.pointer.val = i;
}
}
}
@ -505,14 +505,14 @@ initialize_def (symbol_t *sym, type_t *type, expr_t *init, defspace_t *space,
error (0, "non-constant initializier");
return;
}
if (init->e.value.type == ev_pointer
|| init->e.value.type == ev_field) {
if (init->e.value->type == ev_pointer
|| init->e.value->type == ev_field) {
// FIXME offset pointers
D_INT (sym->s.def) = init->e.value.v.pointer.val;
if (init->e.value.v.pointer.def)
reloc_def_field (init->e.value.v.pointer.def, sym->s.def);
D_INT (sym->s.def) = init->e.value->v.pointer.val;
if (init->e.value->v.pointer.def)
reloc_def_field (init->e.value->v.pointer.def, sym->s.def);
} else {
ex_value_t v = init->e.value;
ex_value_t v = *init->e.value;
if (is_scalar (sym->type))
convert_value (&v, sym->type);
if (v.type == ev_string) {

View file

@ -305,55 +305,55 @@ print_value (expr_t *e, int level, int id)
type_t *type;
const char *label = "?!?";
switch (e->e.value.type) {
switch (e->e.value->type) {
case ev_string:
label = va ("\\\"%s\\\"", e->e.value.v.string_val);
label = va ("\\\"%s\\\"", e->e.value->v.string_val);
break;
case ev_float:
label = va ("%g", e->e.value.v.float_val);
label = va ("%g", e->e.value->v.float_val);
break;
case ev_vector:
label = va ("'%g %g %g'",
e->e.value.v.vector_val[0],
e->e.value.v.vector_val[1],
e->e.value.v.vector_val[2]);
e->e.value->v.vector_val[0],
e->e.value->v.vector_val[1],
e->e.value->v.vector_val[2]);
break;
case ev_quat:
label = va ("'%g %g %g %g'",
e->e.value.v.quaternion_val[0],
e->e.value.v.quaternion_val[1],
e->e.value.v.quaternion_val[2],
e->e.value.v.quaternion_val[3]);
e->e.value->v.quaternion_val[0],
e->e.value->v.quaternion_val[1],
e->e.value->v.quaternion_val[2],
e->e.value->v.quaternion_val[3]);
break;
case ev_pointer:
type = e->e.value.v.pointer.type;
if (e->e.value.v.pointer.def)
type = e->e.value->v.pointer.type;
if (e->e.value->v.pointer.def)
label = va ("(%s)[%d]<%s>",
type ? pr_type_name[type->type] : "???",
e->e.value.v.pointer.val,
e->e.value.v.pointer.def->name);
e->e.value->v.pointer.val,
e->e.value->v.pointer.def->name);
else
label = va ("(%s)[%d]",
type ? pr_type_name[type->type] : "???",
e->e.value.v.pointer.val);
e->e.value->v.pointer.val);
break;
case ev_field:
label = va ("field %d", e->e.value.v.pointer.val);
label = va ("field %d", e->e.value->v.pointer.val);
break;
case ev_entity:
label = va ("ent %d", e->e.value.v.integer_val);
label = va ("ent %d", e->e.value->v.integer_val);
break;
case ev_func:
label = va ("func %d", e->e.value.v.integer_val);
label = va ("func %d", e->e.value->v.integer_val);
break;
case ev_integer:
label = va ("%d", e->e.value.v.integer_val);
label = va ("%d", e->e.value->v.integer_val);
break;
case ev_uinteger:
label = va ("%u", e->e.value.v.uinteger_val);
label = va ("%u", e->e.value->v.uinteger_val);
break;
case ev_short:
label = va ("%d", e->e.value.v.short_val);
label = va ("%d", e->e.value->v.short_val);
break;
case ev_void:
label = "<void>";

View file

@ -94,7 +94,7 @@ get_operand_def (expr_t *expr, operand_t *op)
case sy_func:
return op->o.symbol->s.func->def;
case sy_const:
return get_value_def (&op->o.symbol->s.value, op->type);
return get_value_def (op->o.symbol->s.value, op->type);
case sy_type:
case sy_expr:
case sy_class:

View file

@ -60,6 +60,7 @@
#include "struct.h"
#include "symtab.h"
#include "type.h"
#include "value.h"
#include "qc-parse.h"
static expr_t *free_exprs;
@ -164,16 +165,16 @@ get_type (expr_t *e)
case ex_temp:
return e->e.temp.type;
case ex_value:
if (e->e.value.type == ev_pointer)
return pointer_type (e->e.value.v.pointer.type);
if (e->e.value.type == ev_field)
return field_type (e->e.value.v.pointer.type);
if (e->e.value.type == ev_integer
if (e->e.value->type == ev_pointer)
return pointer_type (e->e.value->v.pointer.type);
if (e->e.value->type == ev_field)
return field_type (e->e.value->v.pointer.type);
if (e->e.value->type == ev_integer
&& options.code.progsversion == PROG_ID_VERSION) {
e->e.value.type = ev_float;
e->e.value.v.float_val = e->e.value.v.integer_val;
e->e.value->type = ev_float;
e->e.value->v.float_val = e->e.value->v.integer_val;
}
return ev_types[e->e.value.type];
return ev_types[e->e.value->type];
}
return 0;
}
@ -511,8 +512,7 @@ new_string_expr (const char *string_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_string;
e->e.value.v.string_val = string_val;
e->e.value = new_string_val (string_val);
return e;
}
@ -521,8 +521,7 @@ new_float_expr (float float_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_float;
e->e.value.v.float_val = float_val;
e->e.value = new_float_val (float_val);
return e;
}
@ -531,8 +530,7 @@ new_vector_expr (const float *vector_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_vector;
VectorCopy (vector_val, e->e.value.v.vector_val);
e->e.value = new_vector_val (vector_val);
return e;
}
@ -541,8 +539,7 @@ new_entity_expr (int entity_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_entity;
e->e.value.v.entity_val = entity_val;
e->e.value = new_entity_val (entity_val);
return e;
}
@ -551,10 +548,7 @@ new_field_expr (int field_val, type_t *type, def_t *def)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_field;
e->e.value.v.pointer.val = field_val;
e->e.value.v.pointer.type = type;
e->e.value.v.pointer.def = def;
e->e.value = new_field_val (field_val, type, def);
return e;
}
@ -563,8 +557,7 @@ new_func_expr (int func_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_func;
e->e.value.v.func_val = func_val;
e->e.value = new_func_val (func_val);
return e;
}
@ -573,10 +566,7 @@ new_pointer_expr (int val, type_t *type, def_t *def)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_pointer;
e->e.value.v.pointer.val = val;
e->e.value.v.pointer.type = type;
e->e.value.v.pointer.def = def;
e->e.value = new_pointer_val (val, type, def);
return e;
}
@ -585,8 +575,7 @@ new_quaternion_expr (const float *quaternion_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_quat;
QuatCopy (quaternion_val, e->e.value.v.quaternion_val);
e->e.value = new_quaternion_val (quaternion_val);
return e;
}
@ -595,8 +584,7 @@ new_integer_expr (int integer_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_integer;
e->e.value.v.integer_val = integer_val;
e->e.value = new_integer_val (integer_val);
return e;
}
@ -605,8 +593,7 @@ new_uinteger_expr (unsigned uinteger_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_uinteger;
e->e.value.v.uinteger_val = uinteger_val;
e->e.value = new_uinteger_val (uinteger_val);
return e;
}
@ -615,8 +602,7 @@ new_short_expr (short short_val)
{
expr_t *e = new_expr ();
e->type = ex_value;
e->e.value.type = ev_short;
e->e.value.v.short_val = short_val;
e->e.value = new_short_val (short_val);
return e;
}
@ -636,7 +622,7 @@ constant_expr (expr_t *e)
{
expr_t *new;
symbol_t *sym;
ex_value_t value;
ex_value_t *value;
if (!is_constant (e))
return e;
@ -649,9 +635,10 @@ constant_expr (expr_t *e)
value = sym->s.value;
} else if (sym->sy_type == sy_var && sym->s.def->constant) {
//FIXME pointers and fields
memset (&value, 0, sizeof (value));
memcpy (&value.v, &D_INT (sym->s.def),
type_size (sym->s.def->type) * sizeof (pr_type_t));
internal_error (e, "what to do here?");
//memset (&value, 0, sizeof (value));
//memcpy (&value.v, &D_INT (sym->s.def),
//type_size (sym->s.def->type) * sizeof (pr_type_t));
} else {
return e;
}
@ -668,7 +655,7 @@ is_string_val (expr_t *e)
{
if (e->type == ex_nil)
return 1;
if (e->type == ex_value && e->e.value.type == ev_string)
if (e->type == ex_value && e->e.value->type == ev_string)
return 1;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_string)
@ -681,11 +668,8 @@ expr_string (expr_t *e)
{
if (e->type == ex_nil)
return 0;
if (e->type == ex_value && e->e.value.type == ev_string)
return e->e.value.v.string_val;
//if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
// && e->e.symbol->type->type == ev_string)
// return e->e.symbol->s.value;
if (e->type == ex_value && e->e.value->type == ev_string)
return e->e.value->v.string_val;
internal_error (e, "not a string constant");
}
@ -694,7 +678,7 @@ is_float_val (expr_t *e)
{
if (e->type == ex_nil)
return 1;
if (e->type == ex_value && e->e.value.type == ev_float)
if (e->type == ex_value && e->e.value->type == ev_float)
return 1;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_float)
@ -707,11 +691,11 @@ expr_float (expr_t *e)
{
if (e->type == ex_nil)
return 0;
if (e->type == ex_value && e->e.value.type == ev_float)
return e->e.value.v.float_val;
if (e->type == ex_value && e->e.value->type == ev_float)
return e->e.value->v.float_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_float)
return e->e.symbol->s.value.v.float_val;
return e->e.symbol->s.value->v.float_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_var
&& e->e.symbol->s.def->constant
&& is_float (e->e.symbol->s.def->type))
@ -724,7 +708,7 @@ is_vector_val (expr_t *e)
{
if (e->type == ex_nil)
return 1;
if (e->type == ex_value && e->e.value.type == ev_vector)
if (e->type == ex_value && e->e.value->type == ev_vector)
return 1;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_vector)
@ -737,11 +721,11 @@ expr_vector (expr_t *e)
{
if (e->type == ex_nil)
return vec3_origin;
if (e->type == ex_value && e->e.value.type == ev_vector)
return e->e.value.v.vector_val;
if (e->type == ex_value && e->e.value->type == ev_vector)
return e->e.value->v.vector_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_vector)
return e->e.symbol->s.value.v.vector_val;
return e->e.symbol->s.value->v.vector_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_var
&& e->e.symbol->s.def->constant
&& e->e.symbol->s.def->type->type == ev_vector)
@ -754,7 +738,7 @@ is_quaternion_val (expr_t *e)
{
if (e->type == ex_nil)
return 1;
if (e->type == ex_value && e->e.value.type == ev_quat)
if (e->type == ex_value && e->e.value->type == ev_quat)
return 1;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_quat)
@ -767,11 +751,11 @@ expr_quaternion (expr_t *e)
{
if (e->type == ex_nil)
return quat_origin;
if (e->type == ex_value && e->e.value.type == ev_quat)
return e->e.value.v.quaternion_val;
if (e->type == ex_value && e->e.value->type == ev_quat)
return e->e.value->v.quaternion_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_quat)
return e->e.symbol->s.value.v.quaternion_val;
return e->e.symbol->s.value->v.quaternion_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_var
&& e->e.symbol->s.def->constant
&& e->e.symbol->s.def->type->type == ev_quat)
@ -784,7 +768,7 @@ is_integer_val (expr_t *e)
{
if (e->type == ex_nil)
return 1;
if (e->type == ex_value && e->e.value.type == ev_integer)
if (e->type == ex_value && e->e.value->type == ev_integer)
return 1;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& (e->e.symbol->type->type == ev_integer
@ -798,12 +782,12 @@ expr_integer (expr_t *e)
{
if (e->type == ex_nil)
return 0;
if (e->type == ex_value && e->e.value.type == ev_integer)
return e->e.value.v.integer_val;
if (e->type == ex_value && e->e.value->type == ev_integer)
return e->e.value->v.integer_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& (e->e.symbol->type->type == ev_integer
|| is_enum (e->e.symbol->type)))
return e->e.symbol->s.value.v.integer_val;
return e->e.symbol->s.value->v.integer_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_var
&& e->e.symbol->s.def->constant
&& is_integral (e->e.symbol->s.def->type))
@ -816,11 +800,11 @@ expr_uinteger (expr_t *e)
{
if (e->type == ex_nil)
return 0;
if (e->type == ex_value && e->e.value.type == ev_uinteger)
return e->e.value.v.uinteger_val;
if (e->type == ex_value && e->e.value->type == ev_uinteger)
return e->e.value->v.uinteger_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_uinteger)
return e->e.symbol->s.value.v.uinteger_val;
return e->e.symbol->s.value->v.uinteger_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_var
&& e->e.symbol->s.def->constant
&& is_integral (e->e.symbol->s.def->type))
@ -833,7 +817,7 @@ is_short_val (expr_t *e)
{
if (e->type == ex_nil)
return 1;
if (e->type == ex_value && e->e.value.type == ev_short)
if (e->type == ex_value && e->e.value->type == ev_short)
return 1;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_short)
@ -846,11 +830,11 @@ expr_short (expr_t *e)
{
if (e->type == ex_nil)
return 0;
if (e->type == ex_value && e->e.value.type == ev_short)
return e->e.value.v.short_val;
if (e->type == ex_value && e->e.value->type == ev_short)
return e->e.value->v.short_val;
if (e->type == ex_symbol && e->e.symbol->sy_type == sy_const
&& e->e.symbol->type->type == ev_short)
return e->e.symbol->s.value.v.short_val;
return e->e.symbol->s.value->v.short_val;
internal_error (e, "not a short constant");
}
@ -998,8 +982,8 @@ field_expr (expr_t *e1, expr_t *e2)
return e1;
e2->type = ex_value;
e2->e.value.type = ev_short;
e2->e.value.v.short_val = field->s.offset;
e2->e.value->type = ev_short;
e2->e.value->v.short_val = field->s.offset;
e = new_binary_expr ('&', e1, e2);
e->e.expr.type = pointer_type (field->type);
return unary_expr ('.', e);
@ -1012,8 +996,8 @@ field_expr (expr_t *e1, expr_t *e2)
if (!ivar)
return new_error_expr ();
e2->type = ex_value;
e2->e.value.type = ev_short;
e2->e.value.v.short_val = ivar->s.offset;
e2->e.value->type = ev_short;
e2->e.value->v.short_val = ivar->s.offset;
e = new_binary_expr ('&', e1, e2);
e->e.expr.type = pointer_type (ivar->type);
return unary_expr ('.', e);
@ -1042,17 +1026,17 @@ field_expr (expr_t *e1, expr_t *e2)
}
def = sym->s.def;
e2 = new_field_expr (0, field->type, def);
} else if (e2->type != ex_value || e2->e.value.type != ev_field) {
} else if (e2->type != ex_value || e2->e.value->type != ev_field) {
internal_error (e2, "unexpected field exression");
}
e2->e.value.v.pointer.val += field->s.offset;
e2->e.value.v.pointer.type = field->type;
e2->e.value->v.pointer.val += field->s.offset;
e2->e.value->v.pointer.type = field->type;
// create a new . expression
return field_expr (e1, e2);
} else {
e2->type = ex_value;
e2->e.value.type = ev_short;
e2->e.value.v.short_val = field->s.offset;
e2->e.value->type = ev_short;
e2->e.value->v.short_val = field->s.offset;
e = address_expr (e1, e2, field->type);
return unary_expr ('.', e);
}
@ -1302,35 +1286,32 @@ bool_expr (int op, expr_t *label, expr_t *e1, expr_t *e2)
void
convert_int (expr_t *e)
{
e->e.value.v.float_val = expr_integer (e);
e->e.value.type = ev_float;
e->e.value->v.float_val = expr_integer (e);
e->e.value->type = ev_float;
e->type = ex_value;
}
void
convert_short (expr_t *e)
{
e->e.value.v.float_val = expr_short (e);
e->e.value.type = ev_float;
e->e.value->v.float_val = expr_short (e);
e->e.value->type = ev_float;
e->type = ex_value;
}
void
convert_short_int (expr_t *e)
{
e->e.value.v.integer_val = expr_short (e);
e->e.value.type = ev_integer;
e->e.value->v.integer_val = expr_short (e);
e->e.value->type = ev_integer;
e->type = ex_value;
}
void
convert_nil (expr_t *e, type_t *t)
{
memset (&e->e.value, 0, sizeof (e->e.value));
e->e.value.type = low_level_type (t);
if (t->type == ev_pointer || t->type == ev_field)
e->e.value.v.pointer.type = t->t.fldptr.type;
e->type = ex_value;
e->e.value = new_nil_val (t);
}
int
@ -2197,10 +2178,7 @@ address_expr (expr_t *e1, expr_t *e2, type_t *t)
if (is_array (type)) {
e = e1;
e->type = ex_value;
e->e.value.type = ev_pointer;
e->e.value.v.pointer.val = 0;
e->e.value.v.pointer.type = t;
e->e.value.v.pointer.def = def;
e->e.value = new_pointer_val (0, t, def);
} else {
e = new_pointer_expr (0, t, def);
e->line = e1->line;
@ -2245,10 +2223,9 @@ address_expr (expr_t *e1, expr_t *e2, type_t *t)
if (e2) {
if (e2->type == ex_error)
return e2;
if (e->type == ex_value && e->e.value.type == ev_pointer
if (e->type == ex_value && e->e.value->type == ev_pointer
&& is_short_val (e2)) {
e->e.value.v.pointer.val += expr_short (e2);
e->e.value.v.pointer.type = t;
e->e.value = new_pointer_val (e->e.value->v.pointer.val + expr_short (e2), t, e->e.value->v.pointer.def);
} else {
if (!is_short_val (e2) || expr_short (e2)) {
if (e->type == ex_expr && e->e.expr.op == '&') {
@ -2475,9 +2452,9 @@ is_indirect (expr_t *e)
if (!(e->type == ex_uexpr && e->e.expr.op == '.'))
return 0;
e = e->e.expr.e1;
if (e->type != ex_value || e->e.value.type != ev_pointer
|| !(POINTER_VAL (e->e.value.v.pointer) >= 0
&& POINTER_VAL (e->e.value.v.pointer) < 65536)) {
if (e->type != ex_value || e->e.value->type != ev_pointer
|| !(POINTER_VAL (e->e.value->v.pointer) >= 0
&& POINTER_VAL (e->e.value->v.pointer) < 65536)) {
return 1;
}
return 0;
@ -2615,9 +2592,9 @@ assign_expr (expr_t *e1, expr_t *e2)
op = PAS;
} else {
e = e1->e.expr.e1;
if ((e->type != ex_value || e->e.value.type != ev_pointer)
|| !(POINTER_VAL (e->e.value.v.pointer) > 0
&& POINTER_VAL (e->e.value.v.pointer) < 65536)) {
if ((e->type != ex_value || e->e.value->type != ev_pointer)
|| !(POINTER_VAL (e->e.value->v.pointer) > 0
&& POINTER_VAL (e->e.value->v.pointer) < 65536)) {
e1 = e;
op = PAS;
}
@ -2631,9 +2608,9 @@ assign_expr (expr_t *e1, expr_t *e2)
}
if (e2->type == ex_uexpr) {
e = e2->e.expr.e1;
if ((e->type != ex_value || e->e.value.type != ev_pointer)
|| !(POINTER_VAL (e->e.value.v.pointer) > 0
&& POINTER_VAL (e->e.value.v.pointer) < 65536)) {
if ((e->type != ex_value || e->e.value->type != ev_pointer)
|| !(POINTER_VAL (e->e.value->v.pointer) > 0
&& POINTER_VAL (e->e.value->v.pointer) < 65536)) {
if (e->type == ex_expr && e->e.expr.op == '&'
&& e->e.expr.type->type == ev_pointer
&& !is_constant (e)) {

View file

@ -212,7 +212,7 @@ qfo_encode_struct (type_t *type)
if (i == num_fields)
internal_error (0, "whoa, what happened?");
if (sym->sy_type == sy_const)
offset = sym->s.value.v.integer_val;
offset = sym->s.value->v.integer_val;
else
offset = sym->s.offset;
ENC_DEF (strct->fields[i].type, field_types[i]);

View file

@ -508,7 +508,7 @@ vector_call (sblock_t *sblock, expr_t *earg, expr_t *param, int ind,
for (i = 0; i < 3; i++) {
n = new_name_expr (names[i]);
v = new_float_expr (earg->e.value.v.vector_val[i]);
v = new_float_expr (earg->e.value->v.vector_val[i]);
a = assign_expr (binary_expr ('.', param, n), v);
param = new_param_expr (get_type (earg), ind);
a->line = earg->line;
@ -544,7 +544,7 @@ expr_call (sblock_t *sblock, expr_t *call, operand_t **op)
pref = "R";
sblock = statement_subexpr (sblock, param, &arguments[ind]);
if (options.code.vector_calls && a->type == ex_value
&& a->e.value.type == ev_vector)
&& a->e.value->type == ev_vector)
sblock = vector_call (sblock, a, param, ind, &arguments[ind]);
else
sblock = statement_subexpr (sblock, a, &arguments[ind]);
@ -558,7 +558,7 @@ expr_call (sblock_t *sblock, expr_t *call, operand_t **op)
sblock = statement_slist (sblock, mov);
} else {
if (options.code.vector_calls && a->type == ex_value
&& a->e.value.type == ev_vector) {
&& a->e.value->type == ev_vector) {
sblock = vector_call (sblock, a, param, ind, 0);
} else {
operand_t *p = 0;
@ -659,10 +659,10 @@ expr_deref (sblock_t *sblock, expr_t *deref, operand_t **op)
s->opc = *op;
sblock_add_statement (sblock, s);
}
} else if (e->type == ex_value && e->e.value.type == ev_pointer) {
} else if (e->type == ex_value && e->e.value->type == ev_pointer) {
*op = new_operand (op_pointer);
(*op)->type = low_level_type (e->e.value.v.pointer.type);
(*op)->o.pointer = &e->e.value.v.pointer;
(*op)->type = low_level_type (e->e.value->v.pointer.type);
(*op)->o.pointer = &e->e.value->v.pointer;
} else {
statement_t *s;
operand_t *ptr = 0;
@ -830,8 +830,8 @@ static sblock_t *
expr_value (sblock_t *sblock, expr_t *e, operand_t **op)
{
*op = new_operand (op_value);
(*op)->type = e->e.value.type;
(*op)->o.value = &e->e.value;
(*op)->type = e->e.value->type;
(*op)->o.value = e->e.value;
return sblock;
}

View file

@ -59,6 +59,7 @@
#include "struct.h"
#include "symtab.h"
#include "type.h"
#include "value.h"
static symbol_t *
find_tag (ty_meta_e meta, symbol_t *tag, type_t *type)
@ -172,7 +173,7 @@ add_enum (symbol_t *enm, symbol_t *name, expr_t *val)
enum_tab = enum_type->t.symtab;
value = 0;
if (enum_tab->symbols)
value = ((symbol_t *)(enum_tab->symtail))->s.value.v.integer_val + 1;
value = ((symbol_t *)(enum_tab->symtail))->s.value->v.integer_val + 1;
if (val) {
if (!is_constant (val))
error (val, "non-constant initializer");
@ -181,8 +182,7 @@ add_enum (symbol_t *enm, symbol_t *name, expr_t *val)
else
value = expr_integer (val);
}
name->s.value.type = ev_integer;
name->s.value.v.integer_val = value;
name->s.value = new_integer_val (value);
symtab_addsymbol (enum_tab, name);
sym = new_symbol_type (name->name, name->type);
sym->sy_type = sy_const;
@ -204,12 +204,12 @@ enum_as_bool (type_t *enm, expr_t **zero, expr_t **one)
for (sym = symtab->symbols; sym; sym = sym->next) {
if (sym->sy_type != sy_const)
continue;
val = sym->s.value.v.integer_val;
val = sym->s.value->v.integer_val;
if (!val) {
zero_sym = sym;
} else {
if (one_sym) {
v = one_sym->s.value.v.integer_val;
v = one_sym->s.value->v.integer_val;
if (val * val > v * v)
continue;
}

View file

@ -67,8 +67,8 @@ static ex_value_t *
get_value (expr_t *e)
{
if (e->type == ex_symbol)
return &e->e.symbol->s.value;
return &e->e.value;
return e->e.symbol->s.value;
return e->e.value;
}
static uintptr_t

View file

@ -71,6 +71,162 @@ typedef struct {
} i;
} immediate_t;
static hashtab_t *value_table;
static ex_value_t *free_values;
static uintptr_t
value_get_hash (const void *_val, void *unused)
{
const ex_value_t *val = (const ex_value_t *) _val;
return Hash_Buffer (&val->v, sizeof (val->v)) + val->type;
}
static int
value_compare (const void *_val1, const void *_val2, void *unused)
{
const ex_value_t *val1 = (const ex_value_t *) _val1;
const ex_value_t *val2 = (const ex_value_t *) _val2;
if (val1->type != val2->type)
return 0;
return memcmp (&val1->v, &val2->v, sizeof (val1->v)) == 0;
}
static ex_value_t *
new_value (void)
{
ex_value_t *value;
ALLOC (256, ex_value_t, values, value);
return value;
}
static ex_value_t *
find_value (const ex_value_t *val)
{
ex_value_t *value;
value = Hash_FindElement (value_table, val);
if (value)
return value;
value = new_value ();
*value = *val;
return value;
}
ex_value_t *
new_string_val (const char *string_val)
{
ex_value_t val;
val.type = ev_string;
if (string_val)
val.v.string_val = save_string (string_val);
return find_value (&val);
}
ex_value_t *
new_float_val (float float_val)
{
ex_value_t val;
val.type = ev_float;
val.v.float_val = float_val;
return find_value (&val);
}
ex_value_t *
new_vector_val (const float *vector_val)
{
ex_value_t val;
val.type = ev_vector;
VectorCopy (vector_val, val.v.vector_val);
return find_value (&val);
}
ex_value_t *
new_entity_val (int entity_val)
{
ex_value_t val;
val.type = ev_entity;
val.v.entity_val = entity_val;
return find_value (&val);
}
ex_value_t *
new_field_val (int field_val, type_t *type, def_t *def)
{
ex_value_t val;
val.type = ev_field;
val.v.pointer.val = field_val;
val.v.pointer.type = type;
val.v.pointer.def = def;
return find_value (&val);
}
ex_value_t *
new_func_val (int func_val)
{
ex_value_t val;
val.type = ev_func;
val.v.func_val = func_val;
return find_value (&val);
}
ex_value_t *
new_pointer_val (int pointer_val, type_t *type, def_t *def)
{
ex_value_t val;
val.type = ev_pointer;
val.v.pointer.val = pointer_val;
val.v.pointer.type = type;
val.v.pointer.def = def;
return find_value (&val);
}
ex_value_t *
new_quaternion_val (const float *quaternion_val)
{
ex_value_t val;
val.type = ev_quat;
QuatCopy (quaternion_val, val.v.quaternion_val);
return find_value (&val);
}
ex_value_t *
new_integer_val (int integer_val)
{
ex_value_t val;
val.type = ev_integer;
val.v.integer_val = integer_val;
return find_value (&val);
}
ex_value_t *
new_uinteger_val (int uinteger_val)
{
ex_value_t val;
val.type = ev_uinteger;
val.v.uinteger_val = uinteger_val;
return find_value (&val);
}
ex_value_t *
new_short_val (short short_val)
{
ex_value_t val;
val.type = ev_short;
val.v.short_val = short_val;
return find_value (&val);
}
ex_value_t *
new_nil_val (type_t *type)
{
ex_value_t val;
val.type = low_level_type (type);
memset (&val.v, 0, sizeof (val.v));
if (val.type == ev_pointer|| val.type == ev_field )
val.v.pointer.type = type->t.fldptr.type;
return find_value (&val);
}
static hashtab_t *string_imm_defs;
static hashtab_t *float_imm_defs;
static hashtab_t *vector_imm_defs;
@ -370,7 +526,8 @@ clear_immediates (void)
{
immediate_t *imm;
if (string_imm_defs) {
if (value_table) {
Hash_FlushTable (value_table);
Hash_FlushTable (string_imm_defs);
Hash_FlushTable (float_imm_defs);
Hash_FlushTable (vector_imm_defs);
@ -381,6 +538,9 @@ clear_immediates (void)
Hash_FlushTable (quaternion_imm_defs);
Hash_FlushTable (integer_imm_defs);
} else {
value_table = Hash_NewTable (16381, 0, 0, 0);
Hash_SetHashCompare (value_table, value_get_hash, value_compare);
string_imm_defs = Hash_NewTable (16381, 0, 0, &string_imm_defs);
Hash_SetHashCompare (string_imm_defs, imm_get_hash, imm_compare);