diff --git a/CONTRIBUTORS b/CONTRIBUTORS index 4de36da..096cee2 100644 --- a/CONTRIBUTORS +++ b/CONTRIBUTORS @@ -14,3 +14,4 @@ Andrew Arnott Geert van Horrik Wesley Eledui Marek Fišera +Shai Nahum diff --git a/README.md b/README.md index 28d2b3d..c3ac774 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ GitLink ![GitLink](design/logo/logo_64.png) -GitLink let's users step through your code hosted on GitHub! **Help make .NET open source projects more accessible by enabling this for your .NET projects, it's just a single additional step in your build**. See the list of [projects using GitLink](#projects-using-gitlink). +GitLink lets users step through your code hosted on GitHub! **Help make .NET open source projects more accessible by enabling this for your .NET projects, it's just a single additional step in your build**. See the list of [projects using GitLink](#projects-using-gitlink). Click here to lend your support to: GitLink and make a donation at pledgie.com ! @@ -78,6 +78,14 @@ There are many more parameters you can use. Display the usage doc with the follo GitLink.exe -h +### Native PDBs + +Native PDBs (from C++ projects) are supported by using -a option: + + GitLink.exe -a + +All known C++ source files from your git depot will be indexed in the PDB. + # How does it work The SrcSrv tool (Srcsrv.dll) enables a client to retrieve the exact version of the source files that were used to build an application. Because the source code for a module can change between versions and over the course of years, it is important to look at the source code as it existed when the version of the module in question was built. @@ -145,6 +153,7 @@ It is also possible to specify a custom url provider. Below is a list of projects already using GitLink (alphabetically ordered). +- ASP.NET Boilerplate - Catel - eXpand - FakeItEasy diff --git a/src/GitLink.Tests/Providers/VisualStudioTeamServicesProviderFacts.cs b/src/GitLink.Tests/Providers/VisualStudioTeamServicesProviderFacts.cs index eeaf596..2b4837d 100644 --- a/src/GitLink.Tests/Providers/VisualStudioTeamServicesProviderFacts.cs +++ b/src/GitLink.Tests/Providers/VisualStudioTeamServicesProviderFacts.cs @@ -19,7 +19,7 @@ public void ReturnsValidInitialization() { var provider = new VisualStudioTeamServicesProvider(); var valid = provider.Initialize("https://my-account.visualstudio.com/_git/main-repo"); - + Assert.IsTrue(valid); } @@ -35,60 +35,47 @@ public void ReturnsInValidInitialization() [TestFixture] public class TheVisualStudioTeamServicesProviderProperties { - [TestCase] - public void ReturnsValidCompany() - { - var provider = new VisualStudioTeamServicesProvider(); - provider.Initialize("https://CatenaLogic.visualstudio.com/_git/main-repo"); - - Assert.AreEqual("CatenaLogic", provider.CompanyName); - } - - [TestCase] - public void ReturnsValidCompanyUrl() + [TestCase("https://CatenaLogic.visualstudio.com/_git/main-repo", "main-repo")] + [TestCase("https://CatenaLogic.visualstudio.com/BigProject/_git/main-repo", "BigProject")] + [TestCase("https://CatenaLogic.visualstudio.com/DefaultCollection/BigProject/_git/main-repo", "BigProject")] + public void ReturnsValidProject(string url, string expectedProjectName) { var provider = new VisualStudioTeamServicesProvider(); - provider.Initialize("https://CatenaLogic.visualstudio.com/_git/main-repo"); + provider.Initialize(url); - Assert.AreEqual("https://CatenaLogic.visualstudio.com/", provider.CompanyUrl); + Assert.AreEqual(expectedProjectName, provider.ProjectName); } - [TestCase] - public void ReturnsValidProject() + [TestCase("https://CatenaLogic.visualstudio.com/_git/main-repo", "CatenaLogic")] + public void ReturnsValidCompany(string url, string expectedCompanyName) { var provider = new VisualStudioTeamServicesProvider(); - provider.Initialize("https://CatenaLogic.visualstudio.com/_git/main-repo"); + provider.Initialize(url); - Assert.AreEqual("main-repo", provider.ProjectName); + Assert.AreEqual(expectedCompanyName, provider.CompanyName); } - [TestCase] - public void ReturnsValidProject2() + [TestCase("https://CatenaLogic.visualstudio.com/Project/_git/main-repo", "main-repo")] + [TestCase("https://CatenaLogic.visualstudio.com/Project/_git/main.repo", "main.repo")] + [TestCase("https://CatenaLogic.visualstudio.com/DefaultCollection/Project/_git/main.repo", "main.repo")] + public void ReturnsValidRepositoryName(string url, string expectedProjectUrl) { var provider = new VisualStudioTeamServicesProvider(); - provider.Initialize("https://CatenaLogic.visualstudio.com/BigProject/_git/main-repo"); + provider.Initialize(url); - Assert.AreEqual("BigProject", provider.ProjectName); + Assert.AreEqual(expectedProjectUrl, provider.ProjectUrl); } - [TestCase] - public void ReturnsValidRepositoryName() + [TestCase("https://CatenaLogic.visualstudio.com/_git/main-repo", "https://CatenaLogic.visualstudio.com/")] + [TestCase("https://CatenaLogic.visualstudio.com/DefaultCollection/BigProject/_git/main-repo", "https://CatenaLogic.visualstudio.com/DefaultCollection/")] + [TestCase("https://CatenaLogic.visualstudio.com/Other.Collection/BigProject/_git/main-repo", "https://CatenaLogic.visualstudio.com/Other.Collection/")] + public void ReturnsValidCompanyUrl(string url, string expectedCompanyUrl) { var provider = new VisualStudioTeamServicesProvider(); - provider.Initialize("https://CatenaLogic.visualstudio.com/Project/_git/main-repo"); + provider.Initialize(url); - Assert.AreEqual("main-repo", provider.ProjectUrl); + Assert.AreEqual(expectedCompanyUrl, provider.CompanyUrl); } - - [TestCase] - public void ReturnsValidRepositoryNameWhenContainsPeriod() - { - var provider = new VisualStudioTeamServicesProvider(); - provider.Initialize("https://CatenaLogic.visualstudio.com/Big.Project/_git/main.repo"); - - Assert.AreEqual("main.repo", provider.ProjectUrl); - } - } } } diff --git a/src/GitLink.sln.DotSettings b/src/GitLink.sln.DotSettings index af92192..f763e30 100644 --- a/src/GitLink.sln.DotSettings +++ b/src/GitLink.sln.DotSettings @@ -28,6 +28,7 @@ False False False + False 20 False @@ -35,6 +36,7 @@ 1 OnSingleLine FirstAttributeOnSingleLine + False <?xml version="1.0" encoding="utf-16"?> <Patterns xmlns="urn:schemas-jetbrains-com:member-reordering-patterns"> <TypePattern Priority="100" DisplayName="Type Pattern"> @@ -416,6 +418,7 @@ II.2.12 <HandlesEvent /> True True True + True None <data /> <data><IncludeFilters /><ExcludeFilters /></data> \ No newline at end of file diff --git a/src/GitLink/GitLink.csproj b/src/GitLink/GitLink.csproj index f7d723b..7dee726 100644 --- a/src/GitLink/GitLink.csproj +++ b/src/GitLink/GitLink.csproj @@ -75,6 +75,7 @@ + diff --git a/src/GitLink/Helpers/PortablePdbHelper.cs b/src/GitLink/Helpers/PortablePdbHelper.cs new file mode 100644 index 0000000..df705a2 --- /dev/null +++ b/src/GitLink/Helpers/PortablePdbHelper.cs @@ -0,0 +1,55 @@ +// -------------------------------------------------------------------------------------------------------------------- +// +// Copyright (c) 2014 - 2016 CatenaLogic. All rights reserved. +// +// -------------------------------------------------------------------------------------------------------------------- + +namespace GitLink +{ + using System.IO; + + internal static class PortablePdbHelper + { + /// + /// Is the given .pdb using the new Portable format ? (https://github.com/dotnet/corefx/blob/master/src/System.Reflection.Metadata/specs/PortablePdb-Metadata.md) + /// + /// .pdb file path + /// Returns if it's a Portable PDB + public static bool IsPortablePdb(string pdbPath) + { + using (var fs = File.Open(pdbPath, FileMode.Open, FileAccess.Read)) + using (var br = new BinaryReader(fs)) + { + // More infos in chapter II.24.2 of ECMA-335 (http://www.ecma-international.org/publications/files/ECMA-ST/ECMA-335.pdf) + var signature = 0x424A5342; + if (br.ReadUInt32() != signature) + { + return false; + } + + var majorVersion = br.ReadUInt16(); + if (majorVersion != 1) + { + return false; + } + + var minorVersion = br.ReadUInt16(); + if (minorVersion != 1) + { + return false; + } + + var reserved = br.ReadUInt32(); + if (reserved != 0) + { + return false; + } + + var versionLength = br.ReadUInt32(); + var version = System.Text.Encoding.UTF8.GetString(br.ReadBytes((int)versionLength)); + + return version.StartsWith("PDB v1.0"); + } + } + } +} \ No newline at end of file diff --git a/src/GitLink/LinkOptions.cs b/src/GitLink/LinkOptions.cs index 145ade8..6b09f1e 100644 --- a/src/GitLink/LinkOptions.cs +++ b/src/GitLink/LinkOptions.cs @@ -23,5 +23,7 @@ public struct LinkOptions public string CommitId { get; set; } public string GitWorkingDirectory { get; set; } + + public bool IndexAllDepotFiles { get; set; } } } diff --git a/src/GitLink/Linker.cs b/src/GitLink/Linker.cs index 28dc0e5..8a7159a 100644 --- a/src/GitLink/Linker.cs +++ b/src/GitLink/Linker.cs @@ -36,147 +36,163 @@ public static class Linker Argument.IsNotNullOrEmpty(() => pdbPath); var projectSrcSrvFile = pdbPath + ".srcsrv"; - string repositoryDirectory; - IReadOnlyCollection sourceFiles; + string repositoryDirectory = null; + IReadOnlyList sourceFiles; IReadOnlyDictionary repoSourceFiles; - using (var pdb = new PdbFile(pdbPath)) - { - sourceFiles = pdb.GetFilesAndChecksums().Keys.ToList(); - if (options.GitWorkingDirectory != null) + if (options.GitWorkingDirectory != null) + { + repositoryDirectory = Path.Combine(options.GitWorkingDirectory, ".git"); + if (!Directory.Exists(repositoryDirectory)) { - repositoryDirectory = Path.Combine(options.GitWorkingDirectory, ".git"); + Log.Error("Provided directory does not contain a git depot."); + return false; } - else - { - string someSourceFile = sourceFiles.FirstOrDefault(); - if (someSourceFile == null) - { - Log.Error("No source files were found in the PDB."); - return false; - } + } + + if (PortablePdbHelper.IsPortablePdb(pdbPath)) + { + Log.Warning("Portable PDB format is not compatible with GitLink. Please use SourceLink (https://github.com/ctaggart/SourceLink)."); + return true; + } - repositoryDirectory = GitDirFinder.TreeWalkForGitDir(Path.GetDirectoryName(someSourceFile)); + if (options.IndexAllDepotFiles) + { + if (repositoryDirectory == null) + { + repositoryDirectory = GitDirFinder.TreeWalkForGitDir(Path.GetDirectoryName(pdbPath)); if (repositoryDirectory == null) { - Log.Error("No source files found that are tracked in a git repo."); + Log.Error("Couldn't auto detect git repo. Please use -baseDir to manually set it."); return false; } } - string workingDirectory = Path.GetDirectoryName(repositoryDirectory); + sourceFiles = GetSourceFilesFromDepot(repositoryDirectory); + } + else + { + sourceFiles = GetSourceFilesFromPdb(pdbPath, !options.SkipVerify); - var repository = new Lazy(() => new Repository(repositoryDirectory)); - try + string someSourceFile = sourceFiles.FirstOrDefault(); + if (someSourceFile == null) { - string commitId = options.CommitId ?? repository.Value.Head.Commits.FirstOrDefault()?.Sha; - if (commitId == null) - { - Log.Error("No commit is checked out to HEAD. Have you committed yet?"); - return false; - } - - var providerManager = new Providers.ProviderManager(); - Providers.IProvider provider; - if (options.GitRemoteUrl == null) - { - var candidateProviders = from remote in repository.Value.Network.Remotes - let p = providerManager.GetProvider(remote.Url) - where p != null - select p; - provider = candidateProviders.FirstOrDefault(); - } - else - { - provider = providerManager.GetProvider(options.GitRemoteUrl.AbsoluteUri); - } + Log.Error("No source files were found in the PDB. If you're PDB is a native one you should use -a option."); + return false; + } - if (provider == null) + if (repositoryDirectory == null) + { + repositoryDirectory = GitDirFinder.TreeWalkForGitDir(Path.GetDirectoryName(sourceFiles.FirstOrDefault())); + if (repositoryDirectory == null) { - Log.Error("Unable to detect the remote git service."); + Log.Error("No source files found that are tracked in a git repo."); return false; } + } + } - try - { - Repository repo = repository.Value; - repoSourceFiles = sourceFiles.ToDictionary(e => e, e => repo.GetNormalizedPath(e)); - } - catch (RepositoryNotFoundException) - { - // Normalize using file system since we can't find the git repo. - Log.Warning($"Unable to find git repo at \"{options.GitWorkingDirectory}\". Using file system to find canonical capitalization of file paths."); - repoSourceFiles = sourceFiles.ToDictionary(e => e, e => GetNormalizedPath(e, workingDirectory)); - } + string workingDirectory = Path.GetDirectoryName(repositoryDirectory); - if (!options.SkipVerify) - { - Log.Debug("Verifying pdb file"); + var repository = new Lazy(() => new Repository(repositoryDirectory)); + try + { + string commitId = options.CommitId ?? repository.Value.Head.Commits.FirstOrDefault()?.Sha; + if (commitId == null) + { + Log.Error("No commit is checked out to HEAD. Have you committed yet?"); + return false; + } - var missingFiles = pdb.FindMissingOrChangedSourceFiles(); - foreach (var missingFile in missingFiles) - { - Log.Warning($"File \"{missingFile}\" missing or changed since the PDB was compiled."); - } - } + var providerManager = new Providers.ProviderManager(); + Providers.IProvider provider; + if (options.GitRemoteUrl == null) + { + var candidateProviders = from remote in repository.Value.Network.Remotes + let p = providerManager.GetProvider(remote.Url) + where p != null + select p; + provider = candidateProviders.FirstOrDefault(); + } + else + { + provider = providerManager.GetProvider(options.GitRemoteUrl.AbsoluteUri); + } - string rawUrl = provider.RawGitUrl; - if (rawUrl.Contains(RevisionPlaceholder) || rawUrl.Contains(FilenamePlaceholder)) - { - if (!rawUrl.Contains(RevisionPlaceholder) || !rawUrl.Contains(FilenamePlaceholder)) - { - Log.Error("Supplied custom URL pattern must contain both a revision and a filename placeholder."); - return false; - } - - rawUrl = rawUrl - .Replace(RevisionPlaceholder, "{0}") - .Replace(FilenamePlaceholder, "%var2%"); - } - else - { - rawUrl = $"{rawUrl}/{{0}}/%var2%"; - } + if (provider == null) + { + Log.Error("Unable to detect the remote git service."); + return false; + } - Log.Info($"Using {string.Format(rawUrl, commitId)} for source server URLs."); - var srcSrvContext = new SrcSrvContext - { - RawUrl = rawUrl, - DownloadWithPowershell = options.Method == LinkMethod.Powershell, - Revision = commitId, - }; - foreach (var sourceFile in repoSourceFiles) - { - // Skip files that aren't tracked by source control. - if (sourceFile.Value != null) - { - string relativePathForUrl = ReplaceSlashes(provider, sourceFile.Value); - srcSrvContext.Paths.Add(Tuple.Create(sourceFile.Key, relativePathForUrl)); - } - } + try + { + Repository repo = repository.Value; + repoSourceFiles = sourceFiles.ToDictionary(e => e, e => repo.GetNormalizedPath(e)); + } + catch (RepositoryNotFoundException) + { + // Normalize using file system since we can't find the git repo. + Log.Warning($"Unable to find git repo at \"{options.GitWorkingDirectory}\". Using file system to find canonical capitalization of file paths."); + repoSourceFiles = sourceFiles.ToDictionary(e => e, e => GetNormalizedPath(e, workingDirectory)); + } - // When using the VisualStudioTeamServicesProvider, add extra infomration to dictionary with VSTS-specific data - if (provider is Providers.VisualStudioTeamServicesProvider) + string rawUrl = provider.RawGitUrl; + if (rawUrl.Contains(RevisionPlaceholder) || rawUrl.Contains(FilenamePlaceholder)) + { + if (!rawUrl.Contains(RevisionPlaceholder) || !rawUrl.Contains(FilenamePlaceholder)) { - srcSrvContext.VstsData["TFS_COLLECTION"] = provider.CompanyUrl; - srcSrvContext.VstsData["TFS_TEAM_PROJECT"] = provider.ProjectName; - srcSrvContext.VstsData["TFS_REPO"] = provider.ProjectUrl; + Log.Error("Supplied custom URL pattern must contain both a revision and a filename placeholder."); + return false; } - CreateSrcSrv(projectSrcSrvFile, srcSrvContext); + rawUrl = rawUrl + .Replace(RevisionPlaceholder, "{0}") + .Replace(FilenamePlaceholder, "%var2%"); } - catch (RepositoryNotFoundException) + else { - Log.Error($"Unable to find git repo at \"{options.GitWorkingDirectory}\"."); - return false; + rawUrl = $"{rawUrl}/{{0}}/%var2%"; } - finally + + Log.Info($"Using {string.Format(rawUrl, commitId)} for source server URLs."); + var srcSrvContext = new SrcSrvContext + { + RawUrl = rawUrl, + DownloadWithPowershell = options.Method == LinkMethod.Powershell, + Revision = commitId, + }; + foreach (var sourceFile in repoSourceFiles) { - if (repository.IsValueCreated) + // Skip files that aren't tracked by source control. + if (sourceFile.Value != null) { - repository.Value.Dispose(); + string relativePathForUrl = ReplaceSlashes(provider, sourceFile.Value); + srcSrvContext.Paths.Add(Tuple.Create(sourceFile.Key, relativePathForUrl)); } } + + // When using the VisualStudioTeamServicesProvider, add extra infomration to dictionary with VSTS-specific data + if (provider is Providers.VisualStudioTeamServicesProvider) + { + srcSrvContext.VstsData["TFS_COLLECTION"] = provider.CompanyUrl; + srcSrvContext.VstsData["TFS_TEAM_PROJECT"] = provider.ProjectName; + srcSrvContext.VstsData["TFS_REPO"] = provider.ProjectUrl; + } + + CreateSrcSrv(projectSrcSrvFile, srcSrvContext); + } + catch (RepositoryNotFoundException) + { + Log.Error($"Unable to find git repo at \"{options.GitWorkingDirectory}\"."); + return false; + } + finally + { + if (repository.IsValueCreated) + { + repository.Value.Dispose(); + } } Log.Debug("Created source server link file, updating pdb file \"{0}\"", Catel.IO.Path.GetRelativePath(pdbPath, repositoryDirectory)); @@ -187,6 +203,51 @@ public static class Linker return true; } + private static List GetSourceFilesFromPdb(string pdbPath, bool verifyFiles) + { + using (var pdb = new PdbFile(pdbPath)) + { + var sources = pdb.GetFilesAndChecksums().Keys.ToList(); + + if (verifyFiles) + { + Log.Debug("Verifying pdb files"); + + var missingFiles = pdb.FindMissingOrChangedSourceFiles(); + foreach (var missingFile in missingFiles) + { + Log.Warning($"File \"{missingFile}\" missing or changed since the PDB was compiled."); + } + } + + return sources; + } + } + + private static List GetSourceFilesFromDepot(string repositoryDirectory) + { + IEnumerable sourceFiles; + var repo = new Repository(repositoryDirectory); + { + sourceFiles = from file in Directory.GetFiles(repo.Info.WorkingDirectory, "*.*", SearchOption.AllDirectories) + where !repo.Ignore.IsPathIgnored(file) + let ext = Path.GetExtension(file) + where string.Equals(ext, ".cs", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".cpp", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".c", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".cc", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".cxx", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".c++", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".h", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".hh", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".inl", StringComparison.OrdinalIgnoreCase) + || string.Equals(ext, ".hpp", StringComparison.OrdinalIgnoreCase) + select file; + } + + return sourceFiles.ToList(); + } + private static void CreateSrcSrv(string srcsrvFile, SrcSrvContext srcSrvContext) { Argument.IsNotNull(nameof(srcSrvContext), srcSrvContext); diff --git a/src/GitLink/Program.cs b/src/GitLink/Program.cs index e8ff243..d9b1585 100644 --- a/src/GitLink/Program.cs +++ b/src/GitLink/Program.cs @@ -31,6 +31,7 @@ private static int Main(string[] args) string baseDir = null; string pdbPath = null; bool skipVerify = false; + bool allDepotFiles = false; LinkMethod method = LinkMethod.Http; var arguments = ArgumentSyntax.Parse(args, syntax => { @@ -39,6 +40,7 @@ private static int Main(string[] args) syntax.DefineOption("commit", ref commitId, "The git ref to assume all the source code belongs to."); syntax.DefineOption("baseDir", ref baseDir, "The path to the root of the git repo."); syntax.DefineOption("s|skipVerify", ref skipVerify, "Verify all source files are available in source control."); + syntax.DefineOption("a|allDepotFiles", ref allDepotFiles, "Index all source files from depot. Add this option for native PDBs (C++)."); syntax.DefineParameter("pdb", ref pdbPath, "The PDB to add source indexing to."); if (!string.IsNullOrEmpty(pdbPath) && !File.Exists(pdbPath)) @@ -65,6 +67,7 @@ private static int Main(string[] args) CommitId = commitId, SkipVerify = skipVerify, Method = method, + IndexAllDepotFiles = allDepotFiles, }; if (!Linker.Link(pdbPath, options)) diff --git a/src/GitLink/Providers/VisualStudioTeamServicesProvider.cs b/src/GitLink/Providers/VisualStudioTeamServicesProvider.cs index f891079..f33e36d 100644 --- a/src/GitLink/Providers/VisualStudioTeamServicesProvider.cs +++ b/src/GitLink/Providers/VisualStudioTeamServicesProvider.cs @@ -13,7 +13,24 @@ namespace GitLink.Providers public class VisualStudioTeamServicesProvider : ProviderBase { - private static readonly Regex HostingUrlPattern = new Regex(@"(?(?(?:https://)?(?([a-zA-Z0-9\-\.]*)?)\.visualstudio\.com/)(?[a-zA-Z0-9\-\.]*)/?_git//?(?[^/]+))"); + // Matches the git origin URL, providing named capture groups + // Example match: https://user.visualstudio.com/DefaultCollection/MyFirstProject/_git/MyFirstRepo + private static readonly Regex HostingUrlPattern = + new Regex( + @"(? + (?:https://)? + (?([a-zA-Z0-9\-\.]*)?) # account name (e.g. user) + \.visualstudio\.com/ + ( + [a-zA-Z0-9\-\.]+/ # collection (optional). e.g. DefaultCollection/ + (?!/?_git/) # Negative lookahead to avoid capturing 'project' group + )? + ) + (?[a-zA-Z0-9\-\.]*) # project name. e.g. MyFirstProject + (?/?_git//?) + (?[^/]+) # the repository's name. e.g. MyFirstRepo + ", + RegexOptions.IgnorePatternWhitespace); public VisualStudioTeamServicesProvider() : base(new GitPreparer()) diff --git a/src/GitLinkTask/GitLink.targets b/src/GitLinkTask/GitLink.targets index 2e25ce8..aff9d5d 100644 --- a/src/GitLinkTask/GitLink.targets +++ b/src/GitLinkTask/GitLink.targets @@ -10,6 +10,7 @@ PdbFile="$(IntermediateOutputPath)$(TargetName).pdb" Method="$(GitLinkMethod)" SkipVerify="$(GitLinkSkipVerify)" + IndexAllDepotFiles="$(GitLinkIndexAllDepotFiles)" GitRemoteUrl="$(GitLinkGitRemoteUrl)" GitWorkingDirectory="$(GitWorkingDirectory)" GitCommitId="$(GitCommitId)" diff --git a/src/GitLinkTask/LinkPdbToGitRemote.cs b/src/GitLinkTask/LinkPdbToGitRemote.cs index 2b4a06c..c79c32f 100644 --- a/src/GitLinkTask/LinkPdbToGitRemote.cs +++ b/src/GitLinkTask/LinkPdbToGitRemote.cs @@ -21,6 +21,8 @@ public string Method public bool SkipVerify { get; set; } + public bool IndexAllDepotFiles { get; set; } + public string GitRemoteUrl { get; set; } public string GitCommitId { get; set; } @@ -40,6 +42,7 @@ public override bool Execute() GitRemoteUrl = GitRemoteUrl != null ? new Uri(GitRemoteUrl, UriKind.Absolute) : null, CommitId = GitCommitId, GitWorkingDirectory = GitWorkingDirectory, + IndexAllDepotFiles = IndexAllDepotFiles, }; bool success = Linker.Link(PdbFile.GetMetadata("FullPath"), options);