|
|
#include "precomp.h"
#pragma hdrstop
#include <netcfgx.h>
#include <devguid.h>
HRESULT HrCreateINetCfg ( IN BOOL fAcquireWriteLock, OUT INetCfg** ppINetCfg) { HRESULT hr; INetCfg* pINetCfg;
// Get the INetCfg interface.
//
hr = CoCreateInstance( CLSID_CNetCfg, NULL, CLSCTX_INPROC_SERVER | CLSCTX_NO_CODE_DOWNLOAD, IID_INetCfg, reinterpret_cast<void**>(&pINetCfg));
if (S_OK == hr) { INetCfgLock * pnclock = NULL;
if (fAcquireWriteLock) { // Get the locking interface
hr = pINetCfg->QueryInterface(IID_INetCfgLock, reinterpret_cast<LPVOID *>(&pnclock)); if (SUCCEEDED(hr)) { LPWSTR pwszLockHolder;
// Attempt to lock the INetCfg for read/write
hr = pnclock->AcquireWriteLock(100, L"InstallIPv6", &pwszLockHolder); if (S_FALSE == hr) { // Couldn't acquire the lock
hr = NETCFG_E_NO_WRITE_LOCK; DisplayMessage(g_hModule, EMSG_NO_WRITE_LOCK, pwszLockHolder); } if (pwszLockHolder) { CoTaskMemFree(pwszLockHolder); } } }
if (S_OK == hr) { hr = pINetCfg->Initialize (NULL); if (S_OK == hr) { *ppINetCfg = pINetCfg; pINetCfg->AddRef(); } else { if (pnclock) { pnclock->ReleaseWriteLock(); } } }
if (pnclock) { pnclock->Release(); }
//Transfer ownership to caller.
pINetCfg->Release(); } return hr; }
DWORD pAddOrRemoveIpv6(BOOL fAddIpv6) { HRESULT hr; INetCfg* pINetCfg; DWORD dwErr = NO_ERROR;
hr = HrCreateINetCfg (TRUE, &pINetCfg); if (S_OK == hr) { INetCfgClassSetup* pSetup;
// Get the setup interface used for installing
// and uninstalling components.
//
hr = pINetCfg->QueryNetCfgClass ( &GUID_DEVCLASS_NETTRANS, IID_INetCfgClassSetup, (VOID**)&pSetup);
if (S_OK == hr) { OBO_TOKEN OboToken; INetCfgComponent* pIComp;
ZeroMemory (&OboToken, sizeof(OboToken)); OboToken.Type = OBO_USER;
if (fAddIpv6) { hr = pSetup->Install ( L"MS_TCPIP6", &OboToken, 0, 0, NULL, NULL, &pIComp);
if (pIComp) { pIComp->Release(); } } else { // Need to remove the component.
// Find it first.
//
hr = pINetCfg->FindComponent ( L"MS_TCPIP6", &pIComp);
if (S_OK == hr) { hr = pSetup->DeInstall ( pIComp, &OboToken, NULL);
pIComp->Release(); } else { DisplayMessage(g_hModule, EMSG_PROTO_NOT_INSTALLED); dwErr = ERROR_SUPPRESS_OUTPUT; } }
if (SUCCEEDED(hr)) { if (NETCFG_S_REBOOT == hr) { hr = S_OK; DisplayMessage(g_hModule, EMSG_REBOOT_NEEDED); dwErr = ERROR_SUPPRESS_OUTPUT; } else { dwErr = ERROR_OKAY; } } else { if (NETCFG_E_NEED_REBOOT == hr) { DisplayMessage(g_hModule, EMSG_REBOOT_NEEDED); dwErr = ERROR_SUPPRESS_OUTPUT; } else { dwErr = hr; } }
pSetup->Release(); }
hr = pINetCfg->Uninitialize(); if (SUCCEEDED(hr)) { INetCfgLock *pnclock;
// Get the locking interface
hr = pINetCfg->QueryInterface(IID_INetCfgLock, reinterpret_cast<LPVOID *>(&pnclock)); if (SUCCEEDED(hr)) { // Attempt to lock the INetCfg for read/write
hr = pnclock->ReleaseWriteLock();
pnclock->Release(); } }
pINetCfg->Release(); } else if (NETCFG_E_NO_WRITE_LOCK == hr) { // Message has already been printed
dwErr = ERROR_SUPPRESS_OUTPUT; } else if (HRESULT_FROM_WIN32(ERROR_ACCESS_DENIED) == hr) { dwErr = ERROR_ACCESS_DENIED; } else { dwErr = hr; }
return dwErr; }
EXTERN_C DWORD IsIpv6Installed( BOOL *bInstalled) { HRESULT hr = S_OK; BOOL fInitCom = TRUE; BOOL fPresent = FALSE; DWORD dwErr = NO_ERROR;
// Initialize COM.
//
hr = CoInitializeEx( NULL, COINIT_DISABLE_OLE1DDE | COINIT_APARTMENTTHREADED );
if (RPC_E_CHANGED_MODE == hr) { // If we changed mode, then we won't uninitialize COM when we are done.
//
hr = S_OK; fInitCom = FALSE; }
if (SUCCEEDED(hr)) { HRESULT hr; INetCfg* pINetCfg;
hr = HrCreateINetCfg (FALSE, &pINetCfg); if (S_OK == hr) { fPresent = (S_OK == pINetCfg->FindComponent(L"MS_TCPIP6", NULL)); pINetCfg->Uninitialize(); pINetCfg->Release(); } else { dwErr = hr; }
if (fInitCom) { CoUninitialize(); } } else { dwErr = hr; }
*bInstalled = fPresent;
return dwErr; }
EXTERN_C DWORD AddOrRemoveIpv6 ( IN BOOL fAddIpv6) {
HRESULT hr = S_OK; BOOL fInitCom = TRUE; DWORD dwErr = NO_ERROR;
// Initialize COM.
//
hr = CoInitializeEx( NULL, COINIT_DISABLE_OLE1DDE | COINIT_APARTMENTTHREADED );
if (RPC_E_CHANGED_MODE == hr) { // If we changed mode, then we won't uninitialize COM when we are done.
//
hr = S_OK; fInitCom = FALSE; }
if (SUCCEEDED(hr)) { dwErr = pAddOrRemoveIpv6(fAddIpv6);
if (fInitCom) { CoUninitialize(); } } else { dwErr = hr; }
return dwErr; }
|