From f226f1ade6cb1de3318168a90f46f90fd05cdf49 Mon Sep 17 00:00:00 2001 From: Valentin Radu Date: Mon, 15 Nov 2021 03:59:19 +0200 Subject: [PATCH] Improved delivery of toast notifications --- CHANGELOG.md | 6 + ExplorerPatcher/dllmain.c | 113 +++++++++++- ExplorerPatcher/settings.reg | 4 +- ExplorerPatcher/updates.c | 324 ++++++++++++++++++++++++++++------- ExplorerPatcher/updates.h | 11 +- ExplorerPatcher/utility.h | 1 + ep_setup/ep_setup.c | 40 ++++- 7 files changed, 424 insertions(+), 75 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4a639e8..e3fab21 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -29,6 +29,7 @@ Tested on build 22000.318 and 22000.346 (currently in Windows Insider beta and r * Hardcoded symbols are now based on file hashes, not build numbers * Better organization for the settings in "Properties" +* Update toast notifications are displayed only as long as they are required. Subsequent notifications no longer have to wait for the previous ones to timeout, but rather they replace the previous ones (#346) (.2) #### Fixes @@ -41,6 +42,11 @@ Tested on build 22000.318 and 22000.346 (currently in Windows Insider beta and r * Removed verbose output from "Settings Manager" * Corrected import from `dxgi.dll` * Fixed typo in configuration UI (#346) (.1) +* Fixed typos and spelling in error message (#346) (.2) +* Fixed bug that prevented "Properties" from working when invoked from Quick Launch or other toolbars (#349) (.2) +* As you may have noticed, releases do not contain unpacked files anymore. Thus, for people looking for a quick way to get the unpacked files, the release notes now include a link to the artifacts generated during during the build process. The artifacts include the usual DLLs (including `dxgi.dll`), plus symbol files and all the helper executables generated during the build. (#351) (.2) +* Setup program version is synchronized with the version of the application (.2) +* Fixed a mismatch between the default value for the setting "Add shortcut to program settings in Win+X menu" displayed in the UI and actually used in the software (#352) (.2) ## 22000.318.36 diff --git a/ExplorerPatcher/dllmain.c b/ExplorerPatcher/dllmain.c index b7844c1..d27d5e9 100644 --- a/ExplorerPatcher/dllmain.c +++ b/ExplorerPatcher/dllmain.c @@ -69,6 +69,7 @@ DWORD bNoMenuAccelerator = FALSE; DWORD bTaskbarMonitorOverride = 0; DWORD dwIMEStyle = 0; DWORD dwTaskbarAl = 0; +DWORD bShowUpdateToast = FALSE; HMODULE hModule = NULL; HANDLE hDelayedInjectionThread = NULL; HANDLE hIsWinXShown = NULL; @@ -137,6 +138,74 @@ HRESULT WINAPI _DllGetClassObject( #ifdef _WIN64 DWORD CheckForUpdatesThread(LPVOID unused) { + HRESULT hr = S_OK; + HSTRING_HEADER header_AppIdHString; + HSTRING AppIdHString = NULL; + HSTRING_HEADER header_ToastNotificationManagerHString; + HSTRING ToastNotificationManagerHString = NULL; + __x_ABI_CWindows_CUI_CNotifications_CIToastNotificationManagerStatics* toastStatics = NULL; + __x_ABI_CWindows_CUI_CNotifications_CIToastNotifier* notifier = NULL; + HSTRING_HEADER header_ToastNotificationHString; + HSTRING ToastNotificationHString = NULL; + __x_ABI_CWindows_CUI_CNotifications_CIToastNotificationFactory* notifFactory = NULL; + __x_ABI_CWindows_CUI_CNotifications_CIToastNotification* toast = NULL; + + if (SUCCEEDED(hr)) + { + hr = RoInitialize(RO_INIT_MULTITHREADED); + } + if (SUCCEEDED(hr)) + { + hr = WindowsCreateStringReference( + APPID, + (UINT32)(sizeof(APPID) / sizeof(TCHAR) - 1), + &header_AppIdHString, + &AppIdHString + ); + } + if (SUCCEEDED(hr)) + { + hr = WindowsCreateStringReference( + RuntimeClass_Windows_UI_Notifications_ToastNotificationManager, + (UINT32)(sizeof(RuntimeClass_Windows_UI_Notifications_ToastNotificationManager) / sizeof(wchar_t) - 1), + &header_ToastNotificationManagerHString, + &ToastNotificationManagerHString + ); + } + if (SUCCEEDED(hr)) + { + hr = RoGetActivationFactory( + ToastNotificationManagerHString, + &UIID_IToastNotificationManagerStatics, + (LPVOID*)&toastStatics + ); + } + if (SUCCEEDED(hr)) + { + hr = toastStatics->lpVtbl->CreateToastNotifierWithId( + toastStatics, + AppIdHString, + ¬ifier + ); + } + if (SUCCEEDED(hr)) + { + hr = WindowsCreateStringReference( + RuntimeClass_Windows_UI_Notifications_ToastNotification, + (UINT32)(sizeof(RuntimeClass_Windows_UI_Notifications_ToastNotification) / sizeof(wchar_t) - 1), + &header_ToastNotificationHString, + &ToastNotificationHString + ); + } + if (SUCCEEDED(hr)) + { + hr = RoGetActivationFactory( + ToastNotificationHString, + &UIID_IToastNotificationFactory, + (LPVOID*)¬ifFactory + ); + } + HANDLE hEvents[2]; hEvents[0] = CreateEventW(NULL, FALSE, FALSE, L"EP_Ev_CheckForUpdates_" _T(EP_CLSID)); hEvents[1] = CreateEventW(NULL, FALSE, FALSE, L"EP_Ev_InstallUpdates_" _T(EP_CLSID)); @@ -144,7 +213,7 @@ DWORD CheckForUpdatesThread(LPVOID unused) { if (dwUpdatePolicy != UPDATE_POLICY_MANUAL) { - InstallUpdatesIfAvailable(UPDATES_OP_DEFAULT, bAllocConsole, dwUpdatePolicy); + InstallUpdatesIfAvailable(hModule, bShowUpdateToast, notifier, notifFactory, &toast, UPDATES_OP_DEFAULT, bAllocConsole, dwUpdatePolicy); } DWORD dwRet = 0; while (TRUE) @@ -153,12 +222,12 @@ DWORD CheckForUpdatesThread(LPVOID unused) { case WAIT_OBJECT_0: { - InstallUpdatesIfAvailable(UPDATES_OP_CHECK, bAllocConsole, dwUpdatePolicy); + InstallUpdatesIfAvailable(hModule, bShowUpdateToast, notifier, notifFactory, &toast, UPDATES_OP_CHECK, bAllocConsole, dwUpdatePolicy); break; } case WAIT_OBJECT_0 + 1: { - InstallUpdatesIfAvailable(UPDATES_OP_INSTALL, bAllocConsole, dwUpdatePolicy); + InstallUpdatesIfAvailable(hModule, bShowUpdateToast, notifier, notifFactory, &toast, UPDATES_OP_INSTALL, bAllocConsole, dwUpdatePolicy); break; } default: @@ -170,6 +239,35 @@ DWORD CheckForUpdatesThread(LPVOID unused) CloseHandle(hEvents[0]); CloseHandle(hEvents[1]); } + + if (toast) + { + toast->lpVtbl->Release(toast); + } + if (notifFactory) + { + notifFactory->lpVtbl->Release(notifFactory); + } + if (ToastNotificationHString) + { + WindowsDeleteString(ToastNotificationHString); + } + if (notifier) + { + notifier->lpVtbl->Release(notifier); + } + if (toastStatics) + { + toastStatics->lpVtbl->Release(toastStatics); + } + if (ToastNotificationManagerHString) + { + WindowsDeleteString(ToastNotificationManagerHString); + } + if (AppIdHString) + { + WindowsDeleteString(AppIdHString); + } } #endif #pragma endregion @@ -3288,6 +3386,15 @@ void WINAPI LoadSettings(BOOL bIsExplorer) &dwUpdatePolicy, &dwSize ); + dwSize = sizeof(DWORD); + RegQueryValueExW( + hKey, + TEXT("IsUpdatePending"), + 0, + NULL, + &bShowUpdateToast, + &dwSize + ); RegCloseKey(hKey); } diff --git a/ExplorerPatcher/settings.reg b/ExplorerPatcher/settings.reg index 69a2a98..07bbd47 100644 --- a/ExplorerPatcher/settings.reg +++ b/ExplorerPatcher/settings.reg @@ -45,7 +45,7 @@ "TaskbarSD"=dword:00000001 [HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Explorer\ExplorerPatcher] ;b Add shortcut to program settings in Win+X menu -"PropertiesInWinX"=dword:00000001 +"PropertiesInWinX"=dword:00000000 ;t ;T System tray @@ -314,7 +314,7 @@ ;t ________________________ ;y Check for updates ;;;EP_CHECK_FOR_UPDATES -;y Install latest version +;y Update ;;;EP_INSTALL_UPDATES ;y Read about changes in the latest releases 🡕 ;https://github.com/valinet/ExplorerPatcher/blob/master/CHANGELOG.md diff --git a/ExplorerPatcher/updates.c b/ExplorerPatcher/updates.c index 07bc8a3..3b6dc19 100644 --- a/ExplorerPatcher/updates.c +++ b/ExplorerPatcher/updates.c @@ -54,7 +54,15 @@ void IsUpdateAvailableHelperCallback( } } -BOOL IsUpdateAvailableHelper(char* url, char* szCheckAgainst, DWORD dwUpdateTimeout, BOOL* lpFail) +BOOL IsUpdateAvailableHelper( + char* url, + char* szCheckAgainst, + DWORD dwUpdateTimeout, + BOOL* lpFail, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotifier* notifier, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotificationFactory* notifFactory, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotification** toast +) { BOOL bIsUpdateAvailable = FALSE; @@ -234,6 +242,14 @@ BOOL IsUpdateAvailableHelper(char* url, char* szCheckAgainst, DWORD dwUpdateTime "\", please allow the elevation request.\n" ); #endif + + if (*toast) + { + notifier->lpVtbl->Hide(notifier, *toast); + (*toast)->lpVtbl->Release((*toast)); + (*toast) = NULL; + } + SHELLEXECUTEINFO ShExecInfo = { 0 }; ShExecInfo.cbSize = sizeof(SHELLEXECUTEINFO); ShExecInfo.fMask = SEE_MASK_NOCLOSEPROCESS; @@ -354,10 +370,21 @@ BOOL IsUpdateAvailable(LPCWSTR wszDataStore, char* szCheckAgainst, BOOL* lpFail) #ifdef UPDATES_VERBOSE_OUTPUT printf("[Updates] Update URL: %s\n", szUpdateURL); #endif - return IsUpdateAvailableHelper(szUpdateURL, szCheckAgainst, dwUpdateTimeout, lpFail); + return IsUpdateAvailableHelper( + szUpdateURL, + szCheckAgainst, + dwUpdateTimeout, + lpFail, + NULL, NULL, NULL + ); } -BOOL UpdateProduct(LPCWSTR wszDataStore) +BOOL UpdateProduct( + LPCWSTR wszDataStore, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotifier* notifier, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotificationFactory* notifFactory, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotification** toast +) { HKEY hKey = NULL; DWORD dwSize = 0; @@ -410,11 +437,108 @@ BOOL UpdateProduct(LPCWSTR wszDataStore) #ifdef UPDATES_VERBOSE_OUTPUT printf("[Updates] Update URL: %s\n", szUpdateURL); #endif - return IsUpdateAvailableHelper(szUpdateURL, NULL, dwUpdateTimeout, NULL); + return IsUpdateAvailableHelper( + szUpdateURL, + NULL, + dwUpdateTimeout, + NULL, + notifier, + notifFactory, + toast + ); } -BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwUpdatePolicy) +BOOL InstallUpdatesIfAvailable( + HMODULE hModule, + BOOL bIsPostUpdate, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotifier* notifier, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotificationFactory* notifFactory, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotification** toast, + DWORD dwOperation, + DWORD bAllocConsole, + DWORD dwUpdatePolicy +) { + wchar_t buf[TOAST_BUFSIZ]; + DWORD dwLeftMost = 0; + DWORD dwSecondLeft = 0; + DWORD dwSecondRight = 0; + DWORD dwRightMost = 0; + QueryVersionInfo(hModule, VS_VERSION_INFO, &dwLeftMost, &dwSecondLeft, &dwSecondRight, &dwRightMost); + + if (bIsPostUpdate) + { + __x_ABI_CWindows_CData_CXml_CDom_CIXmlDocument* inputXml = NULL; + const wchar_t text[] = + L"\r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n"; + swprintf_s(buf, TOAST_BUFSIZ, text, dwLeftMost, dwSecondLeft, dwSecondRight, dwRightMost); + String2IXMLDocument( + buf, + wcslen(buf), + &inputXml, + NULL + ); + if (*toast) + { + notifier->lpVtbl->Hide(notifier, *toast); + (*toast)->lpVtbl->Release((*toast)); + (*toast) = NULL; + } + notifFactory->lpVtbl->CreateToastNotification(notifFactory, inputXml, toast); + if (*toast) + { + notifier->lpVtbl->Show(notifier, *toast); + } + if (inputXml) + { + inputXml->lpVtbl->Release(inputXml); + } + + HKEY hKey = NULL; + DWORD dwSize = 0; + + RegCreateKeyExW( + HKEY_CURRENT_USER, + TEXT(REGPATH), + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_READ | KEY_WOW64_64KEY | KEY_WRITE, + NULL, + &hKey, + NULL + ); + if (hKey == NULL || hKey == INVALID_HANDLE_VALUE) + { + hKey = NULL; + } + if (hKey) + { + dwSize = FALSE; + RegSetValueExW( + hKey, + TEXT("IsUpdatePending"), + 0, + REG_DWORD, + &dwSize, + sizeof(DWORD) + ); + RegCloseKey(hKey); + } + + SwitchToThread(); + } + if (bAllocConsole) { switch (dwUpdatePolicy) @@ -439,44 +563,71 @@ BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwU } } + __x_ABI_CWindows_CData_CXml_CDom_CIXmlDocument* inputXml = NULL; if (dwOperation == UPDATES_OP_INSTALL) { - const wchar_t UpdateAvailableXML[] = + const wchar_t text[] = L"\r\n" + L"activationType=\"protocol\" launch=\"https://github.com/valinet/ExplorerPatcher/releases/latest\" duration=\"long\">\r\n" L" \r\n" L" \r\n" L" \r\n" - L" \r\n" + L" \r\n" L" \r\n" L" \r\n" L" \r\n" L" \r\n"; - HRESULT hr = S_OK; - __x_ABI_CWindows_CData_CXml_CDom_CIXmlDocument* inputXml = NULL; - hr = String2IXMLDocument( - UpdateAvailableXML, - wcslen(UpdateAvailableXML), + swprintf_s(buf, TOAST_BUFSIZ, text, dwLeftMost, dwSecondLeft, dwSecondRight, dwRightMost); + String2IXMLDocument( + buf, + wcslen(buf), &inputXml, -#ifdef DEBUG - stdout -#else NULL -#endif ); - hr = ShowToastMessage( - inputXml, - APPID, - sizeof(APPID) / sizeof(TCHAR) - 1, -#ifdef DEBUG - stdout -#else + } + else if (dwOperation == UPDATES_OP_CHECK) + { + const wchar_t text[] = + L"\r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n"; + swprintf_s(buf, TOAST_BUFSIZ, text, dwLeftMost, dwSecondLeft, dwSecondRight, dwRightMost); + String2IXMLDocument( + buf, + wcslen(buf), + &inputXml, NULL -#endif ); } + if (dwOperation == UPDATES_OP_CHECK || dwOperation == UPDATES_OP_INSTALL) + { + if (*toast) + { + notifier->lpVtbl->Hide(notifier, *toast); + (*toast)->lpVtbl->Release((*toast)); + (*toast) = NULL; + } + notifFactory->lpVtbl->CreateToastNotification(notifFactory, inputXml, toast); + if ((*toast)) + { + notifier->lpVtbl->Show(notifier, *toast); + } + if (inputXml) + { + inputXml->lpVtbl->Release(inputXml); + } + } + WCHAR dllName[MAX_PATH]; GetModuleFileNameW(hModule, dllName, MAX_PATH); wprintf(L"[Updates] Path to module: %s\n", dllName); @@ -491,11 +642,54 @@ BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwU printf("[Updates] An update is available.\n"); if ((dwOperation == UPDATES_OP_DEFAULT && dwUpdatePolicy == UPDATE_POLICY_AUTO) || (dwOperation == UPDATES_OP_INSTALL)) { - UpdateProduct(_T(REGPATH)); + __x_ABI_CWindows_CData_CXml_CDom_CIXmlDocument* inputXml = NULL; + BOOL bOk = UpdateProduct(_T(REGPATH), notifier, notifFactory, toast); + if (!bOk) + { + if (dwOperation == UPDATES_OP_INSTALL) + { + const wchar_t text[] = + L"\r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n" + L" \r\n"; + String2IXMLDocument( + text, + wcslen(text), + &inputXml, + NULL + ); + } + } + if (bOk || (!bOk && (dwOperation == UPDATES_OP_INSTALL))) + { + if (*toast) + { + notifier->lpVtbl->Hide(notifier, *toast); + (*toast)->lpVtbl->Release((*toast)); + (*toast) = NULL; + } + notifFactory->lpVtbl->CreateToastNotification(notifFactory, inputXml, toast); + if ((*toast)) + { + notifier->lpVtbl->Show(notifier, *toast); + } + if (inputXml) + { + inputXml->lpVtbl->Release(inputXml); + } + } } else if ((dwOperation == UPDATES_OP_DEFAULT && dwUpdatePolicy == UPDATE_POLICY_NOTIFY) || (dwOperation == UPDATES_OP_CHECK)) { - const wchar_t UpdateAvailableXML[] = + const wchar_t text[] = L"\r\n" L" \r\n" @@ -507,28 +701,28 @@ BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwU L" \r\n" L" \r\n"; - HRESULT hr = S_OK; __x_ABI_CWindows_CData_CXml_CDom_CIXmlDocument* inputXml = NULL; - hr = String2IXMLDocument( - UpdateAvailableXML, - wcslen(UpdateAvailableXML), + String2IXMLDocument( + text, + wcslen(text), &inputXml, -#ifdef DEBUG - stdout -#else NULL -#endif - ); - hr = ShowToastMessage( - inputXml, - APPID, - sizeof(APPID) / sizeof(TCHAR) - 1, -#ifdef DEBUG - stdout -#else - NULL -#endif ); + if (*toast) + { + notifier->lpVtbl->Hide(notifier, *toast); + (*toast)->lpVtbl->Release((*toast)); + (*toast) = NULL; + } + notifFactory->lpVtbl->CreateToastNotification(notifFactory, inputXml, toast); + if ((*toast)) + { + notifier->lpVtbl->Show(notifier, *toast); + } + if (inputXml) + { + inputXml->lpVtbl->Release(inputXml); + } } return TRUE; @@ -545,7 +739,7 @@ BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwU } if (dwOperation == UPDATES_OP_CHECK || dwOperation == UPDATES_OP_INSTALL) { - const wchar_t UpdateAvailableXML[] = + const wchar_t text[] = L"\r\n" L" \r\n" @@ -557,7 +751,7 @@ BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwU L" \r\n" L" \r\n"; - const wchar_t UpdateAvailableXML2[] = + const wchar_t text2[] = L"\r\n" L" \r\n" @@ -569,28 +763,28 @@ BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwU L" \r\n" L" \r\n"; - HRESULT hr = S_OK; __x_ABI_CWindows_CData_CXml_CDom_CIXmlDocument* inputXml = NULL; - hr = String2IXMLDocument( - bFail ? UpdateAvailableXML2 : UpdateAvailableXML, - wcslen(bFail ? UpdateAvailableXML2 : UpdateAvailableXML), + String2IXMLDocument( + bFail ? text2 : text, + wcslen(bFail ? text2 : text), &inputXml, -#ifdef DEBUG - stdout -#else NULL -#endif - ); - hr = ShowToastMessage( - inputXml, - APPID, - sizeof(APPID) / sizeof(TCHAR) - 1, -#ifdef DEBUG - stdout -#else - NULL -#endif ); + if (*toast) + { + notifier->lpVtbl->Hide(notifier, *toast); + (*toast)->lpVtbl->Release((*toast)); + (*toast) = NULL; + } + notifFactory->lpVtbl->CreateToastNotification(notifFactory, inputXml, toast); + if ((*toast)) + { + notifier->lpVtbl->Show(notifier, *toast); + } + if (inputXml) + { + inputXml->lpVtbl->Release(inputXml); + } } return FALSE; } diff --git a/ExplorerPatcher/updates.h b/ExplorerPatcher/updates.h index 5681fb9..d83a7f2 100644 --- a/ExplorerPatcher/updates.h +++ b/ExplorerPatcher/updates.h @@ -33,7 +33,12 @@ typedef struct IsUpdateAvailableParameters }; BOOL IsUpdatePolicy(LPCWSTR wszDataStore, DWORD dwUpdatePolicy); -BOOL IsUpdateAvailable(LPCWSTR wszDataStore, char* szCheckAgainst); -BOOL UpdateProduct(LPCWSTR wszDataStore); -BOOL InstallUpdatesIfAvailable(DWORD dwOperation, DWORD bAllocConsole, DWORD dwUpdatePolicy); +BOOL InstallUpdatesIfAvailable( + HMODULE hModule, + BOOL bIsPostUpdate, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotifier* notifier, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotificationFactory* notifFactory, + __x_ABI_CWindows_CUI_CNotifications_CIToastNotification** toast, + DWORD dwOperation, DWORD bAllocConsole, DWORD dwUpdatePolicy +); #endif \ No newline at end of file diff --git a/ExplorerPatcher/utility.h b/ExplorerPatcher/utility.h index fe3c092..c5cec90 100644 --- a/ExplorerPatcher/utility.h +++ b/ExplorerPatcher/utility.h @@ -29,6 +29,7 @@ #define DOSMODE_OFFSET 78 #define SETUP_UTILITY_NAME "ep_setup.exe" #define DEFAULT_UPDATE_URL "https://github.com/valinet/ExplorerPatcher/releases/latest/download/" +#define TOAST_BUFSIZ 1024 // This allows compiling with older Windows SDKs as well #ifndef DWMWA_USE_HOSTBACKDROPBRUSH diff --git a/ep_setup/ep_setup.c b/ep_setup/ep_setup.c index 7bc5f7c..a551226 100644 --- a/ep_setup/ep_setup.c +++ b/ep_setup/ep_setup.c @@ -291,7 +291,7 @@ int WINAPI wWinMain( _In_ int nShowCmd ) { - BOOL bOk = TRUE, bInstall = TRUE, bWasShellExt = FALSE; + BOOL bOk = TRUE, bInstall = TRUE, bWasShellExt = FALSE, bIsUpdate = FALSE; SetProcessDpiAwarenessContext(DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2); @@ -326,6 +326,8 @@ int WINAPI wWinMain( &argc ); + bIsUpdate = (argc >= 1 && !_wcsicmp(wargv[0], L"/update_silent")); + WCHAR wszPath[MAX_PATH]; ZeroMemory(wszPath, MAX_PATH * sizeof(WCHAR)); if (bOk) @@ -335,7 +337,7 @@ int WINAPI wWinMain( if (bOk) { wcscat_s(wszPath, MAX_PATH, L"\\dxgi.dll"); - bInstall = !FileExistsW(wszPath) || (argc >= 1 && !_wcsicmp(wargv[0], L"/update_silent")); + bInstall = !FileExistsW(wszPath) || bIsUpdate; } if (!bInstall) { @@ -498,6 +500,40 @@ int WINAPI wWinMain( } else { + if (bIsUpdate) + { + HKEY hKey = NULL; + DWORD dwSize = 0; + + RegCreateKeyExW( + HKEY_CURRENT_USER, + TEXT(REGPATH), + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_READ | KEY_WOW64_64KEY | KEY_WRITE, + NULL, + &hKey, + NULL + ); + if (hKey == NULL || hKey == INVALID_HANDLE_VALUE) + { + hKey = NULL; + } + if (hKey) + { + dwSize = TRUE; + RegSetValueExW( + hKey, + TEXT("IsUpdatePending"), + 0, + REG_DWORD, + &dwSize, + sizeof(DWORD) + ); + RegCloseKey(hKey); + } + } //ZZRestartExplorer(0, 0, 0, 0); } }