namespace WoofWare.PawPrint open System open System.Reflection open System.Reflection.Metadata /// /// Represents detailed information about a field in a .NET assembly. /// This is a strongly-typed representation of FieldDefinition from System.Reflection.Metadata. /// type FieldInfo<'typeGeneric, 'fieldGeneric when 'typeGeneric : comparison and 'typeGeneric :> IComparable<'typeGeneric>> = { /// /// The metadata token handle that uniquely identifies this field in the assembly. /// Handle : FieldDefinitionHandle /// The name of the field. Name : string /// /// The type that declares this field. /// DeclaringType : ConcreteType<'typeGeneric> /// /// The type of the field. /// Signature : 'fieldGeneric /// /// The attributes applied to this field, including visibility, static/instance, /// literal, and other characteristics. /// Attributes : FieldAttributes } override this.ToString () : string = $"%s{this.DeclaringType.Assembly.Name}.{this.DeclaringType.Name}.%s{this.Name}" [] module FieldInfo = let make (mr : MetadataReader) (assembly : AssemblyName) (handle : FieldDefinitionHandle) (def : FieldDefinition) : FieldInfo = let name = mr.GetString def.Name let fieldSig = def.DecodeSignature (TypeDefn.typeProvider assembly, ()) let declaringType = def.GetDeclaringType () let typeGenerics = mr.GetTypeDefinition(declaringType).GetGenericParameters().Count let decType = mr.GetTypeDefinition (declaringType) let declaringTypeNamespace = mr.GetString decType.Namespace let declaringTypeName = mr.GetString decType.Name let declaringType = ConcreteType.make' assembly declaringType declaringTypeNamespace declaringTypeName typeGenerics { Name = name Signature = fieldSig DeclaringType = declaringType Handle = handle Attributes = def.Attributes } let mapTypeGenerics<'a, 'b, 'field when 'a :> IComparable<'a> and 'a : comparison and 'b :> IComparable<'b> and 'b : comparison> (f : int -> 'a -> 'b) (input : FieldInfo<'a, 'field>) : FieldInfo<'b, 'field> = let declaringType = input.DeclaringType |> ConcreteType.mapGeneric f { Handle = input.Handle Name = input.Name DeclaringType = declaringType Signature = input.Signature Attributes = input.Attributes }