// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
// Missing XML comment for publicly visible type or member
#pragma warning disable 1591
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using Debugger.Interop.MetaData;
using Debugger.Interop.CorDebug;
using Debugger.Interop.CorSym;
namespace Debugger.Interop.MetaData
{
/// Wrapper for the unmanaged metadata API.
/// http://msdn.microsoft.com/en-us/library/ms230172.aspx
public class MetaDataImport
{
const int DefaultBufferSize = 8;
// If buffer is too small, enlarge it
const int BufferSizeMultiplier = 4;
IMetaDataImport metaData;
public MetaDataImport(ICorDebugModule pModule)
{
Guid guid = new Guid("{ 0x7dac8207, 0xd3ae, 0x4c75, { 0x9b, 0x67, 0x92, 0x80, 0x1a, 0x49, 0x7d, 0x44 } }");
metaData = (IMetaDataImport)pModule.GetMetaDataInterface(ref guid);
TrackedComObjects.Track(metaData);
}
public ISymUnmanagedReader GetSymReader(string fullname, string searchPath)
{
try {
ISymUnmanagedBinder symBinder = new Debugger.Interop.CorSym.CorSymBinder_SxSClass();
TrackedComObjects.Track(symBinder);
return symBinder.GetReaderForFile(metaData, fullname, searchPath);
} catch (COMException) {
return null;
}
}
public ISymUnmanagedReader GetSymReader(IStream stream)
{
try {
ISymUnmanagedBinder symBinder = new Debugger.Interop.CorSym.CorSymBinder_SxSClass();
TrackedComObjects.Track(symBinder);
return symBinder.GetReaderFromStream(metaData, stream);
} catch (COMException) {
return null;
}
}
// CloseEnum, CountEnum and ResetEnum are not wrapped, use them directly
// GetNameFromToken is obsolete
public uint[] EnumCustomAttributes(uint token_Scope, uint token_TypeOfAttributes)
{
return EnumerateTokens(metaData.EnumCustomAttributes, token_Scope, token_TypeOfAttributes);
}
public IEnumerable EnumCustomAttributeProps(uint token_Scope, uint token_TypeOfAttributes)
{
foreach(uint token in EnumerateTokens(metaData.EnumCustomAttributes, token_Scope, token_TypeOfAttributes)) {
yield return GetCustomAttributeProps(token);
}
}
public uint[] EnumEvents(uint typeDef)
{
return EnumerateTokens(metaData.EnumEvents, typeDef);
}
public IEnumerable EnumEventProps(uint typeDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumEvents, typeDef)) {
yield return GetEventProps(token);
}
}
public uint[] EnumFields(uint typeDef)
{
return EnumerateTokens(metaData.EnumFields, typeDef);
}
public IEnumerable EnumFieldProps(uint typeDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumFields, typeDef)) {
yield return GetFieldProps(token);
}
}
public uint[] EnumFieldsWithName(uint typeDef, string name)
{
return EnumerateTokens(metaData.EnumFieldsWithName, typeDef, name);
}
public IEnumerable EnumFieldPropsWithName(uint typeDef, string name)
{
foreach(uint token in EnumerateTokens(metaData.EnumFieldsWithName, typeDef, name)) {
yield return GetFieldProps(token);
}
}
public uint[] EnumGenericParams(uint typeDef_methodDef)
{
return EnumerateTokens(metaData.EnumGenericParams, typeDef_methodDef);
}
/// MethodDef tokens
public uint[] EnumInterfaceImpls(uint typeDef)
{
return EnumerateTokens(metaData.EnumInterfaceImpls, typeDef);
}
public IEnumerable EnumInterfaceImplProps(uint typeDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumInterfaceImpls, typeDef)) {
yield return GetInterfaceImplProps(token);
}
}
public uint[] EnumMemberRefs(uint typeDef_typeRef_methodDef_moduleRef)
{
return EnumerateTokens(metaData.EnumMemberRefs, typeDef_typeRef_methodDef_moduleRef);
}
public IEnumerable EnumMemberRefProps(uint typeDef_typeRef_methodDef_moduleRef)
{
foreach(uint token in EnumerateTokens(metaData.EnumMemberRefs, typeDef_typeRef_methodDef_moduleRef)) {
yield return GetMemberRefProps(token);
}
}
public uint[] EnumMembers(uint typeDef)
{
return EnumerateTokens(metaData.EnumMembers, typeDef);
}
public IEnumerable EnumMemberProps(uint typeDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumMembers, typeDef)) {
yield return GetMemberProps(token);
}
}
public uint[] EnumMembersWithName(uint typeDef, string name)
{
return EnumerateTokens(metaData.EnumMembersWithName, typeDef, name);
}
public IEnumerable EnumMemberPropsWithName(uint typeDef, string name)
{
foreach(uint token in EnumerateTokens(metaData.EnumMembersWithName, typeDef, name)) {
yield return GetMemberProps(token);
}
}
/// MethodBody and MethodDeclaration tokens
public IEnumerable EnumMethodImpls(uint typeDef)
{
IntPtr enumerator = IntPtr.Zero;
while(true) {
MethodImpl ret = new MethodImpl();
uint[] body = new uint[1];
uint[] decl = new uint[1];
uint fetched;
metaData.EnumMethodImpls(ref enumerator, typeDef, body, decl, 1, out fetched);
if (fetched == 0)
break;
ret.MethodBody = body[0];
ret.MethodDecl = decl[0];
yield return ret;
}
metaData.CloseEnum(enumerator);
}
public uint[] EnumMethods(uint typeDef)
{
return EnumerateTokens(metaData.EnumMethods, typeDef);
}
public IEnumerable EnumMethodProps(uint typeDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumMethods, typeDef)) {
yield return GetMethodProps(token);
}
}
/// Events or properties
public uint[] EnumMethodSemantics(uint methodDef)
{
return EnumerateTokens(metaData.EnumMethodSemantics, methodDef);
}
public uint[] EnumMethodsWithName(uint typeDef, string name)
{
return EnumerateTokens(metaData.EnumMethodsWithName, typeDef, name);
}
public IEnumerable EnumMethodPropsWithName(uint typeDef, string name)
{
foreach(uint token in EnumerateTokens(metaData.EnumMethodsWithName, typeDef, name)) {
yield return GetMethodProps(token);
}
}
public uint[] EnumModuleRefs()
{
return EnumerateTokens(metaData.EnumModuleRefs);
}
public IEnumerable EnumModuleRefProps()
{
foreach(uint token in EnumerateTokens(metaData.EnumModuleRefs)) {
yield return GetModuleRefProps(token);
}
}
public uint[] EnumParams(uint methodDef)
{
return EnumerateTokens(metaData.EnumParams, methodDef);
}
public IEnumerable EnumParamProps(uint methodDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumParams, methodDef)) {
yield return GetParamProps(token);
}
}
public uint[] EnumPermissionSets(uint token_scope_nullable, uint actions)
{
return EnumerateTokens(metaData.EnumPermissionSets, token_scope_nullable, actions);
}
public IEnumerable EnumPermissionSetProps(uint token_scope_nullable, uint actions)
{
foreach(uint token in EnumerateTokens(metaData.EnumPermissionSets, token_scope_nullable, actions)) {
yield return GetPermissionSetProps(token);
}
}
public uint[] EnumProperties(uint typeDef)
{
return EnumerateTokens(metaData.EnumProperties, typeDef);
}
public IEnumerable EnumPropertyProps(uint typeDef)
{
foreach(uint token in EnumerateTokens(metaData.EnumProperties, typeDef)) {
yield return GetPropertyProps(token);
}
}
public uint[] EnumSignatures()
{
return EnumerateTokens(metaData.EnumSignatures);
}
public uint[] EnumTypeDefs()
{
return EnumerateTokens(metaData.EnumTypeDefs);
}
public IEnumerable EnumTypeDefProps()
{
foreach(uint token in EnumerateTokens(metaData.EnumTypeDefs)) {
yield return GetTypeDefProps(token);
}
}
public uint[] EnumTypeRefs()
{
return EnumerateTokens(metaData.EnumTypeRefs);
}
public IEnumerable EnumTypeRefProps()
{
foreach(uint token in EnumerateTokens(metaData.EnumTypeRefs)) {
yield return GetTypeRefProps(token);
}
}
public uint[] EnumTypeSpecs()
{
return EnumerateTokens(metaData.EnumTypeSpecs);
}
public IEnumerable EnumTypeSpecBlobs()
{
foreach(uint token in EnumerateTokens(metaData.EnumTypeSpecs)) {
yield return GetTypeSpecFromToken(token);
}
}
public uint[] EnumUnresolvedMethods()
{
return EnumerateTokens(metaData.EnumUnresolvedMethods);
}
public uint[] EnumUserStrings()
{
return EnumerateTokens(metaData.EnumUserStrings);
}
public IEnumerable EnumUserStringProps()
{
foreach(uint token in EnumerateTokens(metaData.EnumUserStrings)) {
yield return GetUserString(token);
}
}
public uint FindField(uint typeDef_nullable, string name, Blob sigBlob)
{
sigBlob = sigBlob ?? Blob.Empty;
uint fieldDef;
metaData.FindField(typeDef_nullable, name, sigBlob.Adress, sigBlob.Size, out fieldDef);
return fieldDef;
}
public FieldProps FindFieldProps(uint typeDef_nullable, string name, Blob sigBlob)
{
return GetFieldProps(FindField(typeDef_nullable, name, sigBlob));
}
public uint FindMember(uint typeDef_nullable, string name, Blob sigBlob)
{
sigBlob = sigBlob ?? Blob.Empty;
uint memberDef;
metaData.FindMember(typeDef_nullable, name, sigBlob.Adress, sigBlob.Size, out memberDef);
return memberDef;
}
public MemberProps FindMemberProps(uint typeDef_nullable, string name, Blob sigBlob)
{
return GetMemberProps(FindMember(typeDef_nullable, name, sigBlob));
}
public uint FindMemberRef(uint typeRef_nullable, string name, Blob sigBlob)
{
sigBlob = sigBlob ?? Blob.Empty;
uint memberRef;
metaData.FindMemberRef(typeRef_nullable, name, sigBlob.Adress, sigBlob.Size, out memberRef);
return memberRef;
}
public MemberRefProps FindMemberRefProps(uint typeRef_nullable, string name, Blob sigBlob)
{
return GetMemberRefProps(FindMemberRef(typeRef_nullable, name, sigBlob));
}
public uint FindMethod(uint typeDef_nullable, string name, Blob sigBlob)
{
sigBlob = sigBlob ?? Blob.Empty;
uint methodDef;
metaData.FindMethod(typeDef_nullable, name, sigBlob.Adress, sigBlob.Size, out methodDef);
return methodDef;
}
public MethodProps FindMethodProps(uint typeDef_nullable, string name, Blob sigBlob)
{
return GetMethodProps(FindMethod(typeDef_nullable, name, sigBlob));
}
public uint FindTypeDefByName(string name, uint typeDef_typeRef_enclosingClass_nullable)
{
uint typeDef;
metaData.FindTypeDefByName(name, typeDef_typeRef_enclosingClass_nullable, out typeDef);
return typeDef;
}
public TypeDefProps FindTypeDefPropsByName(string name, uint typeDef_typeRef_enclosingClass_nullable)
{
return GetTypeDefProps(FindTypeDefByName(name, typeDef_typeRef_enclosingClass_nullable));
}
public uint FindTypeRef(uint moduleRef_assemblyRef_typeRef_scope, string name)
{
uint typeRef;
metaData.FindTypeRef(moduleRef_assemblyRef_typeRef_scope, name, out typeRef);
return typeRef;
}
public TypeRefProps FindTypeRefProps(uint moduleRef_assemblyRef_typeRef_scope, string name)
{
return GetTypeRefProps(FindTypeRef(moduleRef_assemblyRef_typeRef_scope, name));
}
public ClassLayout GetClassLayout(uint typeDef)
{
ClassLayout ret = new ClassLayout();
ret.TypeDef = typeDef;
ret.FieldOffsets = new COR_FIELD_OFFSET[DefaultBufferSize];
uint returned;
while (true) {
metaData.GetClassLayout(
ret.TypeDef,
out ret.PackSize,
ret.FieldOffsets, (uint)ret.FieldOffsets.Length, out returned,
out ret.ClassSize
);
if (returned < ret.FieldOffsets.Length) break;
ret.FieldOffsets = new COR_FIELD_OFFSET[ret.FieldOffsets.Length * BufferSizeMultiplier];
}
Array.Resize(ref ret.FieldOffsets, (int)returned);
return ret;
}
public Blob GetCustomAttributeByName(uint token_owner, string name)
{
IntPtr blobPtr;
uint blobSize;
metaData.GetCustomAttributeByName(
token_owner,
name,
out blobPtr,
out blobSize
);
return new Blob(blobPtr, blobSize);
}
public CustomAttributeProps GetCustomAttributeProps(uint token)
{
IntPtr blobPtr;
uint blobSize;
CustomAttributeProps ret = new CustomAttributeProps();
ret.Token = token;
metaData.GetCustomAttributeProps(
ret.Token,
out ret.Owner,
out ret.Type,
out blobPtr,
out blobSize
);
ret.Data = new Blob(blobPtr, blobSize);
return ret;
}
public EventProps GetEventProps(uint eventToken)
{
EventProps ret = new EventProps();
ret.Event = eventToken;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
ret.OtherMethods = new uint[DefaultBufferSize];
uint returned;
while(true) {
metaData.GetEventProps(
ret.Event,
out ret.DeclaringClass,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out ret.EventType,
out ret.AddMethod,
out ret.RemoveMethod,
out ret.FireMethod,
ret.OtherMethods, (uint)ret.OtherMethods.Length, out returned
);
if (returned < ret.OtherMethods.Length) break;
ret.OtherMethods = new uint[ret.OtherMethods.Length * BufferSizeMultiplier];
}
Array.Resize(ref ret.OtherMethods, (int)returned);
});
return ret;
}
public Blob GetFieldMarshal(uint token)
{
IntPtr blobPtr;
uint blobSize;
metaData.GetFieldMarshal(
token,
out blobPtr,
out blobSize
);
return new Blob(blobPtr, blobSize);
}
public FieldProps GetFieldProps(uint fieldDef)
{
FieldProps ret = new FieldProps();
IntPtr sigPtr = IntPtr.Zero;
uint sigSize = 0;
ret.Token = fieldDef;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetFieldProps(
ret.Token,
out ret.DeclaringClass,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out sigPtr,
out sigSize,
out ret.ConstantType,
out ret.ConstantPtr,
out ret.ConstantStringLength
);
});
ret.SigBlob = new Blob(sigPtr, sigSize);
return ret;
}
public InterfaceImplProps GetInterfaceImplProps(uint method)
{
InterfaceImplProps ret = new InterfaceImplProps();
ret.Method = method;
metaData.GetInterfaceImplProps(
ret.Method,
out ret.Class,
out ret.Interface
);
return ret;
}
public MemberProps GetMemberProps(uint token)
{
MemberProps ret = new MemberProps();
IntPtr sigPtr = IntPtr.Zero;
uint sigSize = 0;
ret.Token = token;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetMemberProps(
ret.Token,
out ret.Class,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out sigPtr,
out sigSize,
out ret.RVA,
out ret.ImplFlags,
out ret.ConstantType,
out ret.ConstantPtr,
out ret.ConstantStringLength
);
});
ret.SigBlob = new Blob(sigPtr, sigSize);
return ret;
}
public MemberRefProps GetMemberRefProps(uint token)
{
MemberRefProps ret = new MemberRefProps();
IntPtr sigPtr = IntPtr.Zero;
uint sigSize = 0;
ret.Token = token;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetMemberRefProps(
token,
out ret.DeclaringType,
pString, pStringLenght, out stringLenght,
out sigPtr,
out sigSize
);
});
ret.SigBlob = new Blob(sigPtr, sigSize);
return ret;
}
public MethodProps GetMethodProps(uint methodToken)
{
MethodProps ret = new MethodProps();
IntPtr sigPtr = IntPtr.Zero;
uint sigSize = 0;
ret.Token = methodToken;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetMethodProps(
ret.Token,
out ret.ClassToken,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out sigPtr,
out sigSize,
out ret.CodeRVA,
out ret.ImplFlags
);
});
ret.SigBlob = new Blob(sigPtr, sigSize);
return ret;
}
public uint GetMethodSemantics(uint methodDef, uint event_property)
{
uint semFlags;
metaData.GetMethodSemantics(methodDef, event_property, out semFlags);
return semFlags;
}
public uint GetModuleFromScope()
{
uint module;
metaData.GetModuleFromScope(out module);
return module;
}
public ModuleRefProps GetModuleRefProps(uint token)
{
ModuleRefProps ret = new ModuleRefProps();
ret.Token = token;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetModuleRefProps(
token,
pString, pStringLenght, out stringLenght
);
});
return ret;
}
public uint GetNativeCallConvFromSig(Blob sigBlob)
{
uint callConv;
metaData.GetNativeCallConvFromSig(sigBlob.Adress, sigBlob.Size, out callConv);
return callConv;
}
public NestedClassProps GetNestedClassProps(uint nestedClass)
{
NestedClassProps ret = new NestedClassProps();
ret.NestedClass = nestedClass;
metaData.GetNestedClassProps(
ret.NestedClass,
out ret.EnclosingClass
);
return ret;
}
public uint GetParamForMethodIndex(uint methodToken, uint parameterSequence)
{
uint paramToken;
metaData.GetParamForMethodIndex(methodToken, parameterSequence, out paramToken);
return paramToken;
}
public ParamProps GetParamPropsForMethodIndex(uint methodToken, uint parameterSequence)
{
return GetParamProps(GetParamForMethodIndex(methodToken, parameterSequence));
}
public ParamProps GetParamProps(uint paramToken)
{
ParamProps ret = new ParamProps();
ret.ParamDef = paramToken;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetParamProps(
ret.ParamDef,
out ret.MethodDef,
out ret.Sequence,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out ret.ConstantType,
out ret.ConstantPtr,
out ret.ConstantStringLength
);
});
return ret;
}
public PermissionSetProps GetPermissionSetProps(uint permToken)
{
PermissionSetProps ret = new PermissionSetProps();
IntPtr permPtr;
uint permSize;
ret.PermToken = permToken;
metaData.GetPermissionSetProps(
ret.PermToken,
out ret.Action,
out permPtr,
out permSize
);
ret.SigBlob = new Blob(permPtr, permSize);
return ret;
}
public PinvokeMap GetPinvokeMap(uint fieldDef_methodDef)
{
PinvokeMap ret = new PinvokeMap();
ret.Token = fieldDef_methodDef;
ret.ImportName = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetPinvokeMap(
ret.Token,
out ret.Flags,
pString, pStringLenght, out stringLenght,
out ret.ModuleRef
);
});
return ret;
}
public PropertyProps GetPropertyProps(uint prop)
{
PropertyProps ret = new PropertyProps();
IntPtr sigPtr = IntPtr.Zero;
uint sigSize = 0;
ret.Propery = prop;
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
ret.OtherMethods = new uint[DefaultBufferSize];
uint returned;
while(true) {
metaData.GetPropertyProps(
ret.Propery,
out ret.DeclaringClass,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out sigPtr,
out sigSize,
out ret.DefaultValueType,
out ret.DefaultValuePtr,
out ret.DefaultValueStringLength,
out ret.SetterMethod,
out ret.GetterMethod,
ret.OtherMethods, (uint)ret.OtherMethods.Length, out returned
);
if (returned < ret.OtherMethods.Length) break;
ret.OtherMethods = new uint[ret.OtherMethods.Length * BufferSizeMultiplier];
}
Array.Resize(ref ret.OtherMethods, (int)returned);
});
ret.SigBlob = new Blob(sigPtr, sigSize);
return ret;
}
public RVA GetRVA(uint methodDef_fieldDef)
{
RVA ret = new RVA();
ret.Token = methodDef_fieldDef;
metaData.GetRVA(
ret.Token,
out ret.CodeRVA,
out ret.ImplFlags
);
return ret;
}
public ScopeProps GetScopeProps()
{
ScopeProps ret = new ScopeProps();
ret.Name = Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetScopeProps(
pString, pStringLenght, out stringLenght,
out ret.Guid
);
});
return ret;
}
public Blob GetSigFromToken(uint token)
{
IntPtr sigPtr;
uint sigSize;
metaData.GetSigFromToken(
token,
out sigPtr,
out sigSize
);
return new Blob(sigPtr, sigSize);
}
public TypeDefProps GetTypeDefProps(uint typeDef)
{
TypeDefProps ret = new TypeDefProps();
ret.Token = typeDef;
ret.Name =
Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetTypeDefProps(
ret.Token,
pString, pStringLenght, out stringLenght,
out ret.Flags,
out ret.SuperClassToken
);
});
return ret;
}
public TypeRefProps GetTypeRefProps(uint typeRef)
{
TypeRefProps ret = new TypeRefProps();
ret.TypeRef = typeRef;
ret.Name =
Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetTypeRefProps(
ret.TypeRef,
out ret.ResolutionScope,
pString, pStringLenght, out stringLenght
);
});
return ret;
}
public Blob GetTypeSpecFromToken(uint typeSpec)
{
IntPtr sigPtr;
uint sigSize;
metaData.GetTypeSpecFromToken(
typeSpec,
out sigPtr,
out sigSize
);
return new Blob(sigPtr, sigSize);
}
public string GetUserString(uint stringToken)
{
return Util.GetString(delegate(uint pStringLenght, out uint stringLenght, System.IntPtr pString) {
metaData.GetUserString(
stringToken,
pString, pStringLenght, out stringLenght
);
});
}
public bool IsGlobal(uint token)
{
int isGlobal;
metaData.IsGlobal(token, out isGlobal);
return isGlobal != 0;
}
public bool IsValidToken(uint token)
{
return metaData.IsValidToken(token) != 0;
}
public ResolvedTypeRef ResolveTypeRef(uint typeRef, Guid riid)
{
ResolvedTypeRef res = new ResolvedTypeRef();
metaData.ResolveTypeRef(
typeRef,
ref riid,
out res.Scope,
out res.TypeDef
);
return res;
}
#region Util
delegate void TokenEnumerator0(ref IntPtr phEnum, uint[] token, uint maxCount, out uint fetched);
uint[] EnumerateTokens(TokenEnumerator0 tokenEnumerator)
{
IntPtr enumerator = IntPtr.Zero;
uint[] buffer = new uint[DefaultBufferSize];
uint fetched;
tokenEnumerator(ref enumerator, buffer, (uint)buffer.Length, out fetched);
if (fetched < buffer.Length) {
// The tokens did fit the buffer
Array.Resize(ref buffer, (int)fetched);
} else {
// The tokens did not fit the buffer -> Refetch
uint actualCount;
metaData.CountEnum(enumerator, out actualCount);
if (actualCount > buffer.Length) {
buffer = new uint[actualCount];
metaData.ResetEnum(enumerator, 0);
tokenEnumerator(ref enumerator, buffer, (uint)buffer.Length, out fetched);
}
}
metaData.CloseEnum(enumerator);
return buffer;
}
delegate void TokenEnumerator1(ref IntPtr phEnum, T parameter, uint[] token, uint maxCount, out uint fetched);
uint[] EnumerateTokens(TokenEnumerator1 tokenEnumerator, T parameter)
{
IntPtr enumerator = IntPtr.Zero;
uint[] buffer = new uint[DefaultBufferSize];
uint fetched;
tokenEnumerator(ref enumerator, parameter, buffer, (uint)buffer.Length, out fetched);
if (fetched < buffer.Length) {
// The tokens did fit the buffer
Array.Resize(ref buffer, (int)fetched);
} else {
// The tokens did not fit the buffer -> Refetch
uint actualCount;
metaData.CountEnum(enumerator, out actualCount);
if (actualCount > buffer.Length) {
buffer = new uint[actualCount];
metaData.ResetEnum(enumerator, 0);
tokenEnumerator(ref enumerator, parameter, buffer, (uint)buffer.Length, out fetched);
}
}
metaData.CloseEnum(enumerator);
return buffer;
}
delegate void TokenEnumerator2(ref IntPtr phEnum, T parameter1, R parameter2, uint[] token, uint maxCount, out uint fetched);
uint[] EnumerateTokens(TokenEnumerator2 tokenEnumerator, T parameter1, R parameter2)
{
IntPtr enumerator = IntPtr.Zero;
uint[] buffer = new uint[DefaultBufferSize];
uint fetched;
tokenEnumerator(ref enumerator, parameter1, parameter2, buffer, (uint)buffer.Length, out fetched);
if (fetched < buffer.Length) {
// The tokens did fit the buffer
Array.Resize(ref buffer, (int)fetched);
} else {
// The tokens did not fit the buffer -> Refetch
uint actualCount;
metaData.CountEnum(enumerator, out actualCount);
if (actualCount > buffer.Length) {
buffer = new uint[actualCount];
metaData.ResetEnum(enumerator, 0);
tokenEnumerator(ref enumerator, parameter1, parameter2, buffer, (uint)buffer.Length, out fetched);
}
}
metaData.CloseEnum(enumerator);
return buffer;
}
#endregion
}
public class Blob
{
public static readonly Blob Empty = new Blob(IntPtr.Zero, 0);
IntPtr adress;
uint size;
public IntPtr Adress {
get { return adress; }
}
public uint Size {
get { return size; }
}
public Blob(IntPtr adress, uint size)
{
this.adress = adress;
this.size = size;
}
public byte[] GetData()
{
byte[] data = new byte[size];
Marshal.Copy(adress, data, 0, (int)size);
return data;
}
}
public class ClassLayout
{
public uint TypeDef;
public uint PackSize;
public COR_FIELD_OFFSET[] FieldOffsets;
public uint ClassSize;
}
public class CustomAttributeProps
{
public uint Token;
public uint Owner;
public uint Type;
public Blob Data;
}
public class EventProps
{
public uint Event;
public uint DeclaringClass;
public string Name;
public uint Flags;
public uint EventType;
public uint AddMethod;
public uint RemoveMethod;
public uint FireMethod;
public uint[] OtherMethods;
}
public class FieldProps
{
public uint Token;
public string Name;
public uint DeclaringClass;
public uint Flags;
public Blob SigBlob;
public uint ConstantType;
public IntPtr ConstantPtr;
public uint ConstantStringLength;
}
public class InterfaceImplProps
{
public uint Method;
public uint Class;
public uint Interface;
}
public class MemberProps
{
public uint Token;
public uint Class;
public string Name;
public uint Flags;
public Blob SigBlob;
public uint RVA;
public uint ImplFlags;
public uint ConstantType;
public IntPtr ConstantPtr;
public uint ConstantStringLength;
}
public class MemberRefProps
{
public uint Token;
public uint DeclaringType;
public string Name;
public Blob SigBlob;
}
public class MethodImpl
{
public uint MethodBody;
public uint MethodDecl;
}
public class MethodProps
{
public uint Token;
public string Name;
public uint ClassToken;
public uint Flags;
public Blob SigBlob;
public uint CodeRVA;
public uint ImplFlags;
}
public class ModuleRefProps
{
public uint Token;
public string Name;
}
public class NestedClassProps
{
public uint NestedClass;
public uint EnclosingClass;
}
public class ParamProps
{
public uint ParamDef;
public uint MethodDef;
public uint Sequence;
public string Name;
public uint Flags;
public uint ConstantType;
public IntPtr ConstantPtr;
public uint ConstantStringLength;
}
public class PermissionSetProps
{
public uint PermToken;
public uint Action;
public Blob SigBlob;
}
public class PinvokeMap
{
public uint Token;
public uint Flags;
public string ImportName;
public uint ModuleRef;
}
public class PropertyProps
{
public uint Propery;
public uint DeclaringClass;
public string Name;
public uint Flags;
public Blob SigBlob;
public uint DefaultValueType;
public IntPtr DefaultValuePtr;
public uint DefaultValueStringLength;
public uint SetterMethod;
public uint GetterMethod;
public uint[] OtherMethods;
}
public class ResolvedTypeRef
{
public object Scope;
public uint TypeDef;
}
public class RVA
{
public uint Token;
public uint CodeRVA;
public uint ImplFlags;
}
public class ScopeProps
{
public string Name;
public Guid Guid;
}
public class TypeDefProps
{
public uint Token;
public string Name;
public uint Flags;
public uint SuperClassToken;
}
public class TypeRefProps
{
public uint TypeRef;
public uint ResolutionScope;
public string Name;
}
}
#pragma warning restore 1591