CiType ICiTypeVisitor.Visit(CiUnknownType type)
{
CiSymbol symbol = this.Symbols.Lookup(type.Name);
if (symbol is CiType)
{
return((CiType)symbol);
}
if (symbol is CiClass)
{
return new CiClassPtrType {
Name = type.Name, Class = (CiClass)symbol
}
}
;
throw new ResolveException("{0} is not a type", type.Name);
}
CiType ICiTypeVisitor.Visit(CiStringStorageType type)
{
type.Length = (int)ResolveConstExpr(type.LengthExpr, CiIntType.Value);
return(type);
}
CiClass ResolveClass(CiClass klass)
{
if (klass is CiUnknownClass)
{
string name = klass.Name;
klass = this.Symbols.Lookup(name) as CiClass;
if (klass == null)
{
throw new ResolveException("{0} is not a class", name);
}
}
return(klass);
}
CiType ICiTypeVisitor.Visit(CiClassType type)
{
type.Class = ResolveClass(type.Class);
return(type);
}
CiType ICiTypeVisitor.Visit(CiArrayType type)
{
type.ElementType = Resolve(type.ElementType);
return(type);
}
CiType ICiTypeVisitor.Visit(CiArrayStorageType type)
{
type.ElementType = Resolve(type.ElementType);
if (type.LengthExpr != null)
{
type.Length = (int)ResolveConstExpr(type.LengthExpr, CiIntType.Value);
type.LengthExpr = null;
}
return(type);
}
CiType Resolve(CiType type)
{
return(type.Accept(this));
}
CiCondExpr Coerce(CiCondExpr expr, CiType expected)
{
return(new CiCondExpr {
Cond = expr.Cond,
ResultType = expected,
OnTrue = Coerce(expr.OnTrue, expected),
OnFalse = Coerce(expr.OnFalse, expected)
});
}