/// <summary>
        /// This method generates a PowerShell script to automate download of matched PDBs from the public symbol server.
        /// </summary>
        /// <param name="dllSearchPath"></param>
        /// <param name="recurse"></param>
        /// <returns></returns>
        internal string ObtainPDBDownloadCommandsfromDLL(string dllSearchPath, bool recurse)
        {
            if (string.IsNullOrEmpty(dllSearchPath))
            {
                return(null);
            }

            var moduleNames = new string[] { "ntdll", "kernel32", "kernelbase", "ntoskrnl", "sqldk", "sqlmin", "sqllang", "sqltses", "sqlaccess", "qds", "hkruntime", "hkengine", "hkcompile", "sqlos", "sqlservr" };

            var finalCommand = new StringBuilder();

            finalCommand.AppendLine("\tNew-Item -Type Directory -Path <somepath> -ErrorAction SilentlyContinue");

            foreach (var currentModule in moduleNames)
            {
                var    splitRootPaths = dllSearchPath.Split(';');
                string finalFilePath  = null;

                foreach (var currPath in splitRootPaths)
                {
                    var foundFiles = from f in Directory.EnumerateFiles(currPath, currentModule + ".*", recurse ? SearchOption.AllDirectories : SearchOption.TopDirectoryOnly)
                                     where !f.EndsWith(".pdb", StringComparison.InvariantCultureIgnoreCase)
                                     select f;

                    if (foundFiles.Count() > 0)
                    {
                        finalFilePath = foundFiles.First();
                        break;
                    }
                }

                if (!string.IsNullOrEmpty(finalFilePath))
                {
                    using (var dllFileStream = new FileStream(finalFilePath, FileMode.Open, FileAccess.Read, FileShare.Read))
                    {
                        using (var dllFile = new PEFile(dllFileStream, false))
                        {
                            string pdbName;
                            Guid   pdbGuid;
                            int    pdbAge;

                            dllFile.GetPdbSignature(out pdbName, out pdbGuid, out pdbAge);

                            pdbName = System.IO.Path.GetFileNameWithoutExtension(pdbName);

                            var signaturePlusAge = pdbGuid.ToString("N") + pdbAge.ToString();
                            var fileVersion      = dllFile.GetFileVersionInfo().FileVersion;

                            finalCommand.Append("\t");
                            finalCommand.AppendFormat(@"Invoke-WebRequest -uri 'http://msdl.microsoft.com/download/symbols/{0}.pdb/{1}/{0}.pdb' -OutFile '<somepath>\{0}.pdb' # File version {2}", pdbName, signaturePlusAge, fileVersion);
                            finalCommand.AppendLine();
                        }
                    }
                }
            }

            return(finalCommand.ToString());
        }
Beispiel #2
0
 /// <summary>
 ///     Gets the File Version Information that is stored as a resource in the PE file.  (This is what the
 ///     version tab a file's property page is populated with).
 /// </summary>
 /// <returns>IFileVersionInfo.</returns>
 /// <inheritdoc />
 public IFileVersionInfo GetFileVersionInfo() => Converter.Convert(PeFile.GetFileVersionInfo());