Support temp operands in dags.

This commit is contained in:
Bill Currie 2012-07-16 17:37:13 +09:00
parent 9bc65ffedb
commit 7b2e426545
3 changed files with 35 additions and 23 deletions

View file

@ -41,6 +41,11 @@ typedef enum {
op_alias,
} op_type_e;
typedef struct {
struct def_s *def;
struct daglabel_s *daglabel;
} tempop_t;
typedef struct operand_s {
struct operand_s *next;
op_type_e op_type;
@ -51,7 +56,7 @@ typedef struct operand_s {
struct ex_value_s *value;
struct ex_label_s *label;
struct ex_pointer_s *pointer;
struct def_s *def;
tempop_t tempop;
struct operand_s *alias;
} o;
} operand_t;

View file

@ -96,20 +96,24 @@ operand_label (operand_t *op)
o = op;
while (o->op_type == op_alias)
o = o->o.alias;
if (o->op_type != op_symbol) {
if (o->op_type != op_value && o->op_type != op_pointer)
debug (0, "unexpected operand type");
goto make_new_label;
}
if (o->op_type == op_temp) {
label = new_label ();
label->op = op;
o->o.tempop.daglabel = label;
} else if (o->op_type == op_symbol) {
sym = o->o.symbol;
if (sym->daglabel)
return sym->daglabel;
make_new_label:
label = new_label ();
label->op = op;
if (sym)
sym->daglabel = label;
} else {
if (o->op_type != op_value && o->op_type != op_pointer)
debug (0, "unexpected operand type: %d", o->op_type);
label = new_label ();
label->op = op;
}
return label;
}
@ -139,13 +143,16 @@ node (operand_t *op)
o = op;
while (o->op_type == op_alias)
o = o->o.alias;
if (o->op_type != op_symbol)
return 0;
if (o->op_type == op_symbol) {
sym = o->o.symbol;
if (sym->sy_type == sy_const)
return 0;
if (sym->daglabel)
return sym->daglabel->dagnode;
} else if (o->op_type == op_temp) {
if (o->o.tempop.daglabel)
return o->o.tempop.daglabel->dagnode;
}
return 0;
}

View file

@ -107,9 +107,9 @@ get_operand_def (expr_t *expr, operand_t *op)
zero_def.type = &type_short;
return &zero_def; //FIXME
case op_temp:
if (!op->o.def)
op->o.def = temp_def (op->type, op->size);
return op->o.def;
if (!op->o.tempop.def)
op->o.tempop.def = temp_def (op->type, op->size);
return op->o.tempop.def;
case op_pointer:
def = op->o.pointer->def;
if (op->o.pointer->val || op->type != def->type->type) {