Skip to content

Commit

Permalink
Make PersistedAssemblyBuilder public and update all references (#99660)
Browse files Browse the repository at this point in the history
* Add public PersistedAssemblyBuilder and update all references

* Remove unused resource strings
  • Loading branch information
buyaa-n authored Mar 13, 2024
1 parent 4cf19ee commit 3d7ebcf
Show file tree
Hide file tree
Showing 23 changed files with 307 additions and 212 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ private GeneratedMethod BuildTypeNoCache(ServiceCallSite callSite)
var assembly = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName(assemblyName), AssemblyBuilderAccess.RunAndSave);
var module = assembly.DefineDynamicModule(assemblyName, fileName);
#else
var assembly = AssemblyBuilder.DefinePersistedAssembly(new AssemblyName(assemblyName), typeof(object).Assembly);
var assembly = new PersistedAssemblyBuilder(new AssemblyName(assemblyName), typeof(object).Assembly);
var module = assembly.DefineDynamicModule(assemblyName);
#endif
var type = module.DefineType(callSite.ServiceType.Name + "Resolver");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3346,7 +3346,7 @@
</data>
<data name="RFLCT_Targ_ITargMismatch_WithType" xml:space="preserve">
<value>Object type {0} does not match target type {1}.</value>
</data>
</data>
<data name="RFLCT_Targ_StatFldReqTarg" xml:space="preserve">
<value>Non-static field requires a target.</value>
</data>
Expand Down Expand Up @@ -4304,10 +4304,7 @@
<data name="RFLCT_CannotSetInitonlyStaticField" xml:space="preserve">
<value>Cannot set initonly static field '{0}' after type '{1}' is initialized.</value>
</data>
<data name="NotSupported_AssemblySave" xml:space="preserve">
<value>This AssemblyBuilder instance doesn't support saving. Use AssemblyBuilder.DefinePersistedAssembly to create an AssemblyBuilder instance that supports saving.</value>
</data>
<data name="WasmThreads_BlockingWaitNotSupportedOnJSInterop" xml:space="preserve">
<value>Blocking wait is not supported on the JS interop threads.</value>
</data>
</root>
</root>
Original file line number Diff line number Diff line change
Expand Up @@ -33,56 +33,8 @@ public ModuleBuilder DefineDynamicModule(string name)
return GetDynamicModuleCore(name);
}

/// <summary>
/// Defines an <see cref="AssemblyBuilder"/> that can be saved to a file or stream.
/// </summary>
/// <param name="name">The name of the assembly.</param>
/// <param name="coreAssembly">The assembly that denotes the "system assembly" that houses the well-known types such as <see cref="object"/></param>
/// <param name="assemblyAttributes">A collection that contains the attributes of the assembly.</param>
/// <returns>An <see cref="AssemblyBuilder"/> that can be persisted.</returns>
/// <exception cref="ArgumentNullException">The <paramref name="name"/> or <paramref name="name.Name"/> or <paramref name="coreAssembly"/> is null.</exception>
/// <remarks>Currently the persisted assembly doesn't support running, need to save it and load back to run.</remarks>
public static AssemblyBuilder DefinePersistedAssembly(AssemblyName name, Assembly coreAssembly, IEnumerable<CustomAttributeBuilder>? assemblyAttributes = null)
{
ArgumentNullException.ThrowIfNull(name);
ArgumentException.ThrowIfNullOrEmpty(name.Name, "AssemblyName.Name");
ArgumentNullException.ThrowIfNull(coreAssembly);

Type assemblyType = Type.GetType("System.Reflection.Emit.AssemblyBuilderImpl, System.Reflection.Emit", throwOnError: true)!;
ConstructorInfo con = assemblyType.GetConstructor(BindingFlags.NonPublic | BindingFlags.Instance, [typeof(AssemblyName), typeof(Assembly), typeof(IEnumerable<CustomAttributeBuilder>)])!;
return (AssemblyBuilder)con.Invoke([name, coreAssembly, assemblyAttributes]);
}

protected abstract ModuleBuilder? GetDynamicModuleCore(string name);

/// <summary>
/// Serializes the assembly to <see cref="Stream"/>.
/// </summary>
/// <param name="stream">The <see cref="Stream"/> to which the assembly serialized.</param>
/// <exception cref="ArgumentNullException"><paramref name="stream"/> is null.</exception>
/// <exception cref="NotSupportedException">The AssemblyBuilder instance doesn't support saving.</exception>
public void Save(Stream stream) => SaveCore(stream);

/// <summary>
/// Saves the assembly to disk.
/// </summary>
/// <param name="assemblyFileName">The file name of the assembly.</param>
/// <exception cref="ArgumentNullException"><paramref name="assemblyFileName"/> is null.</exception>
/// <exception cref="NotSupportedException">The AssemblyBuilder instance doesn't support saving.</exception>
public void Save(string assemblyFileName)
{
ArgumentNullException.ThrowIfNull(assemblyFileName);

using var peStream = new FileStream(assemblyFileName, FileMode.Create, FileAccess.Write);
SaveCore(peStream);
}

/// <summary>
/// When implemented in a derived type, serializes the assembly to a stream.
/// </summary>
/// <param name="stream">The stream to which the assembly serialized.</param>
protected virtual void SaveCore(Stream stream) => throw new NotSupportedException(SR.NotSupported_AssemblySave);

public void SetCustomAttribute(ConstructorInfo con, byte[] binaryAttribute)
{
ArgumentNullException.ThrowIfNull(con);
Expand Down
22 changes: 18 additions & 4 deletions src/libraries/System.Reflection.Emit/ref/System.Reflection.Emit.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ protected AssemblyBuilder() { }
public static System.Reflection.Emit.AssemblyBuilder DefineDynamicAssembly(System.Reflection.AssemblyName name, System.Reflection.Emit.AssemblyBuilderAccess access) { throw null; }
[System.Diagnostics.CodeAnalysis.RequiresDynamicCode("Defining a dynamic assembly requires dynamic code.")]
public static System.Reflection.Emit.AssemblyBuilder DefineDynamicAssembly(System.Reflection.AssemblyName name, System.Reflection.Emit.AssemblyBuilderAccess access, System.Collections.Generic.IEnumerable<System.Reflection.Emit.CustomAttributeBuilder>? assemblyAttributes) { throw null; }
public static System.Reflection.Emit.AssemblyBuilder DefinePersistedAssembly(System.Reflection.AssemblyName name, System.Reflection.Assembly coreAssembly, System.Collections.Generic.IEnumerable<System.Reflection.Emit.CustomAttributeBuilder>? assemblyAttributes = null) { throw null; }
public System.Reflection.Emit.ModuleBuilder DefineDynamicModule(string name) { throw null; }
protected abstract System.Reflection.Emit.ModuleBuilder DefineDynamicModuleCore(string name);
public override bool Equals(object? obj) { throw null; }
Expand Down Expand Up @@ -55,9 +54,6 @@ protected AssemblyBuilder() { }
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute("Types might be removed by trimming. If the type name is a string literal, consider using Type.GetType instead.")]
public override System.Type? GetType(string name, bool throwOnError, bool ignoreCase) { throw null; }
public override bool IsDefined(System.Type attributeType, bool inherit) { throw null; }
public void Save(string assemblyFileName) { throw null; }
public void Save(System.IO.Stream stream) { throw null; }
protected virtual void SaveCore(System.IO.Stream stream) { }
public void SetCustomAttribute(System.Reflection.ConstructorInfo con, byte[] binaryAttribute) { }
public void SetCustomAttribute(System.Reflection.Emit.CustomAttributeBuilder customBuilder) { }
protected abstract void SetCustomAttributeCore(System.Reflection.ConstructorInfo con, System.ReadOnlySpan<byte> binaryAttribute);
Expand Down Expand Up @@ -474,6 +470,24 @@ public void SetCustomAttribute(System.Reflection.ConstructorInfo con, byte[] bin
public void SetCustomAttribute(System.Reflection.Emit.CustomAttributeBuilder customBuilder) { }
protected abstract void SetCustomAttributeCore(System.Reflection.ConstructorInfo con, System.ReadOnlySpan<byte> binaryAttribute);
}
#if !BUILDING_CORELIB_REFERENCE
public sealed class PersistedAssemblyBuilder : System.Reflection.Emit.AssemblyBuilder
{
public PersistedAssemblyBuilder(System.Reflection.AssemblyName name, System.Reflection.Assembly coreAssembly, System.Collections.Generic.IEnumerable<System.Reflection.Emit.CustomAttributeBuilder>? assemblyAttributes = null) { }
public override string? FullName { get { throw null; } }
public override bool IsDynamic { get { throw null; } }
public override System.Reflection.Module ManifestModule { get { throw null; } }
[System.Diagnostics.CodeAnalysis.RequiresDynamicCode("Defining a dynamic assembly requires dynamic code.")]
protected override System.Reflection.Emit.ModuleBuilder DefineDynamicModuleCore(string name) { throw null; }
protected override System.Reflection.Emit.ModuleBuilder? GetDynamicModuleCore(string name) { throw null; }
[System.CLSCompliantAttribute(false)]
public System.Reflection.Metadata.Ecma335.MetadataBuilder GenerateMetadata(out System.Reflection.Metadata.BlobBuilder ilStream, out System.Reflection.Metadata.BlobBuilder mappedFieldData) { throw null; }
public override System.Reflection.AssemblyName GetName(bool copiedName) { throw null; }
public void Save(string assemblyFileName) { throw null; }
public void Save(System.IO.Stream stream) { throw null; }
protected override void SetCustomAttributeCore(System.Reflection.ConstructorInfo con, System.ReadOnlySpan<byte> binaryAttribute) { throw null; }
}
#endif
public abstract partial class PropertyBuilder : System.Reflection.PropertyInfo
{
protected PropertyBuilder() { }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,5 +10,6 @@
<ProjectReference Include="..\..\System.Runtime.InteropServices\ref\System.Runtime.InteropServices.csproj" />
<ProjectReference Include="..\..\System.Reflection.Primitives\ref\System.Reflection.Primitives.csproj" />
<ProjectReference Include="..\..\System.Reflection.Emit.ILGeneration\ref\System.Reflection.Emit.ILGeneration.csproj" />
<ProjectReference Include="..\..\System.Reflection.Metadata\ref\System.Reflection.Metadata.csproj" />
</ItemGroup>
</Project>

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -117,8 +117,8 @@
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="InvalidOperation_CannotSaveMultipleTimes" xml:space="preserve">
<value>Cannot save an assembly multiple times.</value>
<data name="InvalidOperation_CannotPopulateMultipleTimes" xml:space="preserve">
<value>Cannot populate assembly metadata multiple times.</value>
</data>
<data name="Argument_CannotSetParentToInterface" xml:space="preserve">
<value>Cannot set parent to an interface.</value>
Expand Down Expand Up @@ -249,9 +249,6 @@
<data name="Argument_MustBeInterface" xml:space="preserve">
<value>Type passed must be an interface.</value>
</data>
<data name="TypeLoad_MissingMethod" xml:space="preserve">
<value>Abstract method '{0}' in type '{1}' does not have an implementation.</value>
</data>
<data name="InvalidOperation_BadMethodBody" xml:space="preserve">
<value>Method '{0}' cannot have a method body</value>
</data>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@
<Compile Include="System\Reflection\Emit\ArrayMethod.cs" />
<Compile Include="System\Reflection\Emit\ConstructorBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\CustomAttributeWrapper.cs" />
<Compile Include="System\Reflection\Emit\AssemblyBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\EnumBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\EventBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\FieldBuilderImpl.cs" />
Expand All @@ -24,6 +23,7 @@
<Compile Include="System\Reflection\Emit\MethodBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\ModuleBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\ParameterBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\PersistedAssemblyBuilder.cs" />
<Compile Include="System\Reflection\Emit\PropertyBuilderImpl.cs" />
<Compile Include="System\Reflection\Emit\PseudoCustomAttributesData.cs" />
<Compile Include="System\Reflection\Emit\SignatureHelper.cs" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ internal sealed class ModuleBuilderImpl : ModuleBuilder
private readonly Assembly _coreAssembly;
private readonly string _name;
private readonly MetadataBuilder _metadataBuilder;
private readonly AssemblyBuilderImpl _assemblyBuilder;
private readonly PersistedAssemblyBuilder _assemblyBuilder;
private readonly TypeBuilderImpl _globalTypeBuilder;
private readonly Dictionary<Assembly, AssemblyReferenceHandle> _assemblyReferences = new();
private readonly Dictionary<Type, EntityHandle> _typeReferences = new();
Expand All @@ -37,7 +37,7 @@ internal sealed class ModuleBuilderImpl : ModuleBuilder
private static readonly Type[] s_coreTypes = { typeof(void), typeof(object), typeof(bool), typeof(char), typeof(sbyte), typeof(byte), typeof(short), typeof(ushort), typeof(int),
typeof(uint), typeof(long), typeof(ulong), typeof(float), typeof(double), typeof(string), typeof(nint), typeof(nuint), typeof(TypedReference) };

internal ModuleBuilderImpl(string name, Assembly coreAssembly, MetadataBuilder builder, AssemblyBuilderImpl assemblyBuilder)
internal ModuleBuilderImpl(string name, Assembly coreAssembly, MetadataBuilder builder, PersistedAssemblyBuilder assemblyBuilder)
{
_coreAssembly = coreAssembly;
_name = name;
Expand Down
Loading

0 comments on commit 3d7ebcf

Please sign in to comment.