From 75e06f1784fce6e8f26d8371631892f3f17a3efa Mon Sep 17 00:00:00 2001 From: Bar Arnon Date: Sun, 1 Aug 2021 17:57:43 +0300 Subject: [PATCH] Remove unused System.Reflection.Emit leftovers Follow up to #56153 --- .../System.Private.CoreLib.csproj | 4 +- .../Diagnostics/SymbolStore/ISymWriter.cs | 106 ---- .../System/Reflection/Emit/AssemblyBuilder.cs | 22 +- .../src/System/Reflection/Emit/ILGenerator.cs | 48 -- .../System/Reflection/Emit/ISymWrapperCore.cs | 529 ------------------ .../System/Reflection/Emit/LocalBuilder.cs | 67 --- .../System/Reflection/Emit/MethodBuilder.cs | 47 -- .../System/Reflection/Emit/ModuleBuilder.cs | 44 -- src/coreclr/vm/commodule.cpp | 130 ----- src/coreclr/vm/commodule.h | 4 - .../src/MatchingRefApiCompatBaseline.txt | 2 - ...patBaseline.netcoreapp.netfx461.ignore.txt | 2 - .../Reflection/Emit/LocalBuilder.Mono.cs | 12 - 13 files changed, 4 insertions(+), 1013 deletions(-) delete mode 100644 src/coreclr/System.Private.CoreLib/src/System/Diagnostics/SymbolStore/ISymWriter.cs delete mode 100644 src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ISymWrapperCore.cs diff --git a/src/coreclr/System.Private.CoreLib/System.Private.CoreLib.csproj b/src/coreclr/System.Private.CoreLib/System.Private.CoreLib.csproj index bc40c0e483085..36b4d648bdfb2 100644 --- a/src/coreclr/System.Private.CoreLib/System.Private.CoreLib.csproj +++ b/src/coreclr/System.Private.CoreLib/System.Private.CoreLib.csproj @@ -1,4 +1,4 @@ - + false @@ -136,7 +136,6 @@ - @@ -166,7 +165,6 @@ - diff --git a/src/coreclr/System.Private.CoreLib/src/System/Diagnostics/SymbolStore/ISymWriter.cs b/src/coreclr/System.Private.CoreLib/src/System/Diagnostics/SymbolStore/ISymWriter.cs deleted file mode 100644 index f3ad88e9ef22d..0000000000000 --- a/src/coreclr/System.Private.CoreLib/src/System/Diagnostics/SymbolStore/ISymWriter.cs +++ /dev/null @@ -1,106 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. - -/*============================================================ -** -** -** -** Represents a symbol writer for managed code. Provides methods to -** define documents, sequence points, lexical scopes, and variables. -** -** -===========================================================*/ - -using System.Reflection; - -namespace System.Diagnostics.SymbolStore -{ - // Interface does not need to be marked with the serializable attribute - internal interface ISymbolWriter - { - // Define a source document. Guid's will be provided for the - // languages, vendors, and document types that we currently know - // about. - ISymbolDocumentWriter? DefineDocument(string url, - Guid language, - Guid languageVendor, - Guid documentType); - - // Open a method to emit symbol information into. The given method - // becomes the current method for calls do define sequence points, - // parameters and lexical scopes. There is an implicit lexical - // scope around the entire method. Re-opening a method that has - // been previously closed effectivley erases any previously - // defined symbols for that method. - // - // There can be only one open method at a time. - void OpenMethod(SymbolToken method); - - // Close the current method. Once a method is closed, no more - // symbols can be defined within it. - void CloseMethod(); - - // Define a group of sequence points within the current method. - // Each line/column defines the start of a statement within a - // method. The arrays should be sorted by offset. The offset is - // always the offset from the start of the method, in bytes. - void DefineSequencePoints(ISymbolDocumentWriter document, - int[] offsets, - int[] lines, - int[] columns, - int[] endLines, - int[] endColumns); - - // Open a new lexical scope in the current method. The scope - // becomes the new current scope and is effectivley pushed onto a - // stack of scopes. startOffset is the offset, in bytes from the - // beginning of the method, of the first instruction in the - // lexical scope. Scopes must form a hierarchy. Siblings are not - // allowed to overlap. - // - // OpenScope returns an opaque scope id that can be used with - // SetScopeRange to define a scope's start/end offset at a later - // time. In this case, the offsets passed to OpenScope and - // CloseScope are ignored. - // - // Note: scope id's are only valid in the current method. - // - - int OpenScope(int startOffset); - - // Close the current lexical scope. Once a scope is closed no more - // variables can be defined within it. endOffset points past the - // last instruction in the scope. - void CloseScope(int endOffset); - - // Define a single variable in the current lexical - // scope. startOffset and endOffset are optional. If 0, then they - // are ignored and the variable is defined over the entire - // scope. If non-zero, then they must fall within the offsets of - // the current scope. This can be called multiple times for a - // variable of the same name that has multiple homes throughout a - // scope. (Note: start/end offsets must not overlap in such a - // case.) - void DefineLocalVariable(string name, - FieldAttributes attributes, - byte[] signature, - SymAddressKind addrKind, - int addr1, - int addr2, - int addr3, - int startOffset, - int endOffset); - - // Defines a custom attribute based upon its name. Not to be - // confused with Metadata custom attributes, these attributes are - // held in the symbol store. - void SetSymAttribute(SymbolToken parent, string name, byte[] data); - - // Specifies that the given, fully qualified namespace name is - // being used within the currently open lexical scope. Closing the - // current scope will also stop using the namespace, and the - // namespace will be in use in all scopes that inherit from the - // currently open scope. - void UsingNamespace(string fullName); - } -} diff --git a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/AssemblyBuilder.cs b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/AssemblyBuilder.cs index 0914c0ca7600c..6df43fcf24256 100644 --- a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/AssemblyBuilder.cs +++ b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/AssemblyBuilder.cs @@ -304,18 +304,15 @@ internal static AssemblyBuilder InternalDefineDynamicAssembly( /// a transient module. /// [DynamicSecurityMethod] // Methods containing StackCrawlMark local var has to be marked DynamicSecurityMethod. - public ModuleBuilder DefineDynamicModule(string name) => - DefineDynamicModuleInternal(name, emitSymbolInfo: false); - - private ModuleBuilder DefineDynamicModuleInternal(string name, bool emitSymbolInfo) + public ModuleBuilder DefineDynamicModule(string name) { lock (SyncRoot) { - return DefineDynamicModuleInternalNoLock(name, emitSymbolInfo); + return DefineDynamicModuleInternalNoLock(name); } } - private ModuleBuilder DefineDynamicModuleInternalNoLock(string name, bool emitSymbolInfo) + private ModuleBuilder DefineDynamicModuleInternalNoLock(string name) { if (name == null) { @@ -341,19 +338,6 @@ private ModuleBuilder DefineDynamicModuleInternalNoLock(string name, bool emitSy // Init(...) has already been called on _manifestModuleBuilder in InitManifestModule() ModuleBuilder dynModule = _manifestModuleBuilder; - // Create the symbol writer - ISymbolWriter? writer = null; - if (emitSymbolInfo) - { - writer = SymWrapperCore.SymWriter.CreateSymWriter(); - - // Pass the "real" module to the VM. - // This symfile is never written to disk so filename does not matter. - IntPtr pInternalSymWriter = ModuleBuilder.nCreateISymWriterForDynamicModule(dynModule.InternalModule, "Unused"); - ((SymWrapperCore.SymWriter)writer).InternalSetUnderlyingWriter(pInternalSymWriter); - } - - dynModule.SetSymWriter(writer); _assemblyData._moduleBuilderList.Add(dynModule); if (dynModule == _manifestModuleBuilder) diff --git a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ILGenerator.cs b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ILGenerator.cs index 23a973f15ae34..b5094b0b3ddd2 100644 --- a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ILGenerator.cs +++ b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ILGenerator.cs @@ -1681,25 +1681,6 @@ internal void EnsureCapacity() } } - internal void EmitScopeTree(ISymbolWriter symWriter) - { - for (int i = 0; i < m_iCount; i++) - { - if (m_ScopeActions[i] == ScopeAction.Open) - { - symWriter.OpenScope(m_iOffsets[i]); - } - else - { - symWriter.CloseScope(m_iOffsets[i]); - } - if (m_localSymInfos[i] is LocalSymInfo lsi) - { - lsi.EmitLocalSymInfo(symWriter); - } - } - } - internal int[] m_iOffsets = null!; // array of offsets internal ScopeAction[] m_ScopeActions = null!; // array of scope actions internal int m_iCount; // how many entries in the arrays are occupied @@ -1780,12 +1761,6 @@ private void EnsureCapacity() } } - internal void EmitLineNumberInfo(ISymbolWriter symWriter) - { - for (int i = 0; i < m_DocumentCount; i++) - m_Documents[i].EmitLineNumberInfo(symWriter); - } - private int m_DocumentCount; // how many documents that we have right now private REDocument[] m_Documents = null!; // array of documents private const int InitialSize = 16; @@ -1866,29 +1841,6 @@ private void EnsureCapacity() } } - internal void EmitLineNumberInfo(ISymbolWriter symWriter) - { - if (m_iLineNumberCount == 0) - return; - // reduce the array size to be exact - int[] iOffsetsTemp = new int[m_iLineNumberCount]; - Array.Copy(m_iOffsets, iOffsetsTemp, m_iLineNumberCount); - - int[] iLinesTemp = new int[m_iLineNumberCount]; - Array.Copy(m_iLines, iLinesTemp, m_iLineNumberCount); - - int[] iColumnsTemp = new int[m_iLineNumberCount]; - Array.Copy(m_iColumns, iColumnsTemp, m_iLineNumberCount); - - int[] iEndLinesTemp = new int[m_iLineNumberCount]; - Array.Copy(m_iEndLines, iEndLinesTemp, m_iLineNumberCount); - - int[] iEndColumnsTemp = new int[m_iLineNumberCount]; - Array.Copy(m_iEndColumns, iEndColumnsTemp, m_iLineNumberCount); - - symWriter.DefineSequencePoints(m_document, iOffsetsTemp, iLinesTemp, iColumnsTemp, iEndLinesTemp, iEndColumnsTemp); - } - private int[] m_iOffsets = null!; // array of offsets private int[] m_iLines = null!; // array of offsets private int[] m_iColumns = null!; // array of offsets diff --git a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ISymWrapperCore.cs b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ISymWrapperCore.cs deleted file mode 100644 index 72e3edbd65bae..0000000000000 --- a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ISymWrapperCore.cs +++ /dev/null @@ -1,529 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. - -using System.Runtime.InteropServices; -using System.Runtime.CompilerServices; -using System.Diagnostics.SymbolStore; - -namespace System.Reflection.Emit -{ - //----------------------------------------------------------------------------------- - // On Telesto, we don't ship the ISymWrapper.dll assembly. However, ReflectionEmit - // relies on that assembly to write out managed PDBs. - // - // This file implements the minimum subset of ISymWrapper.dll required to restore - // that functionality. Namely, the SymWriter and SymDocumentWriter objects. - // - // Ideally we wouldn't need ISymWrapper.dll on .NET Framework either - it's an ugly piece - // of legacy. We could just use this (or COM-interop code) everywhere, but we might - // have to worry about compatibility. - // - // We've now got a real implementation even when no debugger is attached. It's - // up to the runtime to ensure it doesn't provide us with an insecure writer - // (eg. diasymreader) in the no-trust scenarios (no debugger, partial-trust code). - //----------------------------------------------------------------------------------- - - - //------------------------------------------------------------------------------ - // SymWrapperCore is never instantiated and is used as an encapsulation class. - // It is our "ISymWrapper.dll" assembly within an assembly. - //------------------------------------------------------------------------------ - internal sealed class SymWrapperCore - { - //------------------------------------------------------------------------------ - // Block instantiation - //------------------------------------------------------------------------------ - private SymWrapperCore() - { - } - - //------------------------------------------------------------------------------ - // Implements Telesto's version of SymDocumentWriter (in the .NET Framework world, - // this type is exposed from ISymWrapper.dll.) - // - // The only thing user code can do with this wrapper is to receive it from - // SymWriter.DefineDocument and pass it back to SymWriter.DefineSequencePoints. - //------------------------------------------------------------------------------ - private unsafe class SymDocumentWriter : ISymbolDocumentWriter - { - //------------------------------------------------------------------------------ - // Ctor - //------------------------------------------------------------------------------ - internal SymDocumentWriter(PunkSafeHandle pDocumentWriterSafeHandle) - { - m_pDocumentWriterSafeHandle = pDocumentWriterSafeHandle; - // The handle is actually a pointer to a native ISymUnmanagedDocumentWriter. - m_pDocWriter = (ISymUnmanagedDocumentWriter*)m_pDocumentWriterSafeHandle.DangerousGetHandle(); - m_vtable = (ISymUnmanagedDocumentWriterVTable)(Marshal.PtrToStructure(m_pDocWriter->m_unmanagedVTable, typeof(ISymUnmanagedDocumentWriterVTable)))!; - } - - //------------------------------------------------------------------------------ - // Returns the underlying ISymUnmanagedDocumentWriter* (as a safehandle.) - //------------------------------------------------------------------------------ - internal PunkSafeHandle GetUnmanaged() - { - return m_pDocumentWriterSafeHandle; - } - - - // ========================================================================================= - // Public interface methods start here. (Well actually, they're all NotSupported - // stubs since that's what they are on the real ISymWrapper.dll.) - // ========================================================================================= - - //------------------------------------------------------------------------------ - // SetSource() wrapper - //------------------------------------------------------------------------------ - void ISymbolDocumentWriter.SetSource(byte[] source) - { - throw new NotSupportedException(); // Intentionally not supported to match .NET Framework - } - - //------------------------------------------------------------------------------ - // SetCheckSum() wrapper - //------------------------------------------------------------------------------ - void ISymbolDocumentWriter.SetCheckSum(Guid algorithmId, byte[] checkSum) - { - int hr = m_vtable.SetCheckSum(m_pDocWriter, algorithmId, (uint)checkSum.Length, checkSum); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - private delegate int DSetCheckSum(ISymUnmanagedDocumentWriter* pThis, Guid algorithmId, uint checkSumSize, [In] byte[] checkSum); - - //------------------------------------------------------------------------------ - // This layout must match the unmanaged ISymUnmanagedDocumentWriter* COM vtable - // exactly. If a member is declared as an IntPtr rather than a delegate, it means - // we don't call that particular member. - //------------------------------------------------------------------------------ - [StructLayout(LayoutKind.Sequential)] - private struct ISymUnmanagedDocumentWriterVTable - { - internal IntPtr QueryInterface; - internal IntPtr AddRef; - internal IntPtr Release; - - internal IntPtr SetSource; - internal DSetCheckSum SetCheckSum; - } - - //------------------------------------------------------------------------------ - // This layout must match the (start) of the unmanaged ISymUnmanagedDocumentWriter - // COM object. - //------------------------------------------------------------------------------ - [StructLayout(LayoutKind.Sequential)] - private struct ISymUnmanagedDocumentWriter - { - internal IntPtr m_unmanagedVTable; - } - - //------------------------------------------------------------------------------ - // Stores underlying ISymUnmanagedDocumentWriter* pointer (wrapped in a safehandle.) - //------------------------------------------------------------------------------ - private PunkSafeHandle m_pDocumentWriterSafeHandle; - - private ISymUnmanagedDocumentWriter* m_pDocWriter; - - //------------------------------------------------------------------------------ - // Stores the "managed vtable" (actually a structure full of delegates that - // P/Invoke to the corresponding unmanaged COM methods.) - //------------------------------------------------------------------------------ - private ISymUnmanagedDocumentWriterVTable m_vtable; - } // class SymDocumentWriter - - - //------------------------------------------------------------------------------ - // Implements Telesto's version of SymWriter (in the .NET Framework world, - // this type is expored from ISymWrapper.dll.) - //------------------------------------------------------------------------------ - internal unsafe class SymWriter : ISymbolWriter - { - //------------------------------------------------------------------------------ - // Creates a SymWriter. The SymWriter is a managed wrapper around the unmanaged - // symbol writer provided by the runtime (ildbsymlib or diasymreader.dll). - //------------------------------------------------------------------------------ - internal static ISymbolWriter CreateSymWriter() - { - return new SymWriter(); - } - - - //------------------------------------------------------------------------------ - // Basic ctor. You'd think this ctor would take the unmanaged symwriter object as an argument - // but to fit in with existing .NET Framework code, the unmanaged writer is passed in - // through a subsequent call to InternalSetUnderlyingWriter - //------------------------------------------------------------------------------ - private SymWriter() - { - } - - //------------------------------------------------------------------------------ - // DefineDocument() wrapper - //------------------------------------------------------------------------------ - ISymbolDocumentWriter? ISymbolWriter.DefineDocument(string url, - Guid language, - Guid languageVendor, - Guid documentType) - { - int hr = m_vtable.DefineDocument(m_pWriter, url, ref language, ref languageVendor, ref documentType, out PunkSafeHandle psymUnmanagedDocumentWriter); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - if (psymUnmanagedDocumentWriter.IsInvalid) - { - return null; - } - return new SymDocumentWriter(psymUnmanagedDocumentWriter); - } - - //------------------------------------------------------------------------------ - // OpenMethod() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.OpenMethod(SymbolToken method) - { - int hr = m_vtable.OpenMethod(m_pWriter, method.GetToken()); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // CloseMethod() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.CloseMethod() - { - int hr = m_vtable.CloseMethod(m_pWriter); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // DefineSequencePoints() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.DefineSequencePoints(ISymbolDocumentWriter document, - int[] offsets, - int[] lines, - int[] columns, - int[] endLines, - int[] endColumns) - { - int spCount = 0; - if (offsets != null) - { - spCount = offsets.Length; - } - else if (lines != null) - { - spCount = lines.Length; - } - else if (columns != null) - { - spCount = columns.Length; - } - else if (endLines != null) - { - spCount = endLines.Length; - } - else if (endColumns != null) - { - spCount = endColumns.Length; - } - if (spCount == 0) - { - return; - } - if ((offsets != null && offsets.Length != spCount) || - (lines != null && lines.Length != spCount) || - (columns != null && columns.Length != spCount) || - (endLines != null && endLines.Length != spCount) || - (endColumns != null && endColumns.Length != spCount)) - { - throw new ArgumentException(); - } - - // Sure, claim to accept any type that implements ISymbolDocumentWriter but the only one that actually - // works is the one returned by DefineDocument. The .NET Framework ISymWrapper commits the same signature fraud. - // Ideally we'd just return a sealed opaque cookie type, which had an internal accessor to - // get the writer out. - // Regardless, this cast is important for security - we cannot allow our caller to provide - // arbitrary instances of this interface. - SymDocumentWriter docwriter = (SymDocumentWriter)document; - int hr = m_vtable.DefineSequencePoints(m_pWriter, docwriter.GetUnmanaged(), spCount!, offsets!, lines!, columns!, endLines!, endColumns!); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // OpenScope() wrapper - //------------------------------------------------------------------------------ - int ISymbolWriter.OpenScope(int startOffset) - { - int hr = m_vtable.OpenScope(m_pWriter, startOffset, out int ret); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - return ret; - } - - //------------------------------------------------------------------------------ - // CloseScope() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.CloseScope(int endOffset) - { - int hr = m_vtable.CloseScope(m_pWriter, endOffset); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // DefineLocalVariable() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.DefineLocalVariable(string name, - FieldAttributes attributes, - byte[] signature, - SymAddressKind addrKind, - int addr1, - int addr2, - int addr3, - int startOffset, - int endOffset) - { - int hr = m_vtable.DefineLocalVariable(m_pWriter, - name, - (int)attributes, - signature.Length, - signature, - (int)addrKind, - addr1, - addr2, - addr3, - startOffset, - endOffset); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // SetSymAttribute() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.SetSymAttribute(SymbolToken parent, string name, byte[] data) - { - int hr = m_vtable.SetSymAttribute(m_pWriter, parent.GetToken(), name, data.Length, data); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // UsingNamespace() wrapper - //------------------------------------------------------------------------------ - void ISymbolWriter.UsingNamespace(string name) - { - int hr = m_vtable.UsingNamespace(m_pWriter, name); - if (hr < 0) - { - throw Marshal.GetExceptionForHR(hr)!; - } - } - - //------------------------------------------------------------------------------ - // InternalSetUnderlyingWriter() wrapper. - // - // Furnishes the native ISymUnmanagedWriter* pointer. - // - // The parameter is actually a pointer to a pointer to an ISymUnmanagedWriter. As - // with the real ISymWrapper.dll, ISymWrapper performs *no* Release (or AddRef) on pointers - // furnished through SetUnderlyingWriter. Lifetime management is entirely up to the caller. - //------------------------------------------------------------------------------ - internal void InternalSetUnderlyingWriter(IntPtr ppUnderlyingWriter) - { - m_pWriter = *((ISymUnmanagedWriter**)ppUnderlyingWriter); - m_vtable = (ISymUnmanagedWriterVTable)(Marshal.PtrToStructure(m_pWriter->m_unmanagedVTable, typeof(ISymUnmanagedWriterVTable)))!; - } - - //------------------------------------------------------------------------------ - // Define delegates for the unmanaged COM methods we invoke. - //------------------------------------------------------------------------------ - private delegate int DInitialize(ISymUnmanagedWriter* pthis, - IntPtr emitter, // IUnknown* - [MarshalAs(UnmanagedType.LPWStr)] string filename, // WCHAR* - IntPtr pIStream, // IStream* - [MarshalAs(UnmanagedType.Bool)] bool fFullBuild - ); - - private delegate int DDefineDocument(ISymUnmanagedWriter* pthis, - [MarshalAs(UnmanagedType.LPWStr)] string url, - [In] ref Guid language, - [In] ref Guid languageVender, - [In] ref Guid documentType, - [Out] out PunkSafeHandle ppsymUnmanagedDocumentWriter - ); - - private delegate int DSetUserEntryPoint(ISymUnmanagedWriter* pthis, int entryMethod); - private delegate int DOpenMethod(ISymUnmanagedWriter* pthis, int entryMethod); - private delegate int DCloseMethod(ISymUnmanagedWriter* pthis); - - private delegate int DDefineSequencePoints(ISymUnmanagedWriter* pthis, - PunkSafeHandle document, - int spCount, - [In] int[] offsets, - [In] int[] lines, - [In] int[] columns, - [In] int[] endLines, - [In] int[] endColumns); - - private delegate int DOpenScope(ISymUnmanagedWriter* pthis, int startOffset, [Out] out int pretval); - private delegate int DCloseScope(ISymUnmanagedWriter* pthis, int endOffset); - - private delegate int DSetScopeRange(ISymUnmanagedWriter* pthis, int scopeID, int startOffset, int endOffset); - - private delegate int DDefineLocalVariable(ISymUnmanagedWriter* pthis, - [MarshalAs(UnmanagedType.LPWStr)] string name, - int attributes, - int cSig, - [In] byte[] signature, - int addrKind, - int addr1, - int addr2, - int addr3, - int startOffset, - int endOffset - ); - - private delegate int DClose(ISymUnmanagedWriter* pthis); - - private delegate int DSetSymAttribute(ISymUnmanagedWriter* pthis, - int parent, - [MarshalAs(UnmanagedType.LPWStr)] string name, - int cData, - [In] byte[] data - ); - - - private delegate int DOpenNamespace(ISymUnmanagedWriter* pthis, [MarshalAs(UnmanagedType.LPWStr)] string name); - private delegate int DCloseNamespace(ISymUnmanagedWriter* pthis); - private delegate int DUsingNamespace(ISymUnmanagedWriter* pthis, [MarshalAs(UnmanagedType.LPWStr)] string name); - - - - //------------------------------------------------------------------------------ - // This layout must match the unmanaged ISymUnmanagedWriter* COM vtable - // exactly. If a member is declared as an IntPtr rather than a delegate, it means - // we don't call that particular member. - //------------------------------------------------------------------------------ - [StructLayout(LayoutKind.Sequential)] - private struct ISymUnmanagedWriterVTable - { - internal IntPtr QueryInterface; - internal IntPtr AddRef; - internal IntPtr Release; - - internal DDefineDocument DefineDocument; - internal DSetUserEntryPoint SetUserEntryPoint; - - internal DOpenMethod OpenMethod; - internal DCloseMethod CloseMethod; - - internal DOpenScope OpenScope; - internal DCloseScope CloseScope; - - internal DSetScopeRange SetScopeRange; - - internal DDefineLocalVariable DefineLocalVariable; - internal IntPtr DefineParameter; - internal IntPtr DefineField; - internal IntPtr DefineGlobalVariable; - - internal DClose Close; - internal DSetSymAttribute SetSymAttribute; - - internal DOpenNamespace OpenNamespace; - internal DCloseNamespace CloseNamespace; - internal DUsingNamespace UsingNamespace; - - internal IntPtr SetMethodSourceRange; - internal DInitialize Initialize; - internal IntPtr GetDebugInfo; - internal DDefineSequencePoints DefineSequencePoints; - } - - //------------------------------------------------------------------------------ - // This layout must match the (start) of the unmanaged ISymUnmanagedWriter - // COM object. - //------------------------------------------------------------------------------ - [StructLayout(LayoutKind.Sequential)] - private struct ISymUnmanagedWriter - { - internal IntPtr m_unmanagedVTable; - } - - //------------------------------------------------------------------------------ - // Stores native ISymUnmanagedWriter* pointer. - // - // As with the real ISymWrapper.dll, ISymWrapper performs *no* Release (or AddRef) on this pointer. - // Managing lifetime is up to the caller (coreclr.dll). - //------------------------------------------------------------------------------ - private ISymUnmanagedWriter* m_pWriter; - - //------------------------------------------------------------------------------ - // Stores the "managed vtable" (actually a structure full of delegates that - // P/Invoke to the corresponding unmanaged COM methods.) - //------------------------------------------------------------------------------ - private ISymUnmanagedWriterVTable m_vtable; - } // class SymWriter - } // class SymWrapperCore - - - - //-------------------------------------------------------------------------------------- - // SafeHandle for RAW MTA IUnknown's. - // - // ! Because the Release occurs in the finalizer thread, this safehandle really takes - // ! an ostrich approach to apartment issues. We only tolerate this here because we're emulating - // ! the .NET Framework's use of ISymWrapper which also pays lip service to COM apartment rules. - // ! - // ! However, think twice about pulling this safehandle out for other uses. - // - // Had to make this a non-nested class since FCall's don't like to bind to nested classes. - //-------------------------------------------------------------------------------------- - internal sealed class PunkSafeHandle : SafeHandle - { - public PunkSafeHandle() - : base((IntPtr)0, true) - { - } - - protected override bool ReleaseHandle() - { - m_Release(handle); - return true; - } - - public override bool IsInvalid => handle == ((IntPtr)0); - - private delegate void DRelease(IntPtr punk); // Delegate type for P/Invoking to coreclr.dll and doing an IUnknown::Release() - private static DRelease m_Release = (DRelease)Marshal.GetDelegateForFunctionPointer(nGetDReleaseTarget(), typeof(DRelease)); - - [MethodImpl(MethodImplOptions.InternalCall)] - private static extern IntPtr nGetDReleaseTarget(); // FCall gets us the native DRelease target (so we don't need named dllexport from coreclr.dll) - - static PunkSafeHandle() - { - m_Release((IntPtr)0); // make one call to make sure the delegate is fully prepped before we're in the critical finalizer situation. - } - } // PunkSafeHandle -} // namespace System.Reflection.Emit diff --git a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.cs b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.cs index eb82f5f58fcdf..e79c026514155 100644 --- a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.cs +++ b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.cs @@ -40,72 +40,5 @@ internal MethodInfo GetMethodBuilder() public override Type LocalType => m_localType; public override int LocalIndex => m_localIndex; #endregion - - #region Public Members - public void SetLocalSymInfo(string name) - { - SetLocalSymInfo(name, 0, 0); - } - - public void SetLocalSymInfo(string name, int startOffset, int endOffset) - { - ModuleBuilder dynMod; - SignatureHelper sigHelp; - byte[] signature; - byte[] mungedSig; - int index; - - MethodBuilder? methodBuilder = m_methodBuilder as MethodBuilder; - if (methodBuilder == null) - // it's a light code gen entity - throw new NotSupportedException(); - dynMod = (ModuleBuilder)methodBuilder.Module; - if (methodBuilder.IsTypeCreated()) - { - // cannot change method after its containing type has been created - throw new InvalidOperationException(SR.InvalidOperation_TypeHasBeenCreated); - } - - // set the name and range of offset for the local - if (dynMod.GetSymWriter() == null) - { - // cannot set local name if not debug module - throw new InvalidOperationException(SR.InvalidOperation_NotADebugModule); - } - - sigHelp = SignatureHelper.GetFieldSigHelper(dynMod); - sigHelp.AddArgument(m_localType); - signature = sigHelp.InternalGetSignature(out int sigLength); - - // The symbol store doesn't want the calling convention on the - // front of the signature, but InternalGetSignature returns - // the callinging convention. So we strip it off. This is a - // bit unfortunate, since it means that we need to allocate - // yet another array of bytes... - mungedSig = new byte[sigLength - 1]; - Buffer.BlockCopy(signature, 1, mungedSig, 0, sigLength - 1); - - index = methodBuilder.GetILGenerator().m_ScopeTree.GetCurrentActiveScopeIndex(); - if (index == -1) - { - // top level scope information is kept with methodBuilder - methodBuilder.m_localSymInfo!.AddLocalSymInfo( - name, - mungedSig, - m_localIndex, - startOffset, - endOffset); - } - else - { - methodBuilder.GetILGenerator().m_ScopeTree.AddLocalSymInfoToCurrentScope( - name, - mungedSig, - m_localIndex, - startOffset, - endOffset); - } - } - #endregion } } diff --git a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/MethodBuilder.cs b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/MethodBuilder.cs index e2df0f5313ece..d11a667946210 100644 --- a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/MethodBuilder.cs +++ b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/MethodBuilder.cs @@ -227,30 +227,6 @@ internal void CreateMethodBodyHelper(ILGenerator il) } m_bIsBaked = true; - - if (dynMod.GetSymWriter() != null) - { - // set the debugging information such as scope and line number - // if it is in a debug module - // - SymbolToken tk = new SymbolToken(MetadataToken); - ISymbolWriter symWriter = dynMod.GetSymWriter()!; - - // call OpenMethod to make this method the current method - symWriter.OpenMethod(tk); - - // call OpenScope because OpenMethod no longer implicitly creating - // the top-levelsmethod scope - // - symWriter.OpenScope(0); - - if (m_localSymInfo != null) - m_localSymInfo.EmitLocalSymInfo(symWriter); - il.m_ScopeTree.EmitScopeTree(symWriter); - il.m_LineNumberInfo.EmitLineNumberInfo(symWriter); - symWriter.CloseScope(il.ILOffset); - symWriter.CloseMethod(); - } } // This is only called from TypeBuilder.CreateType after the method has been created @@ -927,29 +903,6 @@ internal void AddUsingNamespace(string strNamespace) checked { m_iNameSpaceCount++; } } - internal void EmitLocalSymInfo(ISymbolWriter symWriter) - { - int i; - - for (i = 0; i < m_iLocalSymCount; i++) - { - symWriter.DefineLocalVariable( - m_strName[i], - FieldAttributes.PrivateScope, - m_ubSignature[i], - SymAddressKind.ILOffset, - m_iLocalSlot[i], - 0, // addr2 is not used yet - 0, // addr3 is not used - m_iStartOffset[i], - m_iEndOffset[i]); - } - for (i = 0; i < m_iNameSpaceCount; i++) - { - symWriter.UsingNamespace(m_namespace[i]); - } - } - #endregion } diff --git a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ModuleBuilder.cs b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ModuleBuilder.cs index 230bb06bd810e..c5780c919b42a 100644 --- a/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ModuleBuilder.cs +++ b/src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/ModuleBuilder.cs @@ -38,9 +38,6 @@ public override bool Equals(object? obj) // deliberately not [serializable] public class ModuleBuilder : Module { - [MethodImpl(MethodImplOptions.InternalCall)] - internal static extern IntPtr nCreateISymWriterForDynamicModule(Module module, string filename); - internal static string UnmangleTypeName(string typeName) { // Gets the original type name, without '+' name mangling. @@ -77,7 +74,6 @@ internal static string UnmangleTypeName(string typeName) // _TypeBuilder contains both TypeBuilder and EnumBuilder objects private Dictionary _typeBuilderDict = null!; - private ISymbolWriter? _iSymWriter; internal ModuleBuilderData _moduleData = null!; internal InternalModuleBuilder _internalModuleBuilder; // This is the "external" AssemblyBuilder @@ -321,8 +317,6 @@ internal void Init(string strModuleName) _typeBuilderDict = new Dictionary(); } - internal void SetSymWriter(ISymbolWriter? writer) => _iSymWriter = writer; - internal object SyncRoot => ContainingAssemblyBuilder.SyncRoot; #endregion @@ -1573,44 +1567,6 @@ public void SetCustomAttribute(CustomAttributeBuilder customBuilder) customBuilder.CreateCustomAttribute(this, 1); // This is hard coding the module token to 1 } - // This API returns the symbol writer being used to write debug symbols for this - // module (if any). - // - // WARNING: It is unlikely this API can be used correctly by applications in any - // reasonable way. It may be called internally from within TypeBuilder.CreateType. - // - // Specifically: - // 1. The underlying symbol writer (written in unmanaged code) is not necessarily well - // hardenned and fuzz-tested against malicious API calls. The security of partial-trust - // symbol writing is improved by restricting usage of the writer APIs to the well-structured - // uses in ModuleBuilder. - // 2. TypeBuilder.CreateType emits all the symbols for the type. This will effectively - // overwrite anything someone may have written manually about the type (specifically - // ISymbolWriter.OpenMethod is specced to clear anything previously written for the - // specified method) - // 3. Someone could technically update the symbols for a method after CreateType is - // called, but the debugger (which uses these symbols) assumes that they are only - // updated at TypeBuilder.CreateType time. The changes wouldn't be visible (committed - // to the underlying stream) until another type was baked. - // 4. Access to the writer is supposed to be synchronized (the underlying COM API is - // not thread safe, and these are only thin wrappers on top of them). Exposing this - // directly allows the synchronization to be violated. We know that concurrent symbol - // writer access can cause AVs and other problems. The writer APIs should not be callable - // directly by partial-trust code, but if they could this would be a security hole. - // Regardless, this is a reliability bug. - internal ISymbolWriter? GetSymWriter() => _iSymWriter; - - private ISymbolDocumentWriter? DefineDocumentNoLock(string url, Guid language, Guid languageVendor, Guid documentType) - { - if (_iSymWriter == null) - { - // Cannot DefineDocument when it is not a debug module - throw new InvalidOperationException(SR.InvalidOperation_NotADebugModule); - } - - return _iSymWriter.DefineDocument(url, language, languageVendor, documentType); - } - #endregion #endregion diff --git a/src/coreclr/vm/commodule.cpp b/src/coreclr/vm/commodule.cpp index f1ac719c5046a..f38b8797e3a0a 100644 --- a/src/coreclr/vm/commodule.cpp +++ b/src/coreclr/vm/commodule.cpp @@ -14,136 +14,6 @@ #include "ildbsymlib.h" -//=============================================================================================== -// CreateISymWriterforDynamicModule: -// Helper to create a ISymUnmanagedWriter instance and hook it up to a newly created dynamic -// module. This object is used to capture debugging information (source line info, etc.) -// for the dynamic module. This function determines the appropriate symbol format type -// (ILDB or PDB), and in the case of PDB (Windows desktop only) loads diasymreader.dll. -// -// Arguments: -// mod - The ReflectionModule for the new dynamic module -// filenameTemp - the filename at which the module may be saved (ignored if no save access) -// -// Return value: -// The address where the new writer instance has been stored -//=============================================================================================== -static ISymUnmanagedWriter **CreateISymWriterForDynamicModule(ReflectionModule *mod, const WCHAR *wszFilename) -{ - STANDARD_VM_CONTRACT; - - _ASSERTE(mod->IsReflection()); - - // Determine which symbol format to use. For Silverlight 2.0 RTM we use ILDB mode to address security - // and portability issues with diasymreader. - // - // For desktop builds we'll eventually want to make ILDB is the default, but we need to emit PDB format if - // the symbols can be saved to disk to preserve back compat. - // - ESymbolFormat symFormatToUse = eSymbolFormatILDB; - - - static ConfigDWORD dbgForcePDBSymbols; - if(dbgForcePDBSymbols.val(CLRConfig::INTERNAL_DbgForcePDBSymbols) == 1) - { - symFormatToUse = eSymbolFormatPDB; - } - - // Create a stream for the symbols to be emitted into. This - // lives on the Module for the life of the Module. - SafeComHolder pStream(new CGrowableStream()); - - mod->SetInMemorySymbolStream(pStream, symFormatToUse); - - // Create an ISymUnmanagedWriter and initialize it with the - // stream and the proper file name. This symbol writer will be - // replaced with new ones periodically as the symbols get - // retrieved by the debugger. - SafeComHolder pWriter; - - HRESULT hr; - if (symFormatToUse == eSymbolFormatILDB) - { - // Create an ILDB symbol writer from the ildbsymbols library statically linked in - hr = IldbSymbolsCreateInstance(CLSID_CorSymWriter_SxS, - IID_ISymUnmanagedWriter, - (void**)&pWriter); - } - else - { - _ASSERTE(symFormatToUse == eSymbolFormatPDB); - hr = FakeCoCreateInstanceEx(CLSID_CorSymWriter_SxS, - GetInternalSystemDirectory(), - IID_ISymUnmanagedWriter, - (void**)&pWriter, - NULL); - } - - if (SUCCEEDED(hr)) - { - { - GCX_PREEMP(); - - // The other reference is given to the Sym Writer - // But, the writer takes it's own reference. - hr = pWriter->Initialize(mod->GetEmitter(), - wszFilename, - (IStream*)pStream, - TRUE); - } - if (SUCCEEDED(hr)) - { - mod->GetReflectionModule()->SetISymUnmanagedWriter(pWriter.Extract()); - - // Return the address of where we've got our - // ISymUnmanagedWriter stored so we can pass it over - // to the managed symbol writer object that most of - // reflection emit will use to write symbols. - return mod->GetISymUnmanagedWriterAddr(); - } - else - { - COMPlusThrowHR(hr); - } - } - else - { - COMPlusThrowHR(hr); - } -} - -//=============================================================================================== -// Attaches an unmanaged symwriter to a newly created dynamic module. -//=============================================================================================== -FCIMPL2(LPVOID, COMModule::nCreateISymWriterForDynamicModule, ReflectModuleBaseObject* reflectionModuleUNSAFE, StringObject* filenameUNSAFE) -{ - FCALL_CONTRACT; - - REFLECTMODULEBASEREF refModule = (REFLECTMODULEBASEREF)ObjectToOBJECTREF(reflectionModuleUNSAFE); - - ReflectionModule *mod = (ReflectionModule*)refModule->GetModule(); - STRINGREF filename = (STRINGREF)filenameUNSAFE; - - LPVOID pInternalSymWriter = NULL; - - HELPER_METHOD_FRAME_BEGIN_RET_2(filename, refModule); - - SString name; - if (filename != NULL) - { - filename->GetSString(name); - } - - GCX_PREEMP(); - pInternalSymWriter = CreateISymWriterForDynamicModule(mod, name.GetUnicode()); - - HELPER_METHOD_FRAME_END(); - - return pInternalSymWriter; - -} // COMModule::nCreateISymWriterForDynamicModule -FCIMPLEND - //************************************************** // GetTypeRef // This function will return the type token given full qual name. If the type diff --git a/src/coreclr/vm/commodule.h b/src/coreclr/vm/commodule.h index a4ce99c3fe146..4935028f96069 100644 --- a/src/coreclr/vm/commodule.h +++ b/src/coreclr/vm/commodule.h @@ -14,10 +14,6 @@ class Module; class COMModule { public: - // Attaches an unmanaged symwriter to a newly created dynamic module. - static FCDECL2(LPVOID, nCreateISymWriterForDynamicModule, ReflectModuleBaseObject* reflectionModuleUNSAFE, StringObject* filenameUNSAFE); - - // IsTransient // Determine if a Module is transient static diff --git a/src/libraries/System.Reflection.Emit.ILGeneration/src/MatchingRefApiCompatBaseline.txt b/src/libraries/System.Reflection.Emit.ILGeneration/src/MatchingRefApiCompatBaseline.txt index d775316990508..407adb83e1a12 100644 --- a/src/libraries/System.Reflection.Emit.ILGeneration/src/MatchingRefApiCompatBaseline.txt +++ b/src/libraries/System.Reflection.Emit.ILGeneration/src/MatchingRefApiCompatBaseline.txt @@ -1,7 +1,5 @@ Compat issues with assembly System.Reflection.Emit.ILGeneration: MembersMustExist : Member 'public void System.Reflection.Emit.ILGenerator.MarkSequencePoint(System.Diagnostics.SymbolStore.ISymbolDocumentWriter, System.Int32, System.Int32, System.Int32, System.Int32)' does not exist in the reference but it does exist in the implementation. -MembersMustExist : Member 'public void System.Reflection.Emit.LocalBuilder.SetLocalSymInfo(System.String)' does not exist in the reference but it does exist in the implementation. -MembersMustExist : Member 'public void System.Reflection.Emit.LocalBuilder.SetLocalSymInfo(System.String, System.Int32, System.Int32)' does not exist in the reference but it does exist in the implementation. MembersMustExist : Member 'public System.Reflection.Emit.SignatureHelper System.Reflection.Emit.SignatureHelper.GetMethodSigHelper(System.Reflection.Module, System.Runtime.InteropServices.CallingConvention, System.Type)' does not exist in the reference but it does exist in the implementation. MembersMustExist : Member 'public System.Reflection.Emit.SignatureHelper System.Reflection.Emit.SignatureHelper.GetMethodSigHelper(System.Runtime.InteropServices.CallingConvention, System.Type)' does not exist in the reference but it does exist in the implementation. Total Issues: 5 diff --git a/src/libraries/shims/ApiCompatBaseline.netcoreapp.netfx461.ignore.txt b/src/libraries/shims/ApiCompatBaseline.netcoreapp.netfx461.ignore.txt index b964c733e3019..b0420059f5aae 100644 --- a/src/libraries/shims/ApiCompatBaseline.netcoreapp.netfx461.ignore.txt +++ b/src/libraries/shims/ApiCompatBaseline.netcoreapp.netfx461.ignore.txt @@ -132,8 +132,6 @@ MembersMustExist : Member 'System.Reflection.Emit.FieldBuilder.GetToken()' does MembersMustExist : Member 'System.Reflection.Emit.FieldBuilder.SetMarshal(System.Reflection.Emit.UnmanagedMarshal)' does not exist in the implementation but it does exist in the contract. MembersMustExist : Member 'System.Reflection.Emit.ILGenerator.EmitCalli(System.Reflection.Emit.OpCode, System.Runtime.InteropServices.CallingConvention, System.Type, System.Type[])' does not exist in the implementation but it does exist in the contract. MembersMustExist : Member 'System.Reflection.Emit.ILGenerator.MarkSequencePoint(System.Diagnostics.SymbolStore.ISymbolDocumentWriter, System.Int32, System.Int32, System.Int32, System.Int32)' does not exist in the implementation but it does exist in the contract. -MembersMustExist : Member 'System.Reflection.Emit.LocalBuilder.SetLocalSymInfo(System.String)' does not exist in the implementation but it does exist in the contract. -MembersMustExist : Member 'System.Reflection.Emit.LocalBuilder.SetLocalSymInfo(System.String, System.Int32, System.Int32)' does not exist in the implementation but it does exist in the contract. MembersMustExist : Member 'System.Reflection.Emit.MethodBuilder.AddDeclarativeSecurity(System.Security.Permissions.SecurityAction, System.Security.PermissionSet)' does not exist in the implementation but it does exist in the contract. MembersMustExist : Member 'System.Reflection.Emit.MethodBuilder.CreateMethodBody(System.Byte[], System.Int32)' does not exist in the implementation but it does exist in the contract. MembersMustExist : Member 'System.Reflection.Emit.MethodBuilder.GetModule()' does not exist in the implementation but it does exist in the contract. diff --git a/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.Mono.cs b/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.Mono.cs index 6d4a249f538e6..017e072f7bb72 100644 --- a/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.Mono.cs +++ b/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/LocalBuilder.Mono.cs @@ -61,18 +61,6 @@ internal LocalBuilder(Type t, ILGenerator ilgen) this.ilgen = ilgen; } - public void SetLocalSymInfo(string name, int startOffset, int endOffset) - { - this.name = name; - this.startOffset = startOffset; - this.endOffset = endOffset; - } - - public void SetLocalSymInfo(string name) - { - SetLocalSymInfo(name, 0, 0); - } - public override Type LocalType { get