Fix record coercion tolerance of optional fields.

There were cases where coercing a record value with an uninitialized
field could cause a null pointer dereference even though the field
can validly be unset since it has &optional.
This commit is contained in:
Jon Siwek 2013-10-23 11:37:23 -05:00
parent 34aece4ddd
commit 7e95755ce5
4 changed files with 60 additions and 4 deletions

View file

@ -2720,16 +2720,22 @@ RecordVal* RecordVal::CoerceTo(const RecordType* t, Val* aggr, bool allow_orphan
break;
}
Val* v = Lookup(i);
if ( ! v )
// Check for allowable optional fields is outside the loop, below.
continue;
if ( ar_t->FieldType(t_i)->Tag() == TYPE_RECORD
&& ! same_type(ar_t->FieldType(t_i), Lookup(i)->Type()) )
&& ! same_type(ar_t->FieldType(t_i), v->Type()) )
{
Expr* rhs = new ConstExpr(Lookup(i)->Ref());
Expr* rhs = new ConstExpr(v->Ref());
Expr* e = new RecordCoerceExpr(rhs, ar_t->FieldType(t_i)->AsRecordType());
ar->Assign(t_i, e->Eval(0));
continue;
}
ar->Assign(t_i, Lookup(i)->Ref());
ar->Assign(t_i, v->Ref());
}
for ( i = 0; i < ar_t->NumFields(); ++i )