void GenerateBinding(GenerateTypeInfo typeInfo, Analyze.Binding binding) { if (binding.Expression != null) { Analyze.Expressions.Literal literal; // literal -> static field if ((literal = binding.Expression as Analyze.Expressions.Literal) != null) { GenerateLiteralBinding(typeInfo, binding, literal); } } }
void GenerateTypeCtors(GenerateTypeInfo typeInfo) { var baseType = typeInfo.BaseType; var tb = typeInfo.TypeBuilder; var ctor = typeInfo.CTor; { var il = ctor.GetILGenerator(); var mn = Module.SyntaxNode as Parse.Syntax.Module; if (mn != null) { MarkSequencePoint(il, mn.Name, mn.Name); } il.Emit(OpCodes.Nop); il.Emit(OpCodes.Ldarg_0); var mc = baseType.GetConstructor(BindingFlags.NonPublic | BindingFlags.Instance, null, Type.EmptyTypes, null); il.Emit(OpCodes.Call, mc); // leave this on the stack foreach (var fi in typeInfo.FieldsToInit) { } il.Emit(OpCodes.Ret); } var cctor = typeInfo.CCTor; { var il = cctor.GetILGenerator(); var mn = Module.SyntaxNode as Parse.Syntax.Module; if (mn != null) { MarkSequencePoint(il, mn.Children.First(), mn.Children.First()); } il.Emit(OpCodes.Nop); foreach (var fi in typeInfo.StaticFieldsToInit) { MarkSequencePoint(il, fi.Node, fi.Node); fi.GenLoad(il); il.Emit(OpCodes.Stsfld, fi.Field); } il.Emit(OpCodes.Ret); } }
void GenerateLiteralBinding(GenerateTypeInfo typeInfo, Analyze.Binding binding, Analyze.Expressions.Literal literal) { if (literal.ResolvedType == null) { Unit.AddError(new GeneratorError { Message = string.Format(ErrorMessages.E_0017_Generator_UnresolvedType, ApteridError.Truncate(literal.SyntaxNode.Text)), ErrorNode = literal.SyntaxNode }); return; } var atts = FieldAttributes.Static | FieldAttributes.InitOnly; atts |= binding.IsPublic ? FieldAttributes.Public : FieldAttributes.Private; var field = typeInfo.TypeBuilder.DefineField(binding.Name.Name, literal.ResolvedType.CLRType, atts); typeInfo.Bindings.Add(literal, field); if (literal.Value == null) { if (field.FieldType.IsValueType) { field.SetConstant(Activator.CreateInstance(field.FieldType)); } else { field.SetConstant(null); } } else { typeInfo.StaticFieldsToInit.Add(new FieldInitInfo { Node = binding.SyntaxNode, Field = field, GenLoad = il => GenerateLoadLiteral(il, literal, field.FieldType) }); } }
void GenerateType(GenerateTypeInfo info, Analyze.Type type) { }
void GenerateTypeCtors(GenerateTypeInfo typeInfo) { var baseType = typeInfo.BaseType; var tb = typeInfo.TypeBuilder; var ctor = typeInfo.CTor; { var il = ctor.GetILGenerator(); var mn = Module.SyntaxNode as Parse.Syntax.Module; if (mn != null) MarkSequencePoint(il, mn.Name, mn.Name); il.Emit(OpCodes.Nop); il.Emit(OpCodes.Ldarg_0); var mc = baseType.GetConstructor(BindingFlags.NonPublic | BindingFlags.Instance, null, Type.EmptyTypes, null); il.Emit(OpCodes.Call, mc); // leave this on the stack foreach (var fi in typeInfo.FieldsToInit) { } il.Emit(OpCodes.Ret); } var cctor = typeInfo.CCTor; { var il = cctor.GetILGenerator(); var mn = Module.SyntaxNode as Parse.Syntax.Module; if (mn != null) MarkSequencePoint(il, mn.Children.First(), mn.Children.First()); il.Emit(OpCodes.Nop); foreach (var fi in typeInfo.StaticFieldsToInit) { MarkSequencePoint(il, fi.Node, fi.Node); fi.GenLoad(il); il.Emit(OpCodes.Stsfld, fi.Field); } il.Emit(OpCodes.Ret); } }
void GenerateLiteralBinding(GenerateTypeInfo typeInfo, Analyze.Binding binding, Analyze.Expressions.Literal literal) { if (literal.ResolvedType == null) { Unit.AddError(new GeneratorError { Message = string.Format(ErrorMessages.E_0017_Generator_UnresolvedType, ApteridError.Truncate(literal.SyntaxNode.Text)), ErrorNode = literal.SyntaxNode }); return; } var atts = FieldAttributes.Static | FieldAttributes.InitOnly; atts |= binding.IsPublic ? FieldAttributes.Public : FieldAttributes.Private; var field = typeInfo.TypeBuilder.DefineField(binding.Name.Name, literal.ResolvedType.CLRType, atts); typeInfo.Bindings.Add(literal, field); if (literal.Value == null) { if (field.FieldType.IsValueType) field.SetConstant(Activator.CreateInstance(field.FieldType)); else field.SetConstant(null); } else { typeInfo.StaticFieldsToInit.Add(new FieldInitInfo { Node = binding.SyntaxNode, Field = field, GenLoad = il => GenerateLoadLiteral(il, literal, field.FieldType) }); } }