ReactOS 0.4.16-dev-306-g647d351
svchlp.c File Reference
#include "precomp.h"
Include dependency graph for svchlp.c:

Go to the source code of this file.

Functions

void send_msg (const char *type, const char *msg)
 
void service_trace (const char *msg,...)
 
void service_ok (int cnd, const char *msg,...)
 
void service_process (BOOL(*start_service)(PCSTR, PCWSTR), int argc, char **argv)
 
SC_HANDLE register_service_exA (SC_HANDLE scm_handle, PCSTR test_name, PCSTR service_name, PCSTR extra_args OPTIONAL, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCSTR lpLoadOrderGroup OPTIONAL, LPDWORD lpdwTagId OPTIONAL, LPCSTR lpDependencies OPTIONAL, LPCSTR lpServiceStartName OPTIONAL, LPCSTR lpPassword OPTIONAL)
 
SC_HANDLE register_service_exW (SC_HANDLE scm_handle, PCWSTR test_name, PCWSTR service_name, PCWSTR extra_args OPTIONAL, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCWSTR lpLoadOrderGroup OPTIONAL, LPDWORD lpdwTagId OPTIONAL, LPCWSTR lpDependencies OPTIONAL, LPCWSTR lpServiceStartName OPTIONAL, LPCWSTR lpPassword OPTIONAL)
 
SC_HANDLE register_serviceA (SC_HANDLE scm_handle, PCSTR test_name, PCSTR service_name, PCSTR extra_args OPTIONAL)
 
SC_HANDLE register_serviceW (SC_HANDLE scm_handle, PCWSTR test_name, PCWSTR service_name, PCWSTR extra_args OPTIONAL)
 
static DWORD WINAPI pipe_thread (void *param)
 
void test_runner (void(*run_test)(PCSTR, PCWSTR, void *), void *param)
 

Variables

static HANDLE hClientPipe = INVALID_HANDLE_VALUE
 
static WCHAR named_pipe_name [100]
 
static CHAR service_nameA [100]
 
static WCHAR service_nameW [100]
 

Function Documentation

◆ pipe_thread()

static DWORD WINAPI pipe_thread ( void param)
static

Definition at line 226 of file svchlp.c.

227{
228 HANDLE hServerPipe = (HANDLE)param;
229 DWORD read;
230 BOOL res;
231 char buf[512];
232
233 // printf("pipe_thread -- ConnectNamedPipe...\n");
234 res = ConnectNamedPipe(hServerPipe, NULL);
235 ok(res || GetLastError() == ERROR_PIPE_CONNECTED, "ConnectNamedPipe failed: %lu\n", GetLastError());
236 // printf("pipe_thread -- ConnectNamedPipe ok\n");
237
238 while (1)
239 {
240 res = ReadFile(hServerPipe, buf, sizeof(buf), &read, NULL);
241 if (!res)
242 {
244 "ReadFile failed: %lu\n", GetLastError());
245 // printf("pipe_thread -- break loop\n");
246 break;
247 }
248
249 if (!strncmp(buf, "TRACE:", 6))
250 {
251 trace("service trace: %s", buf+6);
252 }
253 else if (!strncmp(buf, "OK:", 3))
254 {
255 ok(1, "service: %s", buf+3);
256 }
257 else if (!strncmp(buf, "FAIL:", 5))
258 {
259 ok(0, "service: %s", buf+5);
260 }
261 else
262 {
263 ok(0, "malformed service message: %s\n", buf);
264 }
265 }
266
267 // printf("pipe_thread -- DisconnectNamedPipe\n");
268
269 /*
270 * Flush the pipe to allow the client to read
271 * the pipe's contents before disconnecting.
272 */
273 FlushFileBuffers(hServerPipe);
274
275 DisconnectNamedPipe(hServerPipe);
276 trace("pipe disconnected\n");
277 return 0;
278}
int strncmp(const char *String1, const char *String2, ACPI_SIZE Count)
Definition: utclib.c:534
#define read
Definition: acwin.h:96
#define trace
Definition: atltest.h:70
#define ok(value,...)
Definition: atltest.h:57
#define NULL
Definition: types.h:112
#define ReadFile(a, b, c, d, e)
Definition: compat.h:742
#define ERROR_INVALID_HANDLE
Definition: compat.h:98
BOOL WINAPI FlushFileBuffers(IN HANDLE hFile)
Definition: fileinfo.c:25
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
GLuint res
Definition: glext.h:9613
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
GLfloat param
Definition: glext.h:5796
BOOL WINAPI ConnectNamedPipe(IN HANDLE hNamedPipe, IN LPOVERLAPPED lpOverlapped)
Definition: npipe.c:701
BOOL WINAPI DisconnectNamedPipe(HANDLE hNamedPipe)
Definition: npipe.c:961
PVOID HANDLE
Definition: typedefs.h:73
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
#define ERROR_BROKEN_PIPE
Definition: winerror.h:183
#define ERROR_PIPE_CONNECTED
Definition: winerror.h:352

Referenced by test_runner().

◆ register_service_exA()

SC_HANDLE register_service_exA ( SC_HANDLE  scm_handle,
PCSTR  test_name,
PCSTR  service_name,
PCSTR extra_args  OPTIONAL,
DWORD  dwDesiredAccess,
DWORD  dwServiceType,
DWORD  dwStartType,
DWORD  dwErrorControl,
LPCSTR lpLoadOrderGroup  OPTIONAL,
LPDWORD lpdwTagId  OPTIONAL,
LPCSTR lpDependencies  OPTIONAL,
LPCSTR lpServiceStartName  OPTIONAL,
LPCSTR lpPassword  OPTIONAL 
)

Definition at line 86 of file svchlp.c.

100{
101 SC_HANDLE service;
102 CHAR service_cmd[MAX_PATH+150];
103
104 /* Retrieve our full path */
105 if (!GetModuleFileNameA(NULL, service_cmd, MAX_PATH))
106 {
107 skip("GetModuleFileNameW failed with error %lu!\n", GetLastError());
108 return NULL;
109 }
110
111 /*
112 * Build up our custom command line. The first parameter is the test name,
113 * the second parameter is the flag used to decide whether we should start
114 * as a service.
115 */
116 StringCbCatA(service_cmd, sizeof(service_cmd), " ");
117 StringCbCatA(service_cmd, sizeof(service_cmd), test_name);
118 StringCbCatA(service_cmd, sizeof(service_cmd), " ");
119 StringCbCatA(service_cmd, sizeof(service_cmd), service_name);
120 if (extra_args)
121 {
122 StringCbCatA(service_cmd, sizeof(service_cmd), " ");
123 StringCbCatA(service_cmd, sizeof(service_cmd), extra_args);
124 }
125
126 trace("service_cmd \"%s\"\n", service_cmd);
127
129 dwDesiredAccess, dwServiceType, dwStartType, dwErrorControl,
130 service_cmd, lpLoadOrderGroup, lpdwTagId, lpDependencies,
131 lpServiceStartName, lpPassword);
132 if (!service && GetLastError() == ERROR_ACCESS_DENIED)
133 {
134 skip("Not enough access right to create service.\n");
135 return NULL;
136 }
137
138 ok(service != NULL, "CreateService failed: %lu\n", GetLastError());
139 return service;
140}
static char service_name[100]
static SC_HANDLE scm_handle
Definition: ServiceArgs.c:20
#define skip(...)
Definition: atltest.h:64
#define MAX_PATH
Definition: compat.h:34
#define ERROR_ACCESS_DENIED
Definition: compat.h:97
DWORD WINAPI GetModuleFileNameA(HINSTANCE hModule, LPSTR lpFilename, DWORD nSize)
Definition: loader.c:539
static const char * test_name
Definition: run.c:177
SC_HANDLE WINAPI CreateServiceA(SC_HANDLE hSCManager, LPCSTR lpServiceName, LPCSTR lpDisplayName, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCSTR lpBinaryPathName, LPCSTR lpLoadOrderGroup, LPDWORD lpdwTagId, LPCSTR lpDependencies, LPCSTR lpServiceStartName, LPCSTR lpPassword)
Definition: scm.c:680
STRSAFEAPI StringCbCatA(STRSAFE_LPSTR pszDest, size_t cbDest, STRSAFE_LPCSTR pszSrc)
Definition: strsafe.h:337
char CHAR
Definition: xmlstorage.h:175

Referenced by register_serviceA().

◆ register_service_exW()

SC_HANDLE register_service_exW ( SC_HANDLE  scm_handle,
PCWSTR  test_name,
PCWSTR  service_name,
PCWSTR extra_args  OPTIONAL,
DWORD  dwDesiredAccess,
DWORD  dwServiceType,
DWORD  dwStartType,
DWORD  dwErrorControl,
LPCWSTR lpLoadOrderGroup  OPTIONAL,
LPDWORD lpdwTagId  OPTIONAL,
LPCWSTR lpDependencies  OPTIONAL,
LPCWSTR lpServiceStartName  OPTIONAL,
LPCWSTR lpPassword  OPTIONAL 
)

Definition at line 142 of file svchlp.c.

156{
157 SC_HANDLE service;
158 WCHAR service_cmd[MAX_PATH+150];
159
160 /* Retrieve our full path */
161 if (!GetModuleFileNameW(NULL, service_cmd, MAX_PATH))
162 {
163 skip("GetModuleFileNameW failed with error %lu!\n", GetLastError());
164 return NULL;
165 }
166
167 /*
168 * Build up our custom command line. The first parameter is the test name,
169 * the second parameter is the flag used to decide whether we should start
170 * as a service.
171 */
172 StringCbCatW(service_cmd, sizeof(service_cmd), L" ");
173 StringCbCatW(service_cmd, sizeof(service_cmd), test_name);
174 StringCbCatW(service_cmd, sizeof(service_cmd), L" ");
175 StringCbCatW(service_cmd, sizeof(service_cmd), service_name);
176 if (extra_args)
177 {
178 StringCbCatW(service_cmd, sizeof(service_cmd), L" ");
179 StringCbCatW(service_cmd, sizeof(service_cmd), extra_args);
180 }
181
182 trace("service_cmd \"%ls\"\n", service_cmd);
183
185 dwDesiredAccess, dwServiceType, dwStartType, dwErrorControl,
186 service_cmd, lpLoadOrderGroup, lpdwTagId, lpDependencies,
187 lpServiceStartName, lpPassword);
188 if (!service && GetLastError() == ERROR_ACCESS_DENIED)
189 {
190 skip("Not enough access right to create service.\n");
191 return NULL;
192 }
193
194 ok(service != NULL, "CreateService failed: %lu\n", GetLastError());
195 return service;
196}
DWORD WINAPI GetModuleFileNameW(HINSTANCE hModule, LPWSTR lpFilename, DWORD nSize)
Definition: loader.c:600
#define L(x)
Definition: ntvdm.h:50
SC_HANDLE WINAPI CreateServiceW(SC_HANDLE hSCManager, LPCWSTR lpServiceName, LPCWSTR lpDisplayName, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCWSTR lpBinaryPathName, LPCWSTR lpLoadOrderGroup, LPDWORD lpdwTagId, LPCWSTR lpDependencies, LPCWSTR lpServiceStartName, LPCWSTR lpPassword)
Definition: scm.c:812
STRSAFEAPI StringCbCatW(STRSAFE_LPWSTR pszDest, size_t cbDest, STRSAFE_LPCWSTR pszSrc)
Definition: strsafe.h:342
__wchar_t WCHAR
Definition: xmlstorage.h:180

Referenced by my_test_server(), and register_serviceW().

◆ register_serviceA()

SC_HANDLE register_serviceA ( SC_HANDLE  scm_handle,
PCSTR  test_name,
PCSTR  service_name,
PCSTR extra_args  OPTIONAL 
)

Definition at line 198 of file svchlp.c.

203{
209 NULL, NULL, NULL, NULL, NULL);
210}
SC_HANDLE register_service_exA(SC_HANDLE scm_handle, PCSTR test_name, PCSTR service_name, PCSTR extra_args OPTIONAL, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCSTR lpLoadOrderGroup OPTIONAL, LPDWORD lpdwTagId OPTIONAL, LPCSTR lpDependencies OPTIONAL, LPCSTR lpServiceStartName OPTIONAL, LPCSTR lpPassword OPTIONAL)
Definition: svchlp.c:86
#define SERVICE_ALL_ACCESS
Definition: winsvc.h:62
#define SERVICE_DEMAND_START
Definition: cmtypes.h:978
#define SERVICE_WIN32_OWN_PROCESS
Definition: cmtypes.h:962
#define SERVICE_ERROR_IGNORE
Definition: cmtypes.h:981

◆ register_serviceW()

SC_HANDLE register_serviceW ( SC_HANDLE  scm_handle,
PCWSTR  test_name,
PCWSTR  service_name,
PCWSTR extra_args  OPTIONAL 
)

Definition at line 212 of file svchlp.c.

217{
223 NULL, NULL, NULL, NULL, NULL);
224}
SC_HANDLE register_service_exW(SC_HANDLE scm_handle, PCWSTR test_name, PCWSTR service_name, PCWSTR extra_args OPTIONAL, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCWSTR lpLoadOrderGroup OPTIONAL, LPDWORD lpdwTagId OPTIONAL, LPCWSTR lpDependencies OPTIONAL, LPCWSTR lpServiceStartName OPTIONAL, LPCWSTR lpPassword OPTIONAL)
Definition: svchlp.c:142

◆ send_msg()

void send_msg ( const char type,
const char msg 
)

Definition at line 27 of file svchlp.c.

28{
29 DWORD written = 0;
30 char buf[512];
31
32 StringCbPrintfA(buf, sizeof(buf), "%s:%s", type, msg);
33 WriteFile(hClientPipe, buf, lstrlenA(buf)+1, &written, NULL);
34}
#define msg(x)
Definition: auth_time.c:54
BOOL WINAPI WriteFile(IN HANDLE hFile, IN LPCVOID lpBuffer, IN DWORD nNumberOfBytesToWrite OPTIONAL, OUT LPDWORD lpNumberOfBytesWritten, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:24
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
int WINAPI lstrlenA(LPCSTR lpString)
Definition: lstring.c:145
STRSAFEAPI StringCbPrintfA(STRSAFE_LPSTR pszDest, size_t cbDest, STRSAFE_LPCSTR pszFormat,...)
Definition: strsafe.h:547
static HANDLE hClientPipe
Definition: svchlp.c:18

Referenced by service_ok(), and service_trace().

◆ service_ok()

void service_ok ( int  cnd,
const char msg,
  ... 
)

Definition at line 48 of file svchlp.c.

49{
51 char buf[512];
52
54 StringCbVPrintfA(buf, sizeof(buf), msg, valist);
56
57 send_msg(cnd ? "OK" : "FAIL", buf);
58}
char * va_list
Definition: acmsvcex.h:78
#define va_end(ap)
Definition: acmsvcex.h:90
#define va_start(ap, A)
Definition: acmsvcex.h:91
static __ms_va_list valist
Definition: printf.c:66
STRSAFEAPI StringCbVPrintfA(STRSAFE_LPSTR pszDest, size_t cbDest, STRSAFE_LPCSTR pszFormat, va_list argList)
Definition: strsafe.h:502
void send_msg(const char *type, const char *msg)
Definition: svchlp.c:27

◆ service_process()

void service_process ( BOOL(*)(PCSTR, PCWSTR start_service,
int  argc,
char **  argv 
)

Definition at line 60 of file svchlp.c.

61{
62 BOOL res;
63
66 StringCbPrintfW(named_pipe_name, sizeof(named_pipe_name), L"\\\\.\\pipe\\%ls_pipe", service_nameW);
67
69 if (!res)
70 return;
71
74 return;
75
76 service_trace("Service process starting...\n");
78 service_trace("Service process stopped.\n");
79
81}
#define CloseHandle
Definition: compat.h:739
#define CP_ACP
Definition: compat.h:109
#define OPEN_EXISTING
Definition: compat.h:775
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
#define CreateFileW
Definition: compat.h:741
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:137
#define MultiByteToWideChar
Definition: compat.h:110
static HRESULT start_service(const WCHAR *name, VARIANT *retval)
Definition: service.c:169
#define argv
Definition: mplay32.c:18
BOOL WINAPI WaitNamedPipeW(LPCWSTR lpNamedPipeName, DWORD nTimeOut)
Definition: npipe.c:458
#define GENERIC_WRITE
Definition: nt_native.h:90
#define _countof(array)
Definition: sndvol32.h:70
STRSAFEAPI StringCbPrintfW(STRSAFE_LPWSTR pszDest, size_t cbDest, STRSAFE_LPCWSTR pszFormat,...)
Definition: strsafe.h:557
STRSAFEAPI StringCbCopyA(STRSAFE_LPSTR pszDest, size_t cbDest, STRSAFE_LPCSTR pszSrc)
Definition: strsafe.h:161
static CHAR service_nameA[100]
Definition: svchlp.c:21
void service_trace(const char *msg,...)
Definition: svchlp.c:36
static WCHAR service_nameW[100]
Definition: svchlp.c:22
static WCHAR named_pipe_name[100]
Definition: svchlp.c:19
#define NMPWAIT_USE_DEFAULT_WAIT
Definition: winbase.h:135

◆ service_trace()

void service_trace ( const char msg,
  ... 
)

Definition at line 36 of file svchlp.c.

37{
39 char buf[512];
40
42 StringCbVPrintfA(buf, sizeof(buf), msg, valist);
44
45 send_msg("TRACE", buf);
46}

Referenced by service_main(), and service_process().

◆ test_runner()

void test_runner ( void(*)(PCSTR, PCWSTR, void *)  run_test,
void param 
)

Definition at line 280 of file svchlp.c.

281{
282 HANDLE hServerPipe = INVALID_HANDLE_VALUE;
284
285 StringCbPrintfW(service_nameW, sizeof(service_nameW), L"WineTestService%lu", GetTickCount());
287 //trace("service_name: %ls\n", service_nameW);
288 StringCbPrintfW(named_pipe_name, sizeof(named_pipe_name), L"\\\\.\\pipe\\%ls_pipe", service_nameW);
289
291 PIPE_TYPE_MESSAGE|PIPE_READMODE_MESSAGE|PIPE_WAIT, 10, 2048, 2048, 10000, NULL);
292 ok(hServerPipe != INVALID_HANDLE_VALUE, "CreateNamedPipe failed: %lu\n", GetLastError());
293 if (hServerPipe == INVALID_HANDLE_VALUE)
294 return;
295
296 hThread = CreateThread(NULL, 0, pipe_thread, (LPVOID)hServerPipe, 0, NULL);
297 ok(hThread != NULL, "CreateThread failed: %lu\n", GetLastError());
298 if (!hThread)
299 goto Quit;
300
302
303 ok(WaitForSingleObject(hThread, 10000) == WAIT_OBJECT_0, "Timeout waiting for thread\n");
304
305Quit:
306 if (hThread)
307 {
308 /* Be sure to kill the thread if it did not already terminate */
311 }
312
313 if (hServerPipe != INVALID_HANDLE_VALUE)
314 CloseHandle(hServerPipe);
315}
#define WideCharToMultiByte
Definition: compat.h:111
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
BOOL WINAPI TerminateThread(IN HANDLE hThread, IN DWORD dwExitCode)
Definition: thread.c:587
DWORD WINAPI GetTickCount(VOID)
Definition: time.c:455
#define run_test(test)
Definition: ms_seh.c:71
HANDLE hThread
Definition: wizard.c:28
HANDLE WINAPI CreateNamedPipeW(LPCWSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD nMaxInstances, DWORD nOutBufferSize, DWORD nInBufferSize, DWORD nDefaultTimeOut, LPSECURITY_ATTRIBUTES lpSecurityAttributes)
Definition: npipe.c:246
static DWORD WINAPI pipe_thread(void *param)
Definition: svchlp.c:226
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
Definition: synch.c:82
#define PIPE_ACCESS_INBOUND
Definition: winbase.h:166
#define PIPE_WAIT
Definition: winbase.h:172
#define PIPE_READMODE_MESSAGE
Definition: winbase.h:171
#define WAIT_OBJECT_0
Definition: winbase.h:432
#define PIPE_TYPE_MESSAGE
Definition: winbase.h:169

Variable Documentation

◆ hClientPipe

HANDLE hClientPipe = INVALID_HANDLE_VALUE
static

Definition at line 18 of file svchlp.c.

Referenced by send_msg(), and service_process().

◆ named_pipe_name

WCHAR named_pipe_name[100]
static

Definition at line 19 of file svchlp.c.

Referenced by service_process(), and test_runner().

◆ service_nameA

CHAR service_nameA[100]
static

Definition at line 21 of file svchlp.c.

Referenced by service_process(), and test_runner().

◆ service_nameW

WCHAR service_nameW[100]
static

Definition at line 22 of file svchlp.c.

Referenced by service_process(), and test_runner().