Esempio n. 1
0
 internal static EvaluationContext CreateMethodContext(
     AppDomain appDomain,
     ImmutableArray <MetadataBlock> blocks,
     ISymUnmanagedReader symReader,
     Guid moduleVersionId,
     int methodToken,
     int methodVersion,
     uint ilOffset,
     int localSignatureToken,
     MakeAssemblyReferencesKind kind = MakeAssemblyReferencesKind.AllAssemblies
     )
 {
     return(CSharpExpressionCompiler.CreateMethodContext(
                appDomain,
                ad => ad.GetMetadataContext(),
                (ad, mc, report) => ad.SetMetadataContext(mc),
                blocks,
                symReader,
                moduleVersionId,
                methodToken,
                methodVersion,
                ilOffset,
                localSignatureToken,
                kind
                ));
 }
Esempio n. 2
0
        internal static CSharpCompilation ToCompilation(
            this ImmutableArray <MetadataBlock> metadataBlocks,
            Guid moduleVersionId,
            MakeAssemblyReferencesKind kind
            )
        {
            var references = metadataBlocks.MakeAssemblyReferences(
                moduleVersionId,
                IdentityComparer,
                kind,
                out var referencesBySimpleName
                );
            var options = s_compilationOptions;

            if (referencesBySimpleName != null)
            {
                Debug.Assert(kind == MakeAssemblyReferencesKind.AllReferences);
                var resolver = new EEMetadataReferenceResolver(
                    IdentityComparer,
                    referencesBySimpleName
                    );
                options = options.WithMetadataReferenceResolver(resolver);
            }
            return(CSharpCompilation.Create(
                       assemblyName: ExpressionCompilerUtilities.GenerateUniqueName(),
                       references: references,
                       options: options
                       ));
        }
Esempio n. 3
0
 internal static MetadataContextId GetContextId(
     Guid moduleVersionId,
     MakeAssemblyReferencesKind kind
     )
 {
     return(kind switch
     {
         MakeAssemblyReferencesKind.AllAssemblies => default,
        internal static EvaluationContext CreateTypeContext <TAppDomain>(
            TAppDomain appDomain,
            GetMetadataContextDelegate <TAppDomain> getMetadataContext,
            ImmutableArray <MetadataBlock> metadataBlocks,
            Guid moduleVersionId,
            int typeToken,
            MakeAssemblyReferencesKind kind)
        {
            CSharpCompilation?compilation;

            if (kind == MakeAssemblyReferencesKind.DirectReferencesOnly)
            {
                // Avoid using the cache for referenced assemblies only
                // since this should be the exceptional case.
                compilation = metadataBlocks.ToCompilationReferencedModulesOnly(moduleVersionId);
                return(EvaluationContext.CreateTypeContext(
                           compilation,
                           moduleVersionId,
                           typeToken));
            }

            var contextId = MetadataContextId.GetContextId(moduleVersionId, kind);
            var previous  = getMetadataContext(appDomain);
            CSharpMetadataContext previousMetadataContext = default;

            if (previous.Matches(metadataBlocks))
            {
                previous.AssemblyContexts.TryGetValue(contextId, out previousMetadataContext);
            }

            // Re-use the previous compilation if possible.
            compilation = previousMetadataContext.Compilation;
            if (compilation == null)
            {
                compilation = metadataBlocks.ToCompilation(moduleVersionId, kind);
            }

            var context = EvaluationContext.CreateTypeContext(
                compilation,
                moduleVersionId,
                typeToken);

            // New type context is not attached to the AppDomain since it is less
            // re-usable than the previous attached method context. (We could hold
            // on to it if we don't have a previous method context but it's unlikely
            // that we evaluated a type-level expression before a method-level.)
            Debug.Assert(context != previousMetadataContext.EvaluationContext);

            return(context);
        }
Esempio n. 5
0
        internal static MetadataContextId GetContextId(Guid moduleVersionId, MakeAssemblyReferencesKind kind)
        {
            switch (kind)
            {
            case MakeAssemblyReferencesKind.AllAssemblies:
                return(default);

            case MakeAssemblyReferencesKind.AllReferences:
                return(new MetadataContextId(moduleVersionId));

            default:
                throw ExceptionUtilities.UnexpectedValue(kind);
            }
        }
 internal static EvaluationContext CreateTypeContext(
     AppDomain appDomain,
     ImmutableArray <MetadataBlock> blocks,
     Guid moduleVersionId,
     int typeToken,
     MakeAssemblyReferencesKind kind = MakeAssemblyReferencesKind.AllAssemblies)
 {
     return(CSharpExpressionCompiler.CreateTypeContext(
                appDomain,
                ad => ad.GetMetadataContext(),
                blocks,
                moduleVersionId,
                typeToken,
                kind));
 }
Esempio n. 7
0
        internal static EvaluationContext CreateMethodContext <TAppDomain>(
            TAppDomain appDomain,
            GetMetadataContextDelegate <TAppDomain> getMetadataContext,
            SetMetadataContextDelegate <TAppDomain> setMetadataContext,
            ImmutableArray <MetadataBlock> metadataBlocks,
            object?symReader,
            Guid moduleVersionId,
            int methodToken,
            int methodVersion,
            uint ilOffset,
            int localSignatureToken,
            MakeAssemblyReferencesKind kind)
        {
            CSharpCompilation compilation;
            int offset = EvaluationContextBase.NormalizeILOffset(ilOffset);

            if (kind == MakeAssemblyReferencesKind.DirectReferencesOnly)
            {
                // Avoid using the cache for referenced assemblies only
                // since this should be the exceptional case.
                compilation = metadataBlocks.ToCompilationReferencedModulesOnly(moduleVersionId);
                return(EvaluationContext.CreateMethodContext(
                           compilation,
                           symReader,
                           moduleVersionId,
                           methodToken,
                           methodVersion,
                           offset,
                           localSignatureToken));
            }

            var contextId        = MetadataContextId.GetContextId(moduleVersionId, kind);
            var previous         = getMetadataContext(appDomain);
            var assemblyContexts = previous.Matches(metadataBlocks) ? previous.AssemblyContexts : ImmutableDictionary <MetadataContextId, CSharpMetadataContext> .Empty;
            CSharpMetadataContext previousMetadataContext;

            assemblyContexts.TryGetValue(contextId, out previousMetadataContext);

            // Re-use the previous compilation if possible.
            compilation = previousMetadataContext.Compilation;
            if (compilation != null)
            {
                // Re-use entire context if method scope has not changed.
                var previousContext = previousMetadataContext.EvaluationContext;
                if (previousContext != null &&
                    previousContext.MethodContextReuseConstraints.HasValue &&
                    previousContext.MethodContextReuseConstraints.GetValueOrDefault().AreSatisfied(moduleVersionId, methodToken, methodVersion, offset))
                {
                    return(previousContext);
                }
            }
            else
            {
                compilation = metadataBlocks.ToCompilation(moduleVersionId, kind);
            }

            var context = EvaluationContext.CreateMethodContext(
                compilation,
                symReader,
                moduleVersionId,
                methodToken,
                methodVersion,
                offset,
                localSignatureToken);

            if (context != previousMetadataContext.EvaluationContext)
            {
                setMetadataContext(
                    appDomain,
                    new MetadataContext <CSharpMetadataContext>(
                        metadataBlocks,
                        assemblyContexts.SetItem(contextId, new CSharpMetadataContext(context.Compilation, context))),
                    report: kind == MakeAssemblyReferencesKind.AllReferences);
            }

            return(context);
        }
Esempio n. 8
0
 /// <summary>
 /// Group module metadata into assemblies.
 /// If <paramref name="moduleVersionId"/> is set, the
 /// assemblies are limited to those referenced by that module.
 /// </summary>
 internal static ImmutableArray <MetadataReference> MakeAssemblyReferences(
     this ImmutableArray <MetadataBlock> metadataBlocks,
     Guid moduleVersionId,
     AssemblyIdentityComparer identityComparer,
     MakeAssemblyReferencesKind kind,
     out IReadOnlyDictionary <