Partilhar via


MetadataBuilder Classe

Definição

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

public ref class MetadataBuilder sealed
public sealed class MetadataBuilder
type MetadataBuilder = class
Public NotInheritable Class MetadataBuilder
Herança
MetadataBuilder

Exemplos

Este exemplo mostra como emitir um assembly de aplicativo de console usando MetadataBuilder:

private static readonly Guid s_guid = new Guid("87D4DBE1-1143-4FAD-AAB3-1001F92068E6");
private static readonly BlobContentId s_contentId = new BlobContentId(s_guid, 0x04030201);

private static MethodDefinitionHandle EmitHelloWorld(MetadataBuilder metadata, BlobBuilder ilBuilder)
{
    // Create module and assembly for a console application.
    metadata.AddModule(
        0,
        metadata.GetOrAddString("ConsoleApplication.exe"),
        metadata.GetOrAddGuid(s_guid),
        default(GuidHandle),
        default(GuidHandle));

    metadata.AddAssembly(
        metadata.GetOrAddString("ConsoleApplication"),
        version: new Version(1, 0, 0, 0),
        culture: default(StringHandle),
        publicKey: default(BlobHandle),
        flags: 0,
        hashAlgorithm: AssemblyHashAlgorithm.None);

    // Create references to System.Object and System.Console types.
    AssemblyReferenceHandle mscorlibAssemblyRef = metadata.AddAssemblyReference(
        name: metadata.GetOrAddString("mscorlib"),
        version: new Version(4, 0, 0, 0),
        culture: default(StringHandle),
        publicKeyOrToken: metadata.GetOrAddBlob(
            new byte[] { 0xB7, 0x7A, 0x5C, 0x56, 0x19, 0x34, 0xE0, 0x89 }
            ),
        flags: default(AssemblyFlags),
        hashValue: default(BlobHandle));

    TypeReferenceHandle systemObjectTypeRef = metadata.AddTypeReference(
        mscorlibAssemblyRef,
        metadata.GetOrAddString("System"),
        metadata.GetOrAddString("Object"));

    TypeReferenceHandle systemConsoleTypeRefHandle = metadata.AddTypeReference(
        mscorlibAssemblyRef,
        metadata.GetOrAddString("System"),
        metadata.GetOrAddString("Console"));

    // Get reference to Console.WriteLine(string) method.
    var consoleWriteLineSignature = new BlobBuilder();

    new BlobEncoder(consoleWriteLineSignature).
        MethodSignature().
        Parameters(1,
            returnType => returnType.Void(),
            parameters => parameters.AddParameter().Type().String());

    MemberReferenceHandle consoleWriteLineMemberRef = metadata.AddMemberReference(
        systemConsoleTypeRefHandle,
        metadata.GetOrAddString("WriteLine"),
        metadata.GetOrAddBlob(consoleWriteLineSignature));

    // Get reference to Object's constructor.
    var parameterlessCtorSignature = new BlobBuilder();

    new BlobEncoder(parameterlessCtorSignature).
        MethodSignature(isInstanceMethod: true).
        Parameters(0, returnType => returnType.Void(), parameters => { });

    BlobHandle parameterlessCtorBlobIndex = metadata.GetOrAddBlob(parameterlessCtorSignature);

    MemberReferenceHandle objectCtorMemberRef = metadata.AddMemberReference(
        systemObjectTypeRef,
        metadata.GetOrAddString(".ctor"),
        parameterlessCtorBlobIndex);

    // Create signature for "void Main()" method.
    var mainSignature = new BlobBuilder();

    new BlobEncoder(mainSignature).
        MethodSignature().
        Parameters(0, returnType => returnType.Void(), parameters => { });

    var methodBodyStream = new MethodBodyStreamEncoder(ilBuilder);

    var codeBuilder = new BlobBuilder();
    InstructionEncoder il;
    
    // Emit IL for Program::.ctor
    il = new InstructionEncoder(codeBuilder);

    // ldarg.0
    il.LoadArgument(0); 

    // call instance void [mscorlib]System.Object::.ctor()
    il.Call(objectCtorMemberRef);

    // ret
    il.OpCode(ILOpCode.Ret);

    int ctorBodyOffset = methodBodyStream.AddMethodBody(il);
    codeBuilder.Clear();

    // Emit IL for Program::Main
    var flowBuilder = new ControlFlowBuilder();
    il = new InstructionEncoder(codeBuilder, flowBuilder);

    // ldstr "hello"
    il.LoadString(metadata.GetOrAddUserString("Hello, world"));

    // call void [mscorlib]System.Console::WriteLine(string)
    il.Call(consoleWriteLineMemberRef);

    // ret
    il.OpCode(ILOpCode.Ret);

    int mainBodyOffset = methodBodyStream.AddMethodBody(il);
    codeBuilder.Clear();

    // Create method definition for Program::Main
    MethodDefinitionHandle mainMethodDef = metadata.AddMethodDefinition(
        MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.HideBySig,
        MethodImplAttributes.IL,
        metadata.GetOrAddString("Main"),
        metadata.GetOrAddBlob(mainSignature),
        mainBodyOffset,
        parameterList: default(ParameterHandle));

    // Create method definition for Program::.ctor
    MethodDefinitionHandle ctorDef = metadata.AddMethodDefinition(
        MethodAttributes.Public | MethodAttributes.HideBySig | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName,
        MethodImplAttributes.IL,
        metadata.GetOrAddString(".ctor"),
        parameterlessCtorBlobIndex,
        ctorBodyOffset,
        parameterList: default(ParameterHandle));

    // Create type definition for the special <Module> type that holds global functions
    metadata.AddTypeDefinition(
        default(TypeAttributes),
        default(StringHandle),
        metadata.GetOrAddString("<Module>"),
        baseType: default(EntityHandle),
        fieldList: MetadataTokens.FieldDefinitionHandle(1),
        methodList: mainMethodDef);

    // Create type definition for ConsoleApplication.Program
    metadata.AddTypeDefinition(
        TypeAttributes.Class | TypeAttributes.Public | TypeAttributes.AutoLayout | TypeAttributes.BeforeFieldInit,
        metadata.GetOrAddString("ConsoleApplication"),
        metadata.GetOrAddString("Program"),
        baseType: systemObjectTypeRef,
        fieldList: MetadataTokens.FieldDefinitionHandle(1),
        methodList: mainMethodDef);
    
    return mainMethodDef;
}

private static void WritePEImage(
    Stream peStream,
    MetadataBuilder metadataBuilder,
    BlobBuilder ilBuilder,
    MethodDefinitionHandle entryPointHandle
    )
{
    // Create executable with the managed metadata from the specified MetadataBuilder.
    var peHeaderBuilder = new PEHeaderBuilder(
        imageCharacteristics: Characteristics.ExecutableImage
        );

    var peBuilder = new ManagedPEBuilder(
        peHeaderBuilder,
        new MetadataRootBuilder(metadataBuilder),
        ilBuilder,
        entryPoint: entryPointHandle,
        flags: CorFlags.ILOnly,
        deterministicIdProvider: content => s_contentId);

    // Write executable into the specified stream.
    var peBlob = new BlobBuilder();
    BlobContentId contentId = peBuilder.Serialize(peBlob);
    peBlob.WriteContentTo(peStream);
}

public static void BuildHelloWorldApp()
{
    using var peStream = new FileStream(
        "ConsoleApplication.exe", FileMode.OpenOrCreate, FileAccess.ReadWrite
        );
    
    var ilBuilder = new BlobBuilder();
    var metadataBuilder = new MetadataBuilder();

    MethodDefinitionHandle entryPoint = EmitHelloWorld(metadataBuilder, ilBuilder);
    WritePEImage(peStream, metadataBuilder, ilBuilder, entryPoint);
}

Comentários

A MetadataBuilder classe permite que você gere assemblies programaticamente. Esses assemblies podem ser salvos em um arquivo, ao contrário dos assemblies dinâmicos gerados pela AssemblyBuilder classe , que não dá suporte ao salvamento de assemblies em um arquivo no .NET 5+ e no .NET Core.

A MetadataBuilder API opera constructos de metadados de baixo nível, como tabelas ou blobs. Para obter uma maneira mais simples de gerar assemblies dinamicamente usando C#, consulte CSharpCompilation na API roslyn.

O formato dos metadados da CLI é definido pela especificação ECMA-335. Para obter mais informações, consulte Standard ECMA-335 – Common Language Infrastructure (CLI) no site Ecma International.

Construtores

MetadataBuilder(Int32, Int32, Int32, Int32)

Cria um construtor para heaps e tabelas de metadados.

Métodos

AddAssembly(StringHandle, Version, StringHandle, BlobHandle, AssemblyFlags, AssemblyHashAlgorithm)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddAssemblyFile(StringHandle, BlobHandle, Boolean)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddAssemblyReference(StringHandle, Version, StringHandle, BlobHandle, AssemblyFlags, BlobHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddConstant(EntityHandle, Object)

Adiciona um valor padrão para um parâmetro, campo ou propriedade.

AddCustomAttribute(EntityHandle, EntityHandle, BlobHandle)

Adiciona um atributo personalizado.

AddCustomDebugInformation(EntityHandle, GuidHandle, BlobHandle)

Adiciona informações de depuração personalizadas.

AddDeclarativeSecurityAttribute(EntityHandle, DeclarativeSecurityAction, BlobHandle)

Adiciona um atributo de segurança declarativa a um tipo, um método ou um assembly.

AddDocument(BlobHandle, GuidHandle, BlobHandle, GuidHandle)

Adiciona informações de depuração do documento.

AddEncLogEntry(EntityHandle, EditAndContinueOperation)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddEncMapEntry(EntityHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddEvent(EventAttributes, StringHandle, EntityHandle)

Adiciona uma definição de evento.

AddEventMap(TypeDefinitionHandle, EventDefinitionHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddExportedType(TypeAttributes, StringHandle, StringHandle, EntityHandle, Int32)

Adiciona um tipo exportado.

AddFieldDefinition(FieldAttributes, StringHandle, BlobHandle)

Adiciona uma definição de campo.

AddFieldLayout(FieldDefinitionHandle, Int32)

Define um layout de campo de uma definição de campo.

AddFieldRelativeVirtualAddress(FieldDefinitionHandle, Int32)

Adiciona um mapeamento de um campo para o respectivo valor inicial armazenado na imagem PE.

AddGenericParameter(EntityHandle, GenericParameterAttributes, StringHandle, Int32)

Adiciona uma definição de parâmetro genérico.

AddGenericParameterConstraint(GenericParameterHandle, EntityHandle)

Adiciona uma restrição de tipo a um parâmetro genérico.

AddImportScope(ImportScopeHandle, BlobHandle)

Adiciona informações de depuração do escopo local.

AddInterfaceImplementation(TypeDefinitionHandle, EntityHandle)

Adiciona uma implementação de interface a um tipo.

AddLocalConstant(StringHandle, BlobHandle)

Adiciona informações de depuração da constante local.

AddLocalScope(MethodDefinitionHandle, ImportScopeHandle, LocalVariableHandle, LocalConstantHandle, Int32, Int32)

Adiciona informações de depuração do escopo local.

AddLocalVariable(LocalVariableAttributes, Int32, StringHandle)

Adiciona informações de depuração da variável local.

AddManifestResource(ManifestResourceAttributes, StringHandle, EntityHandle, UInt32)

Adiciona um recurso de manifesto.

AddMarshallingDescriptor(EntityHandle, BlobHandle)

Adiciona informações de marshaling a um campo ou parâmetro.

AddMemberReference(EntityHandle, StringHandle, BlobHandle)

Adiciona uma linha de tabela MemberRef.

AddMethodDebugInformation(DocumentHandle, BlobHandle)

Adiciona informações de depuração do método.

AddMethodDefinition(MethodAttributes, MethodImplAttributes, StringHandle, BlobHandle, Int32, ParameterHandle)

Adiciona uma definição de método.

AddMethodImplementation(TypeDefinitionHandle, EntityHandle, EntityHandle)

Define uma implementação para uma declaração de método dentro de um tipo.

AddMethodImport(MethodDefinitionHandle, MethodImportAttributes, StringHandle, ModuleReferenceHandle)

Adiciona informações de importação a uma definição de método.

AddMethodSemantics(EntityHandle, MethodSemanticsAttributes, MethodDefinitionHandle)

Associa um método (um getter, um setter, um adicionador etc.) a uma propriedade ou um evento.

AddMethodSpecification(EntityHandle, BlobHandle)

Adiciona uma especificação de método (uma instanciação).

AddModule(Int32, StringHandle, GuidHandle, GuidHandle, GuidHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddModuleReference(StringHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddNestedType(TypeDefinitionHandle, TypeDefinitionHandle)

Define uma relação de aninhamento para definições de tipo especificadas.

AddParameter(ParameterAttributes, StringHandle, Int32)

Adiciona uma definição de parâmetro.

AddProperty(PropertyAttributes, StringHandle, BlobHandle)

Adiciona uma definição de propriedade.

AddPropertyMap(TypeDefinitionHandle, PropertyDefinitionHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddStandaloneSignature(BlobHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

AddStateMachineMethod(MethodDefinitionHandle, MethodDefinitionHandle)

Adiciona informações de depuração do método de máquina de estado.

AddTypeDefinition(TypeAttributes, StringHandle, StringHandle, EntityHandle, FieldDefinitionHandle, MethodDefinitionHandle)

Adiciona uma definição de tipo.

AddTypeLayout(TypeDefinitionHandle, UInt16, UInt32)

Define um layout de tipo de uma definição de tipo.

AddTypeReference(EntityHandle, StringHandle, StringHandle)

Adiciona uma referência de tipo.

AddTypeSpecification(BlobHandle)

A classe MetadataBuilder grava metadados para um assembly de maneira altamente eficaz. Ele foi projetado para ser usado por compiladores e outras ferramentas de geração de assembly.

Equals(Object)

Determina se o objeto especificado é igual ao objeto atual.

(Herdado de Object)
GetHashCode()

Serve como a função de hash padrão.

(Herdado de Object)
GetOrAddBlob(BlobBuilder)

Adicionará o blob especificado de uma matriz de bytes imutável ao heap de blobs, caso ele ainda não esteja lá.

GetOrAddBlob(Byte[])

Adicionará o blob especificado ao heap de blobs, caso ele ainda não esteja lá.

GetOrAddBlob(ImmutableArray<Byte>)

Adicionará o blob especificado de uma matriz de bytes ao heap de blobs, caso ele ainda não esteja lá.

GetOrAddBlobUTF16(String)

Codifica uma cadeia de caracteres usando a codificação UTF16 em um blob e a adiciona ao heap de blobs, caso ainda não exista.

GetOrAddBlobUTF8(String, Boolean)

Codifica uma cadeia de caracteres usando a codificação UTF8 em um blob e a adiciona ao heap de blobs, caso ainda não exista.

GetOrAddConstantBlob(Object)

Codifica um valor de constante em um blob e o adiciona ao heap de blobs, caso ainda não exista. Usa UTF16 para codificar constantes de cadeia de caracteres.

GetOrAddDocumentName(String)

Codifica um nome de documento de depuração e o adiciona ao heap de blobs, caso ele ainda não esteja lá.

GetOrAddGuid(Guid)

Adicionará o GUID especificado ao heap de GUIDs, caso ele ainda não esteja lá.

GetOrAddString(String)

Adiciona a cadeia de caracteres especificada ao heap de cadeias de caracteres, caso ela ainda não esteja lá.

GetOrAddUserString(String)

Adiciona a cadeia de caracteres especificada ao heap de cadeias de caracteres de usuário, caso ela ainda não esteja lá.

GetRowCount(TableIndex)

Retorna o número atual de itens na tabela especificada.

GetRowCounts()

Retorna o número atual de itens em cada tabela.

GetType()

Obtém o Type da instância atual.

(Herdado de Object)
MemberwiseClone()

Cria uma cópia superficial do Object atual.

(Herdado de Object)
ReserveGuid()

Reserva espaço no heap de GUIDs para um GUID.

ReserveUserString(Int32)

Reserva espaço no heap de cadeias de caracteres do usuário para uma cadeia de caracteres do comprimento especificado.

SetCapacity(HeapIndex, Int32)

Define a capacidade do heap especificado.

SetCapacity(TableIndex, Int32)

Define a capacidade da tabela especificada.

ToString()

Retorna uma cadeia de caracteres que representa o objeto atual.

(Herdado de Object)

Aplica-se a