From afb6acc9454ae9043562f989fafebfcb6647ea8a Mon Sep 17 00:00:00 2001 From: Giannis Adamopoulos Date: Mon, 27 Oct 2014 18:26:09 +0000 Subject: [PATCH 1/1] [SHELL32] - Rewrite the monstrosity that was supposed to open control panel items. Still not really correct but works. svn path=/branches/shell-experiments/; revision=65051 --- dll/win32/shell32/folders/cpanel.cpp | 150 ++++----------------------- dll/win32/shell32/folders/cpanel.h | 10 -- 2 files changed, 19 insertions(+), 141 deletions(-) diff --git a/dll/win32/shell32/folders/cpanel.cpp b/dll/win32/shell32/folders/cpanel.cpp index 1033450f0eb..f415461b96e 100644 --- a/dll/win32/shell32/folders/cpanel.cpp +++ b/dll/win32/shell32/folders/cpanel.cpp @@ -763,126 +763,6 @@ HRESULT CPanel_GetIconLocationW(LPCITEMIDLIST pidl, LPWSTR szIconFile, UINT cchM return S_OK; } - -/************************************************************************** -* IShellExecuteHookW Implementation -*/ - -static HRESULT -ExecuteAppletFromCLSID(LPOLESTR pOleStr) -{ - WCHAR wszBuf[128], wszCmd[MAX_PATH]; - DWORD cbCmd = sizeof(wszCmd); - - StringCbPrintfW(wszBuf, sizeof(wszBuf), L"CLSID\\%s\\shell\\open\\command", pOleStr); - - if (RegGetValueW(HKEY_CLASSES_ROOT, wszBuf, NULL, RRF_RT_REG_SZ, NULL, (PVOID)wszCmd, &cbCmd) != ERROR_SUCCESS) - { - ERR("RegGetValueW(%ls) failed with %u\n", wszBuf, GetLastError()); - return E_FAIL; - } - - if (!ExpandEnvironmentStringsW(wszCmd, wszBuf, _countof(wszBuf))) - return E_FAIL; - - PROCESS_INFORMATION pi; - STARTUPINFOW si; - ZeroMemory(&si, sizeof(si)); - si.cb = sizeof(si); - if (!CreateProcessW(NULL, wszBuf, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi)) - return E_FAIL; - - CloseHandle(pi.hProcess); - CloseHandle(pi.hThread); - return S_OK; -} - -EXTERN_C void WINAPI Control_RunDLLW(HWND hWnd, HINSTANCE hInst, LPCWSTR cmd, DWORD nCmdShow); - -HRESULT WINAPI CControlPanelFolder::ExecuteFromIdList(LPCITEMIDLIST pidl) -{ - PIDLCPanelStruct *pCPanel = _ILGetCPanelPointer(ILFindLastID(pidl)); - - if (!pCPanel) - { - /* Is it GUID to control panel applet? */ - IID *piid = _ILGetGUIDPointer(ILFindLastID(pidl)); - if (!piid) - return E_INVALIDARG; - - /* Start it */ - LPOLESTR pOleStr; - if (StringFromCLSID(*piid, &pOleStr) == S_OK) - { - HRESULT hr = ExecuteAppletFromCLSID(pOleStr); - CoTaskMemFree(pOleStr); - return hr; - } - - ERR("Cannot open cpanel applet\n"); - return E_INVALIDARG; - } - - /* Build control panel applet cmd - Note: we pass the applet name to Control_RunDLL to distinguish between multiple applets in one .cpl file */ - WCHAR wszCmd[2*MAX_PATH]; - WCHAR wszAppletName[MAX_PATH]; - - if(!MultiByteToWideChar(CP_ACP, 0, pCPanel->szName + pCPanel->offsDispName, -1, wszAppletName, MAX_PATH)) - return E_FAIL; - - StringCbPrintfW(wszCmd, sizeof(wszCmd), L"rundll32 shell32.dll,Control_RunDLL \"%hs\",\"%ls\"", pCPanel->szName, wszAppletName); - - /* Start the applet */ - TRACE("Run cpl %ls\n", wszCmd); - STARTUPINFO si; - PROCESS_INFORMATION pi; - ZeroMemory(&si, sizeof(si)); - si.cb = sizeof(si); - if (!CreateProcessW(NULL, wszCmd, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi)) - return E_FAIL; - - CloseHandle(pi.hProcess); - CloseHandle(pi.hThread); - return S_OK; -} - -HRESULT WINAPI CControlPanelFolder::Execute(LPSHELLEXECUTEINFOW psei) -{ - TRACE("(%p)->execute(%p)\n", this, psei); - - if (!psei) - return E_INVALIDARG; - - if (!(psei->fMask & SEE_MASK_IDLIST)) - { - FIXME("no idlist given!\n"); - return E_FAIL; - } - - return ExecuteFromIdList((LPCITEMIDLIST)psei->lpIDList); -} - -/************************************************************************** -* IShellExecuteHookA Implementation -*/ - -HRESULT WINAPI CControlPanelFolder::Execute(LPSHELLEXECUTEINFOA psei) -{ - TRACE("(%p)->execute(%p)\n", this, psei); - - if (!psei) - return E_INVALIDARG; - - if (!(psei->fMask & SEE_MASK_IDLIST)) - { - FIXME("no idlist given!\n"); - return E_FAIL; - } - - return ExecuteFromIdList((LPCITEMIDLIST)psei->lpIDList); -} - /************************************************************************** * IContextMenu2 Implementation */ @@ -929,30 +809,38 @@ HRESULT WINAPI CControlPanelFolder::QueryContextMenu( */ HRESULT WINAPI CControlPanelFolder::InvokeCommand(LPCMINVOKECOMMANDINFO lpcmi) { - SHELLEXECUTEINFOW sei; WCHAR szPath[MAX_PATH]; char szTarget[MAX_PATH]; STRRET strret; WCHAR* pszPath; INT Length, cLength; - PIDLCPanelStruct *pcpanel; CComPtr ppf; CComPtr isl; HRESULT hResult; + PIDLCPanelStruct *pcpanel = _ILGetCPanelPointer(apidl[0]); + TRACE("(%p)->(invcom=%p verb=%p wnd=%p)\n", this, lpcmi, lpcmi->lpVerb, lpcmi->hwnd); if (lpcmi->lpVerb == MAKEINTRESOURCEA(IDS_OPEN)) //FIXME { - ZeroMemory(&sei, sizeof(sei)); - sei.cbSize = sizeof(sei); - sei.fMask = SEE_MASK_INVOKEIDLIST; - sei.lpIDList = ILCombine(pidlRoot, apidl[0]); - sei.hwnd = lpcmi->hwnd; - sei.nShow = SW_SHOWNORMAL; - sei.lpVerb = L"open"; -ERR("here\n"); - return Execute(&sei); + LPITEMIDLIST lpIDList = ILCombine(pidlRoot, apidl[0]); + + if (!pcpanel) + { + /* UGLY HACK! */ + LPSHELLBROWSER lpSB = (LPSHELLBROWSER)SendMessageW(lpcmi->hwnd, CWM_GETISHELLBROWSER, 0, 0); + HRESULT hr; + + if (lpSB == NULL) + return E_FAIL; + + hr = lpSB->BrowseObject(lpIDList, 0); + return hr; + } + + /* Note: we pass the applet name to Control_RunDLL to distinguish between multiple applets in one .cpl file */ + ShellExecuteA(NULL, "cplopen", pcpanel->szName, pcpanel->szName + pcpanel->offsDispName, NULL, 0); } else if (lpcmi->lpVerb == MAKEINTRESOURCEA(IDS_CREATELINK)) //FIXME { diff --git a/dll/win32/shell32/folders/cpanel.h b/dll/win32/shell32/folders/cpanel.h index b4d8cc7b5f3..e9f0d56e601 100644 --- a/dll/win32/shell32/folders/cpanel.h +++ b/dll/win32/shell32/folders/cpanel.h @@ -27,8 +27,6 @@ class CControlPanelFolder : public CComObjectRootEx, public IShellFolder2, public IPersistFolder2, - public IShellExecuteHookA, - public IShellExecuteHookW, public IContextMenu2 { private: @@ -75,12 +73,6 @@ class CControlPanelFolder : // IPersistFolder2 virtual HRESULT WINAPI GetCurFolder(LPITEMIDLIST * pidl); - // IShellExecuteHookW - virtual HRESULT WINAPI Execute(LPSHELLEXECUTEINFOW psei); - - // IShellExecuteHookA - virtual HRESULT WINAPI Execute(LPSHELLEXECUTEINFOA psei); - // IContextMenu virtual HRESULT WINAPI QueryContextMenu(HMENU hMenu, UINT indexMenu, UINT idCmdFirst, UINT idCmdLast, UINT uFlags); virtual HRESULT WINAPI InvokeCommand(LPCMINVOKECOMMANDINFO lpcmi); @@ -100,8 +92,6 @@ class CControlPanelFolder : COM_INTERFACE_ENTRY_IID(IID_IPersistFolder, IPersistFolder) COM_INTERFACE_ENTRY_IID(IID_IPersistFolder2, IPersistFolder2) COM_INTERFACE_ENTRY_IID(IID_IPersist, IPersist) - COM_INTERFACE_ENTRY_IID(IID_IShellExecuteHookA, IShellExecuteHookA) - COM_INTERFACE_ENTRY_IID(IID_IShellExecuteHookW, IShellExecuteHookW) COM_INTERFACE_ENTRY_IID(IID_IContextMenu, IContextMenu) COM_INTERFACE_ENTRY_IID(IID_IContextMenu2, IContextMenu2) END_COM_MAP() -- 2.17.1