Bump to 1.11
This commit is contained in:
@@ -2,13 +2,20 @@
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "LegacyUpdateCtrl.h"
|
||||
#include "Utils.h"
|
||||
#include "Compat.h"
|
||||
#include "ElevationHelper.h"
|
||||
#include "Exec.h"
|
||||
#include "HResult.h"
|
||||
#include "LegacyUpdate.h"
|
||||
#include "Registry.h"
|
||||
#include "User.h"
|
||||
#include "Utils.h"
|
||||
#include "VersionInfo.h"
|
||||
#include "WULog.h"
|
||||
#include <atlbase.h>
|
||||
#include <atlcom.h>
|
||||
#include <ShellAPI.h>
|
||||
#include <ShlObj.h>
|
||||
#include <wuapi.h>
|
||||
#include "IUpdateInstaller4.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
@@ -19,7 +26,6 @@ const BSTR permittedHosts[] = {
|
||||
L"test.legacyupdate.net",
|
||||
NULL
|
||||
};
|
||||
const int permittedHostsMax = 2;
|
||||
|
||||
// CLegacyUpdateCtrl message handlers
|
||||
|
||||
@@ -39,7 +45,7 @@ IHTMLDocument2 *CLegacyUpdateCtrl::GetHTMLDocument() {
|
||||
}
|
||||
|
||||
CComPtr<IHTMLDocument2> document;
|
||||
hr = container->QueryInterface(IID_IHTMLDocument2, (void**)&document);
|
||||
hr = container->QueryInterface(IID_IHTMLDocument2, (void **)&document);
|
||||
if (!SUCCEEDED(hr) || document == NULL) {
|
||||
TRACE("GetDocument() failed: %ls\n", GetMessageForHresult(hr));
|
||||
return NULL;
|
||||
@@ -50,7 +56,7 @@ IHTMLDocument2 *CLegacyUpdateCtrl::GetHTMLDocument() {
|
||||
|
||||
HWND CLegacyUpdateCtrl::GetIEWindowHWND() {
|
||||
CComPtr<IOleWindow> oleWindow;
|
||||
HRESULT hr = QueryInterface(IID_IOleWindow, (void**)&oleWindow);
|
||||
HRESULT hr = QueryInterface(IID_IOleWindow, (void **)&oleWindow);
|
||||
if (!SUCCEEDED(hr) || !oleWindow) {
|
||||
goto end;
|
||||
}
|
||||
@@ -94,7 +100,7 @@ BOOL CLegacyUpdateCtrl::IsPermitted(void) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
for (int i = 0; i < permittedHostsMax; i++) {
|
||||
for (int i = 0; permittedHosts[i] != NULL; i++) {
|
||||
if (wcscmp(host, permittedHosts[i]) == 0) {
|
||||
return TRUE;
|
||||
}
|
||||
@@ -107,22 +113,49 @@ end:
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::GetElevatedHelper(CComPtr<IElevationHelper> &retval) {
|
||||
CComPtr<IElevationHelper> elevatedHelper = m_elevatedHelper ? m_elevatedHelper : m_nonElevatedHelper;
|
||||
if (elevatedHelper == NULL) {
|
||||
// Use the helper directly, without elevation. It's the responsibility of the caller to ensure it
|
||||
// is already running as admin on 2k/XP, or that it has requested elevation on Vista+.
|
||||
HRESULT hr = m_nonElevatedHelper.CoCreateInstance(CLSID_ElevationHelper, NULL, CLSCTX_INPROC_SERVER);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
elevatedHelper = m_nonElevatedHelper;
|
||||
}
|
||||
|
||||
retval = elevatedHelper;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
#define DoIsPermittedCheck() \
|
||||
if (!IsPermitted()) { \
|
||||
return E_ACCESSDENIED; \
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::SetClientSite(IOleClientSite *pClientSite) {
|
||||
HRESULT hr = IOleObjectImpl::SetClientSite(pClientSite);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
DoIsPermittedCheck();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::CheckControl(VARIANT_BOOL *retval) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
// Just return true so the site can confirm the control is working.
|
||||
*retval = TRUE;
|
||||
*retval = VARIANT_TRUE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::MessageForHresult(LONG inHresult, BSTR *retval) {
|
||||
DoIsPermittedCheck();
|
||||
*retval = GetMessageForHresult(inHresult);
|
||||
*retval = SysAllocString(GetMessageForHresult(inHresult));
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -130,71 +163,78 @@ STDMETHODIMP CLegacyUpdateCtrl::GetOSVersionInfo(OSVersionField osField, LONG sy
|
||||
DoIsPermittedCheck();
|
||||
|
||||
VariantInit(retval);
|
||||
retval->vt = VT_I4;
|
||||
|
||||
OSVERSIONINFOEX *versionInfo = GetVersionInfo();
|
||||
|
||||
switch (osField) {
|
||||
case e_majorVer:
|
||||
retval->lVal = versionInfo->dwMajorVersion;
|
||||
retval->vt = VT_UI4;
|
||||
retval->ulVal = versionInfo->dwMajorVersion;
|
||||
break;
|
||||
|
||||
case e_minorVer:
|
||||
retval->lVal = versionInfo->dwMinorVersion;
|
||||
retval->vt = VT_UI4;
|
||||
retval->ulVal = versionInfo->dwMinorVersion;
|
||||
break;
|
||||
|
||||
case e_buildNumber:
|
||||
retval->lVal = versionInfo->dwBuildNumber;
|
||||
retval->vt = VT_UI4;
|
||||
retval->ulVal = versionInfo->dwBuildNumber;
|
||||
break;
|
||||
|
||||
case e_platform:
|
||||
retval->lVal = versionInfo->dwPlatformId;
|
||||
retval->vt = VT_UI4;
|
||||
retval->ulVal = versionInfo->dwPlatformId;
|
||||
break;
|
||||
|
||||
case e_SPMajor:
|
||||
retval->vt = VT_I4;
|
||||
retval->lVal = versionInfo->wServicePackMajor;
|
||||
break;
|
||||
|
||||
case e_SPMinor:
|
||||
retval->vt = VT_I4;
|
||||
retval->lVal = versionInfo->wServicePackMinor;
|
||||
break;
|
||||
|
||||
case e_productSuite:
|
||||
retval->vt = VT_I4;
|
||||
retval->lVal = versionInfo->wSuiteMask;
|
||||
break;
|
||||
|
||||
case e_productType:
|
||||
retval->vt = VT_I4;
|
||||
retval->lVal = versionInfo->wProductType;
|
||||
break;
|
||||
|
||||
case e_systemMetric:
|
||||
retval->vt = VT_I4;
|
||||
retval->lVal = GetSystemMetrics(systemMetric);
|
||||
break;
|
||||
|
||||
case e_SPVersionString: {
|
||||
LPWSTR data;
|
||||
DWORD size;
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", L"BuildLab", NULL, &data, &size);
|
||||
if (SUCCEEDED(hr)) {
|
||||
retval->vt = VT_BSTR;
|
||||
retval->bstrVal = SysAllocStringLen(data, size - 1);
|
||||
} else {
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", L"BuildLab", 0, &data, &size);
|
||||
retval->vt = VT_BSTR;
|
||||
retval->bstrVal = SUCCEEDED(hr)
|
||||
? SysAllocStringLen(data, size - 1)
|
||||
// BuildLab doesn't exist on Windows 2000.
|
||||
retval->vt = VT_BSTR;
|
||||
retval->bstrVal = SysAllocString(versionInfo->szCSDVersion);
|
||||
: SysAllocString(versionInfo->szCSDVersion);
|
||||
if (data) {
|
||||
LocalFree(data);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case e_controlVersionString: {
|
||||
LPWSTR data;
|
||||
DWORD size;
|
||||
HRESULT hr = GetOwnVersion(&data, &size);
|
||||
HRESULT hr = GetOwnVersion(&data);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
retval->vt = VT_BSTR;
|
||||
retval->bstrVal = SysAllocStringLen(data, size - 1);
|
||||
retval->bstrVal = SysAllocString(data);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -211,12 +251,10 @@ STDMETHODIMP CLegacyUpdateCtrl::GetOSVersionInfo(OSVersionField osField, LONG sy
|
||||
if (!SUCCEEDED(hr)) {
|
||||
LPWSTR data;
|
||||
DWORD size;
|
||||
hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", L"ProductName", NULL, &data, &size);
|
||||
hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", L"ProductName", 0, &data, &size);
|
||||
if (SUCCEEDED(hr)) {
|
||||
retval->vt = VT_BSTR;
|
||||
retval->bstrVal = SysAllocStringLen(data, size - 1);
|
||||
} else {
|
||||
VariantClear(retval);
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -225,12 +263,11 @@ STDMETHODIMP CLegacyUpdateCtrl::GetOSVersionInfo(OSVersionField osField, LONG sy
|
||||
case e_displayVersion: {
|
||||
LPWSTR data;
|
||||
DWORD size;
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", L"DisplayVersion", NULL, &data, &size);
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", L"DisplayVersion", 0, &data, &size);
|
||||
if (SUCCEEDED(hr)) {
|
||||
retval->vt = VT_BSTR;
|
||||
retval->bstrVal = SysAllocStringLen(data, size - 1);
|
||||
} else {
|
||||
VariantClear(retval);
|
||||
LocalFree(data);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -242,7 +279,7 @@ STDMETHODIMP CLegacyUpdateCtrl::GetOSVersionInfo(OSVersionField osField, LONG sy
|
||||
STDMETHODIMP CLegacyUpdateCtrl::RequestElevation() {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
if (m_elevatedHelper != NULL || GetVersionInfo()->dwMajorVersion < 6) {
|
||||
if (m_elevatedHelper != NULL || !AtLeastWinVista()) {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -269,15 +306,9 @@ STDMETHODIMP CLegacyUpdateCtrl::CreateObject(BSTR progID, IDispatch **retval) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
elevatedHelper = m_elevatedHelper ? m_elevatedHelper : m_nonElevatedHelper;
|
||||
if (elevatedHelper == NULL) {
|
||||
// Use the helper directly, without elevation. It's the responsibility of the caller to ensure it
|
||||
// is already running as admin on 2k/XP, or that it has requested elevation on Vista+.
|
||||
m_nonElevatedHelper.CoCreateInstance(CLSID_ElevationHelper, NULL, CLSCTX_INPROC_SERVER);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
goto end;
|
||||
}
|
||||
elevatedHelper = m_nonElevatedHelper;
|
||||
hr = GetElevatedHelper(elevatedHelper);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
return elevatedHelper->CreateObject(progID, retval);
|
||||
@@ -289,10 +320,27 @@ end:
|
||||
return hr;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::SetBrowserHwnd(IUpdateInstaller *installer) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
if (installer == NULL) {
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
CComPtr<IUpdateInstaller> updateInstaller = NULL;
|
||||
HRESULT hr = installer->QueryInterface(IID_IUpdateInstaller, (void **)&updateInstaller);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
updateInstaller->put_ParentHwnd(GetIEWindowHWND());
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::GetUserType(UserType *retval) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
if (IsUserAnAdmin()) {
|
||||
if (IsUserAdmin()) {
|
||||
// Entire process is elevated.
|
||||
*retval = e_admin;
|
||||
} else if (m_elevatedHelper != NULL) {
|
||||
@@ -302,115 +350,147 @@ STDMETHODIMP CLegacyUpdateCtrl::GetUserType(UserType *retval) {
|
||||
// The control has no admin rights (although it may not have requested them yet).
|
||||
*retval = e_nonAdmin;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::get_IsRebootRequired(VARIANT_BOOL *retval) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
HKEY subkey;
|
||||
HRESULT hr = RegOpenKeyEx(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\WindowsUpdate\\Auto Update\\RebootRequired", 0, KEY_READ, &subkey);
|
||||
*retval = subkey != NULL;
|
||||
if (subkey != NULL) {
|
||||
RegCloseKey(subkey);
|
||||
// Ask WU itself whether a reboot is required
|
||||
CComPtr<ISystemInformation> systemInfo;
|
||||
if (SUCCEEDED(systemInfo.CoCreateInstance(CLSID_SystemInformation, NULL, CLSCTX_INPROC_SERVER))) {
|
||||
if (SUCCEEDED(systemInfo->get_RebootRequired(retval)) && *retval == VARIANT_TRUE) {
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
|
||||
// Check reboot flag in registry
|
||||
HKEY subkey;
|
||||
HRESULT hr = HRESULT_FROM_WIN32(RegOpenKeyEx(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\WindowsUpdate\\Auto Update\\RebootRequired", KEY_WOW64_64KEY, KEY_READ, &subkey));
|
||||
if (SUCCEEDED(hr)) {
|
||||
RegCloseKey(subkey);
|
||||
*retval = VARIANT_TRUE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
*retval = VARIANT_FALSE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::get_IsWindowsUpdateDisabled(VARIANT_BOOL *retval) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
DWORD noWU;
|
||||
HRESULT hr = GetRegistryDword(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Policies\\Explorer", L"NoWindowsUpdate", NULL, &noWU);
|
||||
if (SUCCEEDED(hr) && noWU == 1) {
|
||||
*retval = TRUE;
|
||||
// Future note: These are in HKCU on NT; HKLM on 9x.
|
||||
// Remove links and access to Windows Update
|
||||
DWORD value;
|
||||
HRESULT hr = GetRegistryDword(HKEY_CURRENT_USER, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Policies\\Explorer", L"NoWindowsUpdate", KEY_WOW64_64KEY, &value);
|
||||
if (SUCCEEDED(hr) && value == 1) {
|
||||
*retval = VARIANT_TRUE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
DWORD disableWUAccess;
|
||||
hr = GetRegistryDword(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Policies\\WindowsUpdate", L"DisableWindowsUpdateAccess", NULL, &disableWUAccess);
|
||||
if (SUCCEEDED(hr) && disableWUAccess == 1) {
|
||||
*retval = TRUE;
|
||||
// Remove access to use all Windows Update features
|
||||
hr = GetRegistryDword(HKEY_CURRENT_USER, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Policies\\WindowsUpdate", L"DisableWindowsUpdateAccess", KEY_WOW64_64KEY, &value);
|
||||
if (SUCCEEDED(hr) && value == 1) {
|
||||
*retval = VARIANT_TRUE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
*retval = FALSE;
|
||||
*retval = VARIANT_FALSE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::RebootIfRequired(void) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
HRESULT hr = S_OK;
|
||||
VARIANT_BOOL isRebootRequired;
|
||||
if (SUCCEEDED(get_IsRebootRequired(&isRebootRequired)) && isRebootRequired) {
|
||||
Reboot();
|
||||
if (SUCCEEDED(get_IsRebootRequired(&isRebootRequired)) && isRebootRequired == VARIANT_TRUE) {
|
||||
// Calling Commit() is recommended on Windows 10, to ensure feature updates are properly prepared
|
||||
// prior to the reboot. If IUpdateInstaller4 doesn't exist, we can skip this.
|
||||
CComPtr<IUpdateInstaller4> installer;
|
||||
hr = installer.CoCreateInstance(CLSID_UpdateInstaller, NULL, CLSCTX_INPROC_SERVER);
|
||||
if (SUCCEEDED(hr) && hr != REGDB_E_CLASSNOTREG) {
|
||||
hr = installer->Commit(0);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
CComPtr<IElevationHelper> elevatedHelper;
|
||||
hr = GetElevatedHelper(elevatedHelper);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = elevatedHelper->Reboot();
|
||||
}
|
||||
return S_OK;
|
||||
|
||||
return hr;
|
||||
}
|
||||
|
||||
static HRESULT StartLauncher(LPWSTR params, BOOL wait) {
|
||||
LPWSTR path;
|
||||
HRESULT hr = GetInstallPath(&path);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
PathAppend(path, L"LegacyUpdate.exe");
|
||||
|
||||
DWORD code;
|
||||
hr = Exec(L"open", path, params, NULL, SW_SHOW, wait, &code);
|
||||
if (SUCCEEDED(hr)) {
|
||||
hr = HRESULT_FROM_WIN32(code);
|
||||
}
|
||||
|
||||
return hr;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::ViewWindowsUpdateLog(void) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
WCHAR windir[MAX_PATH];
|
||||
HRESULT hr = SHGetFolderPath(0, CSIDL_WINDOWS, NULL, 0, windir);
|
||||
HRESULT hr = StartLauncher(L"/log", FALSE);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
TRACE(L"SHGetFolderPath() failed: %ls\n", GetMessageForHresult(hr));
|
||||
return hr;
|
||||
// Try directly
|
||||
hr = ::ViewWindowsUpdateLog(SW_SHOWDEFAULT);
|
||||
}
|
||||
|
||||
// Try Windows Server 2003 Resource Kit (or MSYS/Cygwin/etc) tail.exe, falling back to directly
|
||||
// opening the file (most likely in Notepad).
|
||||
// Ignore C4311 and C4302, which is for typecasts. It is due to ShellExec and should be safe to bypass.
|
||||
#pragma warning(disable: 4311 4302)
|
||||
if ((int)ShellExecute(NULL, L"open", L"tail.exe", L"-f WindowsUpdate.log", windir, SW_SHOWDEFAULT) > 32) {
|
||||
return S_OK;
|
||||
}
|
||||
ShellExecute(NULL, L"open", L"WindowsUpdate.log", NULL, windir, SW_SHOWDEFAULT);
|
||||
#pragma warning(default: 4311 4302)
|
||||
return S_OK;
|
||||
return hr;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::OpenWindowsUpdateSettings(void) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
// Some issues arise from the working directory being SysWOW64 rather than System32. Notably,
|
||||
// Windows Vista - 8.1 don't have wuauclt.exe in SysWOW64. Disable WOW64 redirection temporarily
|
||||
// to work around this.
|
||||
PVOID oldValue;
|
||||
BOOL isRedirected = DisableWow64FsRedirection(&oldValue);
|
||||
|
||||
WCHAR systemDir[MAX_PATH];
|
||||
HRESULT hr = SHGetFolderPath(0, CSIDL_SYSTEM, NULL, 0, systemDir);
|
||||
HRESULT hr = StartLauncher(L"/options", FALSE);
|
||||
if (!SUCCEEDED(hr)) {
|
||||
TRACE(L"SHGetFolderPath() failed: %ls\n", GetMessageForHresult(hr));
|
||||
return hr;
|
||||
TRACE(L"OpenWindowsUpdateSettings() failed, falling back: %ls\n", GetMessageForHresult(hr));
|
||||
|
||||
// Might happen if the site isn't trusted, and the user rejected the IE medium integrity prompt.
|
||||
// Use the basic Automatic Updates dialog directly from COM.
|
||||
CComPtr<IAutomaticUpdates> automaticUpdates;
|
||||
hr = automaticUpdates.CoCreateInstance(CLSID_AutomaticUpdates, NULL, CLSCTX_INPROC_SERVER);
|
||||
|
||||
if (SUCCEEDED(hr)) {
|
||||
hr = automaticUpdates->ShowSettingsDialog();
|
||||
}
|
||||
|
||||
if (!SUCCEEDED(hr)) {
|
||||
TRACE(L"OpenWindowsUpdateSettings() failed: %ls\n", GetMessageForHresult(hr));
|
||||
}
|
||||
}
|
||||
|
||||
DWORD majorVersion = GetVersionInfo()->dwMajorVersion;
|
||||
if (majorVersion >= 10) {
|
||||
// Windows 10+: Open Settings app
|
||||
ShellExecute(NULL, NULL, L"ms-settings:windowsupdate-options", NULL, systemDir, SW_SHOWDEFAULT);
|
||||
} else if (majorVersion >= 6) {
|
||||
// Windows Vista, 7, 8: Open Windows Update control panel
|
||||
ShellExecute(NULL, NULL, L"wuauclt.exe", L"/ShowOptions", systemDir, SW_SHOWDEFAULT);
|
||||
} else {
|
||||
// Windows 2000, XP: Open Automatic Updates control panel
|
||||
ShellExecute(NULL, NULL, L"wuaucpl.cpl", NULL, systemDir, SW_SHOWDEFAULT);
|
||||
}
|
||||
|
||||
// Revert WOW64 redirection if we changed it.
|
||||
if (isRedirected) {
|
||||
RevertWow64FsRedirection(oldValue);
|
||||
}
|
||||
return S_OK;
|
||||
return hr;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLegacyUpdateCtrl::get_IsUsingWsusServer(VARIANT_BOOL *retval) {
|
||||
DoIsPermittedCheck();
|
||||
|
||||
DWORD useWUServer;
|
||||
HRESULT hr = GetRegistryDword(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Policies\\Microsoft\\Windows\\WindowsUpdate\\AU", L"UseWUServer", NULL, &useWUServer);
|
||||
*retval = SUCCEEDED(hr) && useWUServer == 1;
|
||||
HRESULT hr = GetRegistryDword(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Policies\\Microsoft\\Windows\\WindowsUpdate\\AU", L"UseWUServer", 0, &useWUServer);
|
||||
*retval = SUCCEEDED(hr) && useWUServer == 1 ? VARIANT_TRUE : VARIANT_FALSE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -419,8 +499,11 @@ STDMETHODIMP CLegacyUpdateCtrl::get_WsusServerUrl(BSTR *retval) {
|
||||
|
||||
LPWSTR data;
|
||||
DWORD size;
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Policies\\Microsoft\\Windows\\WindowsUpdate", L"WUServer", NULL, &data, &size);
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Policies\\Microsoft\\Windows\\WindowsUpdate", L"WUServer", 0, &data, &size);
|
||||
*retval = SUCCEEDED(hr) ? SysAllocStringLen(data, size - 1) : NULL;
|
||||
if (data) {
|
||||
LocalFree(data);
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -429,7 +512,10 @@ STDMETHODIMP CLegacyUpdateCtrl::get_WsusStatusServerUrl(BSTR *retval) {
|
||||
|
||||
LPWSTR data;
|
||||
DWORD size;
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Policies\\Microsoft\\Windows\\WindowsUpdate", L"WUStatusServer", NULL, &data, &size);
|
||||
HRESULT hr = GetRegistryString(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Policies\\Microsoft\\Windows\\WindowsUpdate", L"WUStatusServer", 0, &data, &size);
|
||||
*retval = SUCCEEDED(hr) ? SysAllocStringLen(data, size - 1) : NULL;
|
||||
if (data) {
|
||||
LocalFree(data);
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
Reference in New Issue
Block a user