Skip to content

Commit b79d738

Browse files
authored
Merge pull request github#15993 from michaelnebel/csharp/assemblycachefiltering
C#: Exclude Semmle.* dlls when using the executing runtime.
2 parents dc3ea6c + ef68e33 commit b79d738

File tree

8 files changed

+374
-92
lines changed

8 files changed

+374
-92
lines changed

csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCache.cs

Lines changed: 2 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
using System.Collections.Generic;
2-
using System.IO;
32
using System.Linq;
43
using Semmle.Util.Logging;
54

@@ -20,44 +19,16 @@ internal class AssemblyCache
2019
/// assembly cache.
2120
/// </param>
2221
/// <param name="logger">Callback for progress.</param>
23-
public AssemblyCache(IEnumerable<string> paths, IEnumerable<string> frameworkPaths, ILogger logger)
22+
public AssemblyCache(IEnumerable<AssemblyLookupLocation> paths, IEnumerable<string> frameworkPaths, ILogger logger)
2423
{
2524
this.logger = logger;
2625
foreach (var path in paths)
2726
{
28-
if (File.Exists(path))
29-
{
30-
dllsToIndex.Add(path);
31-
continue;
32-
}
33-
34-
if (Directory.Exists(path))
35-
{
36-
logger.LogInfo($"Finding reference DLLs in {path}...");
37-
AddReferenceDirectory(path);
38-
}
39-
else
40-
{
41-
logger.LogInfo("AssemblyCache: Path not found: " + path);
42-
}
27+
dllsToIndex.AddRange(path.GetDlls(logger));
4328
}
4429
IndexReferences(frameworkPaths);
4530
}
4631

47-
/// <summary>
48-
/// Finds all assemblies nested within a directory
49-
/// and adds them to its index.
50-
/// (Indexing is performed at a later stage by IndexReferences()).
51-
/// </summary>
52-
/// <param name="dir">The directory to index.</param>
53-
private void AddReferenceDirectory(string dir)
54-
{
55-
foreach (var dll in new DirectoryInfo(dir).EnumerateFiles("*.dll", SearchOption.AllDirectories))
56-
{
57-
dllsToIndex.Add(dll.FullName);
58-
}
59-
}
60-
6132
/// <summary>
6233
/// Indexes all DLLs we have located.
6334
/// Because this is a potentially time-consuming operation, it is put into a separate stage.
Lines changed: 95 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.IO;
4+
using System.Linq;
5+
using Semmle.Util.Logging;
6+
7+
namespace Semmle.Extraction.CSharp.DependencyFetching
8+
{
9+
/// <summary>
10+
/// Used to represent a path to an assembly or a directory containing assemblies
11+
/// and a selector function to determine which files to include, when indexing the assemblies.
12+
/// </summary>
13+
internal sealed class AssemblyLookupLocation(string path, Func<string, bool> includeFileName, bool indexSubdirectories = true)
14+
{
15+
public string Path => path;
16+
17+
public AssemblyLookupLocation(string path) : this(path, _ => true) { }
18+
19+
public static implicit operator AssemblyLookupLocation(string path) => new(path);
20+
21+
/// <summary>
22+
/// Finds all assemblies nested within the directory `path`
23+
/// and adds them to the a list of assembly names to index.
24+
/// Indexing is performed at a later stage. This only collects the names.
25+
/// </summary>
26+
/// <param name="dllsToIndex">List of dlls to index.</param>
27+
/// <param name="logger">Logger.</param>
28+
private void AddReferenceDirectory(List<string> dllsToIndex, ILogger logger)
29+
{
30+
try
31+
{
32+
var dlls = new DirectoryInfo(path).EnumerateFiles("*.dll", new EnumerationOptions { RecurseSubdirectories = indexSubdirectories, MatchCasing = MatchCasing.CaseInsensitive, AttributesToSkip = FileAttributes.None });
33+
if (!dlls.Any())
34+
{
35+
logger.LogWarning($"AssemblyLookupLocation: No DLLs found in the path '{path}'.");
36+
return;
37+
}
38+
foreach (var dll in dlls)
39+
{
40+
if (includeFileName(dll.Name))
41+
{
42+
dllsToIndex.Add(dll.FullName);
43+
}
44+
else
45+
{
46+
logger.LogInfo($"AssemblyLookupLocation: Skipping {dll.FullName}.");
47+
}
48+
}
49+
}
50+
catch (Exception e)
51+
{
52+
logger.LogError($"AssemblyLookupLocation: Error while searching for DLLs in '{path}': {e.Message}");
53+
}
54+
}
55+
56+
/// <summary>
57+
/// Returns a list of paths to all assemblies in `path` that should be indexed.
58+
/// </summary>
59+
/// <param name="logger">Logger</param>
60+
public List<string> GetDlls(ILogger logger)
61+
{
62+
var dllsToIndex = new List<string>();
63+
if (File.Exists(path))
64+
{
65+
if (includeFileName(System.IO.Path.GetFileName(path)))
66+
{
67+
dllsToIndex.Add(path);
68+
}
69+
else
70+
{
71+
logger.LogInfo($"AssemblyLookupLocation: Skipping {path}.");
72+
}
73+
return dllsToIndex;
74+
}
75+
76+
if (Directory.Exists(path))
77+
{
78+
logger.LogInfo($"AssemblyLookupLocation: Finding reference DLLs in {path}...");
79+
AddReferenceDirectory(dllsToIndex, logger);
80+
}
81+
else
82+
{
83+
logger.LogInfo("AssemblyLookupLocation: Path not found: " + path);
84+
}
85+
return dllsToIndex;
86+
}
87+
88+
public override bool Equals(object? obj) =>
89+
obj is AssemblyLookupLocation ap && path.Equals(ap.Path);
90+
91+
public override int GetHashCode() => path.GetHashCode();
92+
93+
public override string ToString() => path;
94+
}
95+
}

csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyManager.Nuget.cs

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -12,14 +12,14 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
1212
{
1313
public sealed partial class DependencyManager
1414
{
15-
private void RestoreNugetPackages(List<FileInfo> allNonBinaryFiles, IEnumerable<string> allProjects, IEnumerable<string> allSolutions, HashSet<string> dllPaths)
15+
private void RestoreNugetPackages(List<FileInfo> allNonBinaryFiles, IEnumerable<string> allProjects, IEnumerable<string> allSolutions, HashSet<AssemblyLookupLocation> dllLocations)
1616
{
1717
try
1818
{
1919
var checkNugetFeedResponsiveness = EnvironmentVariables.GetBoolean(EnvironmentVariableNames.CheckNugetFeedResponsiveness);
2020
if (checkNugetFeedResponsiveness && !CheckFeeds(allNonBinaryFiles))
2121
{
22-
DownloadMissingPackages(allNonBinaryFiles, dllPaths, withNugetConfig: false);
22+
DownloadMissingPackages(allNonBinaryFiles, dllLocations, withNugetConfig: false);
2323
return;
2424
}
2525

@@ -55,7 +55,7 @@ private void RestoreNugetPackages(List<FileInfo> allNonBinaryFiles, IEnumerable<
5555
}
5656

5757
nugetPackageDllPaths.ExceptWith(excludedPaths);
58-
dllPaths.UnionWith(nugetPackageDllPaths);
58+
dllLocations.UnionWith(nugetPackageDllPaths.Select(p => new AssemblyLookupLocation(p)));
5959
}
6060
catch (Exception exc)
6161
{
@@ -72,10 +72,10 @@ private void RestoreNugetPackages(List<FileInfo> allNonBinaryFiles, IEnumerable<
7272
.Paths
7373
.Select(d => Path.Combine(packageDirectory.DirInfo.FullName, d))
7474
.ToList();
75-
dllPaths.UnionWith(paths);
75+
dllLocations.UnionWith(paths.Select(p => new AssemblyLookupLocation(p)));
7676

7777
LogAllUnusedPackages(dependencies);
78-
DownloadMissingPackages(allNonBinaryFiles, dllPaths);
78+
DownloadMissingPackages(allNonBinaryFiles, dllLocations);
7979
}
8080

8181
/// <summary>
@@ -148,7 +148,7 @@ private void RestoreProjects(IEnumerable<string> projects, out IEnumerable<strin
148148
CompilationInfos.Add(("Failed project restore with package source error", nugetSourceFailures.ToString()));
149149
}
150150

151-
private void DownloadMissingPackages(List<FileInfo> allFiles, ISet<string> dllPaths, bool withNugetConfig = true)
151+
private void DownloadMissingPackages(List<FileInfo> allFiles, ISet<AssemblyLookupLocation> dllLocations, bool withNugetConfig = true)
152152
{
153153
var alreadyDownloadedPackages = GetRestoredPackageDirectoryNames(packageDirectory.DirInfo);
154154
var alreadyDownloadedLegacyPackages = GetRestoredLegacyPackageNames();
@@ -206,7 +206,7 @@ private void DownloadMissingPackages(List<FileInfo> allFiles, ISet<string> dllPa
206206

207207
CompilationInfos.Add(("Successfully ran fallback nuget restore", successCount.ToString()));
208208

209-
dllPaths.Add(missingPackageDirectory.DirInfo.FullName);
209+
dllLocations.Add(missingPackageDirectory.DirInfo.FullName);
210210
}
211211

212212
private string[] GetAllNugetConfigs(List<FileInfo> allFiles) => allFiles.SelectFileNamesByName("nuget.config").ToArray();

0 commit comments

Comments
 (0)