/// <summary> /// A lot of things going on inside: gets current gpu driver, fetches latest gpu driver from NVIDIA server and fetches download link for latest drivers. /// </summary> private static void GpuInfo() { Console.Write("Retrieving GPU information . . . "); int error = 0; string processURL = null; string confirmURL = null; string gpuURL = null; string gpuName = null; bool foundGpu = false; // query local driver version try { foreach (ManagementObject obj in new ManagementObjectSearcher("SELECT * FROM Win32_VideoController").Get()) { if (obj["Description"].ToString().ToLower().Contains("nvidia")) { gpuName = obj["Description"].ToString().Trim(); OfflineGPUVersion = obj["DriverVersion"].ToString().Replace(".", string.Empty).Substring(5); OfflineGPUVersion = OfflineGPUVersion.Substring(0, 3) + "." + OfflineGPUVersion.Substring(3); // add dot foundGpu = true; break; } else if (obj["PNPDeviceID"].ToString().ToLower().Contains("ven_10de")) { foreach (ManagementObject obj1 in new ManagementClass("Win32_SystemEnclosure").GetInstances()) { foreach (int chassisType in (UInt16[])(obj1["ChassisTypes"])) { gpuName = (chassisType == 3) ? "GTX" : "GTX M"; } } foundGpu = true; break; } else // gpu not found { LogManager.Log(obj["Description"].ToString().Trim() + " is not NVIDIA!", LogManager.Level.INFO); } } if (!foundGpu) { if (ignoreMissingGpu) { gpuName = "GTX"; } else { throw new InvalidDataException(); } } } catch (InvalidDataException) { Console.Write("ERROR!"); Console.WriteLine(); Console.WriteLine("No supported nvidia graphics cards were found, and the application will not continue!"); if (showUI) { Console.ReadKey(); } Environment.Exit(1); } catch (Exception ex) { error++; OfflineGPUVersion = "000.00"; Console.Write("ERROR!"); LogManager.Log(ex.ToString(), LogManager.Level.ERROR); Console.WriteLine(); Console.WriteLine(ex.ToString()); } /// In order to proceed, we must input what GPU we have. /// Looking at the supported products on NVIDIA website for desktop and mobile GeForce series, /// we can see that they're sharing drivers with other GPU families, the only thing we have to do is tell the website /// if we're running a mobile or desktop GPU. int psID = 0, pfID = 0; /// Get correct gpu drivers: /// you do not have to choose the exact GPU, /// looking at supported products, we see that the same driver package includes /// drivers for the majority GPU family. if (gpuName.Contains("M")) // mobile | notebook { psID = 99; // GeForce 900M-series (M for Mobile) pfID = 758; // GTX 970M } else // desktop { psID = 98; // GeForce 900-series pfID = 756; // GTX 970 } // Check if system requires DCH drivers, thanks to https://github.com/Osspial try { using (var regKey = Registry.LocalMachine.OpenSubKey(@"SYSTEM\CurrentControlSet\Services\nvlddmkm", false)) { if (regKey != null) { if (regKey.GetValue("DCHUVen") != null) { dchID = 1; } } } } catch { } // finish request try { gpuURL = $"https://www.nvidia.com/Download/processDriver.aspx?psid={psID}&pfid={pfID}&rpf=1&osid={osID}&lid={langID}&dtcid={dchID}&ctk=0"; WebClient client = new WebClient(); Stream stream = client.OpenRead(gpuURL); StreamReader reader = new StreamReader(stream); processURL = reader.ReadToEnd(); reader.Close(); stream.Close(); } catch (Exception ex) { if (error == 0) { Console.Write("ERROR!"); Console.WriteLine(); error++; } Console.WriteLine(ex.ToString()); } try { // HTMLAgilityPack // thanks to http://www.codeproject.com/Articles/691119/Html-Agility-Pack-Massive-information-extraction-f for a great article var htmlWeb = new HtmlWeb(); HtmlAgilityPack.HtmlDocument htmlDocument = htmlWeb.Load(processURL); // get version var tdVer = htmlDocument.DocumentNode.Descendants().SingleOrDefault(x => x.Id == "tdVersion"); OnlineGPUVersion = tdVer.InnerHtml.Trim().Substring(0, 6); // get release date var tdReleaseDate = htmlDocument.DocumentNode.Descendants().SingleOrDefault(x => x.Id == "tdReleaseDate"); var dates = tdReleaseDate.InnerHtml.Trim(); // get driver release date int status = 0, year = 0, month = 0, day = 0; foreach (var substring in dates.Split('.')) { status++; // goes up starting from 1, being the year, followed by month then day. switch (status) { // year case 1: year = Convert.ToInt32(substring); break; // month case 2: month = Convert.ToInt32(substring); break; // day case 3: day = Convert.ToInt32(substring); break; default: LogManager.Log($"The status: '{status}' is not a recognized status!", LogManager.Level.ERROR); break; } } releaseDate = new DateTime(year, month, day); IEnumerable <HtmlNode> node = htmlDocument.DocumentNode.Descendants("a").Where(x => x.Attributes.Contains("href")); // get driver URL foreach (var child in node) { if (child.Attributes["href"].Value.Contains("/content/DriverDownload-March2009/")) { confirmURL = "https://www.nvidia.com" + child.Attributes["href"].Value.Trim(); break; } } // get release notes URL foreach (var child in node) { if (child.Attributes["href"].Value.Contains("release-notes.pdf")) { pdfURL = child.Attributes["href"].Value.Trim(); break; } } if (pdfURL == null) { if (psID == 98) // if desktop { pdfURL = $"https://us.download.nvidia.com/Windows/{OnlineGPUVersion}/{OnlineGPUVersion}-win10-win8-win7-desktop-release-notes.pdf"; } else { pdfURL = $"https://us.download.nvidia.com/Windows/{OnlineGPUVersion}/{OnlineGPUVersion}-win10-win8-win7-notebook-release-notes.pdf"; } LogManager.Log("No release notes found, but a link to the notes has been crafted by following the template Nvidia uses.", LogManager.Level.INFO); } // get driver description and show it in HTML releaseDesc = htmlDocument.DocumentNode.SelectSingleNode("//div[@id='tab1_content']").InnerHtml.Trim(); // get download link htmlDocument = htmlWeb.Load(confirmURL); node = htmlDocument.DocumentNode.Descendants("a").Where(x => x.Attributes.Contains("href")); foreach (var child in node) { if (child.Attributes["href"].Value.Contains("download.nvidia")) { downloadURL = child.Attributes["href"].Value.Trim(); break; } } var locationPrefix = SettingManager.ReadSetting("Download location"); downloadURL = downloadURL.Substring(4); downloadURL = $"https://{locationPrefix}{downloadURL}"; // get file size using (var responce = WebRequest.Create(downloadURL).GetResponse()) { downloadFileSize = responce.ContentLength; } } catch (Exception ex) { OnlineGPUVersion = "000.00"; LogManager.Log(ex.ToString(), LogManager.Level.ERROR); if (error == 0) { Console.Write("ERROR!"); Console.WriteLine(); error++; } Console.WriteLine(ex.ToString()); } if (error == 0) { Console.Write("OK!"); Console.WriteLine(); } if (debug) { Console.WriteLine($"downloadURL: {downloadURL}"); Console.WriteLine($"pdfURL: {pdfURL}"); Console.WriteLine($"releaseDate: {releaseDate.ToShortDateString()}"); Console.WriteLine($"downloadFileSize: {Math.Round((downloadFileSize / 1024f) / 1024f)} MB ({downloadFileSize:N} bytes)"); Console.WriteLine($"OfflineGPUVersion: {OfflineGPUVersion}"); Console.WriteLine($"OnlineGPUVersion: {OnlineGPUVersion}"); } }
/// <summary> /// Downloads the driver and some other stuff /// </summary> private static void DownloadDriver() { int DateDiff = (DateTime.Now - releaseDate).Days; // how many days between the two dates string theDate = null; if (DateDiff == 1) { theDate = DateDiff + " day ago"; } else if (DateDiff < 1) { theDate = "today"; // we only have the date and not time :/ } else { theDate = DateDiff + " days ago"; } string message = "Graphics card drivers are available, do you want to update now?" + Environment.NewLine + Environment.NewLine; string key = "Show Driver Description"; string val = null; // loop while (val != "true" & val != "false") { val = SettingManager.ReadSetting(key); // refresh value each time if (val == "true") { message = message + "Description: " + releaseDesc + Environment.NewLine + Environment.NewLine; } else if (val == "false") { break; } else { // invalid value SettingManager.SetupSetting(key); } } message += "Driver version: " + OnlineGPUVersion + " (you're running " + OfflineGPUVersion + ")" + Environment.NewLine + "Driver released: " + theDate + " (" + releaseDate.ToShortDateString() + ")"; DialogResult dialog = MessageBox.Show(message, "TinyNvidiaUpdateChecker", MessageBoxButtons.YesNo, MessageBoxIcon.Question); if (dialog == DialogResult.Yes) { Console.WriteLine(); bool error = false; driverFileName = downloadURL.Split('/').Last(); // retrives file name from url try { message = "Where do you want to save the drivers?"; key = "Minimal install"; val = null; // reset value // loop while (val != "true" & val != "false") { val = SettingManager.ReadSetting(key); // refresh value each time if (val == "true") { message += " (you should select a empty folder)"; } else if (val == "false") { break; } else { // invalid value SettingManager.SetupSetting(key); } } DialogResult result; using (FolderBrowserDialog folderDialog = new FolderBrowserDialog()) { folderDialog.Description = message; result = folderDialog.ShowDialog(); // show dialog and get status (will wait for input) switch (result) { case DialogResult.OK: savePath = folderDialog.SelectedPath; break; default: Console.WriteLine("User closed dialog!"); return; } } // don't download driver if it already exists Console.Write("Downloading the driver . . . "); if (showUI && !File.Exists(savePath + @"\" + driverFileName)) { using (WebClient webClient = new WebClient()) { var notifier = new AutoResetEvent(false); var progress = new ProgressBar(); webClient.DownloadProgressChanged += delegate(object sender, DownloadProgressChangedEventArgs e) { progress.Report((double)e.ProgressPercentage / 100); if (e.BytesReceived >= e.TotalBytesToReceive) { notifier.Set(); } }; webClient.DownloadFileAsync(new Uri(downloadURL), savePath + @"\" + driverFileName); notifier.WaitOne(); // sync with the above progress.Dispose(); // get rid of the progress bar } } // show the progress bar gui else if (!showUI && !File.Exists(savePath + @"\" + driverFileName)) { DownloaderForm dlForm = new DownloaderForm(); dlForm.Show(); dlForm.Focus(); dlForm.DownloadFile(new Uri(downloadURL), savePath + @"\" + driverFileName); dlForm.Close(); } else { LogManager.Log("Driver is already downloaded", LogManager.Level.INFO); } } catch (Exception ex) { error = true; Console.Write("ERROR!"); LogManager.Log(ex.Message, LogManager.Level.ERROR); Console.WriteLine(); Console.WriteLine(ex.StackTrace); Console.WriteLine(); } if (error == false) { Console.Write("OK!"); Console.WriteLine(); } if (debug == true) { Console.WriteLine("savePath: " + savePath); } dialog = MessageBox.Show("Do you want view the release PDF?", "TinyNvidiaUpdateChecker", MessageBoxButtons.YesNo, MessageBoxIcon.Question); if (dialog == DialogResult.Yes) { try { Process.Start(pdfURL); } catch (Exception ex) { Console.WriteLine(ex.StackTrace); } } key = "Minimal install"; val = null; // reset value // loop while (val != "true" & val != "false") { val = SettingManager.ReadSetting(key); // refresh value each time if (val == "true") { MakeInstaller(); } else if (val == "false") { break; } else { // invalid value SettingManager.SetupSetting(key); } } dialog = MessageBox.Show("Do you wish to run the driver installer?", "TinyNvidiaUpdateChecker", MessageBoxButtons.YesNo, MessageBoxIcon.Question); if (dialog == DialogResult.Yes) { try { if (val == "true") { // extracted Process.Start(savePath + @"\setup.exe"); } else { Process.Start(savePath + @"\" + driverFileName); } } catch (Exception ex) { Console.WriteLine(ex.StackTrace); } } } }
/// <summary> /// A lot of things going on inside: gets current gpu driver, fetches latest gpu driver from NVIDIA server and fetches download link for latest drivers. /// </summary> private static void GpuInfo() { Console.Write("Retrieving GPU information . . . "); int error = 0; string processURL = null; string confirmURL = null; string gpuURL = null; string gpuName = null; // query local driver version try { while (string.IsNullOrEmpty(gpuName)) { gpuName = SettingManager.ReadSetting("GPU Name"); if (string.IsNullOrEmpty(gpuName)) { SettingManager.SetupSetting("GPU Name"); } } ManagementObjectSearcher objectSearcher = new ManagementObjectSearcher("SELECT * FROM Win32_VideoController"); // TODO: this is not the optimal code foreach (ManagementObject obj in objectSearcher.Get()) { if (obj["Description"].ToString() == gpuName) { OfflineGPUVersion = obj["DriverVersion"].ToString().Replace(".", string.Empty).Substring(5); OfflineGPUVersion = OfflineGPUVersion.Substring(0, 3) + "." + OfflineGPUVersion.Substring(3); // add dot break; } else { // gpu not found } } } catch (Exception ex) { error++; OfflineGPUVersion = "000.00"; Console.Write("ERROR!"); LogManager.Log(ex.ToString(), LogManager.Level.ERROR); Console.WriteLine(); Console.WriteLine(ex.StackTrace); } /// In order to proceed, we must input what GPU we have. /// Looking at the supported products on NVIDIA website for desktop and mobile GeForce series, /// we can see that they're sharing drivers with other GPU families, the only thing we have to do is tell the website /// if we're running a mobile or desktop GPU. int psID = 0; int pfID = 0; /// Get correct gpu drivers: /// you do not have to choose the exact GPU, /// looking at supported products, we see that the same driver package includes /// drivers for the majority GPU family. if (gpuName.Contains("M")) { // mobile | notebook psID = 99; // GeForce 900M-series (M for Mobile) pfID = 758; // GTX 970M } else { // desktop psID = 98; // GeForce 900-series pfID = 756; // GTX 970 } // finish request try { gpuURL = "http://www.nvidia.com/Download/processDriver.aspx?psid=" + psID.ToString() + "&pfid=" + pfID.ToString() + "&rpf=1&osid=" + osID.ToString() + "&lid=" + langID.ToString() + "&ctk=0"; WebClient client = new WebClient(); Stream stream = client.OpenRead(gpuURL); StreamReader reader = new StreamReader(stream); processURL = reader.ReadToEnd(); reader.Close(); stream.Close(); } catch (Exception ex) { if (error == 0) { Console.Write("ERROR!"); Console.WriteLine(); error++; } Console.WriteLine(ex.StackTrace); } try { // HTMLAgilityPack // thanks to http://www.codeproject.com/Articles/691119/Html-Agility-Pack-Massive-information-extraction-f for a great article HtmlWeb htmlWeb = new HtmlWeb(); HtmlAgilityPack.HtmlDocument htmlDocument = htmlWeb.Load(processURL); // get version HtmlNode tdVer = htmlDocument.DocumentNode.Descendants().SingleOrDefault(x => x.Id == "tdVersion"); OnlineGPUVersion = tdVer.InnerHtml.Trim().Substring(0, 6); // get release date HtmlNode tdReleaseDate = htmlDocument.DocumentNode.Descendants().SingleOrDefault(x => x.Id == "tdReleaseDate"); var dates = tdReleaseDate.InnerHtml.Trim(); // not the best code, but does the job, might come back to cleanup in the future int status = 0; int year = 0; int month = 0; int day = 0; foreach (var substring in dates.Split('.')) { status++; // goes up starting from 1, being the year, followed by month then day. switch (status) { // year case 1: year = Convert.ToInt32(substring); break; // month case 2: month = Convert.ToInt32(substring); break; // day case 3: day = Convert.ToInt32(substring); break; default: LogManager.Log("The status: '" + status + "' is not a recognized status!", LogManager.Level.ERROR); break; } } releaseDate = new DateTime(year, month, day); // follows the ISO 8601 standard IEnumerable <HtmlNode> links = htmlDocument.DocumentNode.Descendants("a").Where(x => x.Attributes.Contains("href")); foreach (var link in links) { // get driver URL if (link.Attributes["href"].Value.Contains("/content/DriverDownload-March2009/")) { confirmURL = "http://www.nvidia.com" + link.Attributes["href"].Value.Trim(); } // get release notes URL if (link.Attributes["href"].Value.Contains("release-notes.pdf")) { pdfURL = link.Attributes["href"].Value.Trim(); } } if (pdfURL == null) { if (psID == 98) // if desktop { pdfURL = "http://us.download.nvidia.com/Windows/" + OnlineGPUVersion + "/" + OnlineGPUVersion + "-win10-win8-win7-desktop-release-notes.pdf"; } else { pdfURL = "http://us.download.nvidia.com/Windows/" + OnlineGPUVersion + "/" + OnlineGPUVersion + "-win10-win8-win7-notebook-release-notes.pdf"; } LogManager.Log("No release notes found, but a link to the notes has been crafted by following the template Nvidia uses.", LogManager.Level.INFO); } // get driver desc releaseDesc = htmlDocument.DocumentNode.SelectSingleNode("//div[@id='tab1_content']").InnerHtml.Trim(); releaseDesc = HtmlToText.ConvertHtml(releaseDesc + ".", gpuName.Contains("M")); // Remove not needed information if (psID == 98) // desktop { releaseDesc = releaseDesc.Substring(297, releaseDesc.Length - 297).Trim(); } else // mobile { releaseDesc = releaseDesc.Substring(878, releaseDesc.Length - 878).Trim(); } // get download link htmlDocument = htmlWeb.Load(confirmURL); links = htmlDocument.DocumentNode.Descendants("a").Where(x => x.Attributes.Contains("href")); foreach (var link in links) { if (link.Attributes["href"].Value.Contains("download.nvidia")) { downloadURL = link.Attributes["href"].Value.Trim(); break; // don't need to keep search after we've found what we searched for } } } catch (Exception ex) { OnlineGPUVersion = "000.00"; LogManager.Log(ex.Message, LogManager.Level.ERROR); if (error == 0) { Console.Write("ERROR!"); Console.WriteLine(); error++; } Console.WriteLine(ex.StackTrace); } if (error == 0) { Console.Write("OK!"); Console.WriteLine(); } if (debug == true) { Console.WriteLine("gpuURL: " + gpuURL); Console.WriteLine("processURL: " + processURL); Console.WriteLine("confirmURL: " + confirmURL); Console.WriteLine("downloadURL: " + downloadURL); Console.WriteLine("pdfURL: " + pdfURL); Console.WriteLine("releaseDate: " + releaseDate.ToShortDateString()); Console.WriteLine("OfflineGPUVersion: " + OfflineGPUVersion); Console.WriteLine("OnlineGPUVersion: " + OnlineGPUVersion); } }
/// <summary> /// Check if dependencies are all OK /// </summary> private static void CheckDependencies() { // Check internet connection Console.Write("Searching for a network connection . . . "); switch (NetworkInterface.GetIsNetworkAvailable()) { case true: Console.Write("OK!"); Console.WriteLine(); break; default: Console.Write("ERROR!"); Console.WriteLine(); Console.WriteLine("No network connection was found, the application will now determinate!"); if (showUI == true) { Console.ReadKey(); } Environment.Exit(2); break; } if (!File.Exists("HtmlAgilityPack.dll")) { Console.WriteLine(); Console.Write("Attempting to download HtmlAgilityPack.dll . . . "); try { using (WebClient webClient = new WebClient()) { webClient.DownloadFile("https://github.com/ElPumpo/TinyNvidiaUpdateChecker/releases/download/v" + offlineVer + "/HtmlAgilityPack.dll", "HtmlAgilityPack.dll"); } Console.Write("OK!"); Console.WriteLine(); } catch (Exception ex) { Console.Write("ERROR!"); Console.WriteLine(); Console.WriteLine(ex.StackTrace); Console.WriteLine(); } } string val = null; string key = "Minimal install"; bool checkLib = false; // loop while (val != "true" & val != "false") { val = SettingManager.ReadSetting(key); // refresh value each time if (val == "true") { checkLib = true; } else if (val == "false") { break; } else { // invalid value SettingManager.SetupSetting(key); } } if (checkLib) { if (LibaryHandler.EvaluateLibary() == null) { Console.WriteLine("Doesn't seem like either WinRAR or 7-Zip is installed!"); DialogResult dialogUpdates = MessageBox.Show("Do you want to disable the minimal install feature and use the traditional way?", "TinyNvidiaUpdateChecker", MessageBoxButtons.YesNo, MessageBoxIcon.Warning); if (dialogUpdates == DialogResult.Yes) { SettingManager.SetSetting(key, "false"); } else { Console.WriteLine("The application will determinate itself"); if (showUI == true) { Console.ReadKey(); } Environment.Exit(2); } } } Console.WriteLine(); }
private static void Main(string[] args) { string message = "TinyNvidiaUpdateChecker v" + offlineVer; LogManager.Log(message, LogManager.Level.INFO); Console.Title = message; CheckArgs(args); RunIntro(); // will run intro if no args needs to output stuff if (showUI == true) { AllocConsole(); } ConfigInit(); CheckDependencies(); CheckWinVer(); GetLanguage(); string val = null; string key = "Check for Updates"; while (val != "true" & val != "false") { val = SettingManager.ReadSetting(key); // refresh value each time if (val == "true") { SearchForUpdates(); break; } else if (val == "false") { break; } else { // invalid value SettingManager.SetupSetting(key); } } GpuInfo(); bool hasSelected = false; int iOffline = 0; try { iOffline = Convert.ToInt32(OfflineGPUVersion.Replace(".", string.Empty)); } catch (Exception ex) { OfflineGPUVersion = "Unknown"; Console.WriteLine(ex); } int iOnline = Convert.ToInt32(OnlineGPUVersion.Replace(".", string.Empty)); if (iOnline == iOffline) { Console.WriteLine("Your GPU drivers are up-to-date!"); } else { if (iOffline > iOnline) { Console.WriteLine("Your current GPU driver is newer than remote!"); } if (iOnline < iOffline) { Console.WriteLine("Your GPU drivers are up-to-date!"); } else { Console.WriteLine("There are new drivers available to download!"); hasSelected = true; DownloadDriver(); } } if (hasSelected == false) { if (forceDL == true) { DownloadDriver(); } } Console.WriteLine(); Console.WriteLine("Job done! Press any key to exit."); if (showUI == true) { Console.ReadKey(); } LogManager.Log("BYE!", LogManager.Level.INFO); Environment.Exit(0); }