mirror of
https://github.com/reactos/reactos.git
synced 2025-08-03 05:55:48 +00:00
[RSHELL]
* Make rshell.dll able to register its classes and support CoCreateInstance. svn path=/trunk/; revision=65757
This commit is contained in:
parent
b8416cd7f3
commit
a620535b0f
3 changed files with 173 additions and 0 deletions
|
@ -31,6 +31,7 @@ target_link_libraries(rshell
|
||||||
add_importlibs(rshell
|
add_importlibs(rshell
|
||||||
uxtheme
|
uxtheme
|
||||||
shlwapi
|
shlwapi
|
||||||
|
advapi32
|
||||||
shell32
|
shell32
|
||||||
comctl32
|
comctl32
|
||||||
gdi32
|
gdi32
|
||||||
|
|
|
@ -39,10 +39,84 @@ public:
|
||||||
CRShellModule gModule;
|
CRShellModule gModule;
|
||||||
CAtlWinModule gWinModule;
|
CAtlWinModule gWinModule;
|
||||||
|
|
||||||
|
HINSTANCE g_hRShell;
|
||||||
|
|
||||||
|
static LSTATUS inline _RegSetStringValueW(HKEY hKey, LPCWSTR lpValueName, LPCWSTR lpStringData)
|
||||||
|
{
|
||||||
|
DWORD dwStringDataLen = lstrlenW(lpStringData);
|
||||||
|
|
||||||
|
return RegSetValueExW(hKey, lpValueName, 0, REG_SZ, (BYTE *) lpStringData, 2 * (dwStringDataLen + 1));
|
||||||
|
}
|
||||||
|
|
||||||
|
static HRESULT RegisterComponent(REFGUID clsid, LPCWSTR szDisplayName)
|
||||||
|
{
|
||||||
|
WCHAR szFilename[MAX_PATH];
|
||||||
|
WCHAR szClsid[MAX_PATH];
|
||||||
|
WCHAR szRoot[MAX_PATH];
|
||||||
|
|
||||||
|
if (!StringFromGUID2(clsid, szClsid, _countof(szClsid)))
|
||||||
|
return E_FAIL;
|
||||||
|
|
||||||
|
if (!GetModuleFileNameW(g_hRShell, szFilename, _countof(szFilename)))
|
||||||
|
return E_FAIL;
|
||||||
|
|
||||||
|
HRESULT hr = StringCchPrintfW(szRoot, 0x104u, L"CLSID\\%s", szClsid);
|
||||||
|
if (FAILED(hr))
|
||||||
|
return hr;
|
||||||
|
|
||||||
|
DWORD dwDisposition;
|
||||||
|
HKEY hkRoot;
|
||||||
|
if (RegCreateKeyExW(HKEY_CLASSES_ROOT, szRoot, 0, NULL, 0, KEY_WRITE, 0, &hkRoot, &dwDisposition) != 0)
|
||||||
|
return E_FAIL;
|
||||||
|
|
||||||
|
HKEY hkServer;
|
||||||
|
|
||||||
|
_RegSetStringValueW(hkRoot, NULL, szDisplayName);
|
||||||
|
|
||||||
|
if (RegCreateKeyExW(hkRoot, L"InprocServer32", 0, NULL, 0, KEY_SET_VALUE, 0, &hkServer, &dwDisposition) != 0)
|
||||||
|
{
|
||||||
|
RegCloseKey(hkRoot);
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
_RegSetStringValueW(hkServer, NULL, szFilename);
|
||||||
|
_RegSetStringValueW(hkServer, L"ThreadingModel", L"Both");
|
||||||
|
|
||||||
|
RegCloseKey(hkServer);
|
||||||
|
RegCloseKey(hkRoot);
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
static HRESULT UnregisterComponent(REFGUID clsid)
|
||||||
|
{
|
||||||
|
WCHAR szClsid[MAX_PATH];
|
||||||
|
WCHAR szRoot[MAX_PATH];
|
||||||
|
HKEY hkRoot;
|
||||||
|
|
||||||
|
if (!StringFromGUID2(clsid, szClsid, _countof(szClsid)))
|
||||||
|
return E_FAIL;
|
||||||
|
|
||||||
|
HRESULT hr = StringCchPrintfW(szRoot, 0x104u, L"CLSID\\%s", szClsid);
|
||||||
|
if (FAILED(hr))
|
||||||
|
return hr;
|
||||||
|
|
||||||
|
if (RegOpenKeyExW(HKEY_CLASSES_ROOT, szRoot, 0, KEY_WRITE, &hkRoot) != 0)
|
||||||
|
return E_FAIL;
|
||||||
|
|
||||||
|
RegDeleteKeyW(hkRoot, L"InprocServer32");
|
||||||
|
RegCloseKey(hkRoot);
|
||||||
|
|
||||||
|
RegDeleteKeyW(HKEY_CLASSES_ROOT, szRoot);
|
||||||
|
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
STDAPI_(BOOL) DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID fImpLoad)
|
STDAPI_(BOOL) DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID fImpLoad)
|
||||||
{
|
{
|
||||||
if (dwReason == DLL_PROCESS_ATTACH)
|
if (dwReason == DLL_PROCESS_ATTACH)
|
||||||
{
|
{
|
||||||
|
g_hRShell = hInstance;
|
||||||
|
|
||||||
/* HACK - the global constructors don't run, so I placement new them here */
|
/* HACK - the global constructors don't run, so I placement new them here */
|
||||||
new (&gModule) CRShellModule;
|
new (&gModule) CRShellModule;
|
||||||
new (&gWinModule) CAtlWinModule;
|
new (&gWinModule) CAtlWinModule;
|
||||||
|
@ -58,3 +132,97 @@ STDAPI_(BOOL) DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID fImpLoad)
|
||||||
}
|
}
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
HRESULT
|
||||||
|
WINAPI
|
||||||
|
DllCanUnloadNow(void)
|
||||||
|
{
|
||||||
|
gModule.DllCanUnloadNow();
|
||||||
|
return S_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
STDAPI
|
||||||
|
DllRegisterServer(void)
|
||||||
|
{
|
||||||
|
RegisterComponent(CLSID_StartMenu, L"Shell Start Menu");
|
||||||
|
RegisterComponent(CLSID_MenuDeskBar, L"Shell Menu Desk Bar");
|
||||||
|
RegisterComponent(CLSID_MenuBand, L"Shell Menu Band");
|
||||||
|
RegisterComponent(CLSID_MenuBandSite, L"Shell Menu Band Site");
|
||||||
|
RegisterComponent(CLSID_MergedFolder, L"Merged Shell Folder");
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
STDAPI
|
||||||
|
DllUnregisterServer(void)
|
||||||
|
{
|
||||||
|
UnregisterComponent(CLSID_StartMenu);
|
||||||
|
UnregisterComponent(CLSID_MenuDeskBar);
|
||||||
|
UnregisterComponent(CLSID_MenuBand);
|
||||||
|
UnregisterComponent(CLSID_MenuBandSite);
|
||||||
|
UnregisterComponent(CLSID_MergedFolder);
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
class CRShellClassFactory :
|
||||||
|
public CComObjectRootEx<CComMultiThreadModelNoCS>,
|
||||||
|
public IClassFactory
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
CLSID m_Clsid;
|
||||||
|
|
||||||
|
public:
|
||||||
|
CRShellClassFactory() {}
|
||||||
|
virtual ~CRShellClassFactory() {}
|
||||||
|
|
||||||
|
HRESULT Initialize(REFGUID clsid)
|
||||||
|
{
|
||||||
|
m_Clsid = clsid;
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* IClassFactory */
|
||||||
|
virtual HRESULT WINAPI CreateInstance(LPUNKNOWN pUnkOuter, REFIID riid, LPVOID *ppvObject)
|
||||||
|
{
|
||||||
|
*ppvObject = NULL;
|
||||||
|
|
||||||
|
if (IsEqualCLSID(m_Clsid, CLSID_StartMenu))
|
||||||
|
return CStartMenu_Constructor(riid, ppvObject);
|
||||||
|
|
||||||
|
if (IsEqualCLSID(m_Clsid, CLSID_MenuDeskBar))
|
||||||
|
return CMenuDeskBar_Constructor(riid, ppvObject);
|
||||||
|
|
||||||
|
if (IsEqualCLSID(m_Clsid, CLSID_MenuBand))
|
||||||
|
return CMenuBand_Constructor(riid, ppvObject);
|
||||||
|
|
||||||
|
if (IsEqualCLSID(m_Clsid, CLSID_MenuBandSite))
|
||||||
|
return CMenuSite_Constructor(riid, ppvObject);
|
||||||
|
|
||||||
|
if (IsEqualCLSID(m_Clsid, CLSID_MergedFolder))
|
||||||
|
return CMergedFolder_Constructor(riid, ppvObject);
|
||||||
|
|
||||||
|
return E_NOINTERFACE;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual HRESULT WINAPI LockServer(BOOL fLock)
|
||||||
|
{
|
||||||
|
return E_NOTIMPL;
|
||||||
|
}
|
||||||
|
|
||||||
|
BEGIN_COM_MAP(CRShellClassFactory)
|
||||||
|
COM_INTERFACE_ENTRY_IID(IID_IClassFactory, IClassFactory)
|
||||||
|
END_COM_MAP()
|
||||||
|
};
|
||||||
|
|
||||||
|
STDAPI
|
||||||
|
DllGetClassObject(
|
||||||
|
REFCLSID rclsid,
|
||||||
|
REFIID riid,
|
||||||
|
LPVOID *ppv)
|
||||||
|
{
|
||||||
|
if (!ppv)
|
||||||
|
return E_INVALIDARG;
|
||||||
|
|
||||||
|
*ppv = NULL;
|
||||||
|
|
||||||
|
return ShellObjectCreatorInit<CRShellClassFactory>(rclsid, riid, ppv);
|
||||||
|
}
|
||||||
|
|
|
@ -1,3 +1,7 @@
|
||||||
|
@ stdcall DllCanUnloadNow()
|
||||||
|
@ stdcall DllGetClassObject(ptr ptr ptr)
|
||||||
|
@ stdcall DllRegisterServer()
|
||||||
|
@ stdcall DllUnregisterServer()
|
||||||
@ stdcall CStartMenu_Constructor(ptr ptr)
|
@ stdcall CStartMenu_Constructor(ptr ptr)
|
||||||
@ stdcall CMenuDeskBar_Constructor(ptr ptr);
|
@ stdcall CMenuDeskBar_Constructor(ptr ptr);
|
||||||
@ stdcall CMenuSite_Constructor(ptr ptr);
|
@ stdcall CMenuSite_Constructor(ptr ptr);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue