ReactOS 0.4.15-dev-7788-g1ad9096
shlexec.c File Reference
#include <stdio.h>
#include <assert.h>
#include "wtypes.h"
#include "winbase.h"
#include "windef.h"
#include "shellapi.h"
#include "shlwapi.h"
#include "ddeml.h"
#include "wine/heap.h"
#include "wine/test.h"
#include "shell32_test.h"
Include dependency graph for shlexec.c:

Go to the source code of this file.

Classes

struct  filename_tests_t
 
struct  cmdline_tests_t
 
struct  argify_tests_t
 
struct  fileurl_tests_t
 
struct  dde_tests_t
 
struct  dde_default_app_tests_t
 
struct  dde_thread_info_t
 

Macros

#define CHILD_DDE_TIMEOUT   2500
 
#define okShell_(file, line)   (winetest_set_location(file, line), 0) ? (void)0 : _okShell
 
#define okShell   okShell_(__FILE__, __LINE__)
 
#define okChildString(key, expected)   okChildString_(__FILE__, __LINE__, (key), (expected), (expected))
 
#define okChildStringBroken(key, expected, broken)   okChildString_(__FILE__, __LINE__, (key), (expected), (broken))
 
#define okChildPath(key, expected)   okChildPath_(__FILE__, __LINE__, (key), (expected))
 
#define okChildInt(key, expected)   okChildInt_(__FILE__, __LINE__, (key), (expected))
 
#define okChildIntBroken(key, expected)   okChildIntBroken_(__FILE__, __LINE__, (key), (expected))
 
#define todo_wait   for (_todo_wait = 1; _todo_wait; _todo_wait = 0)
 
#define shell_execute(verb, filename, parameters, directory)    shell_execute_(__FILE__, __LINE__, verb, filename, parameters, directory)
 
#define shell_execute_ex(mask, verb, filename, parameters, directory, class)    shell_execute_ex_(__FILE__, __LINE__, mask, verb, filename, parameters, directory, class)
 
#define URL_SUCCESS   0x1
 
#define USE_COLON   0x2
 
#define USE_BSLASH   0x4
 
#define DDE_DEFAULT_APP_VARIANTS   3
 

Functions

static const charencodeA (const char *str)
 
static unsigned decode_char (char c)
 
static chardecodeA (const char *str)
 
static void WINAPIV WINETEST_PRINTF_ATTR (2, 3)
 
static chargetChildString (const char *sect, const char *key)
 
static HDDEDATA CALLBACK ddeCb (UINT uType, UINT uFmt, HCONV hConv, HSZ hsz1, HSZ hsz2, HDDEDATA hData, ULONG_PTR dwData1, ULONG_PTR dwData2)
 
static void init_event (const char *child_file)
 
static void CALLBACK childTimeout (HWND wnd, UINT msg, UINT_PTR timer, DWORD time)
 
static void doChild (int argc, char **argv)
 
static void dump_child_ (const char *file, int line)
 
static void reset_association_description (void)
 
static void okChildString_ (const char *file, int line, const char *key, const char *expected, const char *bad)
 
static int StrCmpPath (const char *s1, const char *s2)
 
static void okChildPath_ (const char *file, int line, const char *key, const char *expected)
 
static void okChildInt_ (const char *file, int line, const char *key, int expected)
 
static void okChildIntBroken_ (const char *file, int line, const char *key, int expected)
 
static void strcat_param (char *str, const char *name, const char *param)
 
static INT_PTR shell_execute_ (const char *file, int line, LPCSTR verb, LPCSTR filename, LPCSTR parameters, LPCSTR directory)
 
static INT_PTR shell_execute_ex_ (const char *file, int line, DWORD mask, LPCSTR verb, LPCSTR filename, LPCSTR parameters, LPCSTR directory, LPCSTR class)
 
static BOOL create_test_class (const char *class, BOOL protocol)
 
static BOOL create_test_association (const char *extension)
 
static LSTATUS myRegDeleteTreeA (HKEY hKey, LPCSTR lpszSubKey)
 
static void delete_test_class (const char *classname)
 
static void delete_test_association (const char *extension)
 
static void create_test_verb_dde (const char *classname, const char *verb, int rawcmd, const char *cmdtail, const char *ddeexec, const char *application, const char *topic, const char *ifexec)
 
static void create_test_verb (const char *classname, const char *verb, int rawcmd, const char *cmdtail)
 
static DWORD get_long_path_name (const char *shortpath, char *longpath, DWORD longlen)
 
static void test_lpFile_parsed (void)
 
static BOOL test_one_cmdline (const cmdline_tests_t *test)
 
static void test_commandline2argv (void)
 
static void test_argify (void)
 
static void test_filename (void)
 
static void test_fileurls (void)
 
static void test_urls (void)
 
static void test_find_executable (void)
 
static void test_lnks (void)
 
static void test_exes (void)
 
static DWORD WINAPI hooked_WaitForInputIdle (HANDLE process, DWORD timeout)
 
static void hook_WaitForInputIdle (DWORD(WINAPI *new_func)(HANDLE, DWORD))
 
static void test_dde (void)
 
static DWORD CALLBACK ddeThread (LPVOID arg)
 
static void test_dde_default_app (void)
 
static void init_test (void)
 
static void cleanup_test (void)
 
static void test_directory (void)
 
 START_TEST (shlexec)
 

Variables

static char argv0 [MAX_PATH]
 
static int myARGC
 
static char ** myARGV
 
static char tmpdir [MAX_PATH]
 
static char child_file [MAX_PATH]
 
static DLLVERSIONINFO dllver
 
static BOOL skip_shlexec_tests = FALSE
 
static BOOL skip_noassoc_tests = FALSE
 
static HANDLE dde_ready_event
 
static DWORD ddeInst
 
static HSZ hszTopic
 
static char ddeExec [MAX_PATH]
 
static char ddeApplication [MAX_PATH]
 
static BOOL post_quit_on_execute
 
static HANDLE hEvent
 
static char shell_call [2048]
 
static char assoc_desc [2048]
 
static int _todo_wait = 0
 
static int bad_shellexecute = 0
 
static const chartestfiles []
 
static filename_tests_t filename_tests []
 
static filename_tests_t noquotes_tests []
 
static const cmdline_tests_t cmdline_tests []
 
static const argify_tests_t argify_tests []
 
static fileurl_tests_t fileurl_tests []
 
static filename_tests_t lnk_tests []
 
static dde_tests_t dde_tests []
 
static int waitforinputidle_count
 
static dde_default_app_tests_t dde_default_app_tests []
 

Macro Definition Documentation

◆ CHILD_DDE_TIMEOUT

#define CHILD_DDE_TIMEOUT   2500

Definition at line 146 of file shlexec.c.

◆ DDE_DEFAULT_APP_VARIANTS

#define DDE_DEFAULT_APP_VARIANTS   3

Definition at line 2479 of file shlexec.c.

◆ okChildInt

#define okChildInt (   key,
  expected 
)    okChildInt_(__FILE__, __LINE__, (key), (expected))

Definition at line 460 of file shlexec.c.

◆ okChildIntBroken

#define okChildIntBroken (   key,
  expected 
)    okChildIntBroken_(__FILE__, __LINE__, (key), (expected))

Definition at line 469 of file shlexec.c.

◆ okChildPath

#define okChildPath (   key,
  expected 
)    okChildPath_(__FILE__, __LINE__, (key), (expected))

Definition at line 451 of file shlexec.c.

◆ okChildString

#define okChildString (   key,
  expected 
)    okChildString_(__FILE__, __LINE__, (key), (expected), (expected))

Definition at line 383 of file shlexec.c.

◆ okChildStringBroken

#define okChildStringBroken (   key,
  expected,
  broken 
)    okChildString_(__FILE__, __LINE__, (key), (expected), (broken))

Definition at line 384 of file shlexec.c.

◆ okShell

#define okShell   okShell_(__FILE__, __LINE__)

Definition at line 362 of file shlexec.c.

◆ okShell_

#define okShell_ (   file,
  line 
)    (winetest_set_location(file, line), 0) ? (void)0 : _okShell

Definition at line 361 of file shlexec.c.

◆ shell_execute

#define shell_execute (   verb,
  filename,
  parameters,
  directory 
)     shell_execute_(__FILE__, __LINE__, verb, filename, parameters, directory)

Definition at line 569 of file shlexec.c.

◆ shell_execute_ex

#define shell_execute_ex (   mask,
  verb,
  filename,
  parameters,
  directory,
  class 
)     shell_execute_ex_(__FILE__, __LINE__, mask, verb, filename, parameters, directory, class)

Definition at line 674 of file shlexec.c.

◆ todo_wait

#define todo_wait   for (_todo_wait = 1; _todo_wait; _todo_wait = 0)

Definition at line 492 of file shlexec.c.

◆ URL_SUCCESS

#define URL_SUCCESS   0x1

Definition at line 1746 of file shlexec.c.

◆ USE_BSLASH

#define USE_BSLASH   0x4

Definition at line 1748 of file shlexec.c.

◆ USE_COLON

#define USE_COLON   0x2

Definition at line 1747 of file shlexec.c.

Function Documentation

◆ childTimeout()

static void CALLBACK childTimeout ( HWND  wnd,
UINT  msg,
UINT_PTR  timer,
DWORD  time 
)
static

Definition at line 201 of file shlexec.c.

202{
203 trace("childTimeout called\n");
204
206}
#define trace
Definition: atltest.h:70
__analysis_noreturn void WINAPI PostQuitMessage(_In_ int)

Referenced by doChild().

◆ cleanup_test()

static void cleanup_test ( void  )
static

Definition at line 2780 of file shlexec.c.

2781{
2782 char filename[MAX_PATH];
2783 const char* const * testfile;
2784
2785 /* Delete the test files */
2786 testfile=testfiles;
2787 while (*testfile)
2788 {
2789 sprintf(filename, *testfile, tmpdir);
2790 /* Make sure we can delete the files ('test file.noassoc' is read-only now) */
2793 testfile++;
2794 }
2797
2798 /* Delete the test association */
2799 delete_test_association(".shlexec");
2801 delete_test_class("shlproto");
2802
2804
2806}
#define CloseHandle
Definition: compat.h:739
#define MAX_PATH
Definition: compat.h:34
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:137
BOOL WINAPI DeleteFileA(IN LPCSTR lpFileName)
Definition: delete.c:24
BOOL WINAPI RemoveDirectoryA(IN LPCSTR lpPathName)
Definition: dir.c:714
BOOL WINAPI SetFileAttributesA(LPCSTR lpFileName, DWORD dwFileAttributes)
Definition: fileinfo.c:776
void WINAPI DECLSPEC_HOTPATCH CoUninitialize(void)
Definition: compobj.c:2067
const char * filename
Definition: ioapi.h:137
#define sprintf(buf, format,...)
Definition: sprintf.c:55
static char child_file[MAX_PATH]
Definition: shlexec.c:53
static const char * testfiles[]
Definition: shlexec.c:1005
static HANDLE hEvent
Definition: shlexec.c:189
static char tmpdir[MAX_PATH]
Definition: shlexec.c:52
static void delete_test_class(const char *classname)
Definition: shlexec.c:800
static void delete_test_association(const char *extension)
Definition: shlexec.c:805

Referenced by START_TEST().

◆ create_test_association()

static BOOL create_test_association ( const char extension)
static

Definition at line 712 of file shlexec.c.

713{
714 HKEY hkey;
715 char class[MAX_PATH];
716 LONG rc;
717
718 sprintf(class, "shlexec%s", extension);
720 NULL, &hkey, NULL);
721 ok(rc == ERROR_SUCCESS || rc == ERROR_ACCESS_DENIED,
722 "could not create association %s (rc=%d)\n", class, rc);
723 if (rc != ERROR_SUCCESS)
724 return FALSE;
725
726 rc=RegSetValueExA(hkey, NULL, 0, REG_SZ, (LPBYTE) class, strlen(class)+1);
727 ok(rc==ERROR_SUCCESS, "RegSetValueEx '%s' failed, expected ERROR_SUCCESS, got %d\n", class, rc);
728 CloseHandle(hkey);
729
730 return create_test_class(class, FALSE);
731}
ACPI_SIZE strlen(const char *String)
Definition: utclib.c:269
#define ok(value,...)
Definition: atltest.h:57
#define ERROR_SUCCESS
Definition: deptool.c:10
#define NULL
Definition: types.h:112
#define FALSE
Definition: types.h:117
LONG WINAPI RegSetValueExA(HKEY hKey, LPCSTR lpValueName, DWORD Reserved, DWORD dwType, CONST BYTE *lpData, DWORD cbData)
Definition: reg.c:4828
LONG WINAPI RegCreateKeyExA(_In_ HKEY hKey, _In_ LPCSTR lpSubKey, _In_ DWORD Reserved, _In_ LPSTR lpClass, _In_ DWORD dwOptions, _In_ REGSAM samDesired, _In_ LPSECURITY_ATTRIBUTES lpSecurityAttributes, _Out_ PHKEY phkResult, _Out_ LPDWORD lpdwDisposition)
Definition: reg.c:1034
#define ERROR_ACCESS_DENIED
Definition: compat.h:97
#define REG_SZ
Definition: layer.c:22
#define KEY_SET_VALUE
Definition: nt_native.h:1017
long LONG
Definition: pedump.c:60
static BOOL create_test_class(const char *class, BOOL protocol)
Definition: shlexec.c:684
unsigned char * LPBYTE
Definition: typedefs.h:53
#define HKEY_CLASSES_ROOT
Definition: winreg.h:10

Referenced by init_test(), test_dde(), test_dde_default_app(), and test_find_executable().

◆ create_test_class()

static BOOL create_test_class ( const char class,
BOOL  protocol 
)
static

Definition at line 684 of file shlexec.c.

685{
686 HKEY hkey, hkey_shell;
687 LONG rc;
688
689 rc = RegCreateKeyExA(HKEY_CLASSES_ROOT, class, 0, NULL, 0,
691 &hkey, NULL);
692 ok(rc == ERROR_SUCCESS || rc == ERROR_ACCESS_DENIED,
693 "could not create class %s (rc=%d)\n", class, rc);
694 if (rc != ERROR_SUCCESS)
695 return FALSE;
696
697 if (protocol)
698 {
699 rc = RegSetValueExA(hkey, "URL Protocol", 0, REG_SZ, (LPBYTE)"", 1);
700 ok(rc == ERROR_SUCCESS, "RegSetValueEx '%s' failed, expected ERROR_SUCCESS, got %d\n", class, rc);
701 }
702
703 rc = RegCreateKeyExA(hkey, "shell", 0, NULL, 0,
704 KEY_CREATE_SUB_KEY, NULL, &hkey_shell, NULL);
705 ok(rc == ERROR_SUCCESS, "RegCreateKeyEx 'shell' failed, expected ERROR_SUCCESS, got %d\n", rc);
706
707 CloseHandle(hkey);
708 CloseHandle(hkey_shell);
709 return TRUE;
710}
#define TRUE
Definition: types.h:120
#define KEY_CREATE_SUB_KEY
Definition: nt_native.h:1018

Referenced by create_test_association(), init_test(), and test_urls().

◆ create_test_verb()

static void create_test_verb ( const char classname,
const char verb,
int  rawcmd,
const char cmdtail 
)
static

Definition at line 915 of file shlexec.c.

917{
918 create_test_verb_dde(classname, verb, rawcmd, cmdtail, NULL, NULL,
919 NULL, NULL);
921}
WCHAR classname[128]
Definition: startup.c:15
static void create_test_verb_dde(const char *classname, const char *verb, int rawcmd, const char *cmdtail, const char *ddeexec, const char *application, const char *topic, const char *ifexec)
Definition: shlexec.c:814
static void reset_association_description(void)
Definition: shlexec.c:365

Referenced by init_test(), test_argify(), test_find_executable(), and test_urls().

◆ create_test_verb_dde()

static void create_test_verb_dde ( const char classname,
const char verb,
int  rawcmd,
const char cmdtail,
const char ddeexec,
const char application,
const char topic,
const char ifexec 
)
static

Definition at line 814 of file shlexec.c.

818{
819 HKEY hkey_shell, hkey_verb, hkey_cmd;
820 char shell[MAX_PATH];
821 char* cmd;
822 LONG rc;
823
824 strcpy(assoc_desc, " Assoc ");
826 strcat_param(assoc_desc, "verb", verb);
827 sprintf(shell, "%d", rawcmd);
828 strcat_param(assoc_desc, "rawcmd", shell);
829 strcat_param(assoc_desc, "cmdtail", cmdtail);
830 strcat_param(assoc_desc, "ddeexec", ddeexec);
831 strcat_param(assoc_desc, "app", application);
832 strcat_param(assoc_desc, "topic", topic);
833 strcat_param(assoc_desc, "ifexec", ifexec);
834
835 sprintf(shell, "%s\\shell", classname);
837 KEY_CREATE_SUB_KEY, &hkey_shell);
838 ok(rc == ERROR_SUCCESS, "%s key creation failed with %d\n", shell, rc);
839
840 rc=RegCreateKeyExA(hkey_shell, verb, 0, NULL, 0, KEY_CREATE_SUB_KEY,
841 NULL, &hkey_verb, NULL);
842 ok(rc == ERROR_SUCCESS, "%s verb key creation failed with %d\n", verb, rc);
843
844 rc=RegCreateKeyExA(hkey_verb, "command", 0, NULL, 0, KEY_SET_VALUE,
845 NULL, &hkey_cmd, NULL);
846 ok(rc == ERROR_SUCCESS, "\'command\' key creation failed with %d\n", rc);
847
848 if (rawcmd)
849 {
850 rc=RegSetValueExA(hkey_cmd, NULL, 0, REG_SZ, (LPBYTE)cmdtail, strlen(cmdtail)+1);
851 }
852 else
853 {
854 cmd = heap_alloc(strlen(argv0) + 10 + strlen(child_file) + 2 + strlen(cmdtail) + 1);
855 sprintf(cmd,"%s shlexec \"%s\" %s", argv0, child_file, cmdtail);
856 rc=RegSetValueExA(hkey_cmd, NULL, 0, REG_SZ, (LPBYTE)cmd, strlen(cmd)+1);
857 ok(rc == ERROR_SUCCESS, "setting command failed with %d\n", rc);
858 heap_free(cmd);
859 }
860
861 if (ddeexec)
862 {
863 HKEY hkey_ddeexec, hkey_application, hkey_topic, hkey_ifexec;
864
865 rc=RegCreateKeyExA(hkey_verb, "ddeexec", 0, NULL, 0, KEY_SET_VALUE |
866 KEY_CREATE_SUB_KEY, NULL, &hkey_ddeexec, NULL);
867 ok(rc == ERROR_SUCCESS, "\'ddeexec\' key creation failed with %d\n", rc);
868 rc=RegSetValueExA(hkey_ddeexec, NULL, 0, REG_SZ, (LPBYTE)ddeexec,
869 strlen(ddeexec)+1);
870 ok(rc == ERROR_SUCCESS, "set value failed with %d\n", rc);
871
872 if (application)
873 {
874 rc=RegCreateKeyExA(hkey_ddeexec, "application", 0, NULL, 0, KEY_SET_VALUE,
875 NULL, &hkey_application, NULL);
876 ok(rc == ERROR_SUCCESS, "\'application\' key creation failed with %d\n", rc);
877
878 rc=RegSetValueExA(hkey_application, NULL, 0, REG_SZ, (LPBYTE)application,
879 strlen(application)+1);
880 ok(rc == ERROR_SUCCESS, "set value failed with %d\n", rc);
881 CloseHandle(hkey_application);
882 }
883 if (topic)
884 {
885 rc=RegCreateKeyExA(hkey_ddeexec, "topic", 0, NULL, 0, KEY_SET_VALUE,
886 NULL, &hkey_topic, NULL);
887 ok(rc == ERROR_SUCCESS, "\'topic\' key creation failed with %d\n", rc);
888 rc=RegSetValueExA(hkey_topic, NULL, 0, REG_SZ, (LPBYTE)topic,
889 strlen(topic)+1);
890 ok(rc == ERROR_SUCCESS, "set value failed with %d\n", rc);
891 CloseHandle(hkey_topic);
892 }
893 if (ifexec)
894 {
895 rc=RegCreateKeyExA(hkey_ddeexec, "ifexec", 0, NULL, 0, KEY_SET_VALUE,
896 NULL, &hkey_ifexec, NULL);
897 ok(rc == ERROR_SUCCESS, "\'ifexec\' key creation failed with %d\n", rc);
898 rc=RegSetValueExA(hkey_ifexec, NULL, 0, REG_SZ, (LPBYTE)ifexec,
899 strlen(ifexec)+1);
900 ok(rc == ERROR_SUCCESS, "set value failed with %d\n", rc);
901 CloseHandle(hkey_ifexec);
902 }
903 CloseHandle(hkey_ddeexec);
904 }
905
906 CloseHandle(hkey_shell);
907 CloseHandle(hkey_verb);
908 CloseHandle(hkey_cmd);
909}
char * strcpy(char *DstString, const char *SrcString)
Definition: utclib.c:388
static void * heap_alloc(size_t len)
Definition: appwiz.h:66
static BOOL heap_free(void *mem)
Definition: appwiz.h:76
void shell(int argc, const char *argv[])
Definition: cmds.c:1231
LONG WINAPI RegOpenKeyExA(_In_ HKEY hKey, _In_ LPCSTR lpSubKey, _In_ DWORD ulOptions, _In_ REGSAM samDesired, _Out_ PHKEY phkResult)
Definition: reg.c:3327
static const char topic[]
Definition: propsys.c:44
static char assoc_desc[2048]
Definition: shlexec.c:364
static char argv0[MAX_PATH]
Definition: shlexec.c:49
static void strcat_param(char *str, const char *name, const char *param)
Definition: shlexec.c:478
Definition: ftp_var.h:139

Referenced by create_test_verb(), test_dde(), and test_dde_default_app().

◆ ddeCb()

static HDDEDATA CALLBACK ddeCb ( UINT  uType,
UINT  uFmt,
HCONV  hConv,
HSZ  hsz1,
HSZ  hsz2,
HDDEDATA  hData,
ULONG_PTR  dwData1,
ULONG_PTR  dwData2 
)
static

Definition at line 153 of file shlexec.c.

156{
157 DWORD size = 0;
158
159 if (winetest_debug > 2)
160 trace("dde_cb: %04x, %04x, %p, %p, %p, %p, %08lx, %08lx\n",
161 uType, uFmt, hConv, hsz1, hsz2, hData, dwData1, dwData2);
162
163 switch (uType)
164 {
165 case XTYP_CONNECT:
166 if (!DdeCmpStringHandles(hsz1, hszTopic))
167 {
169 ok(size < MAX_PATH, "got size %d\n", size);
171 return (HDDEDATA)TRUE;
172 }
173 return (HDDEDATA)FALSE;
174
175 case XTYP_EXECUTE:
176 size = DdeGetData(hData, (LPBYTE)ddeExec, MAX_PATH, 0);
177 ok(size < MAX_PATH, "got size %d\n", size);
179 DdeFreeDataHandle(hData);
182 return (HDDEDATA)DDE_FACK;
183
184 default:
185 return NULL;
186 }
187}
INT WINAPI DdeCmpStringHandles(HSZ, HSZ)
Definition: ddemisc.c:685
#define XTYP_CONNECT
Definition: ddeml.h:186
#define DDE_FACK
Definition: ddeml.h:216
DWORD WINAPI DdeQueryStringA(DWORD, HSZ, LPSTR, DWORD, INT)
Definition: ddemisc.c:501
#define CP_WINANSI
Definition: ddeml.h:32
#define XTYP_EXECUTE
Definition: ddeml.h:185
BOOL WINAPI DdeFreeDataHandle(HDDEDATA)
Definition: ddemisc.c:1461
DWORD WINAPI DdeGetData(HDDEDATA, LPBYTE, DWORD, DWORD)
Definition: ddemisc.c:1379
#define assert(x)
Definition: debug.h:53
unsigned long DWORD
Definition: ntddk_ex.h:95
GLsizeiptr size
Definition: glext.h:5919
int winetest_debug
static BOOL post_quit_on_execute
Definition: shlexec.c:150
static DWORD ddeInst
Definition: shlexec.c:147
static HSZ hszTopic
Definition: shlexec.c:148
static char ddeExec[MAX_PATH]
Definition: shlexec.c:149
static char ddeApplication[MAX_PATH]
Definition: shlexec.c:149

Referenced by doChild(), and test_dde_default_app().

◆ ddeThread()

static DWORD CALLBACK ddeThread ( LPVOID  arg)
static

Definition at line 2538 of file shlexec.c.

2539{
2541 assert(info && info->filename);
2542 PostThreadMessageA(info->threadIdParent,
2543 WM_QUIT,
2545 0);
2546 ExitThread(0);
2547}
VOID WINAPI ExitThread(IN DWORD uExitCode)
Definition: thread.c:365
#define SEE_MASK_FLAG_DDEWAIT
Definition: shellapi.h:34
#define SEE_MASK_FLAG_NO_UI
Definition: shellapi.h:36
#define shell_execute_ex(mask, verb, filename, parameters, directory, class)
Definition: shlexec.c:674
void * arg
Definition: msvc.h:10
#define WM_QUIT
Definition: winuser.h:1623
BOOL WINAPI PostThreadMessageA(_In_ DWORD, _In_ UINT, _In_ WPARAM, _In_ LPARAM)

Referenced by test_dde_default_app().

◆ decode_char()

static unsigned decode_char ( char  c)
static

Definition at line 87 of file shlexec.c.

88{
89 if (c >= '0' && c <= '9') return c - '0';
90 if (c >= 'a' && c <= 'f') return c - 'a' + 10;
91 assert(c >= 'A' && c <= 'F');
92 return c - 'A' + 10;
93}
const GLubyte * c
Definition: glext.h:8905

Referenced by decodeA().

◆ decodeA()

static char * decodeA ( const char str)
static

Definition at line 95 of file shlexec.c.

96{
97 static char decoded[1024];
98 char* ptr;
99 size_t len,i;
100
101 len = strlen(str) / 2;
102 if (!len--) return NULL;
103 if (len >= sizeof(decoded))
104 {
105 fprintf(stderr, "string is too long!\n");
106 assert(0);
107 }
108 ptr = decoded;
109 for (i = 0; i < len; i++)
110 ptr[i] = (decode_char(str[2 * i]) << 4) | decode_char(str[2 * i + 1]);
111 ptr[len] = '\0';
112 return ptr;
113}
GLenum GLsizei len
Definition: glext.h:6722
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define stderr
Definition: stdio.h:100
_Check_return_opt_ _CRTIMP int __cdecl fprintf(_Inout_ FILE *_File, _In_z_ _Printf_format_string_ const char *_Format,...)
static PVOID ptr
Definition: dispmode.c:27
const WCHAR * str
static unsigned decode_char(char c)
Definition: shlexec.c:87

Referenced by getChildString().

◆ delete_test_association()

static void delete_test_association ( const char extension)
static

Definition at line 805 of file shlexec.c.

806{
807 char classname[MAX_PATH];
808
809 sprintf(classname, "shlexec%s", extension);
812}
static LSTATUS myRegDeleteTreeA(HKEY hKey, LPCSTR lpszSubKey)
Definition: shlexec.c:734

Referenced by cleanup_test(), test_dde(), test_dde_default_app(), and test_find_executable().

◆ delete_test_class()

static void delete_test_class ( const char classname)
static

Definition at line 800 of file shlexec.c.

Referenced by cleanup_test(), delete_test_association(), and test_urls().

◆ doChild()

static void doChild ( int  argc,
char **  argv 
)
static

Definition at line 208 of file shlexec.c.

209{
210 char *filename, buffer[MAX_PATH];
212 int i;
213 UINT_PTR timer;
214
215 filename=argv[2];
218 return;
219
220 /* Arguments */
221 childPrintf(hFile, "[Child]\r\n");
222 if (winetest_debug > 2)
223 {
224 trace("cmdlineA='%s'\n", GetCommandLineA());
225 trace("argcA=%d\n", argc);
226 }
227 childPrintf(hFile, "cmdlineA=%s\r\n", encodeA(GetCommandLineA()));
228 childPrintf(hFile, "argcA=%d\r\n", argc);
229 for (i = 0; i < argc; i++)
230 {
231 if (winetest_debug > 2)
232 trace("argvA%d='%s'\n", i, argv[i]);
233 childPrintf(hFile, "argvA%d=%s\r\n", i, encodeA(argv[i]));
234 }
236 childPrintf(hFile, "longPath=%s\r\n", encodeA(buffer));
237
238 /* Check environment variable inheritance */
239 *buffer = '\0';
240 SetLastError(0);
241 GetEnvironmentVariableA("ShlexecVar", buffer, sizeof(buffer));
242 childPrintf(hFile, "ShlexecVarLE=%d\r\n", GetLastError());
243 childPrintf(hFile, "ShlexecVar=%s\r\n", encodeA(buffer));
244
245 map = OpenFileMappingA(FILE_MAP_READ, FALSE, "winetest_shlexec_dde_map");
246 if (map != NULL)
247 {
248 HANDLE dde_ready;
249 char *shared_block = MapViewOfFile(map, FILE_MAP_READ, 0, 0, 4096);
251 if (shared_block[0] != '\0' || shared_block[1] != '\0')
252 {
253 HDDEDATA hdde;
254 HSZ hszApplication;
255 MSG msg;
256 UINT rc;
257
259 ddeInst = 0;
262 ok(rc == DMLERR_NO_ERROR, "DdeInitializeA() returned %d\n", rc);
263 hszApplication = DdeCreateStringHandleA(ddeInst, shared_block, CP_WINANSI);
264 ok(hszApplication != NULL, "DdeCreateStringHandleA(%s) = NULL\n", shared_block);
265 shared_block += strlen(shared_block) + 1;
267 ok(hszTopic != NULL, "DdeCreateStringHandleA(%s) = NULL\n", shared_block);
268 hdde = DdeNameService(ddeInst, hszApplication, 0, DNS_REGISTER | DNS_FILTEROFF);
269 ok(hdde != NULL, "DdeNameService() failed le=%u\n", GetLastError());
270
272
273 dde_ready = OpenEventA(EVENT_MODIFY_STATE, FALSE, "winetest_shlexec_dde_ready");
274 SetEvent(dde_ready);
275 CloseHandle(dde_ready);
276
277 while (GetMessageA(&msg, NULL, 0, 0))
278 {
279 if (winetest_debug > 2)
280 trace("msg %d lParam=%ld wParam=%lu\n", msg.message, msg.lParam, msg.wParam);
282 }
283
284 Sleep(500);
285 KillTimer(NULL, timer);
286 hdde = DdeNameService(ddeInst, hszApplication, 0, DNS_UNREGISTER);
287 ok(hdde != NULL, "DdeNameService() failed le=%u\n", GetLastError());
288 ok(DdeFreeStringHandle(ddeInst, hszTopic), "DdeFreeStringHandle(topic)\n");
289 ok(DdeFreeStringHandle(ddeInst, hszApplication), "DdeFreeStringHandle(application)\n");
290 ok(DdeUninitialize(ddeInst), "DdeUninitialize() failed\n");
291 }
292 else
293 {
294 dde_ready = OpenEventA(EVENT_MODIFY_STATE, FALSE, "winetest_shlexec_dde_ready");
295 SetEvent(dde_ready);
296 CloseHandle(dde_ready);
297 }
298
299 UnmapViewOfFile(shared_block);
300
301 childPrintf(hFile, "ddeExec=%s\r\n", encodeA(ddeExec));
302 }
303
304 childPrintf(hFile, "Failures=%d\r\n", winetest_get_failures());
306
310}
static int argc
Definition: ServiceArgs.c:12
#define msg(x)
Definition: auth_time.c:54
Definition: _map.h:48
HSZ WINAPI DdeCreateStringHandleA(DWORD, LPCSTR, INT)
Definition: ddemisc.c:577
#define DNS_FILTEROFF
Definition: ddeml.h:155
#define CBF_FAIL_REQUESTS
Definition: ddeml.h:108
#define CBF_FAIL_POKES
Definition: ddeml.h:107
#define DNS_UNREGISTER
Definition: ddeml.h:153
#define DNS_REGISTER
Definition: ddeml.h:152
#define CBF_SKIP_ALLNOTIFICATIONS
Definition: ddeml.h:115
#define DMLERR_NO_ERROR
Definition: ddeml.h:242
BOOL WINAPI DdeUninitialize(DWORD)
Definition: ddemisc.c:1112
BOOL WINAPI DdeFreeStringHandle(DWORD, HSZ)
Definition: ddemisc.c:631
HDDEDATA WINAPI DdeNameService(DWORD, HSZ, HSZ, UINT)
Definition: ddeserver.c:154
#define CBF_FAIL_ADVISES
Definition: ddeml.h:105
UINT WINAPI DdeInitializeA(LPDWORD, PFNCALLBACK, DWORD, DWORD)
Definition: ddemisc.c:1075
#define UnmapViewOfFile
Definition: compat.h:746
#define SetLastError(x)
Definition: compat.h:752
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
#define CreateFileA(a, b, c, d, e, f, g)
Definition: compat.h:740
#define FILE_MAP_READ
Definition: compat.h:776
#define GetEnvironmentVariableA(x, y, z)
Definition: compat.h:754
#define MapViewOfFile
Definition: compat.h:745
HMODULE WINAPI DECLSPEC_HOTPATCH GetModuleHandleA(LPCSTR lpModuleName)
Definition: loader.c:812
DWORD WINAPI GetModuleFileNameA(HINSTANCE hModule, LPSTR lpFilename, DWORD nSize)
Definition: loader.c:539
LPSTR WINAPI GetCommandLineA(VOID)
Definition: proc.c:2003
HANDLE NTAPI OpenFileMappingA(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCSTR lpName)
Definition: filemap.c:284
GLuint buffer
Definition: glext.h:5915
#define CREATE_ALWAYS
Definition: disk.h:72
#define argv
Definition: mplay32.c:18
unsigned __int3264 UINT_PTR
Definition: mstsclib_h.h:274
_In_ HANDLE hFile
Definition: mswsock.h:90
unsigned int UINT
Definition: ndis.h:50
#define GENERIC_WRITE
Definition: nt_native.h:90
LONG winetest_get_failures(void)
static HDDEDATA CALLBACK ddeCb(UINT uType, UINT uFmt, HCONV hConv, HSZ hsz1, HSZ hsz2, HDDEDATA hData, ULONG_PTR dwData1, ULONG_PTR dwData2)
Definition: shlexec.c:153
#define CHILD_DDE_TIMEOUT
Definition: shlexec.c:146
static const char * encodeA(const char *str)
Definition: shlexec.c:67
static void CALLBACK childTimeout(HWND wnd, UINT msg, UINT_PTR timer, DWORD time)
Definition: shlexec.c:201
static void init_event(const char *child_file)
Definition: shlexec.c:190
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
BOOL WINAPI DECLSPEC_HOTPATCH SetEvent(IN HANDLE hEvent)
Definition: synch.c:733
HANDLE WINAPI DECLSPEC_HOTPATCH OpenEventA(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCSTR lpName)
Definition: synch.c:669
TW_UINT32 TW_UINT16 TW_UINT16 MSG
Definition: twain.h:1829
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
#define EVENT_MODIFY_STATE
Definition: winbase.h:163
LRESULT WINAPI DispatchMessageA(_In_ const MSG *)
UINT_PTR WINAPI SetTimer(_In_opt_ HWND, _In_ UINT_PTR, _In_ UINT, _In_opt_ TIMERPROC)
BOOL WINAPI KillTimer(_In_opt_ HWND, _In_ UINT_PTR)
BOOL WINAPI GetMessageA(_Out_ LPMSG, _In_opt_ HWND, _In_ UINT, _In_ UINT)

Referenced by START_TEST().

◆ dump_child_()

static void dump_child_ ( const char file,
int  line 
)
static

Definition at line 312 of file shlexec.c.

313{
314 if (winetest_debug > 1)
315 {
316 char key[18];
317 char* str;
318 int i, c;
319
320 str=getChildString("Child", "cmdlineA");
321 trace_(file, line)("cmdlineA='%s'\n", str);
322 c=GetPrivateProfileIntA("Child", "argcA", -1, child_file);
323 trace_(file, line)("argcA=%d\n",c);
324 for (i=0;i<c;i++)
325 {
326 sprintf(key, "argvA%d", i);
327 str=getChildString("Child", key);
328 trace_(file, line)("%s='%s'\n", key, str);
329 }
330
331 c=GetPrivateProfileIntA("Child", "ShlexecVarLE", -1, child_file);
332 trace_(file, line)("ShlexecVarLE=%d\n", c);
333 str=getChildString("Child", "ShlexecVar");
334 trace_(file, line)("ShlexecVar='%s'\n", str);
335
336 c=GetPrivateProfileIntA("Child", "Failures", -1, child_file);
337 trace_(file, line)("Failures=%d\n", c);
338 }
339}
UINT WINAPI GetPrivateProfileIntA(LPCSTR section, LPCSTR entry, INT def_val, LPCSTR filename)
Definition: profile.c:1326
#define c
Definition: ke_i.h:80
#define trace_(file, line,...)
Definition: kmt_test.h:223
static char * getChildString(const char *sect, const char *key)
Definition: shlexec.c:127
Definition: fci.c:127
Definition: copy.c:22
Definition: parser.c:49

Referenced by shell_execute_(), and shell_execute_ex_().

◆ encodeA()

static const char * encodeA ( const char str)
static

Definition at line 67 of file shlexec.c.

68{
69 static char encoded[2*1024+1];
70 char* ptr;
71 size_t len,i;
72
73 if (!str) return "";
74 len = strlen(str) + 1;
75 if (len >= sizeof(encoded)/2)
76 {
77 fprintf(stderr, "string is too long!\n");
78 assert(0);
79 }
80 ptr = encoded;
81 for (i = 0; i < len; i++)
82 sprintf(&ptr[i * 2], "%02x", (unsigned char)str[i]);
83 ptr[2 * len] = '\0';
84 return ptr;
85}

Referenced by doChild().

◆ get_long_path_name()

static DWORD get_long_path_name ( const char shortpath,
char longpath,
DWORD  longlen 
)
static

Definition at line 930 of file shlexec.c.

931{
932 char tmplongpath[MAX_PATH];
933 const char* p;
934 DWORD sp = 0, lp = 0;
935 DWORD tmplen;
937 HANDLE goit;
938
939 if (!shortpath || !shortpath[0])
940 return 0;
941
942 if (shortpath[1] == ':')
943 {
944 tmplongpath[0] = shortpath[0];
945 tmplongpath[1] = ':';
946 lp = sp = 2;
947 }
948
949 while (shortpath[sp])
950 {
951 /* check for path delimiters and reproduce them */
952 if (shortpath[sp] == '\\' || shortpath[sp] == '/')
953 {
954 if (!lp || tmplongpath[lp-1] != '\\')
955 {
956 /* strip double "\\" */
957 tmplongpath[lp++] = '\\';
958 }
959 tmplongpath[lp] = 0; /* terminate string */
960 sp++;
961 continue;
962 }
963
964 p = shortpath + sp;
965 if (sp == 0 && p[0] == '.' && (p[1] == '/' || p[1] == '\\'))
966 {
967 tmplongpath[lp++] = *p++;
968 tmplongpath[lp++] = *p++;
969 }
970 for (; *p && *p != '/' && *p != '\\'; p++);
971 tmplen = p - (shortpath + sp);
972 lstrcpynA(tmplongpath + lp, shortpath + sp, tmplen + 1);
973 /* Check if the file exists and use the existing file name */
974 goit = FindFirstFileA(tmplongpath, &wfd);
975 if (goit == INVALID_HANDLE_VALUE)
976 return 0;
977 FindClose(goit);
978 strcpy(tmplongpath + lp, wfd.cFileName);
979 lp += strlen(tmplongpath + lp);
980 sp += tmplen;
981 }
982 tmplen = strlen(shortpath) - 1;
983 if ((shortpath[tmplen] == '/' || shortpath[tmplen] == '\\') &&
984 (tmplongpath[lp - 1] != '/' && tmplongpath[lp - 1] != '\\'))
985 tmplongpath[lp++] = shortpath[tmplen];
986 tmplongpath[lp] = 0;
987
988 tmplen = strlen(tmplongpath) + 1;
989 if (tmplen <= longlen)
990 {
991 strcpy(longpath, tmplongpath);
992 tmplen--; /* length without 0 */
993 }
994
995 return tmplen;
996}
#define lstrcpynA
Definition: compat.h:751
HANDLE WINAPI FindFirstFileA(IN LPCSTR lpFileName, OUT LPWIN32_FIND_DATAA lpFindFileData)
Definition: find.c:263
BOOL WINAPI FindClose(HANDLE hFindFile)
Definition: find.c:502
GLfloat GLfloat p
Definition: glext.h:8902
static char shortpath[MAX_PATH]
Definition: batch.c:32
static const WCHAR sp[]
Definition: suminfo.c:287

Referenced by test_fileurls(), and test_lnks().

◆ getChildString()

static char * getChildString ( const char sect,
const char key 
)
static

Definition at line 127 of file shlexec.c.

128{
129 char buf[1024];
130 char* ret;
131
132 GetPrivateProfileStringA(sect, key, "-", buf, sizeof(buf), child_file);
133 if (buf[0] == '\0' || (buf[0] == '-' && buf[1] == '\0')) return NULL;
134 assert(!(strlen(buf) & 1));
135 ret = decodeA(buf);
136 return ret;
137}
INT WINAPI GetPrivateProfileStringA(LPCSTR section, LPCSTR entry, LPCSTR def_val, LPSTR buffer, UINT len, LPCSTR filename)
Definition: profile.c:1204
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
static char * decodeA(const char *str)
Definition: shlexec.c:95
int ret

Referenced by dump_child_(), okChildPath_(), okChildString_(), and test_argify().

◆ hook_WaitForInputIdle()

static void hook_WaitForInputIdle ( DWORD(WINAPI *new_func)(HANDLE, DWORD )
static

Definition at line 2321 of file shlexec.c.

2322{
2323 char *base;
2324 PIMAGE_NT_HEADERS nt_headers;
2325 DWORD import_directory_rva;
2326 PIMAGE_IMPORT_DESCRIPTOR import_descriptor;
2327 int hook_count = 0;
2328
2329 base = (char *) GetModuleHandleA("shell32.dll");
2330 nt_headers = (PIMAGE_NT_HEADERS)(base + ((PIMAGE_DOS_HEADER) base)->e_lfanew);
2331 import_directory_rva = nt_headers->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
2332
2333 /* Search for the correct imported module by walking the import descriptors */
2334 import_descriptor = (PIMAGE_IMPORT_DESCRIPTOR)(base + import_directory_rva);
2335 while (U(*import_descriptor).OriginalFirstThunk != 0)
2336 {
2337 char *import_module_name;
2338
2339 import_module_name = base + import_descriptor->Name;
2340 if (lstrcmpiA(import_module_name, "user32.dll") == 0 ||
2341 lstrcmpiA(import_module_name, "user32") == 0)
2342 {
2343 PIMAGE_THUNK_DATA int_entry;
2344 PIMAGE_THUNK_DATA iat_entry;
2345
2346 /* The import name table and import address table are two parallel
2347 * arrays. We need the import name table to find the imported
2348 * routine and the import address table to patch the address, so
2349 * walk them side by side */
2350 int_entry = (PIMAGE_THUNK_DATA)(base + U(*import_descriptor).OriginalFirstThunk);
2351 iat_entry = (PIMAGE_THUNK_DATA)(base + import_descriptor->FirstThunk);
2352 while (int_entry->u1.Ordinal != 0)
2353 {
2354 if (! IMAGE_SNAP_BY_ORDINAL(int_entry->u1.Ordinal))
2355 {
2356 PIMAGE_IMPORT_BY_NAME import_by_name;
2357 import_by_name = (PIMAGE_IMPORT_BY_NAME)(base + int_entry->u1.AddressOfData);
2358 if (lstrcmpA((char *) import_by_name->Name, "WaitForInputIdle") == 0)
2359 {
2360 /* Found the correct routine in the correct imported module. Patch it. */
2361 DWORD old_prot;
2362 VirtualProtect(&iat_entry->u1.Function, sizeof(ULONG_PTR), PAGE_READWRITE, &old_prot);
2363 iat_entry->u1.Function = (ULONG_PTR) new_func;
2364 VirtualProtect(&iat_entry->u1.Function, sizeof(ULONG_PTR), old_prot, &old_prot);
2365 if (winetest_debug > 1)
2366 trace("Hooked %s.WaitForInputIdle\n", import_module_name);
2367 hook_count++;
2368 break;
2369 }
2370 }
2371 int_entry++;
2372 iat_entry++;
2373 }
2374 break;
2375 }
2376
2377 import_descriptor++;
2378 }
2379 ok(hook_count, "Could not hook WaitForInputIdle()\n");
2380}
#define U(x)
Definition: wordpad.c:45
#define ULONG_PTR
Definition: config.h:101
PIMAGE_NT_HEADERS32 PIMAGE_NT_HEADERS
Definition: ntddk_ex.h:187
int WINAPI lstrcmpiA(LPCSTR lpString1, LPCSTR lpString2)
Definition: lstring.c:42
int WINAPI lstrcmpA(LPCSTR lpString1, LPCSTR lpString2)
Definition: lstring.c:18
DWORD e_lfanew
Definition: crypt.c:1156
#define PAGE_READWRITE
Definition: nt_native.h:1304
struct _IMAGE_IMPORT_DESCRIPTOR * PIMAGE_IMPORT_DESCRIPTOR
#define IMAGE_SNAP_BY_ORDINAL(Ordinal)
Definition: ntimage.h:567
PIMAGE_THUNK_DATA32 PIMAGE_THUNK_DATA
Definition: ntimage.h:566
#define IMAGE_DIRECTORY_ENTRY_IMPORT
Definition: pedump.c:260
struct _IMAGE_IMPORT_BY_NAME * PIMAGE_IMPORT_BY_NAME
IMAGE_OPTIONAL_HEADER32 OptionalHeader
Definition: ntddk_ex.h:184
IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES]
Definition: ntddk_ex.h:178
union _IMAGE_THUNK_DATA32::@2129 u1
uint32_t ULONG_PTR
Definition: typedefs.h:65
BOOL NTAPI VirtualProtect(IN LPVOID lpAddress, IN SIZE_T dwSize, IN DWORD flNewProtect, OUT PDWORD lpflOldProtect)
Definition: virtmem.c:135

Referenced by test_dde().

◆ hooked_WaitForInputIdle()

static DWORD WINAPI hooked_WaitForInputIdle ( HANDLE  process,
DWORD  timeout 
)
static

Definition at line 2303 of file shlexec.c.

2304{
2306 if (winetest_debug > 1)
2307 trace("WaitForInputIdle() waiting for dde event timeout=min(%u,5s)\n", timeout);
2308 timeout = timeout < 5000 ? timeout : 5000;
2310}
static HANDLE dde_ready_event
Definition: shlexec.c:57
static int waitforinputidle_count
Definition: shlexec.c:2302
Definition: dhcpd.h:245
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
Definition: synch.c:82

Referenced by test_dde().

◆ init_event()

static void init_event ( const char child_file)
static

Definition at line 190 of file shlexec.c.

191{
192 char* event_name;
193 event_name=strrchr(child_file, '\\')+1;
194 hEvent=CreateEventA(NULL, FALSE, FALSE, event_name);
195}
_Check_return_ _CRTIMP _CONST_RETURN char *__cdecl strrchr(_In_z_ const char *_Str, _In_ int _Ch)
HANDLE WINAPI DECLSPEC_HOTPATCH CreateEventA(IN LPSECURITY_ATTRIBUTES lpEventAttributes OPTIONAL, IN BOOL bManualReset, IN BOOL bInitialState, IN LPCSTR lpName OPTIONAL)
Definition: synch.c:637

Referenced by doChild(), and init_test().

◆ init_test()

static void init_test ( void  )
static

Definition at line 2649 of file shlexec.c.

2650{
2651 HMODULE hdll;
2652 HRESULT (WINAPI *pDllGetVersion)(DLLVERSIONINFO*);
2653 char filename[MAX_PATH];
2654 WCHAR lnkfile[MAX_PATH];
2655 char params[1024];
2656 const char* const * testfile;
2658 DWORD rc;
2659 HRESULT r;
2660
2661 hdll=GetModuleHandleA("shell32.dll");
2662 pDllGetVersion=(void*)GetProcAddress(hdll, "DllGetVersion");
2663 if (pDllGetVersion)
2664 {
2665 dllver.cbSize=sizeof(dllver);
2666 pDllGetVersion(&dllver);
2667 trace("major=%d minor=%d build=%d platform=%d\n",
2670 }
2671 else
2672 {
2673 memset(&dllver, 0, sizeof(dllver));
2674 }
2675
2676 r = CoInitialize(NULL);
2677 ok(r == S_OK, "CoInitialize failed (0x%08x)\n", r);
2678 if (FAILED(r))
2679 exit(1);
2680
2681 rc=GetModuleFileNameA(NULL, argv0, sizeof(argv0));
2682 ok(rc != 0 && rc < sizeof(argv0), "got %d\n", rc);
2684 {
2685 strcat(argv0, ".so");
2687 "unable to find argv0!\n");
2688 }
2689
2690 /* Older versions (win 2k) fail tests if there is a space in
2691 the path. */
2692 if (dllver.dwMajorVersion <= 5)
2693 strcpy(filename, "c:\\");
2694 else
2695 GetTempPathA(sizeof(filename), filename);
2696 GetTempFileNameA(filename, "wt", 0, tmpdir);
2699 rc = CreateDirectoryA( tmpdir, NULL );
2700 ok( rc, "failed to create %s err %u\n", tmpdir, GetLastError() );
2701 /* Set %TMPDIR% for the tests */
2703
2704 rc = GetTempFileNameA(tmpdir, "wt", 0, child_file);
2705 ok(rc != 0, "got %d\n", rc);
2707
2708 /* Set up the test files */
2709 testfile=testfiles;
2710 while (*testfile)
2711 {
2712 HANDLE hfile;
2713
2714 sprintf(filename, *testfile, tmpdir);
2717 if (hfile==INVALID_HANDLE_VALUE)
2718 {
2719 trace("unable to create '%s': err=%u\n", filename, GetLastError());
2720 assert(0);
2721 }
2722 CloseHandle(hfile);
2723 testfile++;
2724 }
2725
2726 /* Setup the test shortcuts */
2727 sprintf(filename, "%s\\test_shortcut_shlexec.lnk", tmpdir);
2728 MultiByteToWideChar(CP_ACP, 0, filename, -1, lnkfile, ARRAY_SIZE(lnkfile));
2729 desc.description=NULL;
2730 desc.workdir=NULL;
2731 sprintf(filename, "%s\\test file.shlexec", tmpdir);
2732 desc.path=filename;
2733 desc.pidl=NULL;
2734 desc.arguments="ignored";
2735 desc.showcmd=0;
2736 desc.icon=NULL;
2737 desc.icon_id=0;
2738 desc.hotkey=0;
2739 create_lnk(lnkfile, &desc, 0);
2740
2741 sprintf(filename, "%s\\test_shortcut_exe.lnk", tmpdir);
2742 MultiByteToWideChar(CP_ACP, 0, filename, -1, lnkfile, ARRAY_SIZE(lnkfile));
2743 desc.description=NULL;
2744 desc.workdir=NULL;
2745 desc.path=argv0;
2746 desc.pidl=NULL;
2747 sprintf(params, "shlexec \"%s\" Lnk", child_file);
2748 desc.arguments=params;
2749 desc.showcmd=0;
2750 desc.icon=NULL;
2751 desc.icon_id=0;
2752 desc.hotkey=0;
2753 create_lnk(lnkfile, &desc, 0);
2754
2755 /* Create a basic association suitable for most tests */
2756 if (!create_test_association(".shlexec"))
2757 {
2759 skip("Unable to create association for '.shlexec'\n");
2760 return;
2761 }
2762 create_test_verb("shlexec.shlexec", "Open", 0, "Open \"%1\"");
2763 create_test_verb("shlexec.shlexec", "NoQuotes", 0, "NoQuotes %1");
2764 create_test_verb("shlexec.shlexec", "LowerL", 0, "LowerL %l");
2765 create_test_verb("shlexec.shlexec", "QuotedLowerL", 0, "QuotedLowerL \"%l\"");
2766 create_test_verb("shlexec.shlexec", "UpperL", 0, "UpperL %L");
2767 create_test_verb("shlexec.shlexec", "QuotedUpperL", 0, "QuotedUpperL \"%L\"");
2768
2770 create_test_verb("shlexec.sha", "averb", 0, "AVerb \"%1\"");
2771
2772 create_test_class("shlproto", TRUE);
2773 create_test_verb("shlproto", "open", 0, "URL \"%1\"");
2774 create_test_verb("shlproto", "averb", 0, "AVerb \"%1\"");
2775
2776 /* Set an environment variable to see if it is inherited */
2777 SetEnvironmentVariableA("ShlexecVar", "Present");
2778}
char * strcat(char *DstString, const char *SrcString)
Definition: utclib.c:568
#define skip(...)
Definition: atltest.h:64
#define ARRAY_SIZE(A)
Definition: main.h:33
#define CP_ACP
Definition: compat.h:109
#define GetProcAddress(x, y)
Definition: compat.h:753
#define MultiByteToWideChar
Definition: compat.h:110
BOOL WINAPI DECLSPEC_HOTPATCH SetEnvironmentVariableA(IN LPCSTR lpName, IN LPCSTR lpValue)
Definition: environ.c:218
BOOL WINAPI CreateDirectoryA(IN LPCSTR lpPathName, IN LPSECURITY_ATTRIBUTES lpSecurityAttributes)
Definition: dir.c:37
DWORD WINAPI GetFileAttributesA(LPCSTR lpFileName)
Definition: fileinfo.c:636
DWORD WINAPI GetLongPathNameA(IN LPCSTR lpszShortPath, OUT LPSTR lpszLongPath, IN DWORD cchBuffer)
Definition: path.c:1671
DWORD WINAPI GetTempPathA(IN DWORD nBufferLength, OUT LPSTR lpBuffer)
Definition: path.c:2054
HRESULT WINAPI CoInitialize(LPVOID lpReserved)
Definition: compobj.c:1964
UINT WINAPI GetTempFileNameA(IN LPCSTR lpPathName, IN LPCSTR lpPrefixString, IN UINT uUnique, OUT LPSTR lpTempFileName)
Definition: filename.c:26
GLdouble GLdouble GLdouble r
Definition: gl.h:2055
GLenum const GLfloat * params
Definition: glext.h:5645
#define S_OK
Definition: intsafe.h:52
#define FAILED(hr)
Definition: intsafe.h:51
static const WCHAR desc[]
Definition: protectdata.c:36
#define exit(n)
Definition: config.h:202
#define memset(x, y, z)
Definition: compat.h:39
#define create_lnk(a, b, c)
Definition: shell32_test.h:37
static PVOID hdll
Definition: shimdbg.c:126
static void create_test_verb(const char *classname, const char *verb, int rawcmd, const char *cmdtail)
Definition: shlexec.c:915
static DLLVERSIONINFO dllver
Definition: shlexec.c:54
static BOOL skip_shlexec_tests
Definition: shlexec.c:55
static BOOL create_test_association(const char *extension)
Definition: shlexec.c:712
DWORD dwMajorVersion
Definition: shlwapi.h:1955
DWORD dwBuildNumber
Definition: shlwapi.h:1957
DWORD dwMinorVersion
Definition: shlwapi.h:1956
DWORD dwPlatformID
Definition: shlwapi.h:1958
#define INVALID_FILE_ATTRIBUTES
Definition: vfdcmd.c:23
#define HRESULT
Definition: msvc.h:7
#define WINAPI
Definition: msvc.h:6
__wchar_t WCHAR
Definition: xmlstorage.h:180

Referenced by START_TEST(), test_binding(), test_create_element(), test_CreateBinding(), test_editing_mode(), test_event_binding(), test_file_protocol(), test_flash_ax(), test_ftp_protocol(), test_HTMLDocument(), test_HTMLDocument_hlink(), test_HTMLDocument_http(), test_HTMLDocument_StreamInitNew(), test_HTMLDocument_StreamLoad(), test_http_protocol_url(), test_mk_protocol(), test_nooleobj_ax(), test_noquickact_ax(), test_submit(), and test_UIActivate().

◆ myRegDeleteTreeA()

static LSTATUS myRegDeleteTreeA ( HKEY  hKey,
LPCSTR  lpszSubKey 
)
static

Definition at line 734 of file shlexec.c.

735{
736 LONG ret;
737 DWORD dwMaxSubkeyLen, dwMaxValueLen;
738 DWORD dwMaxLen, dwSize;
739 CHAR szNameBuf[MAX_PATH], *lpszName = szNameBuf;
740 HKEY hSubKey = hKey;
741
742 if(lpszSubKey)
743 {
744 ret = RegOpenKeyExA(hKey, lpszSubKey, 0, KEY_READ, &hSubKey);
745 if (ret) return ret;
746 }
747
748 /* Get highest length for keys, values */
749 ret = RegQueryInfoKeyA(hSubKey, NULL, NULL, NULL, NULL,
750 &dwMaxSubkeyLen, NULL, NULL, &dwMaxValueLen, NULL, NULL, NULL);
751 if (ret) goto cleanup;
752
753 dwMaxSubkeyLen++;
754 dwMaxValueLen++;
755 dwMaxLen = max(dwMaxSubkeyLen, dwMaxValueLen);
756 if (dwMaxLen > ARRAY_SIZE(szNameBuf))
757 {
758 /* Name too big: alloc a buffer for it */
759 if (!(lpszName = heap_alloc(dwMaxLen*sizeof(CHAR))))
760 {
762 goto cleanup;
763 }
764 }
765
766
767 /* Recursively delete all the subkeys */
768 while (TRUE)
769 {
770 dwSize = dwMaxLen;
771 if (RegEnumKeyExA(hSubKey, 0, lpszName, &dwSize, NULL,
772 NULL, NULL, NULL)) break;
773
774 ret = myRegDeleteTreeA(hSubKey, lpszName);
775 if (ret) goto cleanup;
776 }
777
778 if (lpszSubKey)
779 ret = RegDeleteKeyA(hKey, lpszSubKey);
780 else
781 while (TRUE)
782 {
783 dwSize = dwMaxLen;
784 if (RegEnumValueA(hKey, 0, lpszName, &dwSize,
785 NULL, NULL, NULL, NULL)) break;
786
787 ret = RegDeleteValueA(hKey, lpszName);
788 if (ret) goto cleanup;
789 }
790
791cleanup:
792 /* Free buffer if allocated */
793 if (lpszName != szNameBuf)
794 heap_free(lpszName);
795 if(lpszSubKey)
796 RegCloseKey(hSubKey);
797 return ret;
798}
#define RegCloseKey(hKey)
Definition: registry.h:49
#define ERROR_NOT_ENOUGH_MEMORY
Definition: dderror.h:7
LONG WINAPI RegQueryInfoKeyA(HKEY hKey, LPSTR lpClass, LPDWORD lpcClass, LPDWORD lpReserved, LPDWORD lpcSubKeys, LPDWORD lpcMaxSubKeyLen, LPDWORD lpcMaxClassLen, LPDWORD lpcValues, LPDWORD lpcMaxValueNameLen, LPDWORD lpcMaxValueLen, LPDWORD lpcbSecurityDescriptor, PFILETIME lpftLastWriteTime)
Definition: reg.c:3612
LONG WINAPI RegEnumValueA(_In_ HKEY hKey, _In_ DWORD dwIndex, _Out_ LPSTR lpName, _Inout_ LPDWORD lpcbName, _Reserved_ LPDWORD lpdwReserved, _Out_opt_ LPDWORD lpdwType, _Out_opt_ LPBYTE lpData, _Inout_opt_ LPDWORD lpcbData)
Definition: reg.c:2697
LONG WINAPI RegDeleteValueA(HKEY hKey, LPCSTR lpValueName)
Definition: reg.c:2325
LONG WINAPI RegEnumKeyExA(_In_ HKEY hKey, _In_ DWORD dwIndex, _Out_ LPSTR lpName, _Inout_ LPDWORD lpcbName, _Reserved_ LPDWORD lpReserved, _Out_opt_ LPSTR lpClass, _Inout_opt_ LPDWORD lpcbClass, _Out_opt_ PFILETIME lpftLastWriteTime)
Definition: reg.c:2448
LONG WINAPI RegDeleteKeyA(_In_ HKEY hKey, _In_ LPCSTR lpSubKey)
Definition: reg.c:1224
static void cleanup(void)
Definition: main.c:1335
FxAutoRegKey hKey
PSDBQUERYRESULT_VISTA PVOID DWORD * dwSize
Definition: env.c:56
#define KEY_READ
Definition: nt_native.h:1023
#define max(a, b)
Definition: svc.c:63
char CHAR
Definition: xmlstorage.h:175

Referenced by delete_test_association(), delete_test_class(), and myRegDeleteTreeA().

◆ okChildInt_()

static void okChildInt_ ( const char file,
int  line,
const char key,
int  expected 
)
static

Definition at line 453 of file shlexec.c.

454{
455 INT result;
458 "%s expected %d, but got %d\n", key, expected, result);
459}
GLuint64EXT * result
Definition: glext.h:11304
BOOL expected
Definition: store.c:2063
#define okShell_(file, line)
Definition: shlexec.c:361
int32_t INT
Definition: typedefs.h:58

Referenced by shell_execute_(), and shell_execute_ex_().

◆ okChildIntBroken_()

static void okChildIntBroken_ ( const char file,
int  line,
const char key,
int  expected 
)
static

Definition at line 462 of file shlexec.c.

463{
464 INT result;
467 "%s expected %d, but got %d\n", key, expected, result);
468}
#define broken(x)
Definition: _sntprintf.h:21

◆ okChildPath_()

static void okChildPath_ ( const char file,
int  line,
const char key,
const char expected 
)
static

Definition at line 423 of file shlexec.c.

424{
425 char* result;
426 int equal, shortequal;
427 result=getChildString("Child", key);
428 if (!result)
429 {
430 okShell_(file,line)(FALSE, "%s expected '%s', but key not found or empty\n", key, expected);
431 return;
432 }
433 shortequal = FALSE;
434 equal = (StrCmpPath(result, expected) == 0);
435 if (!equal)
436 {
437 char altpath[MAX_PATH];
438 DWORD rc = GetLongPathNameA(expected, altpath, sizeof(altpath));
439 if (0 < rc && rc < sizeof(altpath))
440 equal = (StrCmpPath(result, altpath) == 0);
441 if (!equal)
442 {
443 rc = GetShortPathNameA(expected, altpath, sizeof(altpath));
444 if (0 < rc && rc < sizeof(altpath))
445 shortequal = (StrCmpPath(result, altpath) == 0);
446 }
447 }
448 okShell_(file,line)(equal || broken(shortequal) /* XP SP1 */,
449 "%s expected '%s', got '%s'\n", key, expected, result);
450}
DWORD WINAPI GetShortPathNameA(IN LPCSTR lpszLongPath, OUT LPSTR lpszShortPath, IN DWORD cchBuffer)
Definition: path.c:1752
#define equal(x, y)
Definition: reader.cc:56
static int StrCmpPath(const char *s1, const char *s2)
Definition: shlexec.c:386

◆ okChildString_()

static void okChildString_ ( const char file,
int  line,
const char key,
const char expected,
const char bad 
)
static

Definition at line 370 of file shlexec.c.

371{
372 char* result;
373 result=getChildString("Child", key);
374 if (!result)
375 {
376 okShell_(file, line)(FALSE, "%s expected '%s', but key not found or empty\n", key, expected);
377 return;
378 }
380 broken(lstrcmpiA(result, bad) == 0),
381 "%s expected '%s', got '%s'\n", key, expected, result);
382}

Referenced by shell_execute_(), and shell_execute_ex_().

◆ reset_association_description()

static void reset_association_description ( void  )
static

Definition at line 365 of file shlexec.c.

366{
367 *assoc_desc = '\0';
368}

Referenced by create_test_verb(), test_dde(), and test_dde_default_app().

◆ shell_execute_()

static INT_PTR shell_execute_ ( const char file,
int  line,
LPCSTR  verb,
LPCSTR  filename,
LPCSTR  parameters,
LPCSTR  directory 
)
static

Definition at line 496 of file shlexec.c.

497{
498 INT_PTR rc, rcEmpty = 0;
499
500 if(!verb)
501 rcEmpty = shell_execute_(file, line, "", filename, parameters, directory);
502
503 strcpy(shell_call, "ShellExecute(");
504 strcat_param(shell_call, "verb", verb);
506 strcat_param(shell_call, "params", parameters);
508 strcat(shell_call, ")");
510 if (winetest_debug > 1)
511 trace_(file, line)("Called %s\n", shell_call);
512
514 SetLastError(0xcafebabe);
515
516 /* FIXME: We cannot use ShellExecuteEx() here because if there is no
517 * association it displays the 'Open With' dialog and I could not find
518 * a flag to prevent this.
519 */
520 rc=(INT_PTR)ShellExecuteA(NULL, verb, filename, parameters, directory, SW_HIDE);
521
522 if (rc > 32)
523 {
524 int wait_rc;
525 wait_rc=WaitForSingleObject(hEvent, 5000);
526 if (wait_rc == WAIT_TIMEOUT)
527 {
528 HWND wnd = FindWindowA("#32770", "Windows");
529 if (!wnd)
530 wnd = FindWindowA("Shell_Flyout", "");
531 if (wnd != NULL)
532 {
533 SendMessageA(wnd, WM_CLOSE, 0, 0);
534 win_skip("Skipping shellexecute of file with unassociated extension\n");
536 rc = SE_ERR_NOASSOC;
537 }
538 }
540 okShell_(file, line)(wait_rc==WAIT_OBJECT_0 || rc <= 32,
541 "WaitForSingleObject returned %d\n", wait_rc);
542 }
543 /* The child process may have changed the result file, so let profile
544 * functions know about it
545 */
548 {
549 int c;
551 c = GetPrivateProfileIntA("Child", "Failures", -1, child_file);
552 if (c > 0)
554 okChildInt_(file, line, "ShlexecVarLE", 0);
555 okChildString_(file, line, "ShlexecVar", "Present", "Present");
556 }
557
558 if(!verb)
559 {
560 if (rc != rcEmpty && rcEmpty == SE_ERR_NOASSOC) /* NT4 */
562 okShell_(file, line)(rc == rcEmpty ||
563 broken(rc != rcEmpty && rcEmpty == SE_ERR_NOASSOC) /* NT4 */,
564 "Got different return value with empty string: %lu %lu\n", rc, rcEmpty);
565 }
566
567 return rc;
568}
#define WAIT_TIMEOUT
Definition: dderror.h:14
BOOL WINAPI DECLSPEC_HOTPATCH WritePrivateProfileStringA(LPCSTR section, LPCSTR entry, LPCSTR string, LPCSTR filename)
Definition: profile.c:1484
#define todo_wine_if(is_todo)
Definition: custom.c:76
#define win_skip
Definition: test.h:160
void winetest_add_failures(LONG new_failures)
#define SE_ERR_NOASSOC
Definition: shellapi.h:132
static void dump_child_(const char *file, int line)
Definition: shlexec.c:312
static void okChildInt_(const char *file, int line, const char *key, int expected)
Definition: shlexec.c:453
static int bad_shellexecute
Definition: shlexec.c:494
static int _todo_wait
Definition: shlexec.c:491
static char shell_call[2048]
Definition: shlexec.c:348
static INT_PTR shell_execute_(const char *file, int line, LPCSTR verb, LPCSTR filename, LPCSTR parameters, LPCSTR directory)
Definition: shlexec.c:496
static void okChildString_(const char *file, int line, const char *key, const char *expected, const char *bad)
Definition: shlexec.c:370
static BOOL skip_noassoc_tests
Definition: shlexec.c:56
HINSTANCE WINAPI ShellExecuteA(HWND hWnd, LPCSTR lpVerb, LPCSTR lpFile, LPCSTR lpParameters, LPCSTR lpDirectory, INT iShowCmd)
Definition: shlexec.cpp:2284
int32_t INT_PTR
Definition: typedefs.h:64
#define WAIT_OBJECT_0
Definition: winbase.h:406
#define SW_HIDE
Definition: winuser.h:768
#define WM_CLOSE
Definition: winuser.h:1621
LRESULT WINAPI SendMessageA(_In_ HWND, _In_ UINT, _In_ WPARAM, _In_ LPARAM)
HWND WINAPI FindWindowA(_In_opt_ LPCSTR, _In_opt_ LPCSTR)

Referenced by shell_execute_().

◆ shell_execute_ex_()

static INT_PTR shell_execute_ex_ ( const char file,
int  line,
DWORD  mask,
LPCSTR  verb,
LPCSTR  filename,
LPCSTR  parameters,
LPCSTR  directory,
LPCSTR  class 
)
static

Definition at line 572 of file shlexec.c.

576{
577 char smask[11];
580 INT_PTR rc;
581
582 /* Add some flags so we can wait for the child process */
584
585 strcpy(shell_call, "ShellExecuteEx(");
586 sprintf(smask, "0x%x", mask);
587 strcat_param(shell_call, "mask", smask);
588 strcat_param(shell_call, "verb", verb);
590 strcat_param(shell_call, "params", parameters);
592 strcat_param(shell_call, "class", class);
593 strcat(shell_call, ")");
595 if (winetest_debug > 1)
596 trace_(file, line)("Called %s\n", shell_call);
597
598 sei.cbSize=sizeof(sei);
599 sei.fMask=mask;
600 sei.hwnd=NULL;
601 sei.lpVerb=verb;
602 sei.lpFile=filename;
603 sei.lpParameters=parameters;
606 sei.hInstApp=NULL; /* Out */
607 sei.lpIDList=NULL;
608 sei.lpClass=class;
609 sei.hkeyClass=NULL;
610 sei.dwHotKey=0;
611 U(sei).hIcon=NULL;
612 sei.hProcess=(HANDLE)0xdeadbeef; /* Out */
613
615 SetLastError(0xcafebabe);
617 rc=(INT_PTR)sei.hInstApp;
618 okShell_(file, line)((success && rc > 32) || (!success && rc <= 32),
619 "rc=%d and hInstApp=%ld is not allowed\n",
620 success, rc);
621
622 if (rc > 32)
623 {
624 DWORD wait_rc, rc;
625 if (sei.hProcess!=NULL)
626 {
627 wait_rc=WaitForSingleObject(sei.hProcess, 5000);
628 okShell_(file, line)(wait_rc==WAIT_OBJECT_0,
629 "WaitForSingleObject(hProcess) returned %d\n",
630 wait_rc);
631 wait_rc = GetExitCodeProcess(sei.hProcess, &rc);
632 okShell_(file, line)(wait_rc, "GetExitCodeProcess() failed le=%u\n", GetLastError());
634 okShell_(file, line)(rc == 0, "child returned %u\n", rc);
636 }
637 wait_rc=WaitForSingleObject(hEvent, 5000);
639 okShell_(file, line)(wait_rc==WAIT_OBJECT_0,
640 "WaitForSingleObject returned %d\n", wait_rc);
641 }
642 else
644 "returned a process handle %p\n", sei.hProcess);
645
646 /* The child process may have changed the result file, so let profile
647 * functions know about it
648 */
651 {
652 int c;
654 c = GetPrivateProfileIntA("Child", "Failures", -1, child_file);
655 if (c > 0)
657 /* When NOZONECHECKS is specified the environment variables are not
658 * inherited if the process does not have elevated privileges.
659 */
661 {
662 okChildInt_(file, line, "ShlexecVarLE", 203);
663 okChildString_(file, line, "ShlexecVar", "", "");
664 }
665 else
666 {
667 okChildInt_(file, line, "ShlexecVarLE", 0);
668 okChildString_(file, line, "ShlexecVar", "Present", "Present");
669 }
670 }
671
672 return rc;
673}
BOOL WINAPI GetExitCodeProcess(IN HANDLE hProcess, IN LPDWORD lpExitCode)
Definition: proc.c:1168
unsigned int BOOL
Definition: ntddk_ex.h:94
GLenum GLint GLuint mask
Definition: glext.h:6028
#define SEE_MASK_NOCLOSEPROCESS
Definition: shellapi.h:31
#define SEE_MASK_NOZONECHECKS
Definition: shellapi.h:54
#define SEE_MASK_NO_CONSOLE
Definition: shellapi.h:38
BOOL WINAPI DECLSPEC_HOTPATCH ShellExecuteExA(LPSHELLEXECUTEINFOA sei)
Definition: shlexec.cpp:2318
LPCSTR lpParameters
Definition: shellapi.h:313
HINSTANCE hInstApp
Definition: shellapi.h:316
LPCSTR lpDirectory
Definition: shellapi.h:314
PVOID HANDLE
Definition: typedefs.h:73
#define success(from, fromstr, to, tostr)
#define SW_SHOWNORMAL
Definition: winuser.h:770

◆ START_TEST()

START_TEST ( shlexec  )

Definition at line 2861 of file shlexec.c.

2862{
2863
2865 if (myARGC >= 3)
2866 {
2868 /* Skip the tests/failures trace for child processes */
2870 }
2871
2872 init_test();
2873
2875 test_argify();
2877 test_filename();
2878 test_fileurls();
2879 test_urls();
2881 test_lnks();
2882 test_exes();
2883 test_dde();
2886
2887 cleanup_test();
2888}
VOID WINAPI ExitProcess(IN UINT uExitCode)
Definition: proc.c:1487
int winetest_get_mainargs(char ***pargv)
static void test_urls(void)
Definition: shlexec.c:1869
static void test_dde_default_app(void)
Definition: shlexec.c:2549
static void test_find_executable(void)
Definition: shlexec.c:1963
static void test_dde(void)
Definition: shlexec.c:2382
static void test_directory(void)
Definition: shlexec.c:2808
static void test_commandline2argv(void)
Definition: shlexec.c:1359
static void test_exes(void)
Definition: shlexec.c:2204
static void test_lnks(void)
Definition: shlexec.c:2110
static int myARGC
Definition: shlexec.c:50
static void test_filename(void)
Definition: shlexec.c:1603
static void test_fileurls(void)
Definition: shlexec.c:1786
static void init_test(void)
Definition: shlexec.c:2649
static char ** myARGV
Definition: shlexec.c:51
static void test_argify(void)
Definition: shlexec.c:1545
static void doChild(int argc, char **argv)
Definition: shlexec.c:208
static void cleanup_test(void)
Definition: shlexec.c:2780
static void test_lpFile_parsed(void)
Definition: shlexec.c:1092

◆ strcat_param()

static void strcat_param ( char str,
const char name,
const char param 
)
static

Definition at line 478 of file shlexec.c.

479{
480 if (param)
481 {
482 if (str[strlen(str)-1] == '"')
483 strcat(str, ", ");
484 strcat(str, name);
485 strcat(str, "=\"");
486 strcat(str, param);
487 strcat(str, "\"");
488 }
489}
GLfloat param
Definition: glext.h:5796
Definition: name.c:39

Referenced by create_test_verb_dde(), shell_execute_(), and shell_execute_ex_().

◆ StrCmpPath()

static int StrCmpPath ( const char s1,
const char s2 
)
static

Definition at line 386 of file shlexec.c.

387{
388 if (!s1 && !s2) return 0;
389 if (!s2) return 1;
390 if (!s1) return -1;
391 while (*s1)
392 {
393 if (!*s2)
394 {
395 if (*s1=='.')
396 s1++;
397 return (*s1-*s2);
398 }
399 if ((*s1=='/' || *s1=='\\') && (*s2=='/' || *s2=='\\'))
400 {
401 while (*s1=='/' || *s1=='\\')
402 s1++;
403 while (*s2=='/' || *s2=='\\')
404 s2++;
405 }
406 else if (toupper(*s1)==toupper(*s2))
407 {
408 s1++;
409 s2++;
410 }
411 else
412 {
413 return (*s1-*s2);
414 }
415 }
416 if (*s2=='.')
417 s2++;
418 if (*s2)
419 return -1;
420 return 0;
421}
int toupper(int c)
Definition: utclib.c:881
struct S1 s1
struct S2 s2

Referenced by okChildPath_().

◆ test_argify()

static void test_argify ( void  )
static

Definition at line 1545 of file shlexec.c.

1546{
1547 char fileA[MAX_PATH], params[2*MAX_PATH+12];
1548 INT_PTR rc;
1549 const argify_tests_t* test;
1550 const char *bad;
1551 const char* cmd;
1552
1553 /* Test with a long parameter */
1554 for (rc = 0; rc < MAX_PATH; rc++)
1555 fileA[rc] = 'a' + rc % 26;
1556 fileA[MAX_PATH-1] = '\0';
1557 sprintf(params, "shlexec \"%s\" %s", child_file, fileA);
1558
1559 /* We need NOZONECHECKS on Win2003 to block a dialog */
1561 okShell(rc > 32, "failed: rc=%lu\n", rc);
1562 okChildInt("argcA", 4);
1563 okChildPath("argvA3", fileA);
1564
1566 {
1567 skip("No argify tests due to lack of .shlexec association\n");
1568 return;
1569 }
1570
1571 create_test_verb("shlexec.shlexec", "Params232S", 0, "Params232S %2 %3 \"%2\" \"%*\"");
1572 create_test_verb("shlexec.shlexec", "Params23456", 0, "Params23456 \"%2\" \"%3\" \"%4\" \"%5\" \"%6\"");
1573 create_test_verb("shlexec.shlexec", "Params23456789", 0, "Params23456789 \"%2\" \"%3\" \"%4\" \"%5\" \"%6\" \"%7\" \"%8\" \"%9\"");
1574 create_test_verb("shlexec.shlexec", "Params2345Etc", 0, "Params2345Etc ~2=\"%~2\" ~3=\"%~3\" ~4=\"%~4\" ~5=%~5");
1575 create_test_verb("shlexec.shlexec", "Params9Etc", 0, "Params9Etc ~9=\"%~9\"");
1576 create_test_verb("shlexec.shlexec", "Params20", 0, "Params20 \"%20\"");
1577 create_test_verb("shlexec.shlexec", "ParamsBad", 0, "ParamsBad \"%% %- %~ %~0 %~1 %~a %~* %a %b %c %TMPDIR%\"");
1578
1579 sprintf(fileA, "%s\\test file.shlexec", tmpdir);
1580
1582 while (test->params)
1583 {
1584 bad = test->broken ? test->broken : test->cmd;
1585
1586 rc = shell_execute_ex(SEE_MASK_DOENVSUBST, test->verb, fileA, test->params, NULL, NULL);
1587 okShell(rc > 32, "failed: rc=%lu\n", rc);
1588
1589 cmd = getChildString("Child", "cmdlineA");
1590 /* Our commands are such that the verb immediately precedes the
1591 * part we are interested in.
1592 */
1593 if (cmd) cmd = strstr(cmd, test->verb);
1594 if (cmd) cmd += strlen(test->verb);
1595 if (!cmd) cmd = "(null)";
1596 todo_wine_if(test->todo)
1597 okShell(!strcmp(cmd, test->cmd) || broken(!strcmp(cmd, bad)),
1598 "expected '%s', got '%s'\n", cmd, test->cmd);
1599 test++;
1600 }
1601}
int strcmp(const char *String1, const char *String2)
Definition: utclib.c:469
char * strstr(char *String1, char *String2)
Definition: utclib.c:653
GLdouble s
Definition: gl.h:2039
GLdouble n
Definition: glext.h:7729
#define test
Definition: rosglue.h:37
#define SEE_MASK_DOENVSUBST
Definition: shellapi.h:35
#define okShell
Definition: shlexec.c:362
static const argify_tests_t argify_tests[]
Definition: shlexec.c:1420
#define okChildInt(key, expected)
Definition: shlexec.c:460
#define okChildPath(key, expected)
Definition: shlexec.c:451

Referenced by START_TEST().

◆ test_commandline2argv()

static void test_commandline2argv ( void  )
static

Definition at line 1359 of file shlexec.c.

1360{
1361 static const WCHAR exeW[] = {'e','x','e',0};
1362 const cmdline_tests_t* test;
1364 LPWSTR *args;
1365 int numargs;
1366 DWORD le;
1367
1369 while (test->cmd)
1370 {
1371 if (!test_one_cmdline(test))
1372 return;
1373 test++;
1374 }
1375
1376 SetLastError(0xdeadbeef);
1377 args = CommandLineToArgvW(exeW, NULL);
1378 le = GetLastError();
1379 ok(args == NULL && le == ERROR_INVALID_PARAMETER, "expected NULL with ERROR_INVALID_PARAMETER got %p with %u\n", args, le);
1380
1381 SetLastError(0xdeadbeef);
1383 le = GetLastError();
1384 ok(args == NULL && le == ERROR_INVALID_PARAMETER, "expected NULL with ERROR_INVALID_PARAMETER got %p with %u\n", args, le);
1385
1386 *strW = 0;
1387 args = CommandLineToArgvW(strW, &numargs);
1388 ok(numargs == 1 || broken(numargs > 1), "expected 1 args, got %d\n", numargs);
1389 ok(!args || (!args[numargs] || broken(args[numargs] != NULL) /* before Vista */),
1390 "expected NULL-terminated list of commandline arguments\n");
1391 if (numargs == 1)
1392 {
1394 ok(!lstrcmpW(args[0], strW), "wrong path to the current executable: %s instead of %s\n", wine_dbgstr_w(args[0]), wine_dbgstr_w(strW));
1395 }
1396 if (args) LocalFree(args);
1397}
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
DWORD WINAPI GetModuleFileNameW(HINSTANCE hModule, LPWSTR lpFilename, DWORD nSize)
Definition: loader.c:600
HLOCAL NTAPI LocalFree(HLOCAL hMem)
Definition: heapmem.c:1594
#define wine_dbgstr_w
Definition: kernel32.h:34
int WINAPI lstrcmpW(LPCWSTR lpString1, LPCWSTR lpString2)
Definition: lstring.c:170
WCHAR strW[12]
Definition: clipboard.c:2029
#define args
Definition: format.c:66
LPWSTR *WINAPI CommandLineToArgvW(LPCWSTR lpCmdline, int *numargs)
Definition: shell32_main.c:80
static BOOL test_one_cmdline(const cmdline_tests_t *test)
Definition: shlexec.c:1318
static const cmdline_tests_t cmdline_tests[]
Definition: shlexec.c:1157
Definition: match.c:390
WCHAR * LPWSTR
Definition: xmlstorage.h:184

Referenced by START_TEST().

◆ test_dde()

static void test_dde ( void  )
static

Definition at line 2382 of file shlexec.c.

2383{
2384 char filename[MAX_PATH], defApplication[MAX_PATH];
2385 const dde_tests_t* test;
2386 char params[1024];
2387 INT_PTR rc;
2388 HANDLE map;
2389 char *shared_block;
2390 DWORD ddeflags;
2391
2393
2394 sprintf(filename, "%s\\test file.sde", tmpdir);
2395
2396 /* Default service is application name minus path and extension */
2397 strcpy(defApplication, strrchr(argv0, '\\')+1);
2398 *strchr(defApplication, '.') = 0;
2399
2401 4096, "winetest_shlexec_dde_map");
2402 shared_block = MapViewOfFile(map, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, 4096);
2403
2405 test = dde_tests;
2406 while (test->command)
2407 {
2408 if (!create_test_association(".sde"))
2409 {
2410 skip("Unable to create association for '.sde'\n");
2411 return;
2412 }
2413 create_test_verb_dde("shlexec.sde", "Open", 0, test->command, test->ddeexec,
2414 test->application, test->topic, test->ifexec);
2415
2416 if (test->application != NULL || test->topic != NULL)
2417 {
2418 strcpy(shared_block, test->application ? test->application : defApplication);
2419 strcpy(shared_block + strlen(shared_block) + 1, test->topic ? test->topic : SZDDESYS_TOPIC);
2420 }
2421 else
2422 {
2423 shared_block[0] = '\0';
2424 shared_block[1] = '\0';
2425 }
2426 ddeExec[0] = 0;
2427
2429 dde_ready_event = CreateEventA(NULL, TRUE, FALSE, "winetest_shlexec_dde_ready");
2430 rc = shell_execute_ex(ddeflags, NULL, filename, NULL, NULL, NULL);
2432 if (!(ddeflags & SEE_MASK_WAITFORINPUTIDLE) && rc == SE_ERR_DDEFAIL &&
2434 strcmp(winetest_platform, "windows") == 0)
2435 {
2436 /* Windows 10 does not call WaitForInputIdle() for DDE which creates
2437 * a race condition as the DDE server may not have time to start up.
2438 * When that happens the test fails with the above results and we
2439 * compensate by forcing the WaitForInputIdle() call.
2440 */
2441 trace("Adding SEE_MASK_WAITFORINPUTIDLE for Windows 10\n");
2442 ddeflags |= SEE_MASK_WAITFORINPUTIDLE;
2445 continue;
2446 }
2447 okShell(32 < rc, "failed: rc=%lu err=%u\n", rc, GetLastError());
2448 if (test->ddeexec)
2450 broken(waitforinputidle_count == 0) /* Win10 race */,
2451 "WaitForInputIdle() was called %u times\n",
2453 else
2454 okShell(waitforinputidle_count == 0, "WaitForInputIdle() was called %u times for a non-DDE case\n", waitforinputidle_count);
2455
2456 if (32 < rc)
2457 {
2458 if (test->broken)
2459 okChildIntBroken("argcA", test->expectedArgs + 3);
2460 else
2461 okChildInt("argcA", test->expectedArgs + 3);
2462
2463 if (test->expectedArgs == 1) okChildPath("argvA3", filename);
2464
2465 sprintf(params, test->expectedDdeExec, filename);
2466 okChildPath("ddeExec", params);
2467 }
2469
2471 test++;
2472 }
2473
2474 UnmapViewOfFile(shared_block);
2477}
char * strchr(const char *String, int ch)
Definition: utclib.c:501
#define SZDDESYS_TOPIC
Definition: ddeml.h:47
HANDLE NTAPI CreateFileMappingA(IN HANDLE hFile, IN LPSECURITY_ATTRIBUTES lpFileMappingAttributes, IN DWORD flProtect, IN DWORD dwMaximumSizeHigh, IN DWORD dwMaximumSizeLow, IN LPCSTR lpName)
Definition: filemap.c:23
#define ERROR_FILE_NOT_FOUND
Definition: disk.h:79
const char * winetest_platform
#define SEE_MASK_WAITFORINPUTIDLE
Definition: shellapi.h:56
#define SE_ERR_DDEFAIL
Definition: shellapi.h:130
static void hook_WaitForInputIdle(DWORD(WINAPI *new_func)(HANDLE, DWORD))
Definition: shlexec.c:2321
static DWORD WINAPI hooked_WaitForInputIdle(HANDLE process, DWORD timeout)
Definition: shlexec.c:2303
#define okChildIntBroken(key, expected)
Definition: shlexec.c:469
static dde_tests_t dde_tests[]
Definition: shlexec.c:2274
#define FILE_MAP_WRITE
Definition: winbase.h:154
DWORD WINAPI WaitForInputIdle(_In_ HANDLE, _In_ DWORD)

Referenced by START_TEST().

◆ test_dde_default_app()

static void test_dde_default_app ( void  )
static

Definition at line 2549 of file shlexec.c.

2550{
2551 char filename[MAX_PATH];
2552 HSZ hszApplication;
2555 char params[1024];
2556 DWORD threadId;
2557 MSG msg;
2558 INT_PTR rc;
2559 int which = 0;
2560 HDDEDATA ret;
2561 BOOL b;
2562
2564 ddeInst = 0;
2567 ok(rc == DMLERR_NO_ERROR, "got %lx\n", rc);
2568
2569 sprintf(filename, "%s\\test file.sde", tmpdir);
2570
2571 /* It is strictly not necessary to register an application name here, but wine's
2572 * DdeNameService implementation complains if 0 is passed instead of
2573 * hszApplication with DNS_FILTEROFF */
2574 hszApplication = DdeCreateStringHandleA(ddeInst, "shlexec", CP_WINANSI);
2576 ok(hszApplication && hszTopic, "got %p and %p\n", hszApplication, hszTopic);
2577 ret = DdeNameService(ddeInst, hszApplication, 0, DNS_REGISTER | DNS_FILTEROFF);
2578 ok(ret != 0, "got %p\n", ret);
2579
2581 while (test->command)
2582 {
2583 HANDLE thread;
2584
2585 if (!create_test_association(".sde"))
2586 {
2587 skip("Unable to create association for '.sde'\n");
2588 return;
2589 }
2590 sprintf(params, test->command, tmpdir);
2591 create_test_verb_dde("shlexec.sde", "Open", 1, params, "[test]", NULL,
2592 "shlexec", NULL);
2593 ddeApplication[0] = 0;
2594
2595 /* No application will be run as we will respond to the first DDE event,
2596 * so don't wait for it */
2598
2599 thread = CreateThread(NULL, 0, ddeThread, &info, 0, &threadId);
2600 ok(thread != NULL, "got %p\n", thread);
2601 while (GetMessageA(&msg, NULL, 0, 0)) DispatchMessageA(&msg);
2602 rc = msg.wParam > 32 ? 33 : msg.wParam;
2603
2604 /* The first two tests determine which set of results to expect.
2605 * First check the platform as only the first set of results is
2606 * acceptable for Wine.
2607 */
2608 if (strcmp(winetest_platform, "wine"))
2609 {
2611 {
2612 if (strcmp(ddeApplication, test->expectedDdeApplication[0]))
2613 which = 2;
2614 }
2615 else if (test == dde_default_app_tests + 1)
2616 {
2617 if (which == 0 && rc == test->rc[1])
2618 which = 1;
2619 trace("DDE result variant %d\n", which);
2620 }
2621 }
2622
2623 todo_wine_if(test->todo & 0x1)
2624 okShell(rc==test->rc[which], "failed: rc=%lu err=%u\n",
2625 rc, GetLastError());
2626 if (rc == 33)
2627 {
2628 todo_wine_if(test->todo & 0x2)
2629 ok(!strcmp(ddeApplication, test->expectedDdeApplication[which]),
2630 "Expected application '%s', got '%s'\n",
2631 test->expectedDdeApplication[which], ddeApplication);
2632 }
2634
2636 test++;
2637 }
2638
2639 ret = DdeNameService(ddeInst, hszApplication, 0, DNS_UNREGISTER);
2640 ok(ret != 0, "got %p\n", ret);
2642 ok(b, "got %d\n", b);
2643 b = DdeFreeStringHandle(ddeInst, hszApplication);
2644 ok(b, "got %d\n", b);
2646 ok(b, "got %d\n", b);
2647}
BOOLEAN Expected
static HANDLE thread
Definition: service.c:33
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
Definition: thread.c:137
GLboolean GLboolean GLboolean b
Definition: glext.h:6204
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble * u
Definition: glfuncs.h:240
#define d
Definition: ke_i.h:81
#define b
Definition: ke_i.h:79
if(dx< 0)
Definition: linetemp.h:194
#define err(...)
static dde_default_app_tests_t dde_default_app_tests[]
Definition: shlexec.c:2488
static DWORD CALLBACK ddeThread(LPVOID arg)
Definition: shlexec.c:2538
static GLenum which
Definition: wgl_font.c:159
DWORD WINAPI GetCurrentThreadId(void)
Definition: thread.c:459

Referenced by START_TEST().

◆ test_directory()

static void test_directory ( void  )
static

Definition at line 2808 of file shlexec.c.

2809{
2810 char path[MAX_PATH], curdir[MAX_PATH];
2811 char params[1024], dirpath[1024];
2812 INT_PTR rc;
2813
2814 sprintf(path, "%s\\test2.exe", tmpdir);
2816
2817 sprintf(params, "shlexec \"%s\" Exec", child_file);
2818
2819 /* Test with the current directory */
2820 GetCurrentDirectoryA(sizeof(curdir), curdir);
2823 NULL, "test2.exe", params, NULL, NULL);
2824 okShell(rc > 32, "returned %lu\n", rc);
2825 okChildInt("argcA", 4);
2826 okChildString("argvA3", "Exec");
2827 okChildPath("longPath", path);
2828 SetCurrentDirectoryA(curdir);
2829
2831 NULL, "test2.exe", params, NULL, NULL);
2832 okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
2833
2834 /* Explicitly specify the directory to use */
2836 NULL, "test2.exe", params, tmpdir, NULL);
2837 okShell(rc > 32, "returned %lu\n", rc);
2838 okChildInt("argcA", 4);
2839 okChildString("argvA3", "Exec");
2840 okChildPath("longPath", path);
2841
2842 /* Specify it through an environment variable */
2844 NULL, "test2.exe", params, "%TMPDIR%", NULL);
2845 todo_wine okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
2846
2848 NULL, "test2.exe", params, "%TMPDIR%", NULL);
2849 okShell(rc > 32, "returned %lu\n", rc);
2850 okChildInt("argcA", 4);
2851 okChildString("argvA3", "Exec");
2852 okChildPath("longPath", path);
2853
2854 /* Not a colon-separated directory list */
2855 sprintf(dirpath, "%s:%s", curdir, tmpdir);
2857 NULL, "test2.exe", params, dirpath, NULL);
2858 okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
2859}
BOOL WINAPI CopyFileA(IN LPCSTR lpExistingFileName, IN LPCSTR lpNewFileName, IN BOOL bFailIfExists)
Definition: copy.c:404
DWORD WINAPI GetCurrentDirectoryA(IN DWORD nBufferLength, OUT LPSTR lpBuffer)
Definition: path.c:2146
BOOL WINAPI SetCurrentDirectoryA(IN LPCSTR lpPathName)
Definition: path.c:2206
#define todo_wine
Definition: custom.c:79
#define SE_ERR_FNF
Definition: shellapi.h:122
#define okChildString(key, expected)
Definition: shlexec.c:383

Referenced by START_TEST().

◆ test_exes()

static void test_exes ( void  )
static

Definition at line 2204 of file shlexec.c.

2205{
2206 char filename[MAX_PATH];
2207 char params[1024];
2208 INT_PTR rc;
2209
2210 sprintf(params, "shlexec \"%s\" Exec", child_file);
2211
2212 /* We need NOZONECHECKS on Win2003 to block a dialog */
2214 NULL, NULL);
2215 okShell(rc > 32, "returned %lu\n", rc);
2216 okChildInt("argcA", 4);
2217 okChildString("argvA3", "Exec");
2218
2219 if (! skip_noassoc_tests)
2220 {
2221 sprintf(filename, "%s\\test file.noassoc", tmpdir);
2223 {
2225 todo_wine {
2226 okShell(rc==SE_ERR_NOASSOC, "returned %lu\n", rc);
2227 }
2228 }
2229 }
2230 else
2231 {
2232 win_skip("Skipping shellexecute of file with unassociated extension\n");
2233 }
2234
2235 /* test combining executable and parameters */
2236 sprintf(filename, "%s shlexec \"%s\" Exec", argv0, child_file);
2238 okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
2239
2240 sprintf(filename, "\"%s\" shlexec \"%s\" Exec", argv0, child_file);
2242 okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
2243
2244 /* A verb, even if invalid, overrides the normal handling of executables */
2246 "notaverb", argv0, NULL, NULL, NULL);
2247 todo_wine okShell(rc == SE_ERR_NOASSOC, "returned %lu\n", rc);
2248
2249 if (!skip_shlexec_tests)
2250 {
2251 /* A class overrides the normal handling of executables too */
2252 /* FIXME SEE_MASK_FLAG_NO_UI is only needed due to Wine's bug */
2254 NULL, argv0, NULL, NULL, ".shlexec");
2255 todo_wine okShell(rc > 32, "returned %lu\n", rc);
2256 okChildInt("argcA", 5);
2257 todo_wine okChildString("argvA3", "Open");
2258 todo_wine okChildPath("argvA4", argv0);
2259 }
2260}
#define SEE_MASK_CLASSNAME
Definition: shellapi.h:25
#define shell_execute(verb, filename, parameters, directory)
Definition: shlexec.c:569
#define todo_wait
Definition: shlexec.c:492

Referenced by START_TEST().

◆ test_filename()

static void test_filename ( void  )
static

Definition at line 1603 of file shlexec.c.

1604{
1605 char filename[MAX_PATH];
1606 const filename_tests_t* test;
1607 char* c;
1608 INT_PTR rc;
1609
1611 {
1612 skip("No ShellExecute/filename tests due to lack of .shlexec association\n");
1613 return;
1614 }
1615
1617 while (test->basename)
1618 {
1619 BOOL quotedfile = FALSE;
1620
1622 {
1623 win_skip("Skipping shellexecute of file with unassociated extension\n");
1624 test++;
1625 continue;
1626 }
1627
1628 sprintf(filename, test->basename, tmpdir);
1629 if (strchr(filename, '/'))
1630 {
1631 c=filename;
1632 while (*c)
1633 {
1634 if (*c=='\\')
1635 *c='/';
1636 c++;
1637 }
1638 }
1639 if ((test->todo & 0x40)==0)
1640 {
1641 rc=shell_execute(test->verb, filename, NULL, NULL);
1642 }
1643 else
1644 {
1645 char quoted[MAX_PATH + 2];
1646
1647 quotedfile = TRUE;
1648 sprintf(quoted, "\"%s\"", filename);
1649 rc=shell_execute(test->verb, quoted, NULL, NULL);
1650 }
1651 if (rc > 32)
1652 rc=33;
1653 okShell(rc==test->rc ||
1654 broken(quotedfile && rc == SE_ERR_FNF), /* NT4 */
1655 "failed: rc=%ld err=%u\n", rc, GetLastError());
1656 if (rc == 33)
1657 {
1658 const char* verb;
1659 todo_wine_if(test->todo & 0x2)
1660 okChildInt("argcA", 5);
1661 verb=(test->verb ? test->verb : "Open");
1662 todo_wine_if(test->todo & 0x4)
1663 okChildString("argvA3", verb);
1664 todo_wine_if(test->todo & 0x8)
1665 okChildPath("argvA4", filename);
1666 }
1667 test++;
1668 }
1669
1672 {
1673 sprintf(filename, test->basename, tmpdir);
1674 rc=shell_execute(test->verb, filename, NULL, NULL);
1675 if (rc > 32)
1676 rc=33;
1677 todo_wine_if(test->todo & 0x1)
1678 okShell(rc==test->rc, "failed: rc=%ld err=%u\n", rc, GetLastError());
1679 if (rc==0)
1680 {
1681 int count;
1682 const char* verb;
1683 char* str;
1684
1685 verb=(test->verb ? test->verb : "Open");
1686 todo_wine_if(test->todo & 0x4)
1687 okChildString("argvA3", verb);
1688
1689 count=4;
1690 str=filename;
1691 while (1)
1692 {
1693 char attrib[18];
1694 char* space;
1695 space=strchr(str, ' ');
1696 if (space)
1697 *space='\0';
1698 sprintf(attrib, "argvA%d", count);
1699 todo_wine_if(test->todo & 0x8)
1700 okChildPath(attrib, str);
1701 count++;
1702 if (!space)
1703 break;
1704 str=space+1;
1705 }
1707 okChildInt("argcA", count);
1708 }
1709 test++;
1710 }
1711
1712 if (dllver.dwMajorVersion != 0)
1713 {
1714 /* The more recent versions of shell32.dll accept quoted filenames
1715 * while older ones (e.g. 4.00) don't. Still we want to test this
1716 * because IE 6 depends on the new behavior.
1717 * One day we may need to check the exact version of the dll but for
1718 * now making sure DllGetVersion() is present is sufficient.
1719 */
1720 sprintf(filename, "\"%s\\test file.shlexec\"", tmpdir);
1722 okShell(rc > 32, "failed: rc=%ld err=%u\n", rc, GetLastError());
1723 okChildInt("argcA", 5);
1724 okChildString("argvA3", "Open");
1725 sprintf(filename, "%s\\test file.shlexec", tmpdir);
1726 okChildPath("argvA4", filename);
1727 }
1728
1729 sprintf(filename, "\"%s\\test file.sha\"", tmpdir);
1731 todo_wine okShell(rc > 32, "failed: rc=%ld err=%u\n", rc, GetLastError());
1732 okChildInt("argcA", 5);
1733 todo_wine okChildString("argvA3", "averb");
1734 sprintf(filename, "%s\\test file.sha", tmpdir);
1735 todo_wine okChildPath("argvA4", filename);
1736}
while(CdLookupNextInitialFileDirent(IrpContext, Fcb, FileContext))
static void basename(LPCWSTR path, LPWSTR name)
Definition: profile.c:38
GLuint GLuint GLsizei count
Definition: gl.h:1545
#define Open
Definition: syshdrs.h:62
BOOL todo
Definition: filedlg.c:313
static filename_tests_t noquotes_tests[]
Definition: shlexec.c:1082
static filename_tests_t filename_tests[]
Definition: shlexec.c:1039
_In_ CLIPOBJ _In_ BRUSHOBJ _In_ LONG _In_ LONG _In_ LONG x2
Definition: winddi.h:3710

Referenced by START_TEST().

◆ test_fileurls()

static void test_fileurls ( void  )
static

Definition at line 1786 of file shlexec.c.

1787{
1788 char filename[MAX_PATH], fileurl[MAX_PATH], longtmpdir[MAX_PATH];
1789 char command[MAX_PATH];
1790 const fileurl_tests_t* test;
1791 char *s;
1792 INT_PTR rc;
1793
1795 {
1796 skip("No file URL tests due to lack of .shlexec association\n");
1797 return;
1798 }
1799
1801 "file:///nosuchfile.shlexec", NULL, NULL, NULL);
1802 if (rc > 32)
1803 {
1804 win_skip("shell32 is too old (likely < 4.72). Skipping the file URL tests\n");
1805 return;
1806 }
1807
1808 get_long_path_name(tmpdir, longtmpdir, ARRAY_SIZE(longtmpdir));
1809 SetEnvironmentVariableA("urlprefix", "file:///");
1810
1812 while (test->basename)
1813 {
1814 /* Build the file URL */
1815 sprintf(filename, test->basename, longtmpdir);
1816 strcpy(fileurl, test->urlprefix);
1817 strcat(fileurl, filename);
1818 s = fileurl + strlen(test->urlprefix);
1819 while (*s)
1820 {
1821 if (!(test->flags & USE_COLON) && *s == ':')
1822 *s = '|';
1823 else if (!(test->flags & USE_BSLASH) && *s == '\\')
1824 *s = '/';
1825 s++;
1826 }
1827
1828 /* Test it first with FindExecutable() */
1829 rc = (INT_PTR)FindExecutableA(fileurl, NULL, command);
1830 ok(rc == SE_ERR_FNF, "FindExecutable(%s) failed: bad rc=%lu\n", fileurl, rc);
1831
1832 /* Then ShellExecute() */
1833 if ((test->todo & 0x10) == 0)
1834 rc = shell_execute(NULL, fileurl, NULL, NULL);
1835 else todo_wait
1836 rc = shell_execute(NULL, fileurl, NULL, NULL);
1837 if (bad_shellexecute)
1838 {
1839 win_skip("shell32 is too old (likely 4.72). Skipping the file URL tests\n");
1840 break;
1841 }
1842 if (test->flags & URL_SUCCESS)
1843 {
1844 todo_wine_if(test->todo & 0x1)
1845 okShell(rc > 32, "failed: bad rc=%lu\n", rc);
1846 }
1847 else
1848 {
1849 todo_wine_if(test->todo & 0x1)
1850 okShell(rc == SE_ERR_FNF || rc == SE_ERR_PNF ||
1851 broken(rc == SE_ERR_ACCESSDENIED) /* win2000 */,
1852 "failed: bad rc=%lu\n", rc);
1853 }
1854 if (rc == 33)
1855 {
1856 todo_wine_if(test->todo & 0x2)
1857 okChildInt("argcA", 5);
1858 todo_wine_if(test->todo & 0x4)
1859 okChildString("argvA3", "Open");
1860 todo_wine_if(test->todo & 0x8)
1861 okChildPath("argvA4", filename);
1862 }
1863 test++;
1864 }
1865
1866 SetEnvironmentVariableA("urlprefix", NULL);
1867}
#define SE_ERR_PNF
Definition: shellapi.h:123
#define SE_ERR_ACCESSDENIED
Definition: shellapi.h:124
static fileurl_tests_t fileurl_tests[]
Definition: shlexec.c:1750
static DWORD get_long_path_name(const char *shortpath, char *longpath, DWORD longlen)
Definition: shlexec.c:930
#define URL_SUCCESS
Definition: shlexec.c:1746
#define USE_COLON
Definition: shlexec.c:1747
#define USE_BSLASH
Definition: shlexec.c:1748
HINSTANCE WINAPI FindExecutableA(LPCSTR lpFile, LPCSTR lpDirectory, LPSTR lpResult)
Definition: shlexec.cpp:1214
else
Definition: tritemp.h:161

Referenced by START_TEST().

◆ test_find_executable()

static void test_find_executable ( void  )
static

Definition at line 1963 of file shlexec.c.

1964{
1965 char notepad_path[MAX_PATH];
1966 char filename[MAX_PATH];
1967 char command[MAX_PATH];
1968 const filename_tests_t* test;
1969 INT_PTR rc;
1970
1971 if (!create_test_association(".sfe"))
1972 {
1973 skip("Unable to create association for '.sfe'\n");
1974 return;
1975 }
1976 create_test_verb("shlexec.sfe", "Open", 1, "%1");
1977
1978 /* Don't test FindExecutable(..., NULL), it always crashes */
1979
1980 strcpy(command, "your word");
1981 if (0) /* Can crash on Vista! */
1982 {
1984 ok(rc == SE_ERR_FNF || rc > 32 /* nt4 */, "FindExecutable(NULL) returned %ld\n", rc);
1985 ok(strcmp(command, "your word") != 0, "FindExecutable(NULL) returned command=[%s]\n", command);
1986 }
1987
1988 GetSystemDirectoryA( notepad_path, MAX_PATH );
1989 strcat( notepad_path, "\\notepad.exe" );
1990
1991 /* Search for something that should be in the system-wide search path (no default directory) */
1992 strcpy(command, "your word");
1993 rc=(INT_PTR)FindExecutableA("notepad.exe", NULL, command);
1994 ok(rc > 32, "FindExecutable(%s) returned %ld\n", "notepad.exe", rc);
1995 ok(strcasecmp(command, notepad_path) == 0, "FindExecutable(%s) returned command=[%s]\n", "notepad.exe", command);
1996
1997 /* Search for something that should be in the system-wide search path (with default directory) */
1998 strcpy(command, "your word");
1999 rc=(INT_PTR)FindExecutableA("notepad.exe", tmpdir, command);
2000 ok(rc > 32, "FindExecutable(%s) returned %ld\n", "notepad.exe", rc);
2001 ok(strcasecmp(command, notepad_path) == 0, "FindExecutable(%s) returned command=[%s]\n", "notepad.exe", command);
2002
2003 strcpy(command, "your word");
2005 ok(rc == SE_ERR_NOASSOC /* >= win2000 */ || rc > 32 /* win98, nt4 */, "FindExecutable(NULL) returned %ld\n", rc);
2006 ok(strcmp(command, "your word") != 0, "FindExecutable(NULL) returned command=[%s]\n", command);
2007
2008 sprintf(filename, "%s\\test file.sfe", tmpdir);
2010 ok(rc > 32, "FindExecutable(%s) returned %ld\n", filename, rc);
2011 /* Depending on the platform, command could be '%1' or 'test file.sfe' */
2012
2013 rc=(INT_PTR)FindExecutableA("test file.sfe", tmpdir, command);
2014 ok(rc > 32, "FindExecutable(%s) returned %ld\n", filename, rc);
2015
2016 rc=(INT_PTR)FindExecutableA("test file.sfe", NULL, command);
2017 ok(rc == SE_ERR_FNF, "FindExecutable(%s) returned %ld\n", filename, rc);
2018
2020
2021 if (!create_test_association(".shl"))
2022 {
2023 skip("Unable to create association for '.shl'\n");
2024 return;
2025 }
2026 create_test_verb("shlexec.shl", "Open", 0, "Open");
2027
2028 sprintf(filename, "%s\\test file.shl", tmpdir);
2030 ok(rc == SE_ERR_FNF /* NT4 */ || rc > 32, "FindExecutable(%s) returned %ld\n", filename, rc);
2031
2032 sprintf(filename, "%s\\test file.shlfoo", tmpdir);
2034
2036
2037 if (rc > 32)
2038 {
2039 /* On Windows XP and 2003 FindExecutable() is completely broken.
2040 * Probably what it does is convert the filename to 8.3 format,
2041 * which as a side effect converts the '.shlfoo' extension to '.shl',
2042 * and then tries to find an association for '.shl'. This means it
2043 * will normally fail on most extensions with more than 3 characters,
2044 * like '.mpeg', etc.
2045 * Also it means we cannot do any other test.
2046 */
2047 win_skip("FindExecutable() is broken -> not running 4+ character extension tests\n");
2048 return;
2049 }
2050
2052 {
2053 skip("No FindExecutable/filename tests due to lack of .shlexec association\n");
2054 return;
2055 }
2056
2058 while (test->basename)
2059 {
2060 sprintf(filename, test->basename, tmpdir);
2061 if (strchr(filename, '/'))
2062 {
2063 char* c;
2064 c=filename;
2065 while (*c)
2066 {
2067 if (*c=='\\')
2068 *c='/';
2069 c++;
2070 }
2071 }
2072 /* Win98 does not '\0'-terminate command! */
2073 memset(command, '\0', sizeof(command));
2075 if (rc > 32)
2076 rc=33;
2077 todo_wine_if(test->todo & 0x10)
2078 ok(rc==test->rc, "FindExecutable(%s) failed: rc=%ld\n", filename, rc);
2079 if (rc > 32)
2080 {
2081 BOOL equal;
2082 equal=strcmp(command, argv0) == 0 ||
2083 /* NT4 returns an extra 0x8 character! */
2084 (strlen(command) == strlen(argv0)+1 && strncmp(command, argv0, strlen(argv0)) == 0);
2085 todo_wine_if(test->todo & 0x20)
2086 ok(equal, "FindExecutable(%s) returned command='%s' instead of '%s'\n",
2088 }
2089 test++;
2090 }
2091}
int strncmp(const char *String1, const char *String2, ACPI_SIZE Count)
Definition: utclib.c:534
UINT WINAPI GetSystemDirectoryA(OUT LPSTR lpBuffer, IN UINT uSize)
Definition: path.c:2283
#define strcasecmp
Definition: fake.h:9
#define FindExecutable
Definition: shellapi.h:687

Referenced by START_TEST().

◆ test_lnks()

static void test_lnks ( void  )
static

Definition at line 2110 of file shlexec.c.

2111{
2112 char filename[MAX_PATH];
2113 char params[MAX_PATH];
2114 const filename_tests_t* test;
2115 INT_PTR rc;
2116
2118 skip("No FindExecutable/filename tests due to lack of .shlexec association\n");
2119 else
2120 {
2121 /* Should open through our association */
2122 sprintf(filename, "%s\\test_shortcut_shlexec.lnk", tmpdir);
2124 okShell(rc > 32, "failed: rc=%lu err=%u\n", rc, GetLastError());
2125 okChildInt("argcA", 5);
2126 okChildString("argvA3", "Open");
2127 sprintf(params, "%s\\test file.shlexec", tmpdir);
2129 okChildPath("argvA4", filename);
2130
2131 rc=shell_execute_ex(SEE_MASK_NOZONECHECKS|SEE_MASK_DOENVSUBST, NULL, "%TMPDIR%\\test_shortcut_shlexec.lnk", NULL, NULL, NULL);
2132 okShell(rc > 32, "failed: rc=%lu err=%u\n", rc, GetLastError());
2133 okChildInt("argcA", 5);
2134 okChildString("argvA3", "Open");
2135 sprintf(params, "%s\\test file.shlexec", tmpdir);
2137 okChildPath("argvA4", filename);
2138 }
2139
2140 /* Should just run our executable */
2141 sprintf(filename, "%s\\test_shortcut_exe.lnk", tmpdir);
2143 okShell(rc > 32, "failed: rc=%lu err=%u\n", rc, GetLastError());
2144 okChildInt("argcA", 4);
2145 okChildString("argvA3", "Lnk");
2146
2147 if (!skip_shlexec_tests)
2148 {
2149 /* An explicit class overrides lnk's ContextMenuHandler */
2151 okShell(rc > 32, "failed: rc=%lu err=%u\n", rc, GetLastError());
2152 okChildInt("argcA", 5);
2153 okChildString("argvA3", "Open");
2154 okChildPath("argvA4", filename);
2155 }
2156
2157 if (dllver.dwMajorVersion>=6)
2158 {
2159 char* c;
2160 /* Recent versions of shell32.dll accept '/'s in shortcut paths.
2161 * Older versions don't or are quite buggy in this regard.
2162 */
2163 sprintf(filename, "%s\\test_shortcut_exe.lnk", tmpdir);
2164 c=filename;
2165 while (*c)
2166 {
2167 if (*c=='\\')
2168 *c='/';
2169 c++;
2170 }
2172 okShell(rc > 32, "failed: rc=%lu err=%u\n", rc, GetLastError());
2173 okChildInt("argcA", 4);
2174 okChildString("argvA3", "Lnk");
2175 }
2176
2177 sprintf(filename, "%s\\test_shortcut_exe.lnk", tmpdir);
2179 while (test->basename)
2180 {
2181 params[0]='\"';
2182 sprintf(params+1, test->basename, tmpdir);
2183 strcat(params,"\"");
2185 NULL, NULL);
2186 if (rc > 32)
2187 rc=33;
2188 todo_wine_if(test->todo & 0x1)
2189 okShell(rc==test->rc, "failed: rc=%lu err=%u\n", rc, GetLastError());
2190 if (rc==0)
2191 {
2192 todo_wine_if(test->todo & 0x2)
2193 okChildInt("argcA", 5);
2194 todo_wine_if(test->todo & 0x4)
2195 okChildString("argvA3", "Lnk");
2197 okChildPath("argvA4", params);
2198 }
2199 test++;
2200 }
2201}
static filename_tests_t lnk_tests[]
Definition: shlexec.c:2094

Referenced by START_TEST().

◆ test_lpFile_parsed()

static void test_lpFile_parsed ( void  )
static

Definition at line 1092 of file shlexec.c.

1093{
1094 char fileA[MAX_PATH];
1095 INT_PTR rc;
1096
1098 {
1099 skip("No filename parsing tests due to lack of .shlexec association\n");
1100 return;
1101 }
1102
1103 /* existing "drawback_file.noassoc" prevents finding "drawback_file.noassoc foo.shlexec" on wine */
1104 sprintf(fileA, "%s\\drawback_file.noassoc foo.shlexec", tmpdir);
1105 rc=shell_execute(NULL, fileA, NULL, NULL);
1106 okShell(rc > 32, "failed: rc=%lu\n", rc);
1107
1108 /* if quoted, existing "drawback_file.noassoc" not prevents finding "drawback_file.noassoc foo.shlexec" on wine */
1109 sprintf(fileA, "\"%s\\drawback_file.noassoc foo.shlexec\"", tmpdir);
1110 rc=shell_execute(NULL, fileA, NULL, NULL);
1111 okShell(rc > 32 || broken(rc == SE_ERR_FNF) /* Win95/NT4 */,
1112 "failed: rc=%lu\n", rc);
1113
1114 /* error should be SE_ERR_FNF, not SE_ERR_NOASSOC */
1115 sprintf(fileA, "\"%s\\drawback_file.noassoc\" foo.shlexec", tmpdir);
1116 rc=shell_execute(NULL, fileA, NULL, NULL);
1117 okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
1118
1119 /* ""command"" not works on wine (and real win9x and w2k) */
1120 sprintf(fileA, "\"\"%s\\simple.shlexec\"\"", tmpdir);
1121 rc=shell_execute(NULL, fileA, NULL, NULL);
1122 todo_wine okShell(rc > 32 || broken(rc == SE_ERR_FNF) /* Win9x/2000 */,
1123 "failed: rc=%lu\n", rc);
1124
1125 /* nonexisting "drawback_nonexist.noassoc" not prevents finding "drawback_nonexist.noassoc foo.shlexec" on wine */
1126 sprintf(fileA, "%s\\drawback_nonexist.noassoc foo.shlexec", tmpdir);
1127 rc=shell_execute(NULL, fileA, NULL, NULL);
1128 okShell(rc > 32, "failed: rc=%lu\n", rc);
1129
1130 /* is SEE_MASK_DOENVSUBST default flag? Should only be when XP emulates 9x (XP bug or real 95 or ME behavior ?) */
1131 rc=shell_execute(NULL, "%TMPDIR%\\simple.shlexec", NULL, NULL);
1132 todo_wine okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
1133
1134 /* quoted */
1135 rc=shell_execute(NULL, "\"%TMPDIR%\\simple.shlexec\"", NULL, NULL);
1136 todo_wine okShell(rc == SE_ERR_FNF, "returned %lu\n", rc);
1137
1138 /* test SEE_MASK_DOENVSUBST works */
1140 NULL, "%TMPDIR%\\simple.shlexec", NULL, NULL, NULL);
1141 okShell(rc > 32, "failed: rc=%lu\n", rc);
1142
1143 /* quoted lpFile does not work on real win95 and nt4 */
1145 NULL, "\"%TMPDIR%\\simple.shlexec\"", NULL, NULL, NULL);
1146 okShell(rc > 32 || broken(rc == SE_ERR_FNF) /* Win95/NT4 */,
1147 "failed: rc=%lu\n", rc);
1148}

Referenced by START_TEST().

◆ test_one_cmdline()

static BOOL test_one_cmdline ( const cmdline_tests_t test)
static

Definition at line 1318 of file shlexec.c.

1319{
1320 WCHAR cmdW[MAX_PATH], argW[MAX_PATH];
1321 LPWSTR *cl2a;
1322 int cl2a_count;
1323 LPWSTR *argsW;
1324 int i, count;
1325
1326 /* trace("----- cmd='%s'\n", test->cmd); */
1327 MultiByteToWideChar(CP_ACP, 0, test->cmd, -1, cmdW, ARRAY_SIZE(cmdW));
1328 argsW = cl2a = CommandLineToArgvW(cmdW, &cl2a_count);
1329 if (argsW == NULL && cl2a_count == -1)
1330 {
1331 win_skip("CommandLineToArgvW not implemented, skipping\n");
1332 return FALSE;
1333 }
1334 ok(!argsW[cl2a_count] || broken(argsW[cl2a_count] != NULL) /* before Vista */,
1335 "expected NULL-terminated list of commandline arguments\n");
1336
1337 count = 0;
1338 while (test->args[count])
1339 count++;
1340 todo_wine_if(test->todo & 0x1)
1341 ok(cl2a_count == count, "%s: expected %d arguments, but got %d\n", test->cmd, count, cl2a_count);
1342
1343 for (i = 0; i < cl2a_count; i++)
1344 {
1345 if (i < count)
1346 {
1347 MultiByteToWideChar(CP_ACP, 0, test->args[i], -1, argW, ARRAY_SIZE(argW));
1348 todo_wine_if(test->todo & (1 << (i+4)))
1349 ok(!lstrcmpW(*argsW, argW), "%s: arg[%d] expected %s but got %s\n", test->cmd, i, wine_dbgstr_w(argW), wine_dbgstr_w(*argsW));
1350 }
1352 ok(0, "%s: got extra arg[%d]=%s\n", test->cmd, i, wine_dbgstr_w(*argsW));
1353 argsW++;
1354 }
1355 LocalFree(cl2a);
1356 return TRUE;
1357}
return
Definition: dirsup.c:529
@ extra
Definition: id3.c:95
#define for
Definition: utility.h:88
_In_ CLIPOBJ _In_ BRUSHOBJ _In_ LONG x1
Definition: winddi.h:3708

Referenced by test_commandline2argv().

◆ test_urls()

static void test_urls ( void  )
static

Definition at line 1869 of file shlexec.c.

1870{
1871 char url[MAX_PATH];
1872 INT_PTR rc;
1873
1874 if (!create_test_class("fakeproto", FALSE))
1875 {
1876 skip("Unable to create 'fakeproto' class for URL tests\n");
1877 return;
1878 }
1879 create_test_verb("fakeproto", "open", 0, "URL %1");
1880
1881 create_test_class("shlpaverb", TRUE);
1882 create_test_verb("shlpaverb", "averb", 0, "PAVerb \"%1\"");
1883
1884 /* Protocols must be properly declared */
1885 rc = shell_execute(NULL, "notaproto://foo", NULL, NULL);
1887 "%s returned %lu\n", shell_call, rc);
1888
1889 rc = shell_execute(NULL, "fakeproto://foo/bar", NULL, NULL);
1891 "%s returned %lu\n", shell_call, rc);
1892
1893 /* Here's a real live one */
1894 rc = shell_execute(NULL, "shlproto://foo/bar", NULL, NULL);
1895 ok(rc > 32, "%s failed: rc=%lu\n", shell_call, rc);
1896 okChildInt("argcA", 5);
1897 okChildString("argvA3", "URL");
1898 okChildString("argvA4", "shlproto://foo/bar");
1899
1900 /* Check default verb detection */
1901 rc = shell_execute(NULL, "shlpaverb://foo/bar", NULL, NULL);
1902 todo_wine ok(rc > 32 || /* XP+IE7 - Win10 */
1903 broken(rc == SE_ERR_NOASSOC), /* XP+IE6 */
1904 "%s failed: rc=%lu\n", shell_call, rc);
1905 if (rc > 32)
1906 {
1907 okChildInt("argcA", 5);
1908 todo_wine okChildString("argvA3", "PAVerb");
1909 todo_wine okChildString("argvA4", "shlpaverb://foo/bar");
1910 }
1911
1912 /* But alternative verbs are a recent feature! */
1913 rc = shell_execute("averb", "shlproto://foo/bar", NULL, NULL);
1914 ok(rc > 32 || /* Win8 - Win10 */
1915 broken(rc == SE_ERR_ACCESSDENIED), /* XP - Win7 */
1916 "%s failed: rc=%lu\n", shell_call, rc);
1917 if (rc > 32)
1918 {
1919 okChildString("argvA3", "AVerb");
1920 okChildString("argvA4", "shlproto://foo/bar");
1921 }
1922
1923 /* A .lnk ending does not turn a URL into a shortcut */
1924 rc = shell_execute(NULL, "shlproto://foo/bar.lnk", NULL, NULL);
1925 ok(rc > 32, "%s failed: rc=%lu\n", shell_call, rc);
1926 okChildInt("argcA", 5);
1927 okChildString("argvA3", "URL");
1928 okChildString("argvA4", "shlproto://foo/bar.lnk");
1929
1930 /* Neither does a .exe extension */
1931 rc = shell_execute(NULL, "shlproto://foo/bar.exe", NULL, NULL);
1932 ok(rc > 32, "%s failed: rc=%lu\n", shell_call, rc);
1933 okChildInt("argcA", 5);
1934 okChildString("argvA3", "URL");
1935 okChildString("argvA4", "shlproto://foo/bar.exe");
1936
1937 /* But a class name overrides it */
1938 rc = shell_execute(NULL, "shlproto://foo/bar", "shlexec.shlexec", NULL);
1939 ok(rc > 32, "%s failed: rc=%lu\n", shell_call, rc);
1940 okChildInt("argcA", 5);
1941 okChildString("argvA3", "URL");
1942 okChildString("argvA4", "shlproto://foo/bar");
1943
1944 /* Environment variables are expanded in URLs (but not in file URLs!) */
1946 NULL, "shlproto://%TMPDIR%/bar", NULL, NULL, NULL);
1947 okShell(rc > 32, "failed: rc=%lu\n", rc);
1948 okChildInt("argcA", 5);
1949 sprintf(url, "shlproto://%s/bar", tmpdir);
1950 okChildString("argvA3", "URL");
1951 okChildStringBroken("argvA4", url, "shlproto://%TMPDIR%/bar");
1952
1953 /* But only after the path has been identified as a URL */
1954 SetEnvironmentVariableA("urlprefix", "shlproto:///");
1955 rc = shell_execute(NULL, "%urlprefix%foo", NULL, NULL);
1956 todo_wine ok(rc == SE_ERR_FNF, "%s returned %lu\n", shell_call, rc);
1957 SetEnvironmentVariableA("urlprefix", NULL);
1958
1959 delete_test_class("fakeproto");
1960 delete_test_class("shlpaverb");
1961}
static const WCHAR url[]
Definition: encode.c:1432
#define okChildStringBroken(key, expected, broken)
Definition: shlexec.c:384

Referenced by START_TEST().

◆ WINETEST_PRINTF_ATTR()

static void WINAPIV WINETEST_PRINTF_ATTR ( ,
 
)
static

Definition at line 115 of file shlexec.c.

116{
118 char buffer[1024];
119 DWORD w;
120
125}
BOOL WINAPI WriteFile(IN HANDLE hFile, IN LPCVOID lpBuffer, IN DWORD nNumberOfBytesToWrite OPTIONAL, OUT LPDWORD lpNumberOfBytesWritten, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:24
GLubyte GLubyte GLubyte GLubyte w
Definition: glext.h:6102
GLfloat GLfloat GLfloat GLfloat h
Definition: glext.h:7723
int __cdecl vsprintf(char *_Dest, const char *_Format, va_list _Args)
Definition: sprintf.c:733
static __ms_va_list valist
Definition: printf.c:66
Definition: dsound.c:943
#define __ms_va_list
Definition: windef.h:456
#define __ms_va_end(list)
Definition: windef.h:458
#define __ms_va_start(list, arg)
Definition: windef.h:457

Variable Documentation

◆ _todo_wait

int _todo_wait = 0
static

Definition at line 491 of file shlexec.c.

Referenced by shell_execute_(), and shell_execute_ex_().

◆ argify_tests

const argify_tests_t argify_tests[]
static

Definition at line 1420 of file shlexec.c.

Referenced by test_argify().

◆ argv0

◆ assoc_desc

char assoc_desc[2048]
static

◆ bad_shellexecute

int bad_shellexecute = 0
static

Definition at line 494 of file shlexec.c.

Referenced by shell_execute_(), and test_fileurls().

◆ child_file

◆ cmdline_tests

const cmdline_tests_t cmdline_tests[]
static

Definition at line 1157 of file shlexec.c.

Referenced by test_commandline2argv().

◆ dde_default_app_tests

dde_default_app_tests_t dde_default_app_tests[]
static

Definition at line 2488 of file shlexec.c.

Referenced by test_dde_default_app().

◆ dde_ready_event

HANDLE dde_ready_event
static

Definition at line 57 of file shlexec.c.

Referenced by hooked_WaitForInputIdle(), and test_dde().

◆ dde_tests

dde_tests_t dde_tests[]
static
Initial value:
=
{
{"", NULL, NULL, NULL, NULL, 0, ""},
{"\"%1\"", NULL, NULL, NULL, NULL, 1, ""},
{"", "[open(\"%1\")]", "shlexec", "dde", NULL, 0, "[open(\"%s\")]"},
{"\"%1\"", "[open(\"%1\")]", "shlexec", "dde", NULL, 1, "[open(\"%s\")]"},
{"%1", "[open(%1)]", "shlexec", "dde", NULL, 2, "[open(%s)]", TRUE },
{"", "[open(\"%1\")]", "shlexec", "dde", "[ifexec(\"%1\")]", 0, "[ifexec(\"%s\")]"},
{"", "[open(\"%1\")]", "shlexec", NULL, NULL, 0, "[open(\"%s\")]"},
{"", "[open(\"%1\")]", NULL, "dde", NULL, 0, "[open(\"%s\")]"},
{NULL}
}

Definition at line 2274 of file shlexec.c.

Referenced by test_dde().

◆ ddeApplication

char ddeApplication[MAX_PATH]
static

Definition at line 149 of file shlexec.c.

Referenced by ddeCb(), and test_dde_default_app().

◆ ddeExec

char ddeExec[MAX_PATH]
static

Definition at line 149 of file shlexec.c.

Referenced by ddeCb(), doChild(), and test_dde().

◆ ddeInst

DWORD ddeInst
static

Definition at line 147 of file shlexec.c.

Referenced by dde_connect(), ddeCb(), doChild(), and test_dde_default_app().

◆ dllver

DLLVERSIONINFO dllver
static

Definition at line 54 of file shlexec.c.

Referenced by init_test(), test_filename(), and test_lnks().

◆ filename_tests

filename_tests_t filename_tests[]
static

Definition at line 1039 of file shlexec.c.

Referenced by test_filename(), and test_find_executable().

◆ fileurl_tests

fileurl_tests_t fileurl_tests[]
static

Definition at line 1750 of file shlexec.c.

Referenced by test_fileurls().

◆ hEvent

HANDLE hEvent
static

◆ hszTopic

◆ lnk_tests

filename_tests_t lnk_tests[]
static
Initial value:
=
{
{NULL, "%s\\nonexistent.shlexec", 0xa, 33},
{NULL, "%s\\nonexistent.noassoc", 0xa, 33},
{NULL, "%s\\test file.shlexec", 0xa, 33},
{NULL, "%s/%%nasty%% $file.shlexec", 0xa, 33},
{NULL, "%s\\test file.noassoc", 0xa, 33},
{NULL, NULL, 0}
}

Definition at line 2094 of file shlexec.c.

Referenced by test_lnks().

◆ myARGC

int myARGC
static

Definition at line 50 of file shlexec.c.

Referenced by START_TEST().

◆ myARGV

char** myARGV
static

Definition at line 51 of file shlexec.c.

Referenced by START_TEST().

◆ noquotes_tests

filename_tests_t noquotes_tests[]
static
Initial value:
=
{
{"NoQuotes", "%s\\test file.shlexec", 0xa, 33},
{"LowerL", "%s\\test file.shlexec", 0xa, 33},
{"UpperL", "%s\\test file.shlexec", 0xa, 33},
{NULL, NULL, 0}
}

Definition at line 1082 of file shlexec.c.

Referenced by test_filename().

◆ post_quit_on_execute

BOOL post_quit_on_execute
static

Definition at line 150 of file shlexec.c.

Referenced by ddeCb(), doChild(), and test_dde_default_app().

◆ shell_call

char shell_call[2048]
static

Definition at line 348 of file shlexec.c.

Referenced by shell_execute_(), shell_execute_ex_(), and test_urls().

◆ skip_noassoc_tests

BOOL skip_noassoc_tests = FALSE
static

Definition at line 56 of file shlexec.c.

Referenced by shell_execute_(), test_exes(), and test_filename().

◆ skip_shlexec_tests

◆ testfiles

const char* testfiles[]
static
Initial value:
=
{
"%s\\test file.shlexec",
"%s\\%%nasty%% $file.shlexec",
"%s\\test file.noassoc",
"%s\\test file.noassoc.shlexec",
"%s\\test file.shlexec.noassoc",
"%s\\test_shortcut_shlexec.lnk",
"%s\\test_shortcut_exe.lnk",
"%s\\test file.shl",
"%s\\test file.shlfoo",
"%s\\test file.sha",
"%s\\test file.sfe",
"%s\\test file.shlproto",
"%s\\masked file.shlexec",
"%s\\masked",
"%s\\test file.sde",
"%s\\test file.exe",
"%s\\test2.exe",
"%s\\simple.shlexec",
"%s\\drawback_file.noassoc",
"%s\\drawback_file.noassoc foo.shlexec",
"%s\\drawback_nonexist.noassoc foo.shlexec",
}

Definition at line 1005 of file shlexec.c.

Referenced by cleanup_test(), and init_test().

◆ tmpdir

◆ waitforinputidle_count

int waitforinputidle_count
static

Definition at line 2302 of file shlexec.c.

Referenced by hooked_WaitForInputIdle(), and test_dde().