Example #1
0
        public static bool ShouldInclude(this ITypeDefinitionMember member, EmitContext context)
        {
            if (context.IncludePrivateMembers)
            {
                return(true);
            }

            var method = member as IMethodDefinition;

            if (method != null && method.IsVirtual)
            {
                return(true);
            }

            switch (member.Visibility)
            {
            case TypeMemberVisibility.Private:
                return(context.IncludePrivateMembers);

            case TypeMemberVisibility.Assembly:
            case TypeMemberVisibility.FamilyAndAssembly:
                return(context.IncludePrivateMembers || context.Module.SourceAssemblyOpt?.InternalsAreVisible == true);
            }
            return(true);
        }
        public static MetadataWriter Create(
            EmitContext context,
            CommonMessageProvider messageProvider,
            bool metadataOnly,
            bool deterministic,
            bool emitTestCoverageData,
            bool hasPdbStream,
            CancellationToken cancellationToken)
        {
            var             builder = new MetadataBuilder();
            MetadataBuilder?debugBuilderOpt;

            switch (context.Module.DebugInformationFormat)
            {
            case DebugInformationFormat.PortablePdb:
                debugBuilderOpt = hasPdbStream ? new MetadataBuilder() : null;
                break;

            case DebugInformationFormat.Embedded:
                debugBuilderOpt = metadataOnly ? null : new MetadataBuilder();
                break;

            default:
                debugBuilderOpt = null;
                break;
            }

            var dynamicAnalysisDataWriterOpt = emitTestCoverageData ?
                                               new DynamicAnalysisDataWriter(context.Module.DebugDocumentCount, context.Module.HintNumberOfMethodDefinitions) :
                                               null;

            return(new FullMetadataWriter(context, builder, debugBuilderOpt, dynamicAnalysisDataWriterOpt, messageProvider, metadataOnly, deterministic,
                                          emitTestCoverageData, cancellationToken));
        }
Example #3
0
        internal Cci.IMetadataConstant GetMetadataConstantValue(EmitContext context)
        {
            if (!HasMetadataConstantValue)
            {
                return null;
            }

            ConstantValue constant = this.ExplicitDefaultConstantValue;
            TypeSymbol type;
            if (constant.SpecialType != SpecialType.None)
            {
                // preserve the exact type of the constant for primitive types,
                // e.g. it should be Int16 for [DefaultParameterValue((short)1)]int x
                type = this.ContainingAssembly.GetSpecialType(constant.SpecialType);
            }
            else
            {
                // default(struct), enum
                type = this.Type;
            }

            return ((PEModuleBuilder)context.Module).CreateConstant(type, constant.Value,
                                                           syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt,
                                                           diagnostics: context.Diagnostics);
        }
Example #4
0
        public static MetadataWriter Create(
            EmitContext context,
            CommonMessageProvider messageProvider,
            bool allowMissingMethodBodies,
            bool deterministic,
            bool hasPdbStream,
            CancellationToken cancellationToken)
        {
            var heaps = new MetadataHeapsBuilder();
            MetadataHeapsBuilder debugHeapsOpt;

            switch (context.ModuleBuilder.EmitOptions.DebugInformationFormat)
            {
            case DebugInformationFormat.PortablePdb:
                debugHeapsOpt = hasPdbStream ? new MetadataHeapsBuilder() : null;
                break;

            case DebugInformationFormat.Embedded:
                debugHeapsOpt = heaps;
                break;

            default:
                debugHeapsOpt = null;
                break;
            }

            return(new FullMetadataWriter(context, heaps, debugHeapsOpt, messageProvider, allowMissingMethodBodies, deterministic, cancellationToken));
        }
Example #5
0
        public static MetadataWriter Create(
            EmitContext context,
            CommonMessageProvider messageProvider,
            bool allowMissingMethodBodies,
            bool deterministic,
            bool hasPdbStream,
            CancellationToken cancellationToken)
        {
            var             builder = new MetadataBuilder();
            MetadataBuilder debugBuilderOpt;

            switch (context.ModuleBuilder.EmitOptions.DebugInformationFormat)
            {
            case DebugInformationFormat.PortablePdb:
                debugBuilderOpt = hasPdbStream ? new MetadataBuilder() : null;
                break;

            case DebugInformationFormat.Embedded:
                debugBuilderOpt = new MetadataBuilder();
                break;

            default:
                debugBuilderOpt = null;
                break;
            }

            var dynamicAnalysisDataWriterOpt = context.ModuleBuilder.EmitOptions.EmitDynamicAnalysisData ?
                                               new DynamicAnalysisDataWriter(context.Module.DebugDocumentCount, context.Module.HintNumberOfMethodDefinitions) :
                                               null;

            return(new FullMetadataWriter(context, builder, debugBuilderOpt, dynamicAnalysisDataWriterOpt, messageProvider, allowMissingMethodBodies, deterministic, cancellationToken));
        }
 Cci.INamedTypeReference Cci.IGenericTypeInstanceReference.GetGenericType(EmitContext context)
 {
     System.Diagnostics.Debug.Assert(UnderlyingNamedType.OriginalDefinition.IsDefinition);
     PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;
     return moduleBeingBuilt.Translate(this.UnderlyingNamedType.OriginalDefinition, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, 
                                       diagnostics: context.Diagnostics, needDeclaration: true);
 }
Example #7
0
        public PEDeltaAssemblyBuilder(
            SourceAssemblySymbol sourceAssembly,
            string outputName,
            OutputKind outputKind,
            ModulePropertiesForSerialization serializationProperties,
            IEnumerable<ResourceDescription> manifestResources,
            Func<AssemblySymbol, AssemblyIdentity> assemblySymbolMapper,
            EmitBaseline previousGeneration,
            IEnumerable<SemanticEdit> edits)
            : base(sourceAssembly, outputName, outputKind, serializationProperties, manifestResources, assemblySymbolMapper, additionalTypes: ImmutableArray<NamedTypeSymbol>.Empty, metadataOnly:false)
        {
            var context = new EmitContext(this, null, new DiagnosticBag());
            var module = previousGeneration.OriginalMetadata;
            var compilation = sourceAssembly.DeclaringCompilation;
            var metadataAssembly = compilation.GetBoundReferenceManager().CreatePEAssemblyForAssemblyMetadata(AssemblyMetadata.Create(module), MetadataImportOptions.All);
            var metadataDecoder = new Microsoft.CodeAnalysis.CSharp.Symbols.Metadata.PE.MetadataDecoder(metadataAssembly.PrimaryModule);

            previousGeneration = EnsureInitialized(previousGeneration, metadataDecoder);

            var matchToMetadata = new SymbolMatcher(previousGeneration.AnonymousTypeMap, sourceAssembly, context, metadataAssembly);

            SymbolMatcher matchToPrevious = null;
            if (previousGeneration.Ordinal > 0)
            {
                var previousAssembly = ((CSharpCompilation)previousGeneration.Compilation).SourceAssembly;
                var previousContext = new EmitContext((PEModuleBuilder)previousGeneration.PEModuleBuilder, null, new DiagnosticBag());
                matchToPrevious = new SymbolMatcher(previousGeneration.AnonymousTypeMap, sourceAssembly, context, previousAssembly, previousContext);
            }

            this.previousDefinitions = new CSharpDefinitionMap(previousGeneration.OriginalMetadata.Module, edits, metadataDecoder, matchToMetadata, matchToPrevious);
            this.previousGeneration = previousGeneration;
            this.changes = new SymbolChanges(this.previousDefinitions, edits);
        }
Example #8
0
        private FullMetadataWriter(
            EmitContext context,
            MetadataHeapsBuilder heaps,
            CommonMessageProvider messageProvider,
            bool allowMissingMethodBodies,
            bool deterministic,
            CancellationToken cancellationToken)
            : base(heaps, context, messageProvider, allowMissingMethodBodies, deterministic, cancellationToken)
        {
            // EDMAURER make some intelligent guesses for the initial sizes of these things.
            int numMethods           = this.module.HintNumberOfMethodDefinitions;
            int numTypeDefsGuess     = numMethods / 6;
            int numFieldDefsGuess    = numTypeDefsGuess * 4;
            int numPropertyDefsGuess = numMethods / 4;

            _typeDefs          = new DefinitionIndex <ITypeDefinition>(numTypeDefsGuess);
            _eventDefs         = new DefinitionIndex <IEventDefinition>(0);
            _fieldDefs         = new DefinitionIndex <IFieldDefinition>(numFieldDefsGuess);
            _methodDefs        = new DefinitionIndex <IMethodDefinition>(numMethods);
            _propertyDefs      = new DefinitionIndex <IPropertyDefinition>(numPropertyDefsGuess);
            _parameterDefs     = new DefinitionIndex <IParameterDefinition>(numMethods);
            _genericParameters = new DefinitionIndex <IGenericParameter>(0);

            _fieldDefIndex      = new Dictionary <ITypeDefinition, uint>(numTypeDefsGuess);
            _methodDefIndex     = new Dictionary <ITypeDefinition, uint>(numTypeDefsGuess);
            _parameterListIndex = new Dictionary <IMethodDefinition, uint>(numMethods);

            _assemblyRefIndex         = new HeapOrReferenceIndex <IAssemblyReference>(this, AssemblyReferenceComparer.Instance);
            _moduleRefIndex           = new HeapOrReferenceIndex <string>(this);
            _memberRefIndex           = new InstanceAndStructuralReferenceIndex <ITypeMemberReference>(this, new MemberRefComparer(this));
            _methodSpecIndex          = new InstanceAndStructuralReferenceIndex <IGenericMethodInstanceReference>(this, new MethodSpecComparer(this));
            _typeRefIndex             = new HeapOrReferenceIndex <ITypeReference>(this);
            _typeSpecIndex            = new InstanceAndStructuralReferenceIndex <ITypeReference>(this, new TypeSpecComparer(this));
            _standAloneSignatureIndex = new HeapOrReferenceIndex <uint>(this);
        }
        Cci.INestedTypeReference Cci.ISpecializedNestedTypeReference.GetUnspecializedVersion(EmitContext context)
        {
            Debug.Assert(UnderlyingNamedType.OriginalDefinition.IsDefinition);
            var result = ((PEModuleBuilder)context.Module).Translate(this.UnderlyingNamedType.OriginalDefinition, 
                                          (CSharpSyntaxNode)context.SyntaxNodeOpt, context.Diagnostics, needDeclaration: true).AsNestedTypeReference;

            Debug.Assert(result != null);
            return result;
        }
        IEnumerable<Cci.ITypeReference> Cci.IGenericMethodInstanceReference.GetGenericArguments(EmitContext context)
        {
            PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;

            foreach (var arg in UnderlyingMethod.TypeArguments)
            {
                yield return moduleBeingBuilt.Translate(arg, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, diagnostics: context.Diagnostics);
            }
        }
 Cci.IMethodReference Cci.IGenericMethodInstanceReference.GetGenericMethod(EmitContext context)
 {
     // NoPia method might come through here.
     return ((PEModuleBuilder)context.Module).Translate(
         UnderlyingMethod.OriginalDefinition,
         syntaxNodeOpt: context.SyntaxNodeOpt,
         diagnostics: context.Diagnostics,
         needDeclaration: true);
 }
        public byte[] SerializeMethodDebugInfo(EmitContext context, IMethodBody methodBody, uint methodToken, bool isEncDelta, bool suppressNewCustomDebugInfo, out bool emitExternNamespaces)
        {
            emitExternNamespaces = false;

            // CONSIDER: this may not be the same "first" method as in Dev10, but
            // it shouldn't matter since all methods will still forward to a method
            // containing the appropriate information.
            if (_methodBodyWithModuleInfo == null) //UNDONE: || edit-and-continue
            {
                // This module level information could go on every method (and does in
                // the edit-and-continue case), but - as an optimization - we'll just
                // put it on the first method we happen to encounter and then put a
                // reference to the first method's token in every other method (so they
                // can find the information).
                if (context.Module.GetAssemblyReferenceAliases(context).Any())
                {
                    _methodTokenWithModuleInfo = methodToken;
                    _methodBodyWithModuleInfo = methodBody;
                    emitExternNamespaces = true;
                }
            }

            var customDebugInfo = ArrayBuilder<MemoryStream>.GetInstance();

            SerializeIteratorClassMetadata(methodBody, customDebugInfo);

            // NOTE: This is an attempt to match Dev10's apparent behavior.  For iterator methods (i.e. the method
            // that appears in source, not the synthesized ones), Dev10 only emits the ForwardIterator and IteratorLocal
            // custom debug info (e.g. there will be no information about the usings that were in scope).
            // NOTE: There seems to be an unusual behavior in ISymUnmanagedWriter where, if all the methods in a type are
            // iterator methods, no custom debug info is emitted for any method.  Adding a single non-iterator
            // method causes the custom debug info to be produced for all methods (including the iterator methods).
            // Since we are making the same ISymUnmanagedWriter calls as Dev10, we see the same behavior (i.e. this
            // is not a regression).
            if (methodBody.StateMachineTypeName == null)
            {
                SerializeNamespaceScopeMetadata(context, methodBody, customDebugInfo);
                SerializeStateMachineLocalScopes(methodBody, customDebugInfo);
            }

            if (!suppressNewCustomDebugInfo)
            {
                SerializeDynamicLocalInfo(methodBody, customDebugInfo);

                // delta doesn't need this information - we use information recorded by previous generation emit
                if (!isEncDelta)
                {
                    var encMethodInfo = MetadataWriter.GetEncMethodDebugInfo(methodBody);
                    SerializeCustomDebugInformation(encMethodInfo, customDebugInfo);
                }
            }

            byte[] result = SerializeCustomDebugMetadata(customDebugInfo);
            customDebugInfo.Free();
            return result;
        }
        Cci.IAssemblyReference Cci.IModuleReference.GetContainingAssembly(EmitContext context)
        {
            if (this.moduleBeingBuilt.OutputKind.IsNetModule() &&
                ReferenceEquals(moduleBeingBuilt.SourceModule.ContainingAssembly, underlyingModule.ContainingAssembly))
            {
                return null;
            }

            return moduleBeingBuilt.Translate(underlyingModule.ContainingAssembly, context.Diagnostics);
        }
Example #14
0
        public PEDeltaAssemblyBuilder(
            SourceAssemblySymbol sourceAssembly,
            EmitOptions emitOptions,
            OutputKind outputKind,
            Cci.ModulePropertiesForSerialization serializationProperties,
            IEnumerable<ResourceDescription> manifestResources,
            EmitBaseline previousGeneration,
            IEnumerable<SemanticEdit> edits,
            Func<ISymbol, bool> isAddedSymbol)
            : base(sourceAssembly, emitOptions, outputKind, serializationProperties, manifestResources, additionalTypes: ImmutableArray<NamedTypeSymbol>.Empty)
        {
            var initialBaseline = previousGeneration.InitialBaseline;
            var context = new EmitContext(this, null, new DiagnosticBag());

            // Hydrate symbols from initial metadata. Once we do so it is important to reuse these symbols across all generations,
            // in order for the symbol matcher to be able to use reference equality once it maps symbols to initial metadata.
            var metadataSymbols = GetOrCreateMetadataSymbols(initialBaseline, sourceAssembly.DeclaringCompilation);
            var metadataDecoder = (MetadataDecoder)metadataSymbols.MetadataDecoder;
            var metadataAssembly = (PEAssemblySymbol)metadataDecoder.ModuleSymbol.ContainingAssembly;

            var matchToMetadata = new CSharpSymbolMatcher(metadataSymbols.AnonymousTypes, sourceAssembly, context, metadataAssembly);

            CSharpSymbolMatcher matchToPrevious = null;
            if (previousGeneration.Ordinal > 0)
            {
                var previousAssembly = ((CSharpCompilation)previousGeneration.Compilation).SourceAssembly;
                var previousContext = new EmitContext((PEModuleBuilder)previousGeneration.PEModuleBuilder, null, new DiagnosticBag());

                matchToPrevious = new CSharpSymbolMatcher(
                    previousGeneration.AnonymousTypeMap,
                    sourceAssembly: sourceAssembly,
                    sourceContext: context,
                    otherAssembly: previousAssembly,
                    otherContext: previousContext,
                    otherSynthesizedMembersOpt: previousGeneration.SynthesizedMembers);
            }

            _previousDefinitions = new CSharpDefinitionMap(previousGeneration.OriginalMetadata.Module, edits, metadataDecoder, matchToMetadata, matchToPrevious);
            _previousGeneration = previousGeneration;
            _changes = new SymbolChanges(_previousDefinitions, edits, isAddedSymbol);

            // Workaround for https://github.com/dotnet/roslyn/issues/3192.
            // When compiling state machine we stash types of awaiters and state-machine hoisted variables,
            // so that next generation can look variables up and reuse their slots if possible.
            //
            // When we are about to allocate a slot for a lifted variable while compiling the next generation
            // we map its type to the previous generation and then check the slot types that we stashed earlier.
            // If the variable type matches we reuse it. In order to compare the previous variable type with the current one
            // both need to be completely lowered (translated). Standard translation only goes one level deep. 
            // Generic arguments are not translated until they are needed by metadata writer. 
            //
            // In order to get the fully lowered form we run the type symbols of stashed variables thru a deep translator
            // that translates the symbol recursively.
            _deepTranslator = new CSharpSymbolMatcher.DeepTranslator(sourceAssembly.GetSpecialType(SpecialType.System_Object));
        }
Example #15
0
        public static MetadataWriter Create(
            EmitContext context,
            CommonMessageProvider messageProvider,
            bool allowMissingMethodBodies,
            bool deterministic,
            CancellationToken cancellationToken)
        {
            var heaps = new MetadataHeapsBuilder();

            return(new FullMetadataWriter(context, heaps, messageProvider, allowMissingMethodBodies, deterministic, cancellationToken));
        }
Example #16
0
        Cci.PrimitiveTypeCode Cci.ITypeReference.TypeCode(EmitContext context)
        {
            Debug.Assert(this.IsDefinitionOrDistinct());

            if (this.IsDefinition)
            {
                return this.PrimitiveTypeCode;
            }

            return Cci.PrimitiveTypeCode.NotPrimitive;
        }
        internal static void GetConsolidatedTypeArguments(this ITypeReference typeReference, ArrayBuilder<ITypeReference> consolidatedTypeArguments, EmitContext context)
        {
            INestedTypeReference nestedTypeReference = typeReference.AsNestedTypeReference;
            nestedTypeReference?.GetContainingType(context).GetConsolidatedTypeArguments(consolidatedTypeArguments, context);

            IGenericTypeInstanceReference genTypeInstance = typeReference.AsGenericTypeInstanceReference;
            if (genTypeInstance != null)
            {
                consolidatedTypeArguments.AddRange(genTypeInstance.GetGenericArguments(context));
            }
        }
        ImmutableArray<Cci.ITypeReference> Cci.IGenericTypeInstanceReference.GetGenericArguments(EmitContext context)
        {
            PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;
            var builder = ArrayBuilder<Cci.ITypeReference>.GetInstance();
            foreach (TypeSymbol type in UnderlyingNamedType.TypeArgumentsNoUseSiteDiagnostics)
            {
                builder.Add(moduleBeingBuilt.Translate(type, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, diagnostics: context.Diagnostics));
            }

            return builder.ToImmutableAndFree();
        }
        private static void VisitTypeReference(Cci.ITypeReference typeReference, EmitContext context)
        {
            Debug.Assert(typeReference != null);

            Cci.IArrayTypeReference arrayType = typeReference as Cci.IArrayTypeReference;
            if (arrayType != null)
            {
                VisitTypeReference(arrayType.GetElementType(context), context);
                return;
            }

            Cci.IPointerTypeReference pointerType = typeReference as Cci.IPointerTypeReference;
            if (pointerType != null)
            {
                VisitTypeReference(pointerType.GetTargetType(context), context);
                return;
            }

            Debug.Assert(!(typeReference is Cci.IManagedPointerTypeReference));
            //Cci.IManagedPointerTypeReference managedPointerType = typeReference as Cci.IManagedPointerTypeReference;
            //if (managedPointerType != null)
            //{
            //    VisitTypeReference(managedPointerType.GetTargetType(this.context));
            //    return;
            //}

            Cci.IModifiedTypeReference modifiedType = typeReference as Cci.IModifiedTypeReference;
            if (modifiedType != null)
            {
                foreach (var custModifier in modifiedType.CustomModifiers)
                {
                    VisitTypeReference(custModifier.GetModifier(context), context);
                }
                VisitTypeReference(modifiedType.UnmodifiedType, context);
                return;
            }

            // Visit containing type
            Cci.INestedTypeReference nestedType = typeReference.AsNestedTypeReference;
            if (nestedType != null)
            {
                VisitTypeReference(nestedType.GetContainingType(context), context);
            }

            // Visit generic arguments
            Cci.IGenericTypeInstanceReference genericInstance = typeReference.AsGenericTypeInstanceReference;
            if (genericInstance != null)
            {
                foreach (var arg in genericInstance.GetGenericArguments(context))
                {
                    VisitTypeReference(arg, context);
                }
            }
        }
Example #20
0
        Cci.ITypeReference Cci.ITypeMemberReference.GetContainingType(EmitContext context)
        {
            PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;

            Debug.Assert(this.IsDefinitionOrDistinct());

            if (!this.IsDefinition)
            {
                return moduleBeingBuilt.Translate(this.ContainingType, context.SyntaxNodeOpt, context.Diagnostics);
            }

            return (Cci.ITypeReference)this.ContainingType;
        }
        Cci.ITypeReference Cci.IPointerTypeReference.GetTargetType(EmitContext context)
        {
            var type = ((PEModuleBuilder)context.Module).Translate(this.PointedAtType, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, diagnostics: context.Diagnostics);

            if (this.CustomModifiers.Length == 0)
            {
                return type;
            }
            else
            {
                return new Cci.ModifiedTypeReference(type, this.CustomModifiers.As<Cci.ICustomModifier>());
            }
        }
        Cci.ITypeReference Cci.IFieldReference.GetType(EmitContext context)
        {
            var customModifiers = underlyingField.CustomModifiers;
            var type = ((PEModuleBuilder)context.Module).Translate(underlyingField.Type, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, diagnostics: context.Diagnostics);

            if (customModifiers.Length == 0)
            {
                return type;
            }
            else
            {
                return new Cci.ModifiedTypeReference(type, customModifiers);
            }
        }
Example #23
0
        /// <summary>
        /// Zero or more named arguments that specify values for fields and properties of the attribute.
        /// </summary>
        public ImmutableArray<Cci.IMetadataNamedArgument> GetNamedArguments(EmitContext context)
        {
            // Perform fixup 
            Cci.ITypeReference stringType = context.Module.GetPlatformType(Cci.PlatformType.SystemString, context);

#if DEBUG
            // Must have exactly 1 named argument.
            var namedArgs = this.sourceAttribute.GetNamedArguments(context);
            Debug.Assert(namedArgs.Count() == 1);

            // Named argument must be 'File' property of string type
            var fileArg = namedArgs.First();
            Debug.Assert(fileArg.ArgumentName == FilePropertyName);
            Debug.Assert(context.Module.IsPlatformType(fileArg.Type, Cci.PlatformType.SystemString));

            // Named argument value must be a non-empty string
            Debug.Assert(fileArg.ArgumentValue is Cci.IMetadataConstant);
            var fileName = (string)((Cci.IMetadataConstant)fileArg.ArgumentValue).Value;
            Debug.Assert(!String.IsNullOrEmpty(fileName));

            // PermissionSetAttribute type must have a writable public string type property member 'Hex'
            Debug.Assert(((INamedTypeSymbol)this.sourceAttribute.GetType(context)).GetMembers(HexPropertyName).Any(
                member => member.Kind == SymbolKind.Property && ((IPropertySymbol)member).Type.SpecialType == SpecialType.System_String));
#endif

            string hexFileContent;

            // Read the file contents at the resolved file path into a byte array.
            // May throw PermissionSetFileReadException, which is handled in Compilation.Emit.
            var resolver = context.ModuleBuilder.CommonCompilation.Options.XmlReferenceResolver;

            // If the resolver isn't available we won't get here since we had to use it to resolve the path.
            Debug.Assert(resolver != null);

            try
            {
                using (Stream stream = resolver.OpenReadChecked(resolvedPermissionSetFilePath))
                {
                    // Convert the byte array contents into a string in hexa-decimal format.
                    hexFileContent = ConvertToHex(stream);
                }
            }
            catch (IOException e)
            {
                throw new PermissionSetFileReadException(e.Message, resolvedPermissionSetFilePath);
            }

            // Synthesize a named attribute argument "Hex = hexFileContent".
            return ImmutableArray.Create<Cci.IMetadataNamedArgument>(new HexPropertyMetadataNamedArgument(stringType, new MetadataConstant(stringType, hexFileContent)));
        }
Example #24
0
        public static MetadataWriter Create(
            EmitContext context,
            CommonMessageProvider messageProvider,
            bool allowMissingMethodBodies,
            bool deterministic,
            bool hasPdbStream,
            CancellationToken cancellationToken)
        {
            var heaps = new MetadataHeapsBuilder();

            // Portable PDBs not supported yet:
            MetadataHeapsBuilder debugHeapsOpt = null;

            return(new FullMetadataWriter(context, heaps, debugHeapsOpt, messageProvider, allowMissingMethodBodies, deterministic, cancellationToken));
        }
Example #25
0
        ImmutableArray<Cci.IMetadataNamedArgument> Cci.ICustomAttribute.GetNamedArguments(EmitContext context)
        {
            var commonArgs = this.CommonNamedArguments;
            if (commonArgs.IsEmpty)
            {
                return ImmutableArray<Cci.IMetadataNamedArgument>.Empty;
            }

            var builder = ArrayBuilder<Cci.IMetadataNamedArgument>.GetInstance();
            foreach (var namedArgument in commonArgs)
            {
                builder.Add(CreateMetadataNamedArgument(namedArgument.Key, namedArgument.Value, context));
            }
            return builder.ToImmutableAndFree();
        }
        Cci.ITypeReference Cci.IArrayTypeReference.GetElementType(EmitContext context)
        {
            PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;

            var type = moduleBeingBuilt.Translate(this.ElementType, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, diagnostics: context.Diagnostics);

            if (this.CustomModifiers.Length == 0)
            {
                return type;
            }
            else
            {
                return new Cci.ModifiedTypeReference(type, this.CustomModifiers.As<Cci.ICustomModifier>());
            }
        }
Example #27
0
        ImmutableArray<Cci.IMetadataExpression> Cci.ICustomAttribute.GetArguments(EmitContext context)
        {
            var commonArgs = this.CommonConstructorArguments;
            if (commonArgs.IsEmpty)
            {
                return ImmutableArray<Cci.IMetadataExpression>.Empty;
            }

            var builder = ArrayBuilder<Cci.IMetadataExpression>.GetInstance();
            foreach (var argument in commonArgs)
            {
                Debug.Assert(argument.Kind != TypedConstantKind.Error);
                builder.Add(CreateMetadataExpression(argument, context));
            }
            return builder.ToImmutableAndFree();
        }
        internal static ITypeReference GetUninstantiatedGenericType(this ITypeReference typeReference, EmitContext context)
        {
            IGenericTypeInstanceReference genericTypeInstanceReference = typeReference.AsGenericTypeInstanceReference;
            if (genericTypeInstanceReference != null)
            {
                return genericTypeInstanceReference.GetGenericType(context);
            }

            ISpecializedNestedTypeReference specializedNestedType = typeReference.AsSpecializedNestedTypeReference;
            if (specializedNestedType != null)
            {
                return specializedNestedType.GetUnspecializedVersion(context);
            }

            return typeReference;
        }
Example #29
0
        /// <summary>
        /// When emitting ref assemblies, some members will not be included.
        /// </summary>
        public static bool ShouldInclude(this ITypeDefinitionMember member, EmitContext context)
        {
            if (context.IncludePrivateMembers)
            {
                return(true);
            }

            var method = member as IMethodDefinition;

            if (method != null && method.IsVirtual)
            {
                return(true);
            }

            bool acceptBasedOnVisibility = true;

            switch (member.Visibility)
            {
            case TypeMemberVisibility.Private:
                acceptBasedOnVisibility = context.IncludePrivateMembers;
                break;

            case TypeMemberVisibility.Assembly:
            case TypeMemberVisibility.FamilyAndAssembly:
                acceptBasedOnVisibility = context.IncludePrivateMembers || context.Module.SourceAssemblyOpt?.InternalsAreVisible == true;
                break;
            }

            if (acceptBasedOnVisibility)
            {
                return(true);
            }

            if (method?.IsStatic == true)
            {
                foreach (var methodImplementation in method.ContainingTypeDefinition.GetExplicitImplementationOverrides(context))
                {
                    if (methodImplementation.ImplementingMethod == method)
                    {
                        return(true);
                    }
                }
            }

            return(false);
        }
Example #30
0
        Cci.ITypeReference Cci.IFieldReference.GetType(EmitContext context)
        {
            PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;

            var customModifiers = this.CustomModifiers;
            var isFixed = this.IsFixed;
            var implType = isFixed ? this.FixedImplementationType(moduleBeingBuilt) : this.Type;
            var type = moduleBeingBuilt.Translate(implType, context.SyntaxNodeOpt, context.Diagnostics);

            if (isFixed || customModifiers.Length == 0)
            {
                return type;
            }
            else
            {
                return new Cci.ModifiedTypeReference(type, customModifiers.As<Cci.ICustomModifier>());
            }
        }
Example #31
0
        private Cci.IMetadataExpression CreateMetadataExpression(TypedConstant argument, EmitContext context)
        {
            if (argument.IsNull)
            {
                return CreateMetadataConstant(argument.Type, null, context);
            }

            switch (argument.Kind)
            {
                case TypedConstantKind.Array:
                    return CreateMetadataArray(argument, context);

                case TypedConstantKind.Type:
                    return CreateType(argument, context);

                default:
                    return CreateMetadataConstant(argument.Type, argument.Value, context);
            }
        }
        Cci.ITypeReference Cci.ITypeMemberReference.GetContainingType(EmitContext context)
        {
            Debug.Assert(this.IsDefinitionOrDistinct());

            var synthesizedGlobalMethod = this as SynthesizedGlobalMethodSymbol;
            if ((object)synthesizedGlobalMethod != null)
            {
                return synthesizedGlobalMethod.ContainingPrivateImplementationDetailsType;
            }

            if (!this.IsDefinition)
            {
                PEModuleBuilder moduleBeingBuilt = (PEModuleBuilder)context.Module;
                return moduleBeingBuilt.Translate(this.ContainingType,
                                                  syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt,
                                                  diagnostics: context.Diagnostics);
            }

            return this.ContainingType;
        }
Example #33
0
        private FullMetadataWriter(
            EmitContext context,
            MetadataBuilder builder,
            MetadataBuilder debugBuilderOpt,
            DynamicAnalysisDataWriter dynamicAnalysisDataWriterOpt,
            CommonMessageProvider messageProvider,
            bool metadataOnly,
            bool deterministic,
            bool emitTestCoverageData,
            CancellationToken cancellationToken)
            : base(builder, debugBuilderOpt, dynamicAnalysisDataWriterOpt, context, messageProvider, metadataOnly, deterministic,
                   emitTestCoverageData, cancellationToken)
        {
            // EDMAURER make some intelligent guesses for the initial sizes of these things.
            int numMethods           = this.module.HintNumberOfMethodDefinitions;
            int numTypeDefsGuess     = numMethods / 6;
            int numFieldDefsGuess    = numTypeDefsGuess * 4;
            int numPropertyDefsGuess = numMethods / 4;

            _typeDefs          = new DefinitionIndex <ITypeDefinition>(numTypeDefsGuess);
            _eventDefs         = new DefinitionIndex <IEventDefinition>(0);
            _fieldDefs         = new DefinitionIndex <IFieldDefinition>(numFieldDefsGuess);
            _methodDefs        = new DefinitionIndex <IMethodDefinition>(numMethods);
            _propertyDefs      = new DefinitionIndex <IPropertyDefinition>(numPropertyDefsGuess);
            _parameterDefs     = new DefinitionIndex <IParameterDefinition>(numMethods);
            _genericParameters = new DefinitionIndex <IGenericParameter>(0);

            _fieldDefIndex      = new Dictionary <ITypeDefinition, int>(numTypeDefsGuess);
            _methodDefIndex     = new Dictionary <ITypeDefinition, int>(numTypeDefsGuess);
            _parameterListIndex = new Dictionary <IMethodDefinition, int>(numMethods);

            _assemblyRefIndex         = new HeapOrReferenceIndex <AssemblyIdentity>(this);
            _moduleRefIndex           = new HeapOrReferenceIndex <string>(this);
            _memberRefIndex           = new InstanceAndStructuralReferenceIndex <ITypeMemberReference>(this, new MemberRefComparer(this));
            _methodSpecIndex          = new InstanceAndStructuralReferenceIndex <IGenericMethodInstanceReference>(this, new MethodSpecComparer(this));
            _typeRefIndex             = new HeapOrReferenceIndex <ITypeReference>(this);
            _typeSpecIndex            = new InstanceAndStructuralReferenceIndex <ITypeReference>(this, new TypeSpecComparer(this));
            _standAloneSignatureIndex = new HeapOrReferenceIndex <BlobHandle>(this);
        }
        IEnumerable<Cci.IFileReference> Cci.IAssembly.GetFiles(EmitContext context)
        {
            if (_lazyFiles.IsDefault)
            {
                var builder = ArrayBuilder<Cci.IFileReference>.GetInstance();
                try
                {
                    var modules = _sourceAssembly.Modules;
                    for (int i = 1; i < modules.Length; i++)
                    {
                        builder.Add((Cci.IFileReference)Translate(modules[i], context.Diagnostics));
                    }

                    foreach (ResourceDescription resource in ManifestResources)
                    {
                        if (!resource.IsEmbedded)
                        {
                            builder.Add(resource);
                        }
                    }

                    // Dev12 compilers don't report ERR_CryptoHashFailed if there are no files to be hashed.
                    if (ImmutableInterlocked.InterlockedInitialize(ref _lazyFiles, builder.ToImmutable()) && _lazyFiles.Length > 0)
                    {
                        if (!CryptographicHashProvider.IsSupportedAlgorithm(_sourceAssembly.AssemblyHashAlgorithm))
                        {
                            context.Diagnostics.Add(new CSDiagnostic(new CSDiagnosticInfo(ErrorCode.ERR_CryptoHashFailed), NoLocation.Singleton));
                        }
                    }
                }
                finally
                {
                    builder.Free();
                }
            }

            return _lazyFiles;
        }
        public static void VisitReference(Cci.IReference reference, EmitContext context)
        {
            var typeReference = reference as Cci.ITypeReference;
            if (typeReference != null)
            {
                VisitTypeReference(typeReference, context);
                return;
            }

            var methodReference = reference as Cci.IMethodReference;
            if (methodReference != null)
            {
                VisitMethodReference(methodReference, context);
                return;
            }

            var fieldReference = reference as Cci.IFieldReference;
            if (fieldReference != null)
            {
                VisitFieldReference(fieldReference, context);
                return;
            }
        }
        /// <summary>
        /// Returns true if the namespace scope for this method should be forwarded to another method.
        /// Returns non-null <paramref name="forwardToMethod"/> if the forwarding should be done directly via UsingNamespace,
        /// null if the forwarding is done via custom debug info.
        /// </summary>
        public bool ShouldForwardNamespaceScopes(EmitContext context, IMethodBody methodBody, uint methodToken, out IMethodDefinition forwardToMethod)
        {
            if (ShouldForwardToPreviousMethodWithUsingInfo(context, methodBody) || methodBody.ImportScope == null)
            {
                // SerializeNamespaceScopeMetadata will do the actual forwarding in case this is a CSharp method.
                // VB on the other hand adds a "@methodtoken" to the scopes instead.
                if (context.Module.GenerateVisualBasicStylePdb)
                {
                    forwardToMethod = _previousMethodBodyWithUsingInfo.MethodDefinition;
                }
                else
                {
                    forwardToMethod = null;
                }

                return true;
            }

            _previousMethodBodyWithUsingInfo = methodBody;
            _previousMethodTokenWithUsingInfo = methodToken;
            forwardToMethod = null;
            return false;
        }
Example #37
0
 /// <summary>
 /// A list of the files that constitute the assembly. Empty for netmodule. These are not the source language files that may have been
 /// used to compile the assembly, but the files that contain constituent modules of a multi-module assembly as well
 /// as any external resources. It corresponds to the File table of the .NET assembly file format.
 /// </summary>
 public abstract IEnumerable <Cci.IFileReference> GetFiles(EmitContext context);
Example #38
0
 IEnumerable <Cci.ICustomAttribute> Cci.IReference.GetAttributes(EmitContext context) => SpecializedCollections.EmptyEnumerable <Cci.ICustomAttribute>();
Example #39
0
 /// <summary>
 /// Anonymous types defined in the compilation.
 /// </summary>
 public abstract IEnumerable <Cci.INamespaceTypeDefinition> GetAnonymousTypeDefinitions(EmitContext context);
Example #40
0
 /// <summary>
 /// Top-level embedded types (e.g. attribute types that are not present in referenced assemblies).
 /// </summary>
 public abstract IEnumerable <Cci.INamespaceTypeDefinition> GetEmbeddedTypeDefinitions(EmitContext context);
Example #41
0
 internal TypeReferenceIndexer(EmitContext context)
     : base(context)
 {
 }
Example #42
0
 public override IEnumerable <Cci.INamespaceTypeDefinition> GetEmbeddedTypeDefinitions(EmitContext context)
 => GetEmbeddedTypes(context.Diagnostics);
Example #43
0
        public static bool WritePeToStream(
            EmitContext context,
            CommonMessageProvider messageProvider,
            Func <Stream> getPeStream,
            Func <Stream> getPortablePdbStreamOpt,
            PdbWriter nativePdbWriterOpt,
            string pdbPathOpt,
            bool allowMissingMethodBodies,
            bool isDeterministic,
            CancellationToken cancellationToken)
        {
            // If PDB writer is given, we have to have PDB path.
            Debug.Assert(nativePdbWriterOpt == null || pdbPathOpt != null);

            var mdWriter = FullMetadataWriter.Create(context, messageProvider, allowMissingMethodBodies, isDeterministic, getPortablePdbStreamOpt != null, cancellationToken);

            var properties = context.Module.SerializationProperties;

            nativePdbWriterOpt?.SetMetadataEmitter(mdWriter);

            // Since we are producing a full assembly, we should not have a module version ID
            // imposed ahead-of time. Instead we will compute a deterministic module version ID
            // based on the contents of the generated stream.
            Debug.Assert(properties.PersistentIdentifier == default(Guid));

            var ilBuilder = new BlobBuilder(32 * 1024);
            var mappedFieldDataBuilder = new BlobBuilder();
            var managedResourceBuilder = new BlobBuilder(1024);

            Blob mvidFixup, mvidStringFixup;

            mdWriter.BuildMetadataAndIL(
                nativePdbWriterOpt,
                ilBuilder,
                mappedFieldDataBuilder,
                managedResourceBuilder,
                out mvidFixup,
                out mvidStringFixup);

            MethodDefinitionHandle entryPointHandle;
            MethodDefinitionHandle debugEntryPointHandle;

            mdWriter.GetEntryPoints(out entryPointHandle, out debugEntryPointHandle);

            if (!debugEntryPointHandle.IsNil)
            {
                nativePdbWriterOpt?.SetEntryPoint((uint)MetadataTokens.GetToken(debugEntryPointHandle));
            }

            if (nativePdbWriterOpt != null)
            {
                if (context.Module.SourceLinkStreamOpt != null)
                {
                    nativePdbWriterOpt.EmbedSourceLink(context.Module.SourceLinkStreamOpt);
                }

                if (mdWriter.Module.OutputKind == OutputKind.WindowsRuntimeMetadata)
                {
                    // Dev12: If compiling to winmdobj, we need to add to PDB source spans of
                    //        all types and members for better error reporting by WinMDExp.
                    nativePdbWriterOpt.WriteDefinitionLocations(mdWriter.Module.GetSymbolToLocationMap());
                }
                else
                {
#if DEBUG
                    // validate that all definitions are writable
                    // if same scenario would happen in an winmdobj project
                    nativePdbWriterOpt.AssertAllDefinitionsHaveTokens(mdWriter.Module.GetSymbolToLocationMap());
#endif
                }

                // embedded text not currently supported for native PDB and we should have validated that
                Debug.Assert(!mdWriter.Module.DebugDocumentsBuilder.EmbeddedDocuments.Any());
            }

            Stream peStream = getPeStream();
            if (peStream == null)
            {
                return(false);
            }

            BlobContentId pdbContentId = nativePdbWriterOpt?.GetContentId() ?? default(BlobContentId);

            // the writer shall not be used after this point for writing:
            nativePdbWriterOpt = null;

            ushort portablePdbVersion  = 0;
            var    metadataRootBuilder = mdWriter.GetRootBuilder();

            var peHeaderBuilder = new PEHeaderBuilder(
                machine: properties.Machine,
                sectionAlignment: properties.SectionAlignment,
                fileAlignment: properties.FileAlignment,
                imageBase: properties.BaseAddress,
                majorLinkerVersion: properties.LinkerMajorVersion,
                minorLinkerVersion: properties.LinkerMinorVersion,
                majorOperatingSystemVersion: 4,
                minorOperatingSystemVersion: 0,
                majorImageVersion: 0,
                minorImageVersion: 0,
                majorSubsystemVersion: properties.MajorSubsystemVersion,
                minorSubsystemVersion: properties.MinorSubsystemVersion,
                subsystem: properties.Subsystem,
                dllCharacteristics: properties.DllCharacteristics,
                imageCharacteristics: properties.ImageCharacteristics,
                sizeOfStackReserve: properties.SizeOfStackReserve,
                sizeOfStackCommit: properties.SizeOfStackCommit,
                sizeOfHeapReserve: properties.SizeOfHeapReserve,
                sizeOfHeapCommit: properties.SizeOfHeapCommit);

            var deterministicIdProvider = isDeterministic ?
                                          new Func <IEnumerable <Blob>, BlobContentId>(content => BlobContentId.FromHash(CryptographicHashProvider.ComputeSha1(content))) :
                                          null;

            BlobBuilder portablePdbToEmbed = null;
            if (mdWriter.EmitStandaloneDebugMetadata)
            {
                mdWriter.AddRemainingEmbeddedDocuments(mdWriter.Module.DebugDocumentsBuilder.EmbeddedDocuments);

                var portablePdbBlob    = new BlobBuilder();
                var portablePdbBuilder = mdWriter.GetPortablePdbBuilder(metadataRootBuilder.Sizes.RowCounts, debugEntryPointHandle, deterministicIdProvider);
                pdbContentId       = portablePdbBuilder.Serialize(portablePdbBlob);
                portablePdbVersion = portablePdbBuilder.FormatVersion;

                if (getPortablePdbStreamOpt == null)
                {
                    // embed to debug directory:
                    portablePdbToEmbed = portablePdbBlob;
                }
                else
                {
                    // write to Portable PDB stream:
                    Stream portablePdbStream = getPortablePdbStreamOpt();
                    if (portablePdbStream != null)
                    {
                        portablePdbBlob.WriteContentTo(portablePdbStream);
                    }
                }
            }

            DebugDirectoryBuilder debugDirectoryBuilder;
            if (pdbPathOpt != null || isDeterministic || portablePdbToEmbed != null)
            {
                debugDirectoryBuilder = new DebugDirectoryBuilder();
                if (pdbPathOpt != null)
                {
                    string paddedPath = isDeterministic ? pdbPathOpt : PadPdbPath(pdbPathOpt);
                    debugDirectoryBuilder.AddCodeViewEntry(paddedPath, pdbContentId, portablePdbVersion);
                }

                if (isDeterministic)
                {
                    debugDirectoryBuilder.AddReproducibleEntry();
                }

                if (portablePdbToEmbed != null)
                {
                    debugDirectoryBuilder.AddEmbeddedPortablePdbEntry(portablePdbToEmbed, portablePdbVersion);
                }
            }
            else
            {
                debugDirectoryBuilder = null;
            }

            var peBuilder = new ManagedPEBuilder(
                peHeaderBuilder,
                metadataRootBuilder,
                ilBuilder,
                mappedFieldDataBuilder,
                managedResourceBuilder,
                CreateNativeResourceSectionSerializer(context.Module),
                debugDirectoryBuilder,
                CalculateStrongNameSignatureSize(context.Module),
                entryPointHandle,
                properties.CorFlags,
                deterministicIdProvider);

            var peBlob      = new BlobBuilder();
            var peContentId = peBuilder.Serialize(peBlob);

            PatchModuleVersionIds(mvidFixup, mvidStringFixup, peContentId.Guid);

            try
            {
                peBlob.WriteContentTo(peStream);
            }
            catch (Exception e) when(!(e is OperationCanceledException))
            {
                throw new PeWritingException(e);
            }

            return(true);
        }
Example #44
0
 internal ReferenceIndexerBase(EmitContext context)
     : base(context)
 {
 }
Example #45
0
 internal NoPiaReferenceIndexer(EmitContext context)
     : base(context)
 {
 }
Example #46
0
        /// <summary>
        /// Returns all top-level (not nested) types defined in the module.
        /// </summary>
        public override IEnumerable <Cci.INamespaceTypeDefinition> GetTopLevelTypeDefinitions(EmitContext context)
        {
            Cci.TypeReferenceIndexer typeReferenceIndexer = null;
            HashSet <string>         names;

            // First time through, we need to collect emitted names of all top level types.
            if (_namesOfTopLevelTypes == null)
            {
                names = new HashSet <string>();
            }
            else
            {
                names = null;
            }

            // First time through, we need to push things through TypeReferenceIndexer
            // to make sure we collect all to be embedded NoPia types and members.
            if (EmbeddedTypesManagerOpt != null && !EmbeddedTypesManagerOpt.IsFrozen)
            {
                typeReferenceIndexer = new Cci.TypeReferenceIndexer(context);
                Debug.Assert(names != null);

                // Run this reference indexer on the assembly- and module-level attributes first.
                // We'll run it on all other types below.
                // The purpose is to trigger Translate on all types.
                Dispatch(typeReferenceIndexer);
            }

            AddTopLevelType(names, RootModuleType);
            VisitTopLevelType(typeReferenceIndexer, RootModuleType);
            yield return(RootModuleType);

            foreach (var typeDef in GetAnonymousTypeDefinitions(context))
            {
                AddTopLevelType(names, typeDef);
                VisitTopLevelType(typeReferenceIndexer, typeDef);
                yield return(typeDef);
            }

            foreach (var typeDef in GetTopLevelTypeDefinitionsCore(context))
            {
                AddTopLevelType(names, typeDef);
                VisitTopLevelType(typeReferenceIndexer, typeDef);
                yield return(typeDef);
            }

            var privateImpl = PrivateImplClass;

            if (privateImpl != null)
            {
                AddTopLevelType(names, privateImpl);
                VisitTopLevelType(typeReferenceIndexer, privateImpl);
                yield return(privateImpl);
            }

            if (EmbeddedTypesManagerOpt != null)
            {
                foreach (var embedded in EmbeddedTypesManagerOpt.GetTypes(context.Diagnostics, names))
                {
                    AddTopLevelType(names, embedded);
                    yield return(embedded);
                }
            }

            if (names != null)
            {
                Debug.Assert(_namesOfTopLevelTypes == null);
                _namesOfTopLevelTypes = names;
            }
        }
Example #47
0
 /// <summary>
 /// Top-level named types defined in source.
 /// </summary>
 public abstract IEnumerable <Cci.INamespaceTypeDefinition> GetTopLevelSourceTypeDefinitions(EmitContext context);
Example #48
0
 public Cci.IAssemblyReference GetContainingAssembly(EmitContext context)
 {
     return(OutputKind == OutputKind.NetModule ? null : (Cci.IAssemblyReference) this);
 }
Example #49
0
        /// <summary>
        /// Assembly reference aliases (C# only).
        /// </summary>
        public ImmutableArray <Cci.AssemblyReferenceAlias> GetAssemblyReferenceAliases(EmitContext context)
        {
            if (_lazyAssemblyReferenceAliases.IsDefault)
            {
                ImmutableInterlocked.InterlockedCompareExchange(ref _lazyAssemblyReferenceAliases, CalculateAssemblyReferenceAliases(context), default(ImmutableArray <Cci.AssemblyReferenceAlias>));
            }

            return(_lazyAssemblyReferenceAliases);
        }
Example #50
0
        public void BaseInterfacesInMetadata()
        {
            var text = @"
interface I1 { }
interface I2 : I1 { }
class C : I2 { }
";
            var comp = CreateCompilationWithMscorlib(text);
            var global = comp.GlobalNamespace;

            var baseInterface = global.GetMember<NamedTypeSymbol>("I1");
            var derivedInterface = global.GetMember<NamedTypeSymbol>("I2");
            var @class = global.GetMember<NamedTypeSymbol>("C");

            var bothInterfaces = ImmutableArray.Create<NamedTypeSymbol>(baseInterface, derivedInterface);

            Assert.Equal(baseInterface, derivedInterface.AllInterfaces.Single());
            Assert.Equal(derivedInterface, @class.Interfaces.Single());
            Assert.True(@class.AllInterfaces.SetEquals(bothInterfaces, EqualityComparer<NamedTypeSymbol>.Default));

            var typeDef = (Cci.ITypeDefinition)@class;
            var module = new PEAssemblyBuilder((SourceAssemblySymbol)@class.ContainingAssembly, EmitOptions.Default, OutputKind.DynamicallyLinkedLibrary,
                GetDefaultModulePropertiesForSerialization(), SpecializedCollections.EmptyEnumerable<ResourceDescription>());
            var context = new EmitContext(module, null, new DiagnosticBag());
            var cciInterfaces = typeDef.Interfaces(context).Cast<NamedTypeSymbol>().AsImmutable();
            Assert.True(cciInterfaces.SetEquals(bothInterfaces, EqualityComparer<NamedTypeSymbol>.Default));
            context.Diagnostics.Verify();
        }
Example #51
0
 Cci.IDefinition Cci.IReference.AsDefinition(EmitContext context)
 {
     Debug.Assert(ReferenceEquals(context.Module, this));
     return(this);
 }
Example #52
0
        private ImmutableArray <Cci.AssemblyReferenceAlias> CalculateAssemblyReferenceAliases(EmitContext context)
        {
            var result = ArrayBuilder <Cci.AssemblyReferenceAlias> .GetInstance();

            foreach (var assemblyAndAliases in CommonCompilation.GetBoundReferenceManager().GetReferencedAssemblyAliases())
            {
                var assembly = assemblyAndAliases.Item1;
                var aliases  = assemblyAndAliases.Item2;

                for (int i = 0; i < aliases.Length; i++)
                {
                    string alias = aliases[i];

                    // filter out duplicates and global aliases:
                    if (alias != MetadataReferenceProperties.GlobalAlias && aliases.IndexOf(alias, 0, i) < 0)
                    {
                        result.Add(new Cci.AssemblyReferenceAlias(alias, Translate(assembly, context.Diagnostics)));
                    }
                }
            }

            return(result.ToImmutableAndFree());
        }
Example #53
0
 /// <summary>
 /// CorLibrary assembly referenced by this module.
 /// </summary>
 public Cci.IAssemblyReference GetCorLibrary(EmitContext context)
 {
     return(Translate(CommonCorLibrary, context.Diagnostics));
 }
Example #54
0
 public override IEnumerable <Cci.INamespaceTypeDefinition> GetAdditionalTopLevelTypeDefinitions(EmitContext context)
 => GetAdditionalTopLevelTypes(context.Diagnostics);
Example #55
0
        internal static bool WritePeToStream(
            EmitContext context,
            CommonMessageProvider messageProvider,
            Func <Stream> getPeStream,
            Func <Stream> getPortablePdbStreamOpt,
            PdbWriter nativePdbWriterOpt,
            string pdbPathOpt,
            bool metadataOnly,
            bool isDeterministic,
            bool emitTestCoverageData,
            RSAParameters?privateKeyOpt,
            CancellationToken cancellationToken)
        {
            // If PDB writer is given, we have to have PDB path.
            Debug.Assert(nativePdbWriterOpt == null || pdbPathOpt != null);

            var mdWriter = FullMetadataWriter.Create(context, messageProvider, metadataOnly, isDeterministic,
                                                     emitTestCoverageData, getPortablePdbStreamOpt != null, cancellationToken);

            var properties = context.Module.SerializationProperties;

            nativePdbWriterOpt?.SetMetadataEmitter(mdWriter);

            // Since we are producing a full assembly, we should not have a module version ID
            // imposed ahead-of time. Instead we will compute a deterministic module version ID
            // based on the contents of the generated stream.
            Debug.Assert(properties.PersistentIdentifier == default(Guid));

            var ilBuilder = new BlobBuilder(32 * 1024);
            var mappedFieldDataBuilder = new BlobBuilder();
            var managedResourceBuilder = new BlobBuilder(1024);

            Blob mvidFixup, mvidStringFixup;

            mdWriter.BuildMetadataAndIL(
                nativePdbWriterOpt,
                ilBuilder,
                mappedFieldDataBuilder,
                managedResourceBuilder,
                out mvidFixup,
                out mvidStringFixup);

            MethodDefinitionHandle entryPointHandle;
            MethodDefinitionHandle debugEntryPointHandle;

            mdWriter.GetEntryPoints(out entryPointHandle, out debugEntryPointHandle);

            if (!debugEntryPointHandle.IsNil)
            {
                nativePdbWriterOpt?.SetEntryPoint(MetadataTokens.GetToken(debugEntryPointHandle));
            }

            if (nativePdbWriterOpt != null)
            {
                if (context.Module.SourceLinkStreamOpt != null)
                {
                    nativePdbWriterOpt.EmbedSourceLink(context.Module.SourceLinkStreamOpt);
                }

                if (mdWriter.Module.OutputKind == OutputKind.WindowsRuntimeMetadata)
                {
                    // Dev12: If compiling to winmdobj, we need to add to PDB source spans of
                    //        all types and members for better error reporting by WinMDExp.
                    nativePdbWriterOpt.WriteDefinitionLocations(mdWriter.Module.GetSymbolToLocationMap());
                }
                else
                {
#if DEBUG
                    // validate that all definitions are writable
                    // if same scenario would happen in an winmdobj project
                    nativePdbWriterOpt.AssertAllDefinitionsHaveTokens(mdWriter.Module.GetSymbolToLocationMap());
#endif
                }

                nativePdbWriterOpt.WriteRemainingEmbeddedDocuments(mdWriter.Module.DebugDocumentsBuilder.EmbeddedDocuments);
            }

            Stream peStream = getPeStream();
            if (peStream == null)
            {
                return(false);
            }

            BlobContentId pdbContentId = nativePdbWriterOpt?.GetContentId() ?? default;

            // the writer shall not be used after this point for writing:
            nativePdbWriterOpt = null;

            ushort portablePdbVersion  = 0;
            var    metadataRootBuilder = mdWriter.GetRootBuilder();

            var peHeaderBuilder = new PEHeaderBuilder(
                machine: properties.Machine,
                sectionAlignment: properties.SectionAlignment,
                fileAlignment: properties.FileAlignment,
                imageBase: properties.BaseAddress,
                majorLinkerVersion: properties.LinkerMajorVersion,
                minorLinkerVersion: properties.LinkerMinorVersion,
                majorOperatingSystemVersion: 4,
                minorOperatingSystemVersion: 0,
                majorImageVersion: 0,
                minorImageVersion: 0,
                majorSubsystemVersion: properties.MajorSubsystemVersion,
                minorSubsystemVersion: properties.MinorSubsystemVersion,
                subsystem: properties.Subsystem,
                dllCharacteristics: properties.DllCharacteristics,
                imageCharacteristics: properties.ImageCharacteristics,
                sizeOfStackReserve: properties.SizeOfStackReserve,
                sizeOfStackCommit: properties.SizeOfStackCommit,
                sizeOfHeapReserve: properties.SizeOfHeapReserve,
                sizeOfHeapCommit: properties.SizeOfHeapCommit);

            // TODO: replace SHA1 with non-crypto alg: https://github.com/dotnet/roslyn/issues/24737
            var peIdProvider = isDeterministic ?
                               new Func <IEnumerable <Blob>, BlobContentId>(content => BlobContentId.FromHash(CryptographicHashProvider.ComputeHash(HashAlgorithmName.SHA1, content))) :
                               null;

            // We need to calculate the PDB checksum, so we may as well use the calculated hash for PDB ID regardless of whether deterministic build is requested.
            var portablePdbContentHash = default(ImmutableArray <byte>);

            BlobBuilder portablePdbToEmbed = null;
            if (mdWriter.EmitPortableDebugMetadata)
            {
                mdWriter.AddRemainingEmbeddedDocuments(mdWriter.Module.DebugDocumentsBuilder.EmbeddedDocuments);

                // The algorithm must be specified for deterministic builds (checked earlier).
                Debug.Assert(!isDeterministic || context.Module.PdbChecksumAlgorithm.Name != null);

                var portablePdbIdProvider = (context.Module.PdbChecksumAlgorithm.Name != null) ?
                                            new Func <IEnumerable <Blob>, BlobContentId>(content => BlobContentId.FromHash(portablePdbContentHash = CryptographicHashProvider.ComputeHash(context.Module.PdbChecksumAlgorithm, content))) :
                                            null;

                var portablePdbBlob    = new BlobBuilder();
                var portablePdbBuilder = mdWriter.GetPortablePdbBuilder(metadataRootBuilder.Sizes.RowCounts, debugEntryPointHandle, portablePdbIdProvider);
                pdbContentId       = portablePdbBuilder.Serialize(portablePdbBlob);
                portablePdbVersion = portablePdbBuilder.FormatVersion;

                if (getPortablePdbStreamOpt == null)
                {
                    // embed to debug directory:
                    portablePdbToEmbed = portablePdbBlob;
                }
                else
                {
                    // write to Portable PDB stream:
                    Stream portablePdbStream = getPortablePdbStreamOpt();
                    if (portablePdbStream != null)
                    {
                        try
                        {
                            portablePdbBlob.WriteContentTo(portablePdbStream);
                        }
                        catch (Exception e) when(!(e is OperationCanceledException))
                        {
                            throw new SymUnmanagedWriterException(e.Message, e);
                        }
                    }
                }
            }

            DebugDirectoryBuilder debugDirectoryBuilder;
            if (pdbPathOpt != null || isDeterministic || portablePdbToEmbed != null)
            {
                debugDirectoryBuilder = new DebugDirectoryBuilder();
                if (pdbPathOpt != null)
                {
                    string paddedPath = isDeterministic ? pdbPathOpt : PadPdbPath(pdbPathOpt);
                    debugDirectoryBuilder.AddCodeViewEntry(paddedPath, pdbContentId, portablePdbVersion);

                    if (!portablePdbContentHash.IsDefault)
                    {
                        // Emit PDB Checksum entry for Portable and Embedded PDBs. The checksum is not as useful when the PDB is embedded,
                        // however it allows the client to efficiently validate a standalone Portable PDB that
                        // has been extracted from Embedded PDB and placed next to the PE file.
                        debugDirectoryBuilder.AddPdbChecksumEntry(context.Module.PdbChecksumAlgorithm.Name, portablePdbContentHash);
                    }
                }

                if (isDeterministic)
                {
                    debugDirectoryBuilder.AddReproducibleEntry();
                }

                if (portablePdbToEmbed != null)
                {
                    debugDirectoryBuilder.AddEmbeddedPortablePdbEntry(portablePdbToEmbed, portablePdbVersion);
                }
            }
            else
            {
                debugDirectoryBuilder = null;
            }

            var strongNameProvider = context.Module.CommonCompilation.Options.StrongNameProvider;
            var corFlags           = properties.CorFlags;

            var peBuilder = new ExtendedPEBuilder(
                peHeaderBuilder,
                metadataRootBuilder,
                ilBuilder,
                mappedFieldDataBuilder,
                managedResourceBuilder,
                CreateNativeResourceSectionSerializer(context.Module),
                debugDirectoryBuilder,
                CalculateStrongNameSignatureSize(context.Module, privateKeyOpt),
                entryPointHandle,
                corFlags,
                peIdProvider,
                metadataOnly && !context.IncludePrivateMembers);

            var peBlob      = new BlobBuilder();
            var peContentId = peBuilder.Serialize(peBlob, out Blob mvidSectionFixup);

            PatchModuleVersionIds(mvidFixup, mvidSectionFixup, mvidStringFixup, peContentId.Guid);

            if (privateKeyOpt != null && corFlags.HasFlag(CorFlags.StrongNameSigned))
            {
                Debug.Assert(strongNameProvider.Capability == SigningCapability.SignsPeBuilder);
                strongNameProvider.SignPeBuilder(peBuilder, peBlob, privateKeyOpt.Value);
            }

            try
            {
                peBlob.WriteContentTo(peStream);
            }
            catch (Exception e) when(!(e is OperationCanceledException))
            {
                throw new PeWritingException(e);
            }

            return(true);
        }
Example #56
0
 Cci.ITypeReference Cci.IParameterTypeInformation.GetType(EmitContext context)
 {
     return type;
 }
Example #57
0
 public abstract Cci.ITypeReference GetPlatformType(Cci.PlatformType platformType, EmitContext context);
Example #58
0
        public IEnumerable <Cci.INamespaceTypeDefinition> GetTopLevelTypeDefinitionsCore(EmitContext context)
        {
            foreach (var typeDef in GetAdditionalTopLevelTypeDefinitions(context))
            {
                yield return(typeDef);
            }

            foreach (var typeDef in GetEmbeddedTypeDefinitions(context))
            {
                yield return(typeDef);
            }

            foreach (var typeDef in GetTopLevelSourceTypeDefinitions(context))
            {
                yield return(typeDef);
            }
        }
Example #59
0
 Cci.ITypeReference Cci.IParameterTypeInformation.GetType(EmitContext context)
 {
     return ((PEModuleBuilder)context.Module).Translate(UnderlyingParameter.Type, syntaxNodeOpt: (CSharpSyntaxNode)context.SyntaxNodeOpt, diagnostics: context.Diagnostics);
 }
Example #60
0
 protected abstract Cci.IAssemblyReference GetCorLibraryReferenceToEmit(EmitContext context);