Something went wrong. Try again.
Reactos
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714/* * PROJECT: ReactOS Shell * LICENSE: LGPL-2.1-or-later (https://spdx.org/licenses/LGPL-2.1-or-later) * PURPOSE: CNetConnectionManager class * COPYRIGHT: Copyright 2008 Johannes Anderwald (johannes.anderwald@reactos.org) */
#include "precomp.h"
VOID NormalizeOperStatus(MIB_IFROW *IfEntry, NETCON_PROPERTIES * Props);
/*************************************************************** * INetConnection Interface */
HRESULTWINAPICNetConnection::Initialize(PINetConnectionItem pItem){ m_Props = pItem->Props; m_dwAdapterIndex = pItem->dwAdapterIndex;
if (pItem->Props.pszwName) { m_Props.pszwName = static_cast<PWSTR>(CoTaskMemAlloc((wcslen(pItem->Props.pszwName)+1)*sizeof(WCHAR))); if (m_Props.pszwName) wcscpy(m_Props.pszwName, pItem->Props.pszwName); }
if (pItem->Props.pszwDeviceName) { m_Props.pszwDeviceName = static_cast<PWSTR>(CoTaskMemAlloc((wcslen(pItem->Props.pszwDeviceName)+1)*sizeof(WCHAR))); if (m_Props.pszwDeviceName) wcscpy(m_Props.pszwDeviceName, pItem->Props.pszwDeviceName); }
return S_OK;}
CNetConnection::~CNetConnection(){ CoTaskMemFree(m_Props.pszwName); CoTaskMemFree(m_Props.pszwDeviceName);}
HRESULTWINAPICNetConnection::Connect(){ return E_NOTIMPL;}
BOOLFindNetworkAdapter(HDEVINFO hInfo, SP_DEVINFO_DATA *pDevInfo, LPWSTR pGuid){ DWORD dwIndex, dwSize; HKEY hSubKey; WCHAR szNetCfg[50]; WCHAR szDetail[200] = L"SYSTEM\\CurrentControlSet\\Control\\Class\\";
dwIndex = 0; do { ZeroMemory(pDevInfo, sizeof(SP_DEVINFO_DATA)); pDevInfo->cbSize = sizeof(SP_DEVINFO_DATA);
/* get device info */ if (!SetupDiEnumDeviceInfo(hInfo, dwIndex++, pDevInfo)) break;
/* get device software registry path */ if (!SetupDiGetDeviceRegistryPropertyW(hInfo, pDevInfo, SPDRP_DRIVER, NULL, (LPBYTE)&szDetail[39], sizeof(szDetail)/sizeof(WCHAR) - 40, &dwSize)) break;
/* open device registry key */ if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szDetail, 0, KEY_READ, &hSubKey) != ERROR_SUCCESS) break;
/* query NetCfgInstanceId for current device */ dwSize = sizeof(szNetCfg); if (RegQueryValueExW(hSubKey, L"NetCfgInstanceId", NULL, NULL, (LPBYTE)szNetCfg, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); break; } RegCloseKey(hSubKey); if (!_wcsicmp(pGuid, szNetCfg)) { return TRUE; } } while (TRUE);
return FALSE;}
HRESULTWINAPICNetConnection::Disconnect(){ HKEY hKey; NETCON_PROPERTIES * pProperties; LPOLESTR pDisplayName; WCHAR szPath[200]; DWORD dwSize, dwType; LPWSTR pPnp; HDEVINFO hInfo; SP_DEVINFO_DATA DevInfo; SP_PROPCHANGE_PARAMS PropChangeParams; HRESULT hr;
hr = GetProperties(&pProperties); if (FAILED_UNEXPECTEDLY(hr)) return hr;
hInfo = SetupDiGetClassDevsW(&GUID_DEVCLASS_NET, NULL, NULL, DIGCF_PRESENT ); if (!hInfo) { NcFreeNetconProperties(pProperties); return E_FAIL; }
if (FAILED(StringFromCLSID((CLSID)pProperties->guidId, &pDisplayName))) { NcFreeNetconProperties(pProperties); SetupDiDestroyDeviceInfoList(hInfo); return E_FAIL; } NcFreeNetconProperties(pProperties);
if (FindNetworkAdapter(hInfo, &DevInfo, pDisplayName)) { PropChangeParams.ClassInstallHeader.cbSize = sizeof(SP_CLASSINSTALL_HEADER); PropChangeParams.ClassInstallHeader.InstallFunction = DIF_PROPERTYCHANGE; //; PropChangeParams.StateChange = DICS_DISABLE; PropChangeParams.Scope = DICS_FLAG_CONFIGSPECIFIC; PropChangeParams.HwProfile = 0;
if (!SetupDiSetClassInstallParams(hInfo, &DevInfo, &PropChangeParams.ClassInstallHeader, sizeof(SP_PROPCHANGE_PARAMS)) || !SetupDiCallClassInstaller(DIF_PROPERTYCHANGE, hInfo, &DevInfo)) { hr = HRESULT_FROM_WIN32(GetLastError()); } } SetupDiDestroyDeviceInfoList(hInfo);
swprintf(szPath, L"SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\%s\\Connection", pDisplayName); CoTaskMemFree(pDisplayName);
if (FAILED_UNEXPECTEDLY(hr)) return hr;
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szPath, 0, KEY_READ, &hKey) != ERROR_SUCCESS) return E_FAIL;
dwSize = 0; if (RegQueryValueExW(hKey, L"PnpInstanceID", NULL, &dwType, NULL, &dwSize) != ERROR_SUCCESS || dwType != REG_SZ) { RegCloseKey(hKey); return E_FAIL; }
pPnp = static_cast<PWSTR>(CoTaskMemAlloc(dwSize)); if (!pPnp) { RegCloseKey(hKey); return E_FAIL; }
if (RegQueryValueExW(hKey, L"PnpInstanceID", NULL, &dwType, (LPBYTE)pPnp, &dwSize) != ERROR_SUCCESS) { CoTaskMemFree(pPnp); RegCloseKey(hKey); return E_FAIL; } RegCloseKey(hKey);
swprintf(szPath, L"System\\CurrentControlSet\\Hardware Profiles\\Current\\System\\CurrentControlSet\\Enum\\%s", pPnp); CoTaskMemFree(pPnp);
if (RegCreateKeyExW(HKEY_LOCAL_MACHINE, szPath, 0, NULL, 0, KEY_WRITE, NULL, &hKey, NULL) != ERROR_SUCCESS) return E_FAIL;
dwSize = 1; /* enable = 0, disable = 1 */ RegSetValueExW(hKey, L"CSConfigFlags", 0, REG_DWORD, (LPBYTE)&dwSize, sizeof(DWORD)); RegCloseKey(hKey);
return S_OK;}
HRESULTWINAPICNetConnection::Delete(){ return E_NOTIMPL;}
HRESULTWINAPICNetConnection::Duplicate( LPCWSTR pszwDuplicateName, INetConnection **ppCon){ return E_NOTIMPL;}
HRESULTWINAPICNetConnection::GetProperties(NETCON_PROPERTIES **ppProps){ MIB_IFROW IfEntry; HKEY hKey; LPOLESTR pStr; WCHAR szName[140]; DWORD dwShowIcon, dwNotifyDisconnect, dwType, dwSize; NETCON_PROPERTIES * pProperties; HRESULT hr;
if (!ppProps) return E_POINTER;
pProperties = static_cast<NETCON_PROPERTIES*>(CoTaskMemAlloc(sizeof(NETCON_PROPERTIES))); if (!pProperties) return E_OUTOFMEMORY;
CopyMemory(pProperties, &m_Props, sizeof(NETCON_PROPERTIES)); pProperties->pszwName = NULL;
if (m_Props.pszwDeviceName) { pProperties->pszwDeviceName = static_cast<LPWSTR>(CoTaskMemAlloc((wcslen(m_Props.pszwDeviceName)+1)*sizeof(WCHAR))); if (pProperties->pszwDeviceName) wcscpy(pProperties->pszwDeviceName, m_Props.pszwDeviceName); }
*ppProps = pProperties;
/* get updated adapter characteristics */ ZeroMemory(&IfEntry, sizeof(IfEntry)); IfEntry.dwIndex = m_dwAdapterIndex; if (GetIfEntry(&IfEntry) != NO_ERROR) return NOERROR;
NormalizeOperStatus(&IfEntry, pProperties);
hr = StringFromCLSID((CLSID)m_Props.guidId, &pStr); if (SUCCEEDED(hr)) { wcscpy(szName, L"SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\"); wcscat(szName, pStr); wcscat(szName, L"\\Connection");
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szName, 0, KEY_READ, &hKey) == ERROR_SUCCESS) { dwSize = sizeof(dwShowIcon); if (RegQueryValueExW(hKey, L"ShowIcon", NULL, &dwType, (LPBYTE)&dwShowIcon, &dwSize) == ERROR_SUCCESS && dwType == REG_DWORD) { if (dwShowIcon) pProperties->dwCharacter |= NCCF_SHOW_ICON; else pProperties->dwCharacter &= ~NCCF_SHOW_ICON; }
dwSize = sizeof(dwNotifyDisconnect); if (RegQueryValueExW(hKey, L"IpCheckingEnabled", NULL, &dwType, (LPBYTE)&dwNotifyDisconnect, &dwSize) == ERROR_SUCCESS && dwType == REG_DWORD) { if (dwNotifyDisconnect) pProperties->dwCharacter |= NCCF_NOTIFY_DISCONNECTED; else pProperties->dwCharacter &= ~NCCF_NOTIFY_DISCONNECTED; }
dwSize = sizeof(szName); if (RegQueryValueExW(hKey, L"Name", NULL, &dwType, (LPBYTE)szName, &dwSize) == ERROR_SUCCESS) { /* use updated name */ dwSize = wcslen(szName) + 1; pProperties->pszwName = static_cast<PWSTR>(CoTaskMemAlloc(dwSize * sizeof(WCHAR))); if (pProperties->pszwName) CopyMemory(pProperties->pszwName, szName, dwSize * sizeof(WCHAR)); } else { /* use cached name */ if (m_Props.pszwName) { pProperties->pszwName = static_cast<PWSTR>(CoTaskMemAlloc((wcslen(m_Props.pszwName)+1)*sizeof(WCHAR))); if (pProperties->pszwName) wcscpy(pProperties->pszwName, m_Props.pszwName); } } RegCloseKey(hKey); } CoTaskMemFree(pStr); }
/* Enable 'Rename' and 'Delete' for Adminstrators only */ if (IsUserAdmin()) { pProperties->dwCharacter |= NCCF_ALLOW_RENAME;
/* Virtual network interfaces can be deleted */ if (IfEntry.dwType == IF_TYPE_TUNNEL) { pProperties->dwCharacter |= NCCF_ALLOW_REMOVAL; } } else { pProperties->dwCharacter &= ~(NCCF_ALLOW_RENAME | NCCF_ALLOW_REMOVAL); }
return S_OK;}
HRESULTWINAPICNetConnection::GetUiObjectClassId(CLSID *pclsid){ if (m_Props.MediaType == NCM_LAN) { CopyMemory(pclsid, &CLSID_LanConnectionUi, sizeof(CLSID)); return S_OK; }
return E_NOTIMPL;}
HRESULTWINAPICNetConnection::Rename(LPCWSTR pszwDuplicateName){ WCHAR szName[140]; LPOLESTR pStr; DWORD dwSize; HKEY hKey; HRESULT hr;
if (pszwDuplicateName == NULL || wcslen(pszwDuplicateName) == 0) return S_OK;
if (m_Props.pszwName) { CoTaskMemFree(m_Props.pszwName); m_Props.pszwName = NULL; }
dwSize = (wcslen(pszwDuplicateName) + 1) * sizeof(WCHAR); m_Props.pszwName = static_cast<PWSTR>(CoTaskMemAlloc(dwSize)); if (m_Props.pszwName == NULL) return E_OUTOFMEMORY;
wcscpy(m_Props.pszwName, pszwDuplicateName);
hr = StringFromCLSID((CLSID)m_Props.guidId, &pStr); if (SUCCEEDED(hr)) { wcscpy(szName, L"SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\"); wcscat(szName, pStr); wcscat(szName, L"\\Connection");
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szName, 0, KEY_WRITE, &hKey) == ERROR_SUCCESS) { RegSetValueExW(hKey, L"Name", NULL, REG_SZ, (LPBYTE)m_Props.pszwName, dwSize); RegCloseKey(hKey); }
CoTaskMemFree(pStr); }
return hr;}
HRESULT WINAPI CNetConnection_CreateInstance(PINetConnectionItem pItem, REFIID riid, LPVOID * ppv){ return ShellObjectCreatorInit<CNetConnection>(pItem, riid, ppv);}
CNetConnectionManager::CNetConnectionManager() : m_pHead(NULL), m_pCurrent(NULL){}
HRESULTWINAPICNetConnectionManager::EnumConnections( NETCONMGR_ENUM_FLAGS Flags, IEnumNetConnection **ppEnum){ TRACE("EnumConnections\n");
if (!ppEnum) return E_POINTER;
if (Flags != NCME_DEFAULT) return E_FAIL;
*ppEnum = static_cast<IEnumNetConnection*>(this); AddRef(); return S_OK;}
/*************************************************************** * IEnumNetConnection Interface */
HRESULTWINAPICNetConnectionManager::Next( ULONG celt, INetConnection **rgelt, ULONG *pceltFetched){ HRESULT hr;
if (!pceltFetched || !rgelt) return E_POINTER;
if (celt != 1) return E_FAIL;
if (!m_pCurrent) return S_FALSE;
hr = CNetConnection_CreateInstance(m_pCurrent, IID_PPV_ARG(INetConnection, rgelt)); m_pCurrent = m_pCurrent->Next;
return hr;}
HRESULTWINAPICNetConnectionManager::Skip(ULONG celt){ while (m_pCurrent && celt-- > 0) m_pCurrent = m_pCurrent->Next;
if (celt) return S_FALSE; else return S_OK;
}
HRESULTWINAPICNetConnectionManager::Reset(){ m_pCurrent = m_pHead; return S_OK;}
HRESULTWINAPICNetConnectionManager::Clone(IEnumNetConnection **ppenum){ return E_NOTIMPL;}
BOOLGetAdapterIndexFromNetCfgInstanceId(PIP_ADAPTER_INFO pAdapterInfo, LPWSTR szNetCfg, PDWORD pIndex){ WCHAR szBuffer[50]; IP_ADAPTER_INFO * pCurrentAdapter;
pCurrentAdapter = pAdapterInfo; while (pCurrentAdapter) { szBuffer[0] = L'\0'; if (MultiByteToWideChar(CP_ACP, 0, pCurrentAdapter->AdapterName, -1, szBuffer, sizeof(szBuffer)/sizeof(szBuffer[0]))) { szBuffer[(sizeof(szBuffer)/sizeof(WCHAR))-1] = L'\0'; } if (!_wcsicmp(szBuffer, szNetCfg)) { *pIndex = pCurrentAdapter->Index; return TRUE; } pCurrentAdapter = pCurrentAdapter->Next; } return FALSE;}
VOIDNormalizeOperStatus( MIB_IFROW *IfEntry, NETCON_PROPERTIES * Props){ switch (IfEntry->dwOperStatus) { case MIB_IF_OPER_STATUS_NON_OPERATIONAL: Props->Status = NCS_HARDWARE_DISABLED; break; case MIB_IF_OPER_STATUS_UNREACHABLE: Props->Status = NCS_DISCONNECTED; break; case MIB_IF_OPER_STATUS_DISCONNECTED: Props->Status = NCS_MEDIA_DISCONNECTED; break; case MIB_IF_OPER_STATUS_CONNECTING: Props->Status = NCS_CONNECTING; break; case MIB_IF_OPER_STATUS_CONNECTED: Props->Status = NCS_CONNECTED; break; case MIB_IF_OPER_STATUS_OPERATIONAL: Props->Status = NCS_CONNECTED; break; default: break; }}
HRESULTCNetConnectionManager::EnumerateINetConnections(){ DWORD dwSize, dwResult, dwIndex, dwAdapterIndex, dwShowIcon, dwNotifyDisconnect; MIB_IFTABLE *pIfTable; MIB_IFROW IfEntry; IP_ADAPTER_INFO * pAdapterInfo; HDEVINFO hInfo; SP_DEVINFO_DATA DevInfo; HKEY hSubKey; WCHAR szNetCfg[50]; WCHAR szAdapterNetCfg[50]; WCHAR szDetail[200] = L"SYSTEM\\CurrentControlSet\\Control\\Class\\"; WCHAR szName[130] = L"SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\"; PINetConnectionItem pCurrent = NULL;
/* get the IfTable */ dwSize = 0; if (GetIfTable(NULL, &dwSize, TRUE) != ERROR_INSUFFICIENT_BUFFER) return E_FAIL;
pIfTable = static_cast<PMIB_IFTABLE>(CoTaskMemAlloc(dwSize)); if (!pIfTable) return E_OUTOFMEMORY;
dwResult = GetIfTable(pIfTable, &dwSize, TRUE); if (dwResult != NO_ERROR) { CoTaskMemFree(pIfTable); return HRESULT_FROM_WIN32(dwResult); }
dwSize = 0; dwResult = GetAdaptersInfo(NULL, &dwSize); if (dwResult!= ERROR_BUFFER_OVERFLOW) { CoTaskMemFree(pIfTable); return HRESULT_FROM_WIN32(dwResult); }
pAdapterInfo = static_cast<PIP_ADAPTER_INFO>(CoTaskMemAlloc(dwSize)); if (!pAdapterInfo) { CoTaskMemFree(pIfTable); return E_OUTOFMEMORY; }
dwResult = GetAdaptersInfo(pAdapterInfo, &dwSize); if (dwResult != NO_ERROR) { CoTaskMemFree(pIfTable); CoTaskMemFree(pAdapterInfo); return HRESULT_FROM_WIN32(dwResult); }
hInfo = SetupDiGetClassDevs(&GUID_DEVCLASS_NET, NULL, NULL, DIGCF_PRESENT ); if (!hInfo) { CoTaskMemFree(pIfTable); CoTaskMemFree(pAdapterInfo); return E_FAIL; }
dwIndex = 0; do { ZeroMemory(&DevInfo, sizeof(SP_DEVINFO_DATA)); DevInfo.cbSize = sizeof(DevInfo);
/* get device info */ if (!SetupDiEnumDeviceInfo(hInfo, dwIndex++, &DevInfo)) break;
/* get device software registry path */ if (!SetupDiGetDeviceRegistryPropertyW(hInfo, &DevInfo, SPDRP_DRIVER, NULL, (LPBYTE)&szDetail[39], sizeof(szDetail)/sizeof(WCHAR) - 40, &dwSize)) break;
/* open device registry key */ if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szDetail, 0, KEY_READ, &hSubKey) != ERROR_SUCCESS) break;
/* query NetCfgInstanceId for current device */ dwSize = sizeof(szNetCfg); if (RegQueryValueExW(hSubKey, L"NetCfgInstanceId", NULL, NULL, (LPBYTE)szNetCfg, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); break; } RegCloseKey(hSubKey);
/* get the current adapter index from NetCfgInstanceId */ if (!GetAdapterIndexFromNetCfgInstanceId(pAdapterInfo, szNetCfg, &dwAdapterIndex)) continue;
/* get detailed adapter info */ ZeroMemory(&IfEntry, sizeof(IfEntry)); IfEntry.dwIndex = dwAdapterIndex; if (GetIfEntry(&IfEntry) != NO_ERROR) break;
/* allocate new INetConnectionItem */ PINetConnectionItem pNew = static_cast<PINetConnectionItem>(CoTaskMemAlloc(sizeof(INetConnectionItem))); if (!pNew) break;
ZeroMemory(pNew, sizeof(INetConnectionItem)); pNew->dwAdapterIndex = dwAdapterIndex; /* store NetCfgInstanceId */ CLSIDFromString(szNetCfg, &pNew->Props.guidId); NormalizeOperStatus(&IfEntry, &pNew->Props);
switch (IfEntry.dwType) { case IF_TYPE_ETHERNET_CSMACD: pNew->Props.MediaType = NCM_LAN; break; case IF_TYPE_IEEE80211: pNew->Props.MediaType = NCM_SHAREDACCESSHOST_RAS; break; default: break; } /* open network connections details */ wcscpy(&szName[80], szNetCfg); wcscpy(&szName[118], L"\\Connection");
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szName, 0, KEY_READ, &hSubKey) == ERROR_SUCCESS) { /* retrieve name of connection */ dwSize = sizeof(szAdapterNetCfg); if (RegQueryValueExW(hSubKey, L"Name", NULL, NULL, (LPBYTE)szAdapterNetCfg, &dwSize) == ERROR_SUCCESS) { pNew->Props.pszwName = static_cast<PWSTR>(CoTaskMemAlloc((wcslen(szAdapterNetCfg)+1) * sizeof(WCHAR))); if (pNew->Props.pszwName) wcscpy(pNew->Props.pszwName, szAdapterNetCfg); } dwSize = sizeof(dwShowIcon); if (RegQueryValueExW(hSubKey, L"ShowIcon", NULL, NULL, (LPBYTE)&dwShowIcon, &dwSize) == ERROR_SUCCESS) { if (dwShowIcon) pNew->Props.dwCharacter |= NCCF_SHOW_ICON; } dwSize = sizeof(dwNotifyDisconnect); if (RegQueryValueExW(hSubKey, L"IpCheckingEnabled", NULL, NULL, (LPBYTE)&dwNotifyDisconnect, &dwSize) == ERROR_SUCCESS) { if (dwNotifyDisconnect) pNew->Props.dwCharacter |= NCCF_NOTIFY_DISCONNECTED; } RegCloseKey(hSubKey); }
/* Get the adapter device description */ dwSize = 0; SetupDiGetDeviceRegistryPropertyW(hInfo, &DevInfo, SPDRP_DEVICEDESC, NULL, NULL, 0, &dwSize); if (dwSize != 0) { pNew->Props.pszwDeviceName = static_cast<PWSTR>(CoTaskMemAlloc(dwSize)); if (pNew->Props.pszwDeviceName) SetupDiGetDeviceRegistryPropertyW(hInfo, &DevInfo, SPDRP_DEVICEDESC, NULL, (PBYTE)pNew->Props.pszwDeviceName, dwSize, &dwSize); }
if (pCurrent) pCurrent->Next = pNew; else m_pHead = pNew;
pCurrent = pNew; } while (TRUE);
CoTaskMemFree(pIfTable); CoTaskMemFree(pAdapterInfo); SetupDiDestroyDeviceInfoList(hInfo);
m_pCurrent = m_pHead; return (m_pHead != NULL ? S_OK : S_FALSE);}
HRESULT CNetConnectionManager::Initialize(){ HRESULT hr = EnumerateINetConnections(); if (FAILED_UNEXPECTEDLY(hr)) { /* If something went wrong during the enumeration print an error don't enumerate anything */ m_pCurrent = m_pHead = NULL; return S_FALSE; } return S_OK;}
HRESULT WINAPI CNetConnectionManager_CreateInstance(REFIID riid, LPVOID * ppv){#if USE_CUSTOM_CONMGR return ShellObjectCreatorInit<CNetConnectionManager>(riid, ppv);#else return CoCreateInstance(CLSID_ConnectionManager, NULL, CLSCTX_ALL, riid, ppv);#endif}