| File: ILCompiler\Metadata\Transform.Field.cs | Web Access |
| Project: src\runtime\src\coreclr\tools\aot\ILCompiler.MetadataTransform\ILCompiler.MetadataTransform.csproj (ILCompiler.MetadataTransform) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. using System; using System.Collections.Generic; using Internal.Metadata.NativeFormat.Writer; using Cts = Internal.TypeSystem; using Ecma = System.Reflection.Metadata; using Debug = System.Diagnostics.Debug; using FieldAttributes = System.Reflection.FieldAttributes; namespace ILCompiler.Metadata { internal partial class Transform<TPolicy> { internal EntityMap<Cts.FieldDesc, MetadataRecord> _fields = new EntityMap<Cts.FieldDesc, MetadataRecord>(EqualityComparer<Cts.FieldDesc>.Default); private Action<Cts.FieldDesc, Field> _initFieldDef; private Action<Cts.FieldDesc, MemberReference> _initFieldRef; public override MetadataRecord HandleQualifiedField(Cts.FieldDesc field) { if (_policy.GeneratesMetadata(field) && field.GetTypicalFieldDefinition() == field) { QualifiedField record = new QualifiedField(); record.Field = HandleFieldDefinition(field); record.EnclosingType = (TypeDefinition)HandleType(field.OwningType); return record; } else { return HandleFieldReference(field); } } private Field HandleFieldDefinition(Cts.FieldDesc field) { Debug.Assert(field.GetTypicalFieldDefinition() == field); Debug.Assert(_policy.GeneratesMetadata(field)); return (Field)_fields.GetOrCreate(field, _initFieldDef ??= InitializeFieldDefinition); } private void InitializeFieldDefinition(Cts.FieldDesc entity, Field record) { record.Name = HandleString(entity.GetName()); record.Flags = GetFieldAttributes(entity); var ecmaField = entity as Cts.Ecma.EcmaField; if (ecmaField != null) { Ecma.MetadataReader reader = ecmaField.MetadataReader; Ecma.FieldDefinition fieldDef = reader.GetFieldDefinition(ecmaField.Handle); record.Signature = new FieldSignature { Type = entity.HasEmbeddedSignatureData ? HandleFieldSignature(ecmaField.Module, fieldDef.Signature) : HandleType(entity.FieldType), }; Ecma.ConstantHandle defaultValueHandle = fieldDef.GetDefaultValue(); if (!defaultValueHandle.IsNil) { record.DefaultValue = HandleConstant(ecmaField.Module, defaultValueHandle); } Ecma.CustomAttributeHandleCollection customAttributes = fieldDef.GetCustomAttributes(); if (customAttributes.Count > 0) { record.CustomAttributes = HandleCustomAttributes(ecmaField.Module, customAttributes); } int offset = fieldDef.GetOffset(); if (offset >= 0) record.Offset = (uint)offset; } else { throw new NotImplementedException(); } } private MetadataRecord HandleFieldSignature(Cts.Ecma.EcmaModule module, Ecma.BlobHandle sigBlob) { Ecma.BlobReader reader = module.MetadataReader.GetBlobReader(sigBlob); Ecma.SignatureHeader header = reader.ReadSignatureHeader(); Debug.Assert(header.Kind == Ecma.SignatureKind.Field); return HandleType(module, ref reader); } private MemberReference HandleFieldReference(Cts.FieldDesc field) { return (MemberReference)_fields.GetOrCreate(field, _initFieldRef ??= InitializeFieldReference); } private void InitializeFieldReference(Cts.FieldDesc entity, MemberReference record) { record.Name = HandleString(entity.GetName()); record.Parent = HandleType(entity.OwningType); record.Signature = new FieldSignature { Type = HandleType(entity.GetTypicalFieldDefinition().FieldType), // TODO: CustomModifiers }; } private static FieldAttributes GetFieldAttributes(Cts.FieldDesc field) { FieldAttributes result; var ecmaField = field as Cts.Ecma.EcmaField; if (ecmaField != null) { var fieldDefinition = ecmaField.MetadataReader.GetFieldDefinition(ecmaField.Handle); result = fieldDefinition.Attributes; } else { result = 0; if (field.IsStatic) result |= FieldAttributes.Static; if (field.IsInitOnly) result |= FieldAttributes.InitOnly; if (field.IsLiteral) result |= FieldAttributes.Literal; if (field.HasRva) result |= FieldAttributes.HasFieldRVA; // Not set: Visibility, NotSerialized, SpecialName, RTSpecialName, HasFieldMarshal, HasDefault } return result; } } }