void ReadProperties() { if (!m_tHeap.HasTable(PropertyTable.RId)) { m_properties = new PropertyDefinition [0]; return; } PropertyTable propsTable = m_tableReader.GetPropertyTable(); PropertyMapTable pmapTable = m_tableReader.GetPropertyMapTable(); m_properties = new PropertyDefinition [propsTable.Rows.Count]; for (int i = 0; i < pmapTable.Rows.Count; i++) { PropertyMapRow pmapRow = pmapTable [i]; if (pmapRow.Parent == 0) { continue; } TypeDefinition owner = GetTypeDefAt(pmapRow.Parent); GenericContext context = new GenericContext(owner); int start = (int)pmapRow.PropertyList, last = propsTable.Rows.Count + 1, end; if (i < pmapTable.Rows.Count - 1) { end = (int)pmapTable [i + 1].PropertyList; } else { end = last; } if (end > last) { end = last; } for (int j = start; j < end; j++) { PropertyRow prow = propsTable [j - 1]; PropertySig psig = m_sigReader.GetPropSig(prow.Type); PropertyDefinition pdef = new PropertyDefinition( m_root.Streams.StringsHeap [prow.Name], GetTypeRefFromSig(psig.Type, context), prow.Flags); pdef.MetadataToken = MetadataToken.FromMetadataRow(TokenType.Property, j - 1); pdef.PropertyType = GetModifierType(psig.CustomMods, pdef.PropertyType); if (!IsDeleted(pdef)) { owner.Properties.Add(pdef); } m_properties [j - 1] = pdef; } } }
void PatchMethods() { MethodTable methodTable = (MethodTable)stripped_tables [MethodTable.RId]; if (methodTable == null) { return; } RVA method_rva = RVA.Zero; for (int i = 0; i < methodTable.Rows.Count; i++) { MethodRow methodRow = methodTable[i]; MetadataToken methodToken = MetadataToken.FromMetadataRow(TokenType.Method, i); MethodDefinition method = (MethodDefinition)assembly.MainModule.LookupByToken(methodToken); method_rva = method_rva != RVA.Zero ? method_rva : reflection_writer.CodeWriter.WriteMethodBody(method); methodRow.RVA = method_rva; } }
void ReadMethods() { if (!m_tHeap.HasTable(MethodTable.RId)) { m_meths = new MethodDefinition [0]; return; } MethodTable mTable = m_tableReader.GetMethodTable(); m_meths = new MethodDefinition [mTable.Rows.Count]; for (int i = 0; i < mTable.Rows.Count; i++) { MethodRow mRow = mTable [i]; MethodDefinition meth = new MethodDefinition( m_root.Streams.StringsHeap [mRow.Name], mRow.Flags); meth.RVA = mRow.RVA; meth.ImplAttributes = mRow.ImplFlags; meth.MetadataToken = MetadataToken.FromMetadataRow(TokenType.Method, i); m_meths [i] = meth; } }
void ReadEvents() { if (!m_tHeap.HasTable(EventTable.RId)) { m_events = new EventDefinition [0]; return; } EventTable evtTable = m_tableReader.GetEventTable(); EventMapTable emapTable = m_tableReader.GetEventMapTable(); m_events = new EventDefinition [evtTable.Rows.Count]; for (int i = 0; i < emapTable.Rows.Count; i++) { EventMapRow emapRow = emapTable [i]; if (emapRow.Parent == 0) { continue; } TypeDefinition owner = GetTypeDefAt(emapRow.Parent); GenericContext context = new GenericContext(owner); int start = (int)emapRow.EventList, last = evtTable.Rows.Count + 1, end; if (i < (emapTable.Rows.Count - 1)) { end = (int)emapTable [i + 1].EventList; } else { end = last; } if (end > last) { end = last; } for (int j = start; j < end; j++) { EventRow erow = evtTable [j - 1]; EventDefinition edef = new EventDefinition( m_root.Streams.StringsHeap [erow.Name], GetTypeDefOrRef(erow.EventType, context), erow.EventFlags); edef.MetadataToken = MetadataToken.FromMetadataRow(TokenType.Event, j - 1); if (!IsDeleted(edef)) { owner.Events.Add(edef); } m_events [j - 1] = edef; } } }
void AddTypeRef(TypeRefTable typesRef, int i) { // Check if index has been already added. if (m_typeRefs [i] != null) { return; } TypeRefRow type = typesRef [i]; IMetadataScope scope = null; TypeReference parent = null; if (type.ResolutionScope != MetadataToken.Zero) { switch (type.ResolutionScope.TokenType) { case TokenType.AssemblyRef: scope = m_module.AssemblyReferences [(int)type.ResolutionScope.RID - 1]; break; case TokenType.ModuleRef: scope = m_module.ModuleReferences [(int)type.ResolutionScope.RID - 1]; break; case TokenType.Module: scope = m_module.Assembly.Modules [(int)type.ResolutionScope.RID - 1]; break; case TokenType.TypeRef: AddTypeRef(typesRef, (int)type.ResolutionScope.RID - 1); parent = GetTypeRefAt(type.ResolutionScope.RID); scope = parent.Scope; break; } } TypeReference t = new TypeReference( m_root.Streams.StringsHeap [type.Name], m_root.Streams.StringsHeap [type.Namespace], scope); t.MetadataToken = MetadataToken.FromMetadataRow(TokenType.TypeRef, i); if (parent != null) { t.DeclaringType = parent; } m_typeRefs [i] = t; m_module.TypeReferences.Add(t); }
void ReadAllFields() { TypeDefTable tdefTable = m_tableReader.GetTypeDefTable(); if (!m_tHeap.HasTable(FieldTable.RId)) { m_fields = new FieldDefinition [0]; return; } FieldTable fldTable = m_tableReader.GetFieldTable(); m_fields = new FieldDefinition [fldTable.Rows.Count]; for (int i = 0; i < m_typeDefs.Length; i++) { TypeDefinition dec = m_typeDefs [i]; GenericContext context = new GenericContext(dec); int index = i, next; if (index == tdefTable.Rows.Count - 1) { next = fldTable.Rows.Count + 1; } else { next = (int)(tdefTable [index + 1]).FieldList; } for (int j = (int)tdefTable [index].FieldList; j < next; j++) { FieldRow frow = fldTable [j - 1]; FieldSig fsig = m_sigReader.GetFieldSig(frow.Signature); FieldDefinition fdef = new FieldDefinition( m_root.Streams.StringsHeap [frow.Name], this.GetTypeRefFromSig(fsig.Type, context), frow.Flags); fdef.MetadataToken = MetadataToken.FromMetadataRow(TokenType.Field, j - 1); if (fsig.CustomMods.Length > 0) { fdef.FieldType = GetModifierType(fsig.CustomMods, fdef.FieldType); } dec.Fields.Add(fdef); m_fields [j - 1] = fdef; } } }
public override void VisitModuleReferenceCollection(ModuleReferenceCollection modules) { if (!m_tHeap.HasTable(ModuleRefTable.RId)) { return; } ModuleRefTable mrTable = m_tableReader.GetModuleRefTable(); for (int i = 0; i < mrTable.Rows.Count; i++) { ModuleRefRow mrRow = mrTable [i]; ModuleReference mod = new ModuleReference(ReadString(mrRow.Name)); mod.MetadataToken = MetadataToken.FromMetadataRow(TokenType.ModuleRef, i); modules.Add(mod); } }
public TypeReference GetTypeSpecAt(uint rid, GenericContext context) { int index = (int)rid - 1; TypeReference tspec = m_typeSpecs [index]; if (tspec != null) { return(tspec); } TypeSpecTable tsTable = m_tableReader.GetTypeSpecTable(); TypeSpecRow tsRow = tsTable [index]; TypeSpec ts = m_sigReader.GetTypeSpec(tsRow.Signature); tspec = GetTypeRefFromSig(ts.Type, context); tspec.MetadataToken = MetadataToken.FromMetadataRow(TokenType.TypeSpec, index); m_typeSpecs [index] = tspec; return(tspec); }
void ReadGenericParameters() { if (!m_tHeap.HasTable(GenericParamTable.RId)) { return; } GenericParamTable gpTable = m_tableReader.GetGenericParamTable(); m_genericParameters = new GenericParameter [gpTable.Rows.Count]; for (int i = 0; i < gpTable.Rows.Count; i++) { GenericParamRow gpRow = gpTable [i]; IGenericParameterProvider owner; if (gpRow.Owner.TokenType == TokenType.Method) { owner = GetMethodDefAt(gpRow.Owner.RID); } else if (gpRow.Owner.TokenType == TokenType.TypeDef) { owner = GetTypeDefAt(gpRow.Owner.RID); } else { throw new ReflectionException("Unknown owner type for generic parameter"); } GenericParameter gp = new GenericParameter((int)gpRow.Number, owner); gp.Attributes = gpRow.Flags; gp.Name = MetadataRoot.Streams.StringsHeap [gpRow.Name]; gp.MetadataToken = MetadataToken.FromMetadataRow(TokenType.GenericParam, i); owner.GenericParameters.Add(gp); m_genericParameters [i] = gp; } }
void CompleteMethods() { TypeDefTable tdefTable = m_tableReader.GetTypeDefTable(); if (!m_tHeap.HasTable(MethodTable.RId)) { m_meths = new MethodDefinition [0]; return; } MethodTable methTable = m_tableReader.GetMethodTable(); ParamTable paramTable = m_tableReader.GetParamTable(); if (!m_tHeap.HasTable(ParamTable.RId)) { m_parameters = new ParameterDefinition [0]; } else { m_parameters = new ParameterDefinition [paramTable.Rows.Count]; } for (int i = 0; i < m_typeDefs.Length; i++) { TypeDefinition dec = m_typeDefs [i]; int index = i, next; if (index == tdefTable.Rows.Count - 1) { next = methTable.Rows.Count + 1; } else { next = (int)(tdefTable [index + 1]).MethodList; } for (int j = (int)tdefTable [index].MethodList; j < next; j++) { MethodRow methRow = methTable [j - 1]; MethodDefinition mdef = m_meths [j - 1]; if (mdef.IsConstructor) { dec.Constructors.Add(mdef); } else { dec.Methods.Add(mdef); } GenericContext context = new GenericContext(mdef); MethodDefSig msig = m_sigReader.GetMethodDefSig(methRow.Signature); mdef.HasThis = msig.HasThis; mdef.ExplicitThis = msig.ExplicitThis; mdef.CallingConvention = msig.MethCallConv; int prms; if (j == methTable.Rows.Count) { prms = m_parameters.Length + 1; } else { prms = (int)(methTable [j]).ParamList; } ParameterDefinition retparam = null; //TODO: optimize this ParamRow pRow = null; int start = (int)methRow.ParamList - 1; if (paramTable != null && start < prms - 1) { pRow = paramTable [start]; } if (pRow != null && pRow.Sequence == 0) // ret type { retparam = new ParameterDefinition( m_root.Streams.StringsHeap [pRow.Name], 0, pRow.Flags, null); retparam.Method = mdef; m_parameters [start] = retparam; start++; } for (int k = 0; k < msig.ParamCount; k++) { int pointer = start + k; if (paramTable != null && pointer < prms - 1) { pRow = paramTable [pointer]; } Param psig = msig.Parameters [k]; ParameterDefinition pdef; if (pRow != null) { pdef = BuildParameterDefinition( m_root.Streams.StringsHeap [pRow.Name], pRow.Sequence, pRow.Flags, psig, context); pdef.MetadataToken = MetadataToken.FromMetadataRow(TokenType.Param, pointer); m_parameters [pointer] = pdef; } else { pdef = BuildParameterDefinition( string.Concat("A_", mdef.IsStatic ? k : k + 1), k + 1, (ParamAttributes)0, psig, context); } pdef.Method = mdef; mdef.Parameters.Add(pdef); } mdef.ReturnType = GetMethodReturnType(msig, context); MethodReturnType mrt = mdef.ReturnType as MethodReturnType; mrt.Method = mdef; if (retparam != null) { mrt.Parameter = retparam; mrt.Parameter.ParameterType = mrt.ReturnType; } } } uint eprid = CodeReader.GetRid((int)m_reader.Image.CLIHeader.EntryPointToken); if (eprid > 0 && eprid <= m_meths.Length) { m_module.Assembly.EntryPoint = GetMethodDefAt(eprid); } }
public override void VisitTypeDefinitionCollection(TypeDefinitionCollection types) { // type def reading TypeDefTable typesTable = m_tableReader.GetTypeDefTable(); m_typeDefs = new TypeDefinition [typesTable.Rows.Count]; for (int i = 0; i < typesTable.Rows.Count; i++) { TypeDefRow type = typesTable [i]; TypeDefinition t = new TypeDefinition( m_root.Streams.StringsHeap [type.Name], m_root.Streams.StringsHeap [type.Namespace], type.Flags); t.MetadataToken = MetadataToken.FromMetadataRow(TokenType.TypeDef, i); m_typeDefs [i] = t; } // nested types if (m_tHeap.HasTable(NestedClassTable.RId)) { NestedClassTable nested = m_tableReader.GetNestedClassTable(); for (int i = 0; i < nested.Rows.Count; i++) { NestedClassRow row = nested [i]; TypeDefinition parent = GetTypeDefAt(row.EnclosingClass); TypeDefinition child = GetTypeDefAt(row.NestedClass); parent.NestedTypes.Add(child); } } foreach (TypeDefinition type in m_typeDefs) { types.Add(type); } // type ref reading if (m_tHeap.HasTable(TypeRefTable.RId)) { TypeRefTable typesRef = m_tableReader.GetTypeRefTable(); m_typeRefs = new TypeReference [typesRef.Rows.Count]; for (int i = 0; i < typesRef.Rows.Count; i++) { AddTypeRef(typesRef, i); } } else { m_typeRefs = new TypeReference [0]; } ReadTypeSpecs(); ReadMethodSpecs(); ReadMethods(); ReadGenericParameters(); // set base types for (int i = 0; i < typesTable.Rows.Count; i++) { TypeDefRow type = typesTable [i]; TypeDefinition child = m_typeDefs [i]; child.BaseType = GetTypeDefOrRef(type.Extends, new GenericContext(child)); } CompleteMethods(); ReadAllFields(); ReadMemberReferences(); }
public MemberReference GetMemberRefAt(uint rid, GenericContext context) { int index = (int)rid - 1; MemberReference member = m_memberRefs [rid - 1]; if (member != null) { return(member); } MemberRefTable mrTable = m_tableReader.GetMemberRefTable(); MemberRefRow mrefRow = mrTable [index]; Signature sig = m_sigReader.GetMemberRefSig(mrefRow.Class.TokenType, mrefRow.Signature); switch (mrefRow.Class.TokenType) { case TokenType.TypeDef: case TokenType.TypeRef: case TokenType.TypeSpec: TypeReference declaringType = GetTypeDefOrRef(mrefRow.Class, context); GenericContext nc = context.Clone(); if (declaringType is GenericInstanceType) { TypeReference ct = declaringType; while (ct is GenericInstanceType) { ct = (ct as GenericInstanceType).ElementType; } nc.Type = ct; nc.AllowCreation = ct.GetType() == typeof(TypeReference); } if (sig is FieldSig) { FieldSig fs = sig as FieldSig; member = new FieldReference( m_root.Streams.StringsHeap [mrefRow.Name], declaringType, GetTypeRefFromSig(fs.Type, nc)); } else { string name = m_root.Streams.StringsHeap [mrefRow.Name]; MethodSig ms = sig as MethodSig; MethodReference methref = new MethodReference( name, ms.HasThis, ms.ExplicitThis, ms.MethCallConv); methref.DeclaringType = declaringType; if (sig is MethodDefSig) { int arity = (sig as MethodDefSig).GenericParameterCount; for (int i = 0; i < arity; i++) { methref.GenericParameters.Add(new GenericParameter(i, methref)); } } nc.Method = methref; methref.ReturnType = GetMethodReturnType(ms, nc); methref.ReturnType.Method = methref; for (int j = 0; j < ms.ParamCount; j++) { Param p = ms.Parameters [j]; ParameterDefinition pdef = BuildParameterDefinition( string.Concat("A_", j), j, new ParamAttributes(), p, nc); pdef.Method = methref; methref.Parameters.Add(pdef); } member = methref; nc.Method = methref; } break; case TokenType.Method: // really not sure about this MethodDefinition methdef = GetMethodDefAt(mrefRow.Class.RID); member = new MethodReference( methdef.Name, methdef.HasThis, methdef.ExplicitThis, methdef.CallingConvention); member.DeclaringType = methdef.DeclaringType; break; case TokenType.ModuleRef: break; // TODO, implement that, or not } member.MetadataToken = MetadataToken.FromMetadataRow(TokenType.MemberRef, index); m_module.MemberReferences.Add(member); m_memberRefs [index] = member; return(member); }