private static bool CheckCore(
            string baseDirectory,
            IEnumerable <CommandLineAnalyzerReference> analyzerReferences,
            IAnalyzerAssemblyLoader loader,
            ICompilerServerLogger?logger,
            [NotNullWhen(false)]
            out List <string>?errorMessages)
        {
            errorMessages = null;
            var resolvedPaths = new List <string>();

            foreach (var analyzerReference in analyzerReferences)
            {
                string?resolvedPath = FileUtilities.ResolveRelativePath(analyzerReference.FilePath, basePath: null, baseDirectory: baseDirectory, searchPaths: SpecializedCollections.EmptyEnumerable <string>(), fileExists: File.Exists);
                if (resolvedPath != null)
                {
                    resolvedPath = FileUtilities.TryNormalizeAbsolutePath(resolvedPath);
                    if (resolvedPath != null)
                    {
                        resolvedPaths.Add(resolvedPath);
                    }
                }

                // Don't worry about paths we can't resolve. The compiler will report an error for that later.
            }

            // Register analyzers and their dependencies upfront,
            // so that assembly references can be resolved:
            foreach (var resolvedPath in resolvedPaths)
            {
                loader.AddDependencyLocation(resolvedPath);
            }

            // Load all analyzer assemblies:
            var loadedAssemblies = new List <Assembly>();

            foreach (var resolvedPath in resolvedPaths)
            {
                loadedAssemblies.Add(loader.LoadFromPath(resolvedPath));
            }

            // Third, check that the MVIDs of the files on disk match the MVIDs of the loaded assemblies.
            for (int i = 0; i < resolvedPaths.Count; i++)
            {
                var resolvedPath       = resolvedPaths[i];
                var loadedAssembly     = loadedAssemblies[i];
                var resolvedPathMvid   = AssemblyUtilities.ReadMvid(resolvedPath);
                var loadedAssemblyMvid = loadedAssembly.ManifestModule.ModuleVersionId;

                if (resolvedPathMvid != loadedAssemblyMvid)
                {
                    var message = $"analyzer assembly '{resolvedPath}' has MVID '{resolvedPathMvid}' but loaded assembly '{loadedAssembly.FullName}' has MVID '{loadedAssemblyMvid}'";
                    errorMessages ??= new List <string>();
                    errorMessages.Add(message);
                }
            }

            return(errorMessages == null);
        }
        public Assembly GetAssembly()
        {
            if (_lazyAssembly == null)
            {
                _lazyAssembly = _assemblyLoader.LoadFromPath(_fullPath);
            }

            return(_lazyAssembly);
        }
        /// <summary>
        /// Instantiates a single plugin based on an attribute that implements <see cref="ICompilerPluginAttribute"/>.
        /// </summary>
        private ICompilerPlugin InstantiatePlugin(Compilation compilation, AttributeData attribute)
        {
            INamedTypeSymbol attributeClass = attribute.AttributeClass;
            string           assemblyPath   = GetAssemblyPath(compilation, attributeClass.ContainingAssembly);
            Assembly         assembly       = _assemblyLoader.LoadFromPath(assemblyPath);
            string           attributeName  = attributeClass.ToDisplayString(SymbolDisplayFormat.QualifiedNameOnlyFormat);
            Type             attributeType  = assembly.GetType(attributeName);
            var instance = (ICompilerPluginAttribute)Activator.CreateInstance(attributeType);

            return(instance.Create());
        }
Esempio n. 4
0
 public Assembly LoadFromPath(string fullPath)
 {
     try {
         // We want to load the analyzer assembly assets in default context.
         // Use Assembly.Load instead of Assembly.LoadFrom to ensure that if the assembly is ngen'ed, then the native image gets loaded.
         return(Assembly.Load(AssemblyName.GetAssemblyName(fullPath)));
     } catch (Exception) {
         // Use the fallback loader if we fail to load the assembly in the default context.
         return(fallbackLoader.LoadFromPath(fullPath));
     }
 }
Esempio n. 5
0
        private static bool CheckCore(string baseDirectory, IEnumerable <CommandLineAnalyzerReference> analyzerReferences, IAnalyzerAssemblyLoader loader, IEnumerable <string> ignorableReferenceNames)
        {
            var resolvedPaths = new List <string>();

            foreach (var analyzerReference in analyzerReferences)
            {
                string resolvedPath = FileUtilities.ResolveRelativePath(analyzerReference.FilePath, basePath: null, baseDirectory: baseDirectory, searchPaths: SpecializedCollections.EmptyEnumerable <string>(), fileExists: File.Exists);
                if (resolvedPath != null)
                {
                    resolvedPath = FileUtilities.TryNormalizeAbsolutePath(resolvedPath);
                    if (resolvedPath != null)
                    {
                        resolvedPaths.Add(resolvedPath);
                    }
                }

                // Don't worry about paths we can't resolve. The compiler will report an error for that later.
            }

            // First, check that the set of references is complete, modulo items in the safe list.
            foreach (var resolvedPath in resolvedPaths)
            {
                var missingDependencies = AssemblyUtilities.IdentifyMissingDependencies(resolvedPath, resolvedPaths);

                foreach (var missingDependency in missingDependencies)
                {
                    if (!ignorableReferenceNames.Any(name => missingDependency.Name.StartsWith(name)))
                    {
                        CompilerServerLogger.Log($"Analyzer assembly {resolvedPath} depends on '{missingDependency}' but it was not found.");
                        return(false);
                    }
                }
            }

            // Register analyzers and their dependencies upfront,
            // so that assembly references can be resolved:
            foreach (var resolvedPath in resolvedPaths)
            {
                loader.AddDependencyLocation(resolvedPath);
            }

            // Load all analyzer assemblies:
            var loadedAssemblies = new List <Assembly>();

            foreach (var resolvedPath in resolvedPaths)
            {
                loadedAssemblies.Add(loader.LoadFromPath(resolvedPath));
            }

            // Third, check that the MVIDs of the files on disk match the MVIDs of the loaded assemblies.
            for (int i = 0; i < resolvedPaths.Count; i++)
            {
                var resolvedPath       = resolvedPaths[i];
                var loadedAssembly     = loadedAssemblies[i];
                var resolvedPathMvid   = AssemblyUtilities.ReadMvid(resolvedPath);
                var loadedAssemblyMvid = loadedAssembly.ManifestModule.ModuleVersionId;

                if (resolvedPathMvid != loadedAssemblyMvid)
                {
                    CompilerServerLogger.Log($"Analyzer assembly {resolvedPath} has MVID '{resolvedPathMvid}' but loaded assembly '{loadedAssembly.FullName}' has MVID '{loadedAssemblyMvid}'.");
                    return(false);
                }
            }

            return(true);
        }
        private static bool CheckCore(string baseDirectory, IEnumerable<CommandLineAnalyzerReference> analyzerReferences, IAnalyzerAssemblyLoader loader, IEnumerable<string> ignorableReferenceNames)
        {
            var resolvedPaths = new List<string>();

            foreach (var analyzerReference in analyzerReferences)
            {
                string resolvedPath = FileUtilities.ResolveRelativePath(analyzerReference.FilePath, basePath: null, baseDirectory: baseDirectory, searchPaths: SpecializedCollections.EmptyEnumerable<string>(), fileExists: File.Exists);
                if (File.Exists(resolvedPath))
                {
                    resolvedPath = FileUtilities.TryNormalizeAbsolutePath(resolvedPath);
                    if (resolvedPath != null)
                    {
                        resolvedPaths.Add(resolvedPath);
                    }
                }

                // Don't worry about paths we can't resolve. The compiler will report an error for that later.
            }

            // First, check that the set of references is complete, modulo items in the safe list.
            foreach (var resolvedPath in resolvedPaths)
            {
                var missingDependencies = AssemblyUtilities.IdentifyMissingDependencies(resolvedPath, resolvedPaths);

                foreach (var missingDependency in missingDependencies)
                {
                    if (!ignorableReferenceNames.Any(name => missingDependency.Name.StartsWith(name)))
                    {
                        CompilerServerLogger.Log($"Analyzer assembly {resolvedPath} depends on '{missingDependency}' but it was not found.");
                        return false;
                    }
                }
            }

            // Second, load all of the assemblies upfront.
            foreach (var resolvedPath in resolvedPaths)
            {
                loader.AddDependencyLocation(resolvedPath);
            }

            var loadedAssemblies = new List<Assembly>();
            foreach (var resolvedPath in resolvedPaths)
            {
                loadedAssemblies.Add(loader.LoadFromPath(resolvedPath));
            }

            // Third, check that the MVIDs of the files on disk match the MVIDs of the loaded assemblies.
            for (int i = 0; i < resolvedPaths.Count; i++)
            {
                var resolvedPath = resolvedPaths[i];
                var loadedAssembly = loadedAssemblies[i];
                var resolvedPathMvid = AssemblyUtilities.ReadMvid(resolvedPath);
                var loadedAssemblyMvid = loadedAssembly.ManifestModule.ModuleVersionId;

                if (resolvedPathMvid != loadedAssemblyMvid)
                {
                    CompilerServerLogger.Log($"Analyzer assembly {resolvedPath} has MVID '{resolvedPathMvid}' but loaded assembly '{loadedAssembly.FullName}' has MVID '{loadedAssemblyMvid}'.");
                    return false;
                }
            }

            return true;
        }
Esempio n. 7
0
 public Assembly LoadFromPath(string fullPath) => _desktopLoader.LoadFromPath(ResolvePath(fullPath));
Esempio n. 8
0
 public Assembly LoadFromPath(string fullPath)
 {
     return(_impl.LoadFromPath(fullPath));
 }