ir_value_life_merge_into, to merge the liferange of one value into the range of another, testing in test_ir

This commit is contained in:
Wolfgang (Blub) Bumiller 2012-06-25 14:51:31 +02:00
parent 01af44f3c8
commit db7b9a4f96
3 changed files with 114 additions and 1 deletions

79
ir.c
View file

@ -584,6 +584,83 @@ bool ir_value_life_merge(ir_value *self, size_t s)
return ir_value_life_insert(self, i, new_entry);
}
bool ir_value_life_merge_into(ir_value *self, const ir_value *other)
{
size_t i, myi;
if (!other->life_count)
return true;
if (!self->life_count) {
for (i = 0; i < other->life_count; ++i) {
if (!ir_value_life_add(self, other->life[i]))
return false;
}
return true;
}
myi = 0;
for (i = 0; i < other->life_count; ++i)
{
const ir_life_entry_t *life = &other->life[i];
while (true)
{
ir_life_entry_t *entry = &self->life[myi];
if (life->end+1 < entry->start)
{
/* adding an interval before entry */
if (!ir_value_life_insert(self, myi, *life))
return false;
++myi;
break;
}
if (life->start < entry->start &&
life->end >= entry->start)
{
/* starts earlier and overlaps */
entry->start = life->start;
}
if (life->end > entry->end &&
life->start-1 <= entry->end)
{
/* ends later and overlaps */
entry->end = life->end;
}
/* see if our change combines it with the next ranges */
while (myi+1 < self->life_count &&
entry->end+1 >= self->life[1+myi].start)
{
/* overlaps with (myi+1) */
if (entry->end < self->life[1+myi].end)
entry->end = self->life[1+myi].end;
if (!ir_value_life_remove(self, myi+1))
return false;
entry = &self->life[myi];
}
/* see if we're after the entry */
if (life->start > entry->end)
{
++myi;
/* append if we're at the end */
if (myi >= self->life_count) {
if (!ir_value_life_add(self, *life))
return false;
break;
}
/* otherweise check the next range */
continue;
}
break;
}
}
return true;
}
bool ir_values_overlap(ir_value *a, ir_value *b)
{
/* For any life entry in A see if it overlaps with
@ -1425,7 +1502,7 @@ bool ir_function_calculate_liferanges(ir_function *self)
*/
bool ir_function_allocate_locals(ir_function *self)
{
return false;
return true;
}
/* Get information about which operand

1
ir.h
View file

@ -89,6 +89,7 @@ MEM_VECTOR_PROTO(ir_value, ir_life_entry_t, life);
/* merge an instruction into the life-range */
/* returns false if the lifepoint was already known */
bool ir_value_life_merge(ir_value*, size_t);
bool ir_value_life_merge_into(ir_value*, const ir_value*);
/* check if a value lives at a specific point */
bool ir_value_lives(ir_value*, size_t);
/* check if the life-range of 2 values overlaps */

View file

@ -9,6 +9,8 @@
int main()
{
int lf;
ir_builder *b = ir_builder_new("test");
ir_value *va = ir_builder_create_global(b, "a", TYPE_FLOAT);
ir_value *v3 = ir_builder_create_global(b, "const_f_3", TYPE_FLOAT);
@ -16,6 +18,10 @@ int main()
ir_value *vc = ir_builder_create_global(b, "c", TYPE_FLOAT);
ir_value *vd = ir_builder_create_global(b, "d", TYPE_FLOAT);
ir_value *life1 = ir_builder_create_global(b, "life1", TYPE_FLOAT);
ir_value *life2 = ir_builder_create_global(b, "life2", TYPE_FLOAT);
ir_value *life3 = ir_builder_create_global(b, "life3", TYPE_FLOAT);
ir_function *fmain = NULL;
ir_value *la = NULL;
ir_block *bmain = NULL;
@ -110,6 +116,35 @@ int main()
ir_value_dump_life(vig, printf);
ir_value_dump_life(la, printf);
ir_value_life_merge_into(retval, vig);
ir_value_dump_life(retval, printf);
ir_value_life_merge(x1, 12);
ir_value_life_merge(x1, 13);
ir_value_life_merge(x1, 14);
ir_value_life_merge_into(retval, x1);
ir_value_dump_life(retval, printf);
ir_value_life_merge(x1, 20);
ir_value_life_merge(x1, 21);
ir_value_life_merge(x1, 22);
ir_value_life_merge_into(retval, x1);
ir_value_dump_life(retval, printf);
ir_value_life_merge(x2, 1);
ir_value_life_merge(x2, 2);
ir_value_life_merge_into(retval, x2);
ir_value_dump_life(retval, printf);
for (lf = 4; lf <= 15; ++lf)
ir_value_life_merge(life1, lf);
ir_value_life_merge_into(retval, life1);
ir_value_dump_life(retval, printf);
for (lf = 17; lf <= 18; ++lf)
ir_value_life_merge(life2, lf);
ir_value_life_merge_into(retval, life2);
ir_value_dump_life(retval, printf);
for (lf = 2; lf <= 29; ++lf)
ir_value_life_merge(life3, lf);
ir_value_life_merge_into(retval, life3);
ir_value_dump_life(retval, printf);
ir_builder_delete(b);
return 0;
}