📄 ast.cs
字号:
Scope scope = m_symbol.MemberScope;
int iLastValue = -1;
Scope prev = s.SetCurrentContext(scope);
for(int i = 0; i < this.Fields.Length; i++)
{
FieldDecl f = this.Fields[i];
Exp e = f.InitialExp;
//Debug.Assert(e != null);
// Evaluate e to a literal...
//Exp.TrySimplify(ref e);
int iValue;
if (e != null)
{
IntExp e2 = e as IntExp;
Debug.Assert(e2 != null, "Can only assign to an integer literal"); //@todo - legit error
iValue = e2.Value;
}
else
{
if (i == 0)
iValue = 0;
else
iValue = iLastValue + 1;
}
// Need to create an object of type 'ThisEnum' with integer value iValue;
//Type tEnum = this.Symbol.CLRType;
// errors
//System.ComponentModel.TypeConverter c = new System.ComponentModel.TypeConverter();
//object o2 = c.ConvertTo(iValue, tEnum);
// errors
// object oValue = System.Enum.ToObject(tEnum, iValue);
iLastValue = iValue;
f.ResolveMemberAsLiteral(this.m_symbol, s, iValue);
LiteralFieldExpEntry l = (LiteralFieldExpEntry) f.Symbol;
l.SetInfo(provider);
}
//s.PopScope(scope);
s.RestoreContext(prev);
}
public override void ResolveBodies(ISemanticResolver s)
{
// @todo - set LiteralFieldExpEntry's Data here
}
#endregion // Resolution
// Add this type to the topological list of types
bool m_fReported = false;
public override void ReportClass(ArrayList alClasses)
{
if (m_fReported)
return;
m_fReported = true;
// Emit forces us to CreateType() on outer classes
// before inner classes.
TypeEntry tOuter = this.Symbol.GetContainingType();
if (tOuter != null)
{
ClassDecl c = tOuter.Node;
Debug.Assert(c != null); // containing type should not be imported
c.ReportClass(alClasses);
}
alClasses.Add(this);
}
// Get the CLR type that this node represents. Useful for codegen.
public override System.Type CLRType
{
get {
return this.m_symbol.CLRType;
}
}
public override void GenerateType(Blue.CodeGen.EmitCodeGen gen)
{
gen.GenerateEnum(this);
}
}
#endregion // enums
#region Class type declaration
//-----------------------------------------------------------------------------
// Declare a class
// A class decl represents Classes, Interfaces, and Structs (value-types)
//-----------------------------------------------------------------------------
public class ClassDecl : TypeDeclBase
{
#region Construction
// For interface types
public ClassDecl(
Identifier idName,
TypeSig [] arSuper, // super class & implemented interfaces
MethodDecl [] alMethods,
PropertyDecl[] alProperties,
Modifiers mods
)
{
Debug.Assert(idName != null);
Debug.Assert(alMethods != null);
m_strName = idName.Text;
m_arSuper = (arSuper == null) ? new TypeSig[0] : arSuper;
m_alMethods = alMethods;
m_alProperties = alProperties;
m_alNestedTypes = m_sEmptyTypeList;
// @todo - this is wrong
m_filerange = idName.Location;
//m_mods.FlagSetter = mods.Flags | Modifiers.EFlags.Abstract;
m_mods = mods;
m_mods.SetAbstract();
m_genre = TypeEntry.Genre.cInterface;
}
// For non-interface types
public ClassDecl(
Identifier idName,
TypeSig [] arSuper, // super class & implemented interfaces
MethodDecl [] alMethods,
PropertyDecl[] alProperties,
FieldDecl[] alFields,
EventDecl [] alEvents,
TypeDeclBase[] alNestedTypes,
Modifiers mods,
bool fIsClass // true for class, false for struct
)
{
Debug.Assert(idName != null);
Debug.Assert(alMethods != null);
Debug.Assert(alFields != null);
Debug.Assert(alProperties != null);
Debug.Assert(alEvents != null);
m_strName = idName.Text;
m_arSuper = (arSuper == null) ? new TypeSig[0] : arSuper;
m_alNestedTypes = (alNestedTypes == null) ? m_sEmptyTypeList : alNestedTypes;
m_alMethods = alMethods;
m_alProperties = alProperties;
m_alFields = alFields;
m_alEvents = alEvents;
// @todo - this is wrong
m_filerange = idName.Location;
if (!fIsClass) // structs are implicitly sealed.
mods.SetSealed();
m_mods = mods;
m_genre = fIsClass ? TypeEntry.Genre.cClass : TypeEntry.Genre.cStruct;
}
#endregion
#region Properties & Data
static TypeDeclBase [] m_sEmptyTypeList = new TypeDeclBase[0];
readonly TypeEntry.Genre m_genre;
public bool IsInterface
{
get { return m_genre == TypeEntry.Genre.cInterface; }
}
public bool IsClass
{
get { return m_genre == TypeEntry.Genre.cClass; }
}
public bool IsStruct
{
get { return m_genre == TypeEntry.Genre.cStruct; }
}
MethodDecl m_nodeStaticInit;
public MethodDecl StaticInitMethod
{
get {return m_nodeStaticInit; }
}
MethodDecl m_nodeInstanceInit;
public MethodDecl InstanceInitMethod
{
get {return m_nodeInstanceInit; }
}
protected Modifiers m_mods;
public Modifiers Mods
{
get { return m_mods; }
}
TypeSig [] m_arSuper; // super class & implemented interfaces
public MethodDecl[] Methods
{
get { return m_alMethods; }
}
public string Name
{
get { return m_strName; }
}
public PropertyDecl[] Properties
{
get { return m_alProperties; }
}
public FieldDecl[] Fields
{
get { return m_alFields; }
}
public EventDecl[] Events
{
get { return m_alEvents; }
}
protected MethodDecl[] m_alMethods;
protected FieldDecl[] m_alFields;
protected PropertyDecl[] m_alProperties;
protected EventDecl[] m_alEvents;
protected TypeDeclBase[] m_alNestedTypes;
public TypeDeclBase[] NestedTypes
{
get { return m_alNestedTypes; }
}
readonly string m_strName;
protected TypeEntry m_symbol;
public TypeEntry Symbol
{
get { return m_symbol; }
}
#endregion
#region Checks
// Debugging check
public override void DebugCheck(ISemanticResolver s)
{
Debug.Assert(m_strName != null);
//Debug.Assert(IsClass ^ IsInterface); // mutually exclusive options
// Verify symbol
Debug.Assert(m_symbol != null);
Debug.Assert(m_symbol.Node == this);
Debug.Assert(m_symbol.MemberScope != null); // this may be ok
Debug.Assert(m_symbol.Name == m_strName);
Debug.Assert(m_symbol.CLRType != null);
Debug.Assert(m_arSuper != null);
// The only class without a super class is system.object.
// But all user-defined classes must have some super class
if (!IsInterface)
{
Debug.Assert(m_symbol.Super!= null);
if (m_symbol.Super != null)
{
// If we inherit from a user-defined class, then
// check the AST
/*
if (IdSuper != null)
{
Debug.Assert(IdSuper.Text == m_symbol.Super.Name);
}
*/
}
// Fields
foreach(FieldDecl f in m_alFields)
{
f.DebugCheck(s);
}
}
else
{
// For interfaces, we don't extend a class
Debug.Assert(m_symbol.Super == null);
}
// Methods
foreach(MethodDecl m in m_alMethods)
{
m.DebugCheck(s);
}
// Properties
foreach(PropertyDecl p in m_alProperties)
p.DebugCheck(s);
// Nested types
foreach(TypeDeclBase t in m_alNestedTypes)
t.DebugCheck(s);
}
// Dump as XML
public override void Dump(XmlWriter o)
{
o.WriteStartElement("ClassDecl");
o.WriteAttributeString("name", m_strName);
if (m_symbol != null)
o.WriteAttributeString("symbol", m_symbol.ToString());
if (IsInterface)
o.WriteAttributeString("IsInterface", "yes");
if (IsClass)
o.WriteAttributeString("IsClass", "yes");
if (IsStruct)
o.WriteAttributeString("IsStruct", "yes");
foreach(TypeSig t in m_arSuper)
{
o.WriteAttributeString("super", t.ToString());
}
if (!IsInterface)
{
foreach(FieldDecl f in m_alFields)
{
f.Dump(o);
}
}
foreach(MethodDecl m in m_alMethods)
{
m.Dump(o);
}
foreach(PropertyDecl p in m_alProperties)
p.Dump(o);
foreach(TypeDeclBase t in m_alNestedTypes)
t.Dump(o);
o.WriteEndElement();
}
#endregion
#region Resolution
#region Topological Sort
// Recursive One-time build a topological sort of classes.
bool m_fReported = false;
public override void ReportClass(ArrayList alClasses)
{
// keep flag to avoid cycles
if (m_fReported)
return;
m_fReported = true;
// Add all of our dependencies before us
if (this.IsClass && (this.Symbol.Super.Node != null))
Symbol.Super.Node.ReportClass(alClasses);
foreach(TypeEntry t in this.Symbol.BaseInterfaces)
{
if (t.Node != null)
{
t.Node.ReportClass(alClasses);
}
}
// Emit forces us to CreateType() on outer classes
// before inner classes.
TypeEntry tOuter = this.Symbol.GetContainingType();
if (tOuter != null)
{
ClassDecl c = tOuter.Node;
Debug.Assert(c != null); // containing type should not be imported
c.ReportClass(alClasses);
}
#if true
if (!IsInterface)
{
// @error - what if the value type is a nested class?
// Any field that's a value type has to be done before us.
foreach(FieldDecl f in this.Fields)
{
if (f.Symbol.FieldType.IsImported)
continue; // imported types don't have to be added.
#if true
// Any field that's nested in the current type doesn't need to be added
if (f.Symbol.FieldType.CLRType.DeclaringType == this.Symbol.CLRType)
continue;
#endif
Type t = f.Symbol.CLRType;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -