- Start Implementing Network Connections ShellFolder

svn path=/trunk/; revision=35707
This commit is contained in:
Johannes Anderwald 2008-08-27 17:18:25 +00:00
parent ac962ebea4
commit f971e1392e
12 changed files with 1725 additions and 0 deletions

View file

@ -0,0 +1,125 @@
#include <precomp.h>
typedef struct
{
const IClassFactoryVtbl *lpVtbl;
LONG ref;
CLSID *rclsid;
LPFNCREATEINSTANCE lpfnCI;
const IID * riidInst;
} IClassFactoryImpl;
static
HRESULT
WINAPI
IClassFactory_fnQueryInterface(
LPCLASSFACTORY iface,
REFIID riid,
LPVOID *ppvObj)
{
IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
*ppvObj = NULL;
if(IsEqualIID(riid, &IID_IUnknown) || IsEqualIID(riid, &IID_IClassFactory))
{
*ppvObj = This;
InterlockedIncrement(&This->ref);
return S_OK;
}
return E_NOINTERFACE;
}
static
ULONG
WINAPI
IClassFactory_fnAddRef(
LPCLASSFACTORY iface)
{
IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
ULONG refCount = InterlockedIncrement(&This->ref);
return refCount;
}
static
ULONG
WINAPI
IClassFactory_fnRelease(
LPCLASSFACTORY iface)
{
IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
ULONG refCount = InterlockedDecrement(&This->ref);
if (!refCount)
{
HeapFree(GetProcessHeap(),0,This);
return 0;
}
return refCount;
}
static
HRESULT
WINAPI
IClassFactory_fnCreateInstance(
LPCLASSFACTORY iface,
LPUNKNOWN pUnkOuter,
REFIID riid,
LPVOID *ppvObject)
{
IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
*ppvObject = NULL;
if ( This->riidInst==NULL || IsEqualCLSID(riid, This->riidInst) || IsEqualCLSID(riid, &IID_IUnknown) )
{
return This->lpfnCI(pUnkOuter, riid, ppvObject);
}
return E_NOINTERFACE;
}
static
HRESULT
WINAPI IClassFactory_fnLockServer(
LPCLASSFACTORY iface,
BOOL fLock)
{
//IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
return E_NOTIMPL;
}
static const IClassFactoryVtbl dclfvt =
{
IClassFactory_fnQueryInterface,
IClassFactory_fnAddRef,
IClassFactory_fnRelease,
IClassFactory_fnCreateInstance,
IClassFactory_fnLockServer
};
IClassFactory *
IClassFactory_fnConstructor(
LPFNCREATEINSTANCE lpfnCI,
PLONG pcRefDll,
REFIID riidInst)
{
IClassFactoryImpl* lpclf;
lpclf = HeapAlloc(GetProcessHeap(),0,sizeof(IClassFactoryImpl));
lpclf->ref = 1;
lpclf->lpVtbl = &dclfvt;
lpclf->lpfnCI = lpfnCI;
if (pcRefDll)
InterlockedIncrement(pcRefDll);
lpclf->riidInst = riidInst;
return (LPCLASSFACTORY)lpclf;
}

View file

@ -0,0 +1,364 @@
#include <precomp.h>
WINE_DEFAULT_DEBUG_CHANNEL(shell);
typedef struct tagGUIDStruct
{
BYTE dummy; /* offset 01 is unknown */
GUID guid; /* offset 02 */
} GUIDStruct;
#define PT_GUID 0x1F
typedef struct tagPIDLDATA
{
BYTE type; /*00*/
union
{
struct tagGUIDStruct guid;
struct tagVALUEStruct value;
}u;
} PIDLDATA, *LPPIDLDATA;
typedef struct tagENUMLIST
{
struct tagENUMLIST *pNext;
LPITEMIDLIST pidl;
}ENUMLIST, *LPENUMLIST;
typedef struct
{
const IEnumIDListVtbl *lpVtbl;
LONG ref;
LPENUMLIST mpFirst;
LPENUMLIST mpLast;
LPENUMLIST mpCurrent;
} IEnumIDListImpl;
/**************************************************************************
* AddToEnumList()
*/
BOOL
AddToEnumList(
IEnumIDList * iface,
LPITEMIDLIST pidl)
{
LPENUMLIST pNew;
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
if (!iface || !pidl)
return FALSE;
pNew = (LPENUMLIST)SHAlloc(sizeof(ENUMLIST));
if(pNew)
{
pNew->pNext = NULL;
pNew->pidl = pidl;
if(!This->mpFirst)
{
This->mpFirst = pNew;
This->mpCurrent = pNew;
}
if(This->mpLast)
{
/*add the new item to the end of the list */
This->mpLast->pNext = pNew;
}
/*update the last item pointer */
This->mpLast = pNew;
return TRUE;
}
return FALSE;
}
static
HRESULT
WINAPI
IEnumIDList_fnQueryInterface(
IEnumIDList * iface,
REFIID riid,
LPVOID *ppvObj)
{
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
*ppvObj = NULL;
if (IsEqualIID(riid, &IID_IUnknown) || IsEqualIID(riid, &IID_IEnumIDList))
{
*ppvObj = This;
IEnumIDList_AddRef((IEnumIDList*)*ppvObj);
return S_OK;
}
return E_NOINTERFACE;
}
static
ULONG
WINAPI
IEnumIDList_fnAddRef(
IEnumIDList * iface)
{
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
ULONG refCount = InterlockedIncrement(&This->ref);
return refCount;
}
static
ULONG
WINAPI IEnumIDList_fnRelease(
IEnumIDList * iface)
{
LPENUMLIST pDelete;
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
ULONG refCount = InterlockedDecrement(&This->ref);
if (!refCount)
{
while(This->mpFirst)
{
pDelete = This->mpFirst;
This->mpFirst = pDelete->pNext;
SHFree(pDelete->pidl);
SHFree(pDelete);
}
HeapFree(GetProcessHeap(),0,This);
}
return refCount;
}
static
HRESULT
WINAPI
IEnumIDList_fnNext(
IEnumIDList * iface,
ULONG celt,
LPITEMIDLIST * rgelt,
ULONG *pceltFetched)
{
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
ULONG i;
HRESULT hr = S_OK;
LPITEMIDLIST temp;
if(pceltFetched)
*pceltFetched = 0;
*rgelt=0;
if(celt > 1 && !pceltFetched)
{
return E_INVALIDARG;
}
if(celt > 0 && !This->mpCurrent)
{
return S_FALSE;
}
for(i = 0; i < celt; i++)
{
if(!(This->mpCurrent))
break;
temp = ILClone(This->mpCurrent->pidl);
rgelt[i] = temp;
This->mpCurrent = This->mpCurrent->pNext;
}
if(pceltFetched)
{
*pceltFetched = i;
}
return hr;
}
static
HRESULT
WINAPI
IEnumIDList_fnSkip(
IEnumIDList * iface,ULONG celt)
{
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
DWORD dwIndex;
HRESULT hr = S_OK;
for(dwIndex = 0; dwIndex < celt; dwIndex++)
{
if(!This->mpCurrent)
{
hr = S_FALSE;
break;
}
This->mpCurrent = This->mpCurrent->pNext;
}
return hr;
}
static
HRESULT
WINAPI
IEnumIDList_fnReset(
IEnumIDList * iface)
{
IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
This->mpCurrent = This->mpFirst;
return S_OK;
}
static
HRESULT
WINAPI
IEnumIDList_fnClone(
IEnumIDList * iface,
LPENUMIDLIST * ppenum)
{
//IEnumIDListImpl *This = (IEnumIDListImpl *)iface;
return E_NOTIMPL;
}
static const IEnumIDListVtbl eidlvt =
{
IEnumIDList_fnQueryInterface,
IEnumIDList_fnAddRef,
IEnumIDList_fnRelease,
IEnumIDList_fnNext,
IEnumIDList_fnSkip,
IEnumIDList_fnReset,
IEnumIDList_fnClone,
};
IEnumIDList * IEnumIDList_Constructor(void)
{
IEnumIDListImpl *lpeidl = HeapAlloc(GetProcessHeap(),
HEAP_ZERO_MEMORY, sizeof(IEnumIDListImpl));
if (lpeidl)
{
lpeidl->ref = 1;
lpeidl->lpVtbl = &eidlvt;
}
return (IEnumIDList*)lpeidl;
}
LPPIDLDATA _ILGetDataPointer(LPCITEMIDLIST pidl)
{
if(pidl && pidl->mkid.cb != 0x00)
return (LPPIDLDATA) &(pidl->mkid.abID);
return NULL;
}
LPITEMIDLIST _ILAlloc(BYTE type, unsigned int size)
{
LPITEMIDLIST pidlOut = NULL;
pidlOut = SHAlloc(size + 5);
if(pidlOut)
{
LPPIDLDATA pData;
ZeroMemory(pidlOut, size + 5);
pidlOut->mkid.cb = size + 3;
pData = _ILGetDataPointer(pidlOut);
if (pData)
pData->type = type;
}
return pidlOut;
}
LPITEMIDLIST _ILCreateNetConnect()
{
LPITEMIDLIST pidlOut;
pidlOut = _ILAlloc(PT_GUID, sizeof(GUIDStruct));
if (pidlOut)
{
LPPIDLDATA pData = _ILGetDataPointer(pidlOut);
memcpy(&(pData->u.guid.guid), &CLSID_NetworkConnections, sizeof(GUID));
}
else
{
pidlOut = NULL;
}
return pidlOut;
}
IID* _ILGetGUIDPointer(LPCITEMIDLIST pidl)
{
LPPIDLDATA pdata =_ILGetDataPointer(pidl);
if (!pdata)
return NULL;
if (pdata->type != PT_GUID)
return NULL;
else
return &(pdata->u.guid.guid);
}
BOOL _ILIsNetConnect(LPCITEMIDLIST pidl)
{
REFIID iid = _ILGetGUIDPointer(pidl);
if (iid)
return IsEqualIID(iid, &CLSID_NetworkConnections);
return FALSE;
}
LPITEMIDLIST ILCreateNetConnectItem(MIB_IFROW * pRow, LPWSTR szName, LPWSTR szAdapterName)
{
PIDLDATA tmp;
LPITEMIDLIST pidl;
VALUEStruct * p;
int size = sizeof(struct tagVALUEStruct);
tmp.type = 0x00;
tmp.u.value.dummy = 0xFF;
tmp.u.value.dwOperStatus = pRow->dwOperStatus;
tmp.u.value.dwType = pRow->dwType;
tmp.u.value.dwNameLength = wcslen(szName) + 1;
size += (tmp.u.value.dwNameLength + wcslen(szAdapterName)) * sizeof(WCHAR);
pidl = (LPITEMIDLIST)SHAlloc(size + 4);
if (!pidl)
return pidl;
pidl->mkid.cb = size+2;
memcpy(pidl->mkid.abID, &tmp, 2+sizeof(struct tagVALUEStruct));
p = &((PIDLDATA*)pidl->mkid.abID)->u.value;
wcscpy(&p->szName[0], szName);
wcscpy(p->szName + tmp.u.value.dwNameLength, szAdapterName);
*(WORD*)((char*)pidl+(size+2)) = 0;
return pidl;
}
VALUEStruct * _ILGetValueStruct(LPCITEMIDLIST pidl)
{
LPPIDLDATA pdata = _ILGetDataPointer(pidl);
if (pdata && pdata->type==0x00)
return (VALUEStruct*)&(pdata->u.value);
return NULL;
}

View file

View file

@ -0,0 +1,144 @@
#include "precomp.h"
HINSTANCE netshell_hInstance;
const GUID CLSID_NetworkConnections = {0x7007ACC7, 0x3202, 0x11D1, {0xAA, 0xD2, 0x00, 0x80, 0x5F, 0xC1, 0x27, 0x0E}};
const GUID GUID_DEVCLASS_NET = {0x4d36e972, 0xe325, 0x11ce, {0xbf, 0xc1, 0x08, 0x00, 0x2b, 0xe1, 0x03, 0x18}};
static const WCHAR szNetConnectClass[] = L"CLSID\\{7007ACC7-3202-11D1-AAD2-00805FC1270E}";
static const WCHAR szNamespaceKey[] = L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\ControlPanel\\NameSpace\\{7007ACC7-3202-11D1-AAD2-00805FC1270E}";
static INTERFACE_TABLE InterfaceTable[] =
{
{
&CLSID_NetworkConnections,
ISF_NetConnect_Constructor
},
{
NULL,
NULL
}
};
BOOL
WINAPI
DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID fImpLoad)
{
switch (fdwReason)
{
case DLL_PROCESS_ATTACH:
netshell_hInstance = hinstDLL;
DisableThreadLibraryCalls(netshell_hInstance);
break;
default:
break;
}
return TRUE;
}
HRESULT
WINAPI
DllCanUnloadNow(void)
{
return S_FALSE;
}
STDAPI
DllRegisterServer(void)
{
HKEY hKey, hSubKey;
WCHAR szName[MAX_PATH] = {0};
WCHAR szNet[20];
UINT Length, Offset;
if (RegCreateKeyExW(HKEY_CLASSES_ROOT, szNetConnectClass, 0, NULL, 0, KEY_WRITE, NULL, &hKey, NULL) != ERROR_SUCCESS)
return SELFREG_E_CLASS;
if (LoadStringW(netshell_hInstance, IDS_NETWORKCONNECTION, szName, MAX_PATH))
{
szName[MAX_PATH-1] = L'\0';
RegSetValueW(hKey, NULL, REG_SZ, szName, (wcslen(szName)+1) * sizeof(WCHAR));
}
if (RegCreateKeyExW(HKEY_LOCAL_MACHINE, szNamespaceKey, 0, NULL, 0, KEY_WRITE, NULL, &hSubKey, NULL) == ERROR_SUCCESS)
{
RegSetValueW(hSubKey, NULL, REG_SZ, szName, (wcslen(szName)+1) * sizeof(WCHAR));
RegCloseKey(hSubKey);
}
Length = swprintf(szNet, L",-%u", IDS_NETWORKCONNECTION);
Offset = GetModuleFileNameW(netshell_hInstance, &szName[1], MAX_PATH);
if (Offset + Length + 2 < MAX_PATH)
{
/* set localized name */
szName[0] = L'@';
wcscpy(&szName[Offset+1], szNet);
RegSetValueExW(hKey, L"LocalizedString", 0, REG_SZ, (const LPBYTE)szName, (wcslen(szName)+1) * sizeof(WCHAR));
}
szName[Offset+1] = L'\0';
/* store default icon */
if (RegCreateKeyExW(hKey, L"DefaultIcon", 0, NULL, 0, KEY_WRITE, NULL, &hSubKey, NULL) == ERROR_SUCCESS)
{
RegSetValueW(hSubKey, NULL, REG_SZ, &szName[1], (Offset+1) * sizeof(WCHAR));
RegCloseKey(hSubKey);
}
if (RegCreateKeyExW(hKey, L"InProcServer32", 0, NULL, 0, KEY_WRITE, NULL, &hSubKey, NULL) == ERROR_SUCCESS)
{
RegSetValueW(hSubKey, NULL, REG_SZ, &szName[1], (Offset+1) * sizeof(WCHAR));
RegCloseKey(hSubKey);
}
if (RegCreateKeyExW(hKey, L"ShellFolder", 0, NULL, 0, KEY_WRITE, NULL, &hSubKey, NULL) == ERROR_SUCCESS)
{
DWORD dwAttributes = SFGAO_FOLDER;
RegSetValueExW(hSubKey, L"Attributes",0, REG_BINARY, (const LPBYTE)&dwAttributes, sizeof(DWORD));
}
return S_OK;
}
STDAPI
DllUnregisterServer(void)
{
SHDeleteKeyW(HKEY_CLASSES_ROOT, szNetConnectClass);
SHDeleteKeyW(HKEY_LOCAL_MACHINE, szNamespaceKey);
return S_OK;
}
STDAPI
DllGetClassObject(
REFCLSID rclsid,
REFIID riid,
LPVOID* ppv
)
{
UINT i;
HRESULT hres = E_OUTOFMEMORY;
IClassFactory * pcf = NULL;
if (!ppv)
return E_INVALIDARG;
*ppv = NULL;
for (i = 0; InterfaceTable[i].riid; i++)
{
if (IsEqualIID(InterfaceTable[i].riid, rclsid))
{
pcf = IClassFactory_fnConstructor(InterfaceTable[i].lpfnCI, NULL, NULL);
break;
}
}
if (!pcf)
{
return CLASS_E_CLASSNOTAVAILABLE;
}
hres = IClassFactory_QueryInterface(pcf, riid, ppv);
IClassFactory_Release(pcf);
return hres;
}

View file

@ -0,0 +1,27 @@
<module name="netshell" type="win32dll" baseaddress="${BASEADDRESS_SHELL32}" installbase="system32" installname="netshell.dll">
<autoregister infsection="OleControlDlls" type="Both" />
<importlibrary definition="netshell.spec.def" />
<include base="netshell">.</include>
<define name="_WIN32_IE">0x600</define>
<define name="_WIN32_WINNT">0x600</define>
<define name="WINVER">0x600</define>
<define name="_NETSHELL_" />
<library>shlwapi</library>
<library>shell32</library>
<library>version</library>
<library>iphlpapi</library>
<library>kernel32</library>
<library>wine</library>
<library>ole32</library>
<library>user32</library>
<library>uuid</library>
<library>advapi32</library>
<library>setupapi</library>
<pch>precomp.h</pch>
<file>netshell.c</file>
<file>shfldr_netconnect.c</file>
<file>enumlist.c</file>
<file>netshell.rc</file>
<file>classfactory.c</file>
<file>netshell.spec</file>
</module>

View file

@ -0,0 +1,10 @@
#include <windows.h>
#include "shlobj.h"
#include "resource.h"
LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL
IDI_SHELL_NETWORK_FOLDER ICON "res/netshell.ico"
#include "lang/de-DE.rc"
#include "lang/en-US.rc"

View file

@ -0,0 +1,34 @@
1 stub DoInitialCleanup
2 stdcall DllCanUnloadNow()
3 stdcall DllGetClassObject(ptr ptr ptr)
4 stdcall DllRegisterServer()
5 stdcall DllUnregisterServer()
6 stub HrCreateDesktopIcon
7 stub HrGetAnswerFileParametersForNetCard
8 stub HrGetExtendedStatusFromNCS
9 stub HrGetIconFromMediaType
10 stub HrGetInstanceGuidOfPreNT5NetCardInstance
11 stub HrGetNetConExtendedStatusFromGuid
12 stub HrGetNetConExtendedStatusFromINetConnection
13 stub HrGetStatusStringFromNetConExtendedStatus
14 stub HrIsIpStateCheckingEnabled
15 stub HrLaunchConnection
16 stub HrLaunchConnectionEx
17 stub HrLaunchNetworkOptionalComponents
18 stub HrOemUpgrade
19 stub HrRenameConnection
20 stub HrRunWizard
21 stub InvokeDunFile
22 stub NcFreeNetconProperties
23 stub NcIsValidConnectionName
24 stub NetSetupAddRasConnection
25 stub NetSetupFinishInstall
26 stub NetSetupInstallSoftware
27 stub NetSetupPrepareSysPrep
28 stub NetSetupRequestWizardPages
29 stub NetSetupSetProgressCallback
30 stub NormalizeExtendedStatus
31 stub RaiseSupportDialog
32 stub RepairConnection
33 stub StartNCW

View file

@ -0,0 +1,82 @@
#ifndef _PRECOMP_H__
#define _PRECOMP_H__
#include "config.h"
#include <stdarg.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <assert.h>
#include <ctype.h>
#include <malloc.h>
#define COBJMACROS
#define NONAMELESSUNION
#define NONAMELESSSTRUCT
#include <windows.h>
#include <shlguid.h>
#include <shlwapi.h>
#include <shlobj.h>
#include <shldisp.h>
#include <cpl.h>
#include <objbase.h>
#include <ole2.h>
#include <ocidl.h>
#include <shobjidl.h>
#include <shellapi.h>
#include <olectl.h>
#include <iphlpapi.h>
#include <shtypes.h>
#include <setupapi.h>
#include <devguid.h>
#include "wine/debug.h"
#include "wine/unicode.h"
#include "resource.h"
typedef struct {
int colnameid;
int pcsFlags;
int fmt;
int cxChar;
} shvheader;
typedef HRESULT (CALLBACK *LPFNCREATEINSTANCE)(IUnknown* pUnkOuter, REFIID riid, LPVOID* ppvObject);
typedef struct {
REFIID riid;
LPFNCREATEINSTANCE lpfnCI;
} INTERFACE_TABLE;
typedef struct tagVALUEStruct
{
BYTE dummy;
DWORD dwType;
DWORD dwOperStatus;
DWORD dwNameLength;
WCHAR szName[1];
}VALUEStruct;
/* globals */
extern HINSTANCE netshell_hInstance;
extern const GUID CLSID_NetworkConnections;
extern const GUID GUID_DEVCLASS_NET;
/* shfldr_netconnect.c */
HRESULT WINAPI ISF_NetConnect_Constructor (IUnknown * pUnkOuter, REFIID riid, LPVOID * ppv);
/* enumlist.c */
IEnumIDList * IEnumIDList_Constructor(void);
LPITEMIDLIST _ILCreateNetConnect();
LPITEMIDLIST ILCreateNetConnectItem(MIB_IFROW * pRow, LPWSTR szName, LPWSTR szAdapterName);
BOOL _ILIsNetConnect (LPCITEMIDLIST pidl);
BOOL AddToEnumList(IEnumIDList * iface, LPITEMIDLIST pidl);
VALUEStruct * _ILGetValueStruct(LPCITEMIDLIST pidl);
/* classfactory.c */
IClassFactory * IClassFactory_fnConstructor(LPFNCREATEINSTANCE lpfnCI, PLONG pcRefDll, REFIID riidInst);
#endif

Binary file not shown.

After

Width:  |  Height:  |  Size: 39 KiB

View file

@ -0,0 +1,31 @@
/* icons */
#define IDI_SHELL_NETWORK_FOLDER 100
/* dialogs */
/* dialog controls */
/* resource constants */
#define IDS_NETWORKCONNECTION 10000
#define IDS_SHV_COLUMN_NAME 10001
#define IDS_SHV_COLUMN_TYPE 10002
#define IDS_SHV_COLUMN_STATE 10003
#define IDS_SHV_COLUMN_DEVNAME 10004
#define IDS_SHV_COLUMN_PHONE 10005
#define IDS_SHV_COLUMN_OWNER 10006
#define IDS_TYPE_ETHERNET 10007
#define IDS_STATUS_NON_OPERATIONAL 10008
#define IDS_STATUS_UNREACHABLE 10009
#define IDS_STATUS_DISCONNECTED 10010
#define IDS_STATUS_CONNECTING 10011
#define IDS_STATUS_CONNECTED 10012
#define IDS_STATUS_OPERATIONAL 10013

View file

@ -0,0 +1,905 @@
/*
* Network Connections Shell Folder
*
* Copyright 2008 Johannes Anderwald <janderwald@reactos.org>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include <precomp.h>
WINE_DEFAULT_DEBUG_CHANNEL (shell);
/***********************************************************************
* IShellFolder implementation
*/
typedef struct {
const IShellFolder2Vtbl *lpVtbl;
LONG ref;
const IContextMenu2Vtbl *lpVtblContextMenu;
const IPersistFolder2Vtbl *lpVtblPersistFolder2;
/* both paths are parsible from the desktop */
LPITEMIDLIST pidlRoot; /* absolute pidl */
LPCITEMIDLIST apidl; /* currently focused font item */
} IGenericSFImpl, *LPIGenericSFImpl;
static const shvheader NetConnectSFHeader[] = {
{IDS_SHV_COLUMN_NAME, SHCOLSTATE_TYPE_STR | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 20},
{IDS_SHV_COLUMN_TYPE, SHCOLSTATE_TYPE_STR | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 8},
{IDS_SHV_COLUMN_STATE, SHCOLSTATE_TYPE_STR | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 10},
{IDS_SHV_COLUMN_DEVNAME, SHCOLSTATE_TYPE_DATE | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 12},
{IDS_SHV_COLUMN_PHONE, SHCOLSTATE_TYPE_STR | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 10},
{IDS_SHV_COLUMN_OWNER, SHCOLSTATE_TYPE_STR | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 5}
};
#define NETCONNECTSHELLVIEWCOLUMNS 6
#define COLUMN_NAME 0
#define COLUMN_TYPE 1
#define COLUMN_STATUS 2
#define COLUMN_DEVNAME 3
#define COLUMN_PHONE 4
#define COLUMN_OWNER 5
static LPIGenericSFImpl __inline impl_from_IContextMenu2(IContextMenu2 *iface)
{
return (LPIGenericSFImpl)((char *)iface - FIELD_OFFSET(IGenericSFImpl, lpVtblContextMenu));
}
static LPIGenericSFImpl __inline impl_from_IPersistFolder2(IPersistFolder2 *iface)
{
return (LPIGenericSFImpl)((char *)iface - FIELD_OFFSET(IGenericSFImpl, lpVtblPersistFolder2));
}
/**************************************************************************
* ISF_NetConnect_fnQueryInterface
*
* NOTE
* supports not IPersist/IPersistFolder
*/
static HRESULT WINAPI ISF_NetConnect_fnQueryInterface (IShellFolder2 *iface, REFIID riid, LPVOID *ppvObj)
{
IGenericSFImpl *This = (IGenericSFImpl *)iface;
*ppvObj = NULL;
if (IsEqualIID (riid, &IID_IUnknown) ||
IsEqualIID (riid, &IID_IShellFolder) ||
IsEqualIID (riid, &IID_IShellFolder2))
{
*ppvObj = This;
}
else if (IsEqualIID (riid, &IID_IPersistFolder) ||
IsEqualIID (riid, &IID_IPersistFolder2))
{
*ppvObj = (LPVOID *)&This->lpVtblPersistFolder2;
}
if (*ppvObj)
{
IUnknown_AddRef ((IUnknown *) (*ppvObj));
return S_OK;
}
return E_NOINTERFACE;
}
static ULONG WINAPI ISF_NetConnect_fnAddRef (IShellFolder2 * iface)
{
IGenericSFImpl *This = (IGenericSFImpl *)iface;
ULONG refCount = InterlockedIncrement(&This->ref);
return refCount;
}
static ULONG WINAPI ISF_NetConnect_fnRelease (IShellFolder2 * iface)
{
IGenericSFImpl *This = (IGenericSFImpl *)iface;
ULONG refCount = InterlockedDecrement(&This->ref);
if (!refCount)
{
SHFree (This->pidlRoot);
HeapFree (GetProcessHeap(), 0, This);
}
return refCount;
}
/**************************************************************************
* ISF_NetConnect_fnParseDisplayName
*/
static HRESULT WINAPI ISF_NetConnect_fnParseDisplayName (IShellFolder2 * iface,
HWND hwndOwner, LPBC pbcReserved, LPOLESTR lpszDisplayName,
DWORD * pchEaten, LPITEMIDLIST * ppidl, DWORD * pdwAttributes)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
HRESULT hr = E_UNEXPECTED;
*ppidl = 0;
if (pchEaten)
*pchEaten = 0; /* strange but like the original */
return hr;
}
/**************************************************************************
* CreateNetConnectEnumListss()
*/
static BOOL CreateNetConnectEnumList(IEnumIDList *list, DWORD dwFlags)
{
DWORD dwSize, dwResult, dwIndex;
MIB_IFTABLE *pIfTable;
MIB_IFROW IfEntry;
IP_ADAPTER_INFO * pAdapterInfo, *pCurrentAdapter;
HDEVINFO hInfo;
SP_DEVINFO_DATA DevInfo;
HKEY hSubKey;
WCHAR szNetCfg[50];
WCHAR szAdapterNetCfg[50];
LPITEMIDLIST pidl;
WCHAR szDetail[200] = L"SYSTEM\\CurrentControlSet\\Control\\Class\\";
WCHAR szName[130] = L"SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\";
/* get the IfTable */
dwSize = 0;
if (GetIfTable(NULL, &dwSize, TRUE) != ERROR_INSUFFICIENT_BUFFER)
return FALSE;
pIfTable = (PMIB_IFTABLE)HeapAlloc(GetProcessHeap(), 0, dwSize);
if (!pIfTable)
return FALSE;
dwResult = GetIfTable(pIfTable, &dwSize, TRUE);
if (dwResult != NO_ERROR)
{
HeapFree(GetProcessHeap(), 0, pIfTable);
return FALSE;
}
dwSize = 0;
dwResult = GetAdaptersInfo(NULL, &dwSize);
if (dwResult!= ERROR_BUFFER_OVERFLOW)
{
HeapFree(GetProcessHeap(), 0, pIfTable);
return FALSE;
}
pAdapterInfo = (PIP_ADAPTER_INFO)HeapAlloc(GetProcessHeap(), 0, dwSize);
if (!pAdapterInfo)
{
HeapFree(GetProcessHeap(), 0, pIfTable);
return FALSE;
}
if (GetAdaptersInfo(pAdapterInfo, &dwSize) != NO_ERROR)
{
HeapFree(GetProcessHeap(), 0, pIfTable);
HeapFree(GetProcessHeap(), 0, pAdapterInfo);
return FALSE;
}
hInfo = SetupDiGetClassDevs(&GUID_DEVCLASS_NET, NULL, NULL, DIGCF_PRESENT );
if (!hInfo)
{
HeapFree(GetProcessHeap(), 0, pIfTable);
HeapFree(GetProcessHeap(), 0, pAdapterInfo);
return FALSE;
}
dwIndex = 0;
do
{
ZeroMemory(&DevInfo, sizeof(SP_DEVINFO_DATA));
DevInfo.cbSize = sizeof(DevInfo);
if (SetupDiEnumDeviceInfo(hInfo, dwIndex++, &DevInfo))
{
if (SetupDiGetDeviceRegistryPropertyW(hInfo, &DevInfo, SPDRP_DRIVER, NULL, (LPBYTE)&szDetail[39], sizeof(szDetail)/sizeof(WCHAR) - 40, &dwSize))
{
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szDetail, 0, KEY_READ, &hSubKey) == ERROR_SUCCESS)
{
dwSize = sizeof(szNetCfg);
dwResult = RegQueryValueExW(hSubKey, L"NetCfgInstanceId", NULL, NULL, (LPBYTE)szNetCfg, &dwSize);
if (dwResult == ERROR_SUCCESS)
{
pCurrentAdapter = pAdapterInfo;
while(pCurrentAdapter)
{
szAdapterNetCfg[0] = L'\0';
if (MultiByteToWideChar(CP_ACP, 0, pCurrentAdapter->AdapterName, -1, szAdapterNetCfg, sizeof(szAdapterNetCfg)/sizeof(szAdapterNetCfg[0])))
{
szAdapterNetCfg[(sizeof(szAdapterNetCfg)/sizeof(WCHAR))-1] = L'\0';
}
if (!wcsicmp(szAdapterNetCfg, szNetCfg))
{
ZeroMemory(&IfEntry, sizeof(IfEntry));
IfEntry.dwIndex = pCurrentAdapter->Index;
dwResult = GetIfEntry(&IfEntry);
if (dwResult == NO_ERROR)
{
if (IfEntry.dwType == IF_TYPE_ETHERNET_CSMACD || IfEntry.dwType == IF_TYPE_IEEE80211)
{
wcscpy(&szName[80], szNetCfg);
wcscpy(&szName[118], L"\\Connection");
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, szName, 0, KEY_READ, &hSubKey) == ERROR_SUCCESS)
{
dwSize = sizeof(szAdapterNetCfg);
if (RegQueryValueExW(hSubKey, L"Name", NULL, NULL, (LPBYTE)szAdapterNetCfg, &dwSize) != ERROR_SUCCESS)
{
if (!SetupDiGetDeviceRegistryPropertyW(hInfo, &DevInfo, SPDRP_FRIENDLYNAME, NULL, (PBYTE)szAdapterNetCfg, sizeof(szAdapterNetCfg)/sizeof(WCHAR), &dwSize))
{
szDetail[0] = 0;
}
}
RegCloseKey(hSubKey);
}
szNetCfg[0] = 0;
SetupDiGetDeviceRegistryPropertyW(hInfo, &DevInfo, SPDRP_DEVICEDESC, NULL, (PBYTE)szNetCfg, sizeof(szNetCfg)/sizeof(WCHAR), &dwSize);
pidl = ILCreateNetConnectItem(&IfEntry, szAdapterNetCfg, szNetCfg);
if (pidl)
{
AddToEnumList(list, pidl);
}
}
}
break;
}
pCurrentAdapter = pCurrentAdapter->Next;
}
}
}
}
}else if (GetLastError() == ERROR_NO_MORE_ITEMS)
{
break;
}
}while(TRUE);
HeapFree(GetProcessHeap(), 0, pAdapterInfo);
HeapFree(GetProcessHeap(), 0, pIfTable);
SetupDiDestroyDeviceInfoList(hInfo);
return FALSE;
}
/**************************************************************************
* ISF_NetConnect_fnEnumObjects
*/
static HRESULT WINAPI ISF_NetConnect_fnEnumObjects (IShellFolder2 * iface,
HWND hwndOwner, DWORD dwFlags, LPENUMIDLIST * ppEnumIDList)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
*ppEnumIDList = IEnumIDList_Constructor();
if(*ppEnumIDList)
CreateNetConnectEnumList(*ppEnumIDList, dwFlags);
return (*ppEnumIDList) ? S_OK : E_OUTOFMEMORY;
}
/**************************************************************************
* ISF_NetConnect_fnBindToObject
*/
static HRESULT WINAPI ISF_NetConnect_fnBindToObject (IShellFolder2 * iface,
LPCITEMIDLIST pidl, LPBC pbcReserved, REFIID riid, LPVOID * ppvOut)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
/**************************************************************************
* ISF_NetConnect_fnBindToStorage
*/
static HRESULT WINAPI ISF_NetConnect_fnBindToStorage (IShellFolder2 * iface,
LPCITEMIDLIST pidl, LPBC pbcReserved, REFIID riid, LPVOID * ppvOut)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
*ppvOut = NULL;
return E_NOTIMPL;
}
/**************************************************************************
* ISF_NetConnect_fnCompareIDs
*/
static HRESULT WINAPI ISF_NetConnect_fnCompareIDs (IShellFolder2 * iface,
LPARAM lParam, LPCITEMIDLIST pidl1, LPCITEMIDLIST pidl2)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
/**************************************************************************
* ISF_NetConnect_fnCreateViewObject
*/
static HRESULT WINAPI ISF_NetConnect_fnCreateViewObject (IShellFolder2 * iface,
HWND hwndOwner, REFIID riid, LPVOID * ppvOut)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
IShellView* pShellView;
CSFV cvf;
HRESULT hr = E_NOINTERFACE;
if (!ppvOut)
return hr;
*ppvOut = NULL;
if (IsEqualIID (riid, &IID_IShellView))
{
ZeroMemory(&cvf, sizeof(cvf));
cvf.cbSize = sizeof(cvf);
cvf.pshf = (IShellFolder*)iface;
hr = SHCreateShellFolderViewEx(&cvf, &pShellView);
if (SUCCEEDED(hr))
{
hr = IShellView_QueryInterface (pShellView, riid, ppvOut);
IShellView_Release (pShellView);
}
}
return hr;
}
/**************************************************************************
* ISF_NetConnect_fnGetAttributesOf
*/
static HRESULT WINAPI ISF_NetConnect_fnGetAttributesOf (IShellFolder2 * iface,
UINT cidl, LPCITEMIDLIST * apidl, DWORD * rgfInOut)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
HRESULT hr = S_OK;
static const DWORD dwNetConnectAttributes = SFGAO_STORAGE | SFGAO_HASPROPSHEET | SFGAO_STORAGEANCESTOR |
SFGAO_FILESYSANCESTOR | SFGAO_FOLDER | SFGAO_FILESYSTEM | SFGAO_HASSUBFOLDER | SFGAO_CANRENAME | SFGAO_CANDELETE;
if (!rgfInOut)
return E_INVALIDARG;
if (cidl && !apidl)
return E_INVALIDARG;
if (*rgfInOut == 0)
*rgfInOut = ~0;
if(cidl == 0)
*rgfInOut = dwNetConnectAttributes;
/* make sure SFGAO_VALIDATE is cleared, some apps depend on that */
*rgfInOut &= ~SFGAO_VALIDATE;
return hr;
}
/**************************************************************************
* ISF_NetConnect_fnGetUIObjectOf
*
* PARAMETERS
* hwndOwner [in] Parent window for any output
* cidl [in] array size
* apidl [in] simple pidl array
* riid [in] Requested Interface
* prgfInOut [ ] reserved
* ppvObject [out] Resulting Interface
*
*/
static HRESULT WINAPI ISF_NetConnect_fnGetUIObjectOf (IShellFolder2 * iface,
HWND hwndOwner, UINT cidl, LPCITEMIDLIST * apidl, REFIID riid,
UINT * prgfInOut, LPVOID * ppvOut)
{
IGenericSFImpl *This = (IGenericSFImpl *)iface;
IUnknown *pObj = NULL;
HRESULT hr = E_INVALIDARG;
if (!ppvOut)
return hr;
*ppvOut = NULL;
if (IsEqualIID (riid, &IID_IContextMenu) && (cidl >= 1))
{
pObj = (IUnknown*)(&This->lpVtblContextMenu);
This->apidl = apidl[0];
IUnknown_AddRef(pObj);
hr = S_OK;
}
else
hr = E_NOINTERFACE;
if (SUCCEEDED(hr) && !pObj)
hr = E_OUTOFMEMORY;
*ppvOut = pObj;
return hr;
}
/**************************************************************************
* ISF_NetConnect_fnGetDisplayNameOf
*
*/
static HRESULT WINAPI ISF_NetConnect_fnGetDisplayNameOf (IShellFolder2 * iface,
LPCITEMIDLIST pidl, DWORD dwFlags, LPSTRRET strRet)
{
LPWSTR pszName;
HRESULT hr = E_FAIL;
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
if (!strRet)
return E_INVALIDARG;
pszName = CoTaskMemAlloc(MAX_PATH * sizeof(WCHAR));
if (!pszName)
return E_OUTOFMEMORY;
if (_ILIsNetConnect (pidl))
{
if (LoadStringW(netshell_hInstance, IDS_NETWORKCONNECTION, pszName, MAX_PATH))
{
pszName[MAX_PATH-1] = L'\0';
hr = S_OK;
}
}
else
{
VALUEStruct * val = _ILGetValueStruct(pidl);
if (val)
{
wcscpy(pszName, val->szName);
hr = S_OK;
}
}
if (SUCCEEDED(hr))
{
strRet->uType = STRRET_WSTR;
strRet->u.pOleStr = pszName;
}
else
{
CoTaskMemFree(pszName);
}
return hr;
}
/**************************************************************************
* ISF_NetConnect_fnSetNameOf
* Changes the name of a file object or subfolder, possibly changing its item
* identifier in the process.
*
* PARAMETERS
* hwndOwner [in] Owner window for output
* pidl [in] simple pidl of item to change
* lpszName [in] the items new display name
* dwFlags [in] SHGNO formatting flags
* ppidlOut [out] simple pidl returned
*/
static HRESULT WINAPI ISF_NetConnect_fnSetNameOf (IShellFolder2 * iface,
HWND hwndOwner, LPCITEMIDLIST pidl, /*simple pidl */
LPCOLESTR lpName, DWORD dwFlags, LPITEMIDLIST * pPidlOut)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
static HRESULT WINAPI ISF_NetConnect_fnGetDefaultSearchGUID (
IShellFolder2 * iface, GUID * pguid)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
static HRESULT WINAPI ISF_NetConnect_fnEnumSearches (IShellFolder2 * iface,
IEnumExtraSearch ** ppenum)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
static HRESULT WINAPI ISF_NetConnect_fnGetDefaultColumn (IShellFolder2 * iface,
DWORD dwRes, ULONG * pSort, ULONG * pDisplay)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
if (pSort)
*pSort = 0;
if (pDisplay)
*pDisplay = 0;
return S_OK;
}
static HRESULT WINAPI ISF_NetConnect_fnGetDefaultColumnState (
IShellFolder2 * iface, UINT iColumn, DWORD * pcsFlags)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
if (!pcsFlags || iColumn >= NETCONNECTSHELLVIEWCOLUMNS)
return E_INVALIDARG;
*pcsFlags = NetConnectSFHeader[iColumn].pcsFlags;
return S_OK;
}
static HRESULT WINAPI ISF_NetConnect_fnGetDetailsEx (IShellFolder2 * iface,
LPCITEMIDLIST pidl, const SHCOLUMNID * pscid, VARIANT * pv)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
static HRESULT WINAPI ISF_NetConnect_fnGetDetailsOf (IShellFolder2 * iface,
LPCITEMIDLIST pidl, UINT iColumn, SHELLDETAILS * psd)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
WCHAR buffer[MAX_PATH] = {0};
HRESULT hr = E_FAIL;
VALUEStruct * val;
if (iColumn >= NETCONNECTSHELLVIEWCOLUMNS)
return E_FAIL;
psd->fmt = NetConnectSFHeader[iColumn].fmt;
psd->cxChar = NetConnectSFHeader[iColumn].cxChar;
if (pidl == NULL)
{
psd->str.uType = STRRET_WSTR;
if (LoadStringW(netshell_hInstance, NetConnectSFHeader[iColumn].colnameid, buffer, MAX_PATH))
hr = SHStrDupW(buffer, &psd->str.u.pOleStr);
return hr;
}
if (iColumn == COLUMN_NAME)
{
psd->str.uType = STRRET_WSTR;
return IShellFolder2_GetDisplayNameOf(iface, pidl, SHGDN_NORMAL, &psd->str);
}
val = _ILGetValueStruct(pidl);
if (!val)
return E_FAIL;
switch(iColumn)
{
case COLUMN_TYPE:
if (val->dwType == IF_TYPE_ETHERNET_CSMACD || val->dwType == IF_TYPE_IEEE80211)
{
if (LoadStringW(netshell_hInstance, IDS_TYPE_ETHERNET, buffer, MAX_PATH))
{
psd->str.uType = STRRET_WSTR;
hr = SHStrDupW(buffer, &psd->str.u.pOleStr);
}
}
break;
case COLUMN_STATUS:
buffer[0] = L'\0';
if (val->dwOperStatus == MIB_IF_OPER_STATUS_NON_OPERATIONAL)
LoadStringW(netshell_hInstance, IDS_STATUS_NON_OPERATIONAL, buffer, MAX_PATH);
else if (val->dwOperStatus == MIB_IF_OPER_STATUS_UNREACHABLE)
LoadStringW(netshell_hInstance, IDS_STATUS_UNREACHABLE, buffer, MAX_PATH);
else if (val->dwOperStatus == MIB_IF_OPER_STATUS_DISCONNECTED)
LoadStringW(netshell_hInstance, IDS_STATUS_DISCONNECTED, buffer, MAX_PATH);
else if (val->dwOperStatus == MIB_IF_OPER_STATUS_CONNECTING)
LoadStringW(netshell_hInstance, IDS_STATUS_CONNECTING, buffer, MAX_PATH);
else if (val->dwOperStatus == MIB_IF_OPER_STATUS_CONNECTED)
LoadStringW(netshell_hInstance, IDS_STATUS_CONNECTED, buffer, MAX_PATH);
else if (val->dwOperStatus == MIB_IF_OPER_STATUS_OPERATIONAL)
LoadStringW(netshell_hInstance, IDS_STATUS_OPERATIONAL, buffer, MAX_PATH);
if (buffer[0])
{
buffer[MAX_PATH-1] = L'\0';
psd->str.uType = STRRET_WSTR;
hr = SHStrDupW(buffer, &psd->str.u.pOleStr);
}
break;
case COLUMN_DEVNAME:
wcscpy(buffer, val->szName + val->dwNameLength);
buffer[MAX_PATH-1] = L'\0';
psd->str.uType = STRRET_WSTR;
hr = SHStrDupW(buffer, &psd->str.u.pOleStr);
break;
case COLUMN_PHONE:
case COLUMN_OWNER:
psd->str.u.cStr[0] = '\0';
psd->str.uType = STRRET_CSTR;
break;
}
return hr;
}
static HRESULT WINAPI ISF_NetConnect_fnMapColumnToSCID (IShellFolder2 * iface,
UINT column, SHCOLUMNID * pscid)
{
//IGenericSFImpl *This = (IGenericSFImpl *)iface;
return E_NOTIMPL;
}
static const IShellFolder2Vtbl vt_ShellFolder2 = {
ISF_NetConnect_fnQueryInterface,
ISF_NetConnect_fnAddRef,
ISF_NetConnect_fnRelease,
ISF_NetConnect_fnParseDisplayName,
ISF_NetConnect_fnEnumObjects,
ISF_NetConnect_fnBindToObject,
ISF_NetConnect_fnBindToStorage,
ISF_NetConnect_fnCompareIDs,
ISF_NetConnect_fnCreateViewObject,
ISF_NetConnect_fnGetAttributesOf,
ISF_NetConnect_fnGetUIObjectOf,
ISF_NetConnect_fnGetDisplayNameOf,
ISF_NetConnect_fnSetNameOf,
/* ShellFolder2 */
ISF_NetConnect_fnGetDefaultSearchGUID,
ISF_NetConnect_fnEnumSearches,
ISF_NetConnect_fnGetDefaultColumn,
ISF_NetConnect_fnGetDefaultColumnState,
ISF_NetConnect_fnGetDetailsEx,
ISF_NetConnect_fnGetDetailsOf,
ISF_NetConnect_fnMapColumnToSCID
};
/**************************************************************************
* IContextMenu2 Implementation
*/
/************************************************************************
* ISF_NetConnect_IContextMenu_QueryInterface
*/
static HRESULT WINAPI ISF_NetConnect_IContextMenu2_QueryInterface(IContextMenu2 * iface, REFIID iid, LPVOID * ppvObject)
{
IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return IShellFolder2_QueryInterface((IShellFolder2*)This, iid, ppvObject);
}
/************************************************************************
* ISF_NetConnect_IContextMenu_AddRef
*/
static ULONG WINAPI ISF_NetConnect_IContextMenu2_AddRef(IContextMenu2 * iface)
{
IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return IShellFolder2_AddRef((IShellFolder2*)This);
}
/************************************************************************
* ISF_NetConnect_IContextMenu_Release
*/
static ULONG WINAPI ISF_NetConnect_IContextMenu2_Release(IContextMenu2 * iface)
{
IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return IShellFolder2_Release((IShellFolder2*)This);
}
/**************************************************************************
* ISF_NetConnect_IContextMenu_QueryContextMenu()
*/
static HRESULT WINAPI ISF_NetConnect_IContextMenu2_QueryContextMenu(
IContextMenu2 *iface,
HMENU hMenu,
UINT indexMenu,
UINT idCmdFirst,
UINT idCmdLast,
UINT uFlags)
{
int Count = 1;
//IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, Count);
}
/**************************************************************************
* ISF_NetConnect_IContextMenu_InvokeCommand()
*/
static HRESULT WINAPI ISF_NetConnect_IContextMenu2_InvokeCommand(
IContextMenu2 *iface,
LPCMINVOKECOMMANDINFO lpcmi)
{
//IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return S_OK;
}
/**************************************************************************
* ISF_NetConnect_IContextMenu_GetCommandString()
*
*/
static HRESULT WINAPI ISF_NetConnect_IContextMenu2_GetCommandString(
IContextMenu2 *iface,
UINT_PTR idCommand,
UINT uFlags,
UINT* lpReserved,
LPSTR lpszName,
UINT uMaxNameLen)
{
//IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return E_FAIL;
}
/**************************************************************************
* ISF_NetConnect_IContextMenu_HandleMenuMsg()
*/
static HRESULT WINAPI ISF_NetConnect_IContextMenu2_HandleMenuMsg(
IContextMenu2 *iface,
UINT uMsg,
WPARAM wParam,
LPARAM lParam)
{
//IGenericSFImpl * This = impl_from_IContextMenu2(iface);
return E_NOTIMPL;
}
static const IContextMenu2Vtbl vt_ContextMenu2 =
{
ISF_NetConnect_IContextMenu2_QueryInterface,
ISF_NetConnect_IContextMenu2_AddRef,
ISF_NetConnect_IContextMenu2_Release,
ISF_NetConnect_IContextMenu2_QueryContextMenu,
ISF_NetConnect_IContextMenu2_InvokeCommand,
ISF_NetConnect_IContextMenu2_GetCommandString,
ISF_NetConnect_IContextMenu2_HandleMenuMsg
};
/************************************************************************
* ISF_NetConnect_PersistFolder2_QueryInterface
*/
static HRESULT WINAPI ISF_NetConnect_PersistFolder2_QueryInterface (IPersistFolder2 * iface,
REFIID iid, LPVOID * ppvObj)
{
IGenericSFImpl * This = impl_from_IPersistFolder2(iface);
return IShellFolder2_QueryInterface ((IShellFolder2*)This, iid, ppvObj);
}
/************************************************************************
* ISF_NetConnect_PersistFolder2_AddRef
*/
static ULONG WINAPI ISF_NetConnect_PersistFolder2_AddRef (IPersistFolder2 * iface)
{
IGenericSFImpl * This = impl_from_IPersistFolder2(iface);
return IShellFolder2_AddRef((IShellFolder2*)This);
}
/************************************************************************
* ISF_NetConnect_PersistFolder2_Release
*/
static ULONG WINAPI ISF_NetConnect_PersistFolder2_Release (IPersistFolder2 * iface)
{
IGenericSFImpl * This = impl_from_IPersistFolder2(iface);
return IShellFolder2_Release((IShellFolder2*)This);
}
/************************************************************************
* ISF_NetConnect_PersistFolder2_GetClassID
*/
static HRESULT WINAPI ISF_NetConnect_PersistFolder2_GetClassID (
IPersistFolder2 * iface, CLSID * lpClassId)
{
//IGenericSFImpl * This = impl_from_IPersistFolder2(iface);
if (!lpClassId)
return E_POINTER;
*lpClassId = CLSID_NetworkConnections;
return S_OK;
}
/************************************************************************
* ISF_NetConnect_PersistFolder2_Initialize
*
* NOTES: it makes no sense to change the pidl
*/
static HRESULT WINAPI ISF_NetConnect_PersistFolder2_Initialize (
IPersistFolder2 * iface, LPCITEMIDLIST pidl)
{
IGenericSFImpl * This = impl_from_IPersistFolder2(iface);
SHFree(This->pidlRoot);
This->pidlRoot = ILClone(pidl);
return S_OK;
}
/**************************************************************************
* ISF_NetConnect_PersistFolder2_GetCurFolder
*/
static HRESULT WINAPI ISF_NetConnect_PersistFolder2_GetCurFolder (
IPersistFolder2 * iface, LPITEMIDLIST * pidl)
{
IGenericSFImpl * This = impl_from_IPersistFolder2(iface);
if (!pidl)
return E_POINTER;
*pidl = ILClone (This->pidlRoot);
return S_OK;
}
static const IPersistFolder2Vtbl vt_PersistFolder2 =
{
ISF_NetConnect_PersistFolder2_QueryInterface,
ISF_NetConnect_PersistFolder2_AddRef,
ISF_NetConnect_PersistFolder2_Release,
ISF_NetConnect_PersistFolder2_GetClassID,
ISF_NetConnect_PersistFolder2_Initialize,
ISF_NetConnect_PersistFolder2_GetCurFolder
};
/**************************************************************************
* ISF_NetConnect_Constructor
*/
HRESULT WINAPI ISF_NetConnect_Constructor (IUnknown * pUnkOuter, REFIID riid, LPVOID * ppv)
{
IGenericSFImpl *sf;
if (!ppv)
return E_POINTER;
if (pUnkOuter)
return CLASS_E_NOAGGREGATION;
sf = (IGenericSFImpl *) HeapAlloc ( GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof (IGenericSFImpl));
if (!sf)
return E_OUTOFMEMORY;
sf->ref = 1;
sf->lpVtbl = &vt_ShellFolder2;
sf->lpVtblPersistFolder2 = &vt_PersistFolder2;
sf->lpVtblContextMenu = &vt_ContextMenu2;
sf->pidlRoot = _ILCreateNetConnect(); /* my qualified pidl */
if (!SUCCEEDED (IShellFolder2_QueryInterface ((IShellFolder2*)sf, riid, ppv)))
{
IShellFolder2_Release((IShellFolder2*)sf);
return E_NOINTERFACE;
}
return S_OK;
}

View file

@ -196,6 +196,9 @@
<directory name="netid">
<xi:include href="netid/netid.rbuild" />
</directory>
<directory name="netshell">
<xi:include href="netshell/netshell.rbuild" />
</directory>
<directory name="newdev">
<xi:include href="newdev/newdev.rbuild" />
</directory>