37 internal struct Record : IRecord
41 internal int Constructor;
42 internal BlobHandle Value;
44 readonly
int IRecord.FilterKey => Parent;
46 public readonly
int CompareTo(Record other) => Comparer<int>.Default.Compare(EncodeHasCustomAttribute(Parent), EncodeHasCustomAttribute(other.Parent));
50 internal const int Index = 0x0C;
55 for (
int i = 0; i < records.Length; i++)
57 records[i].Parent = mr.ReadHasCustomAttribute();
58 records[i].Constructor = mr.ReadCustomAttributeType();
59 records[i].Value = MetadataTokens.BlobHandle(mr.ReadBlobIndex());
63 internal override void Write(ModuleBuilder module)
65 for (
int i = 0; i < rowCount; i++)
67 var h = module.Metadata.AddCustomAttribute(
68 MetadataTokens.EntityHandle(records[i].Parent),
69 MetadataTokens.EntityHandle(records[i].Constructor),
72 Debug.Assert(h == MetadataTokens.CustomAttributeHandle(i + 1));
76 internal void Fixup(ModuleBuilder moduleBuilder)
78 var genericParamFixup = moduleBuilder.GenericParamTable.GetIndexFixup();
80 for (
int i = 0; i < rowCount; i++)
82 moduleBuilder.FixupPseudoToken(
ref records[i].Constructor);
83 moduleBuilder.FixupPseudoToken(
ref records[i].Parent);
84 if (MetadataTokens.EntityHandle(records[i].Parent).Kind == HandleKind.GenericParameter)
85 records[i].Parent = (GenericParamTable.Index << 24) + genericParamFixup[(records[i].Parent & 0xFFFFFF) - 1] + 1;
94 internal static int EncodeHasCustomAttribute(
int token) => (token >> 24)
switch
96 MethodDefTable.Index => (token & 0xFFFFFF) << 5 | 0,
97 FieldTable.Index => (token & 0xFFFFFF) << 5 | 1,
98 TypeRefTable.Index => (token & 0xFFFFFF) << 5 | 2,
100 ParamTable.Index => (token & 0xFFFFFF) << 5 | 4,
102 MemberRefTable.Index => (token & 0xFFFFFF) << 5 | 6,
105 DeclSecurityTable.Index =>
throw new NotImplementedException(),
106 PropertyTable.Index => (token & 0xFFFFFF) << 5 | 9,
107 EventTable.Index => (token & 0xFFFFFF) << 5 | 10,
108 StandAloneSigTable.Index => (token & 0xFFFFFF) << 5 | 11,
110 TypeSpecTable.Index => (token & 0xFFFFFF) << 5 | 13,
112 AssemblyRefTable.Index => (token & 0xFFFFFF) << 5 | 15,
113 FileTable.Index => (token & 0xFFFFFF) << 5 | 16,
114 ExportedTypeTable.Index => (token & 0xFFFFFF) << 5 | 17,
116 GenericParamTable.Index => (token & 0xFFFFFF) << 5 | 19,
118 MethodSpecTable.Index => (token & 0xFFFFFF) << 5 | 21,
119 _ =>
throw new InvalidOperationException(),