diff options
author | Tomáš Rylek <trylek@microsoft.com> | 2018-12-18 22:26:54 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2018-12-18 22:26:54 +0100 |
commit | b7b1aa016ac4eb13a54e49c1f9e137b9dab01a66 (patch) | |
tree | 8b112c2331ff5c01d13afc299aeecdd8c3c86ae4 /src/tools | |
parent | 12a8870119b3e8023d68868792b29c28991168b3 (diff) | |
download | coreclr-b7b1aa016ac4eb13a54e49c1f9e137b9dab01a66.tar.gz coreclr-b7b1aa016ac4eb13a54e49c1f9e137b9dab01a66.tar.bz2 coreclr-b7b1aa016ac4eb13a54e49c1f9e137b9dab01a66.zip |
Add support for parsing field signatures (#21573)
This change adds basic field signature parsing support to R2RDump
and it improves parsing of two fixup types (FIELD_ADDRESS and
CCTOR_TRIGGER).
Thanks
Tomas
Diffstat (limited to 'src/tools')
-rw-r--r-- | src/tools/r2rdump/R2RSignature.cs | 78 |
1 files changed, 62 insertions, 16 deletions
diff --git a/src/tools/r2rdump/R2RSignature.cs b/src/tools/r2rdump/R2RSignature.cs index 852521ae24..a714383cf0 100644 --- a/src/tools/r2rdump/R2RSignature.cs +++ b/src/tools/r2rdump/R2RSignature.cs @@ -97,14 +97,34 @@ namespace R2RDump /// <param name="memberRefHandle">Member reference handle</param> private string EmitMemberReferenceName(MemberReferenceHandle memberRefHandle, string owningTypeOverride) { - MemberReference methodRef = _metadataReader.GetMemberReference(memberRefHandle); + MemberReference memberRef = _metadataReader.GetMemberReference(memberRefHandle); StringBuilder builder = new StringBuilder(); DisassemblingGenericContext genericContext = new DisassemblingGenericContext(Array.Empty<string>(), Array.Empty<string>()); - MethodSignature<String> methodSig = methodRef.DecodeMethodSignature<string, DisassemblingGenericContext>(this, genericContext); - builder.Append(methodSig.ReturnType); - builder.Append(" "); - builder.Append(EmitContainingTypeAndMethodName(methodRef, owningTypeOverride)); - builder.Append(EmitMethodSignature(methodSig)); + switch (memberRef.GetKind()) + { + case MemberReferenceKind.Field: + { + string fieldSig = memberRef.DecodeFieldSignature<string, DisassemblingGenericContext>(this, genericContext); + builder.Append(fieldSig); + builder.Append(" "); + builder.Append(EmitContainingTypeAndMemberName(memberRef, owningTypeOverride)); + break; + } + + case MemberReferenceKind.Method: + { + MethodSignature<String> methodSig = memberRef.DecodeMethodSignature<string, DisassemblingGenericContext>(this, genericContext); + builder.Append(methodSig.ReturnType); + builder.Append(" "); + builder.Append(EmitContainingTypeAndMemberName(memberRef, owningTypeOverride)); + builder.Append(EmitMethodSignature(methodSig)); + break; + } + + default: + throw new NotImplementedException(memberRef.GetKind().ToString()); + } + return builder.ToString(); } @@ -176,17 +196,17 @@ namespace R2RDump } /// <summary> - /// Emit containing type and method name and extract the method signature from a method reference. + /// Emit containing type and member name. /// </summary> - /// <param name="methodRef">Method reference to format</param> - /// <param name="methodSignature">Output method signature</param> - private string EmitContainingTypeAndMethodName(MemberReference methodRef, string owningTypeOverride) + /// <param name="memberRef">Member reference to format</param> + /// <param name="owningTypeOverride">Optional override for the owning type, null = MemberReference.Parent</param> + private string EmitContainingTypeAndMemberName(MemberReference memberRef, string owningTypeOverride) { if (owningTypeOverride == null) { - owningTypeOverride = EmitHandleName(methodRef.Parent, namespaceQualified: true, owningTypeOverride: null); + owningTypeOverride = EmitHandleName(memberRef.Parent, namespaceQualified: true, owningTypeOverride: null); } - return owningTypeOverride + "." + EmitString(methodRef.Name); + return owningTypeOverride + "." + EmitString(memberRef.Name); } /// <summary> @@ -550,13 +570,13 @@ namespace R2RDump case ReadyToRunFixupKind.READYTORUN_FIXUP_FieldAddress: - builder.Append("FIELD_ADDRESS"); - // TODO + ParseField(builder); + builder.Append(" (FIELD_ADDRESS)"); break; case ReadyToRunFixupKind.READYTORUN_FIXUP_CctorTrigger: - builder.Append("CCTOR_TRIGGER"); - // TODO + ParseType(builder); + builder.Append(" (CCTOR_TRIGGER)"); break; @@ -936,6 +956,32 @@ namespace R2RDump } /// <summary> + /// Parse field signature and output its textual representation into the given string builder. + /// </summary> + /// <param name="builder">Output string builder</param> + private void ParseField(StringBuilder builder) + { + uint flags = ReadUInt(); + string owningTypeOverride = null; + if ((flags & (uint)ReadyToRunFieldSigFlags.READYTORUN_FIELD_SIG_OwnerType) != 0) + { + StringBuilder owningTypeBuilder = new StringBuilder(); + ParseType(owningTypeBuilder); + owningTypeOverride = owningTypeBuilder.ToString(); + } + uint fieldToken; + if ((flags & (uint)ReadyToRunFieldSigFlags.READYTORUN_FIELD_SIG_MemberRefToken) != 0) + { + fieldToken = ReadUInt() | (uint)CorTokenType.mdtMemberRef; + } + else + { + fieldToken = ReadUInt() | (uint)CorTokenType.mdtFieldDef; + } + builder.Append(MetadataNameFormatter.FormatHandle(_metadataReader, MetadataTokens.Handle((int)fieldToken), namespaceQualified: false, owningTypeOverride: owningTypeOverride)); + } + + /// <summary> /// Read R2R helper signature. /// </summary> /// <returns></returns> |