From 9b716539182864bc077e362febcda74da50287ed Mon Sep 17 00:00:00 2001 From: Alex Miccolis Date: Tue, 15 Feb 2022 17:54:20 -0600 Subject: [PATCH] [SHELL32] Stop SHELL_execute from always executing files (#4363) CORE-18038 Add a check (PathIsExeW) to SHELL_execute to prevent it from executing non-exe files. --- dll/win32/shell32/shlexec.cpp | 55 ++++++++++++++++++++--------------- 1 file changed, 31 insertions(+), 24 deletions(-) diff --git a/dll/win32/shell32/shlexec.cpp b/dll/win32/shell32/shlexec.cpp index b8f3bb2ca16..f1fce51cc9f 100644 --- a/dll/win32/shell32/shlexec.cpp +++ b/dll/win32/shell32/shlexec.cpp @@ -25,6 +25,8 @@ WINE_DEFAULT_DEBUG_CHANNEL(exec); +EXTERN_C BOOL PathIsExeW(LPCWSTR lpszPath); + #define SEE_MASK_CLASSALL (SEE_MASK_CLASSNAME | SEE_MASK_CLASSKEY) typedef UINT_PTR (*SHELL_ExecuteW32)(const WCHAR *lpCmd, WCHAR *env, BOOL shWait, @@ -2139,32 +2141,37 @@ static BOOL SHELL_execute(LPSHELLEXECUTEINFOW sei, SHELL_ExecuteW32 execfunc) lpFile = sei_tmp.lpFile; wcmd = wcmdBuffer; - len = lstrlenW(wszApplicationName) + 3; - if (sei_tmp.lpParameters[0]) - len += 1 + lstrlenW(wszParameters); - if (len > wcmdLen) - { - wcmd = (LPWSTR)HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR)); - wcmdLen = len; - } - swprintf(wcmd, L"\"%s\"", wszApplicationName); - if (sei_tmp.lpParameters[0]) - { - strcatW(wcmd, L" "); - strcatW(wcmd, wszParameters); - } - retval = execfunc(wcmd, NULL, FALSE, &sei_tmp, sei); - if (retval > 32) + /* Only execute if it has an executable extension */ + if (PathIsExeW(lpFile)) { - HeapFree(GetProcessHeap(), 0, wszApplicationName); - if (wszParameters != parametersBuffer) - HeapFree(GetProcessHeap(), 0, wszParameters); - if (wszDir != dirBuffer) - HeapFree(GetProcessHeap(), 0, wszDir); - if (wcmd != wcmdBuffer) - HeapFree(GetProcessHeap(), 0, wcmd); - return TRUE; + len = lstrlenW(wszApplicationName) + 3; + if (sei_tmp.lpParameters[0]) + len += 1 + lstrlenW(wszParameters); + if (len > wcmdLen) + { + wcmd = (LPWSTR)HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR)); + wcmdLen = len; + } + swprintf(wcmd, L"\"%s\"", wszApplicationName); + if (sei_tmp.lpParameters[0]) + { + strcatW(wcmd, L" "); + strcatW(wcmd, wszParameters); + } + + retval = execfunc(wcmd, NULL, FALSE, &sei_tmp, sei); + if (retval > 32) + { + HeapFree(GetProcessHeap(), 0, wszApplicationName); + if (wszParameters != parametersBuffer) + HeapFree(GetProcessHeap(), 0, wszParameters); + if (wszDir != dirBuffer) + HeapFree(GetProcessHeap(), 0, wszDir); + if (wcmd != wcmdBuffer) + HeapFree(GetProcessHeap(), 0, wcmd); + return TRUE; + } } /* Else, try to find the executable */