54 LPWSTR pch, pGroupNameStart, lpServiceGroup;
80 if ((*
pch ==
' ') || (*
pch ==
'\t'))
101 if ((*
pch !=
' ') && (*
pch !=
'\t'))
break;
113 if (*
pch ==
'k' || *
pch ==
'K')
126 pGroupNameStart =
pch;
132 pGroupNameStart = ++
pch;
133 while (*
pch)
if (*
pch++ ==
'"')
break;
138 while ((*
pch) && ((*
pch !=
' ') && (*
pch !=
'\t')))
pch++;
148 *pGroupName = pGroupNameStart;
155 DBG_TRACE(
"Command line : %ws\n", pszCmdLine);
158 DBG_TRACE(
"Service Group : %ws\n", lpServiceGroup);
165 "%ws [-k <key>] | [-r] | <service>\n\n"
166 " -k <key> Host all services whose ImagePath matches\n"
167 " %ws -k <key>.\n\n",
188 ASSERT(pOptions->ServiceGroupName);
192 pOptions->ServiceGroupName,
204 pOptions->ServiceGroupName,
215 L"CoInitializeSecurityParam",
219 pOptions->CoInitializeSecurityParam =
dwData;
223 if (pOptions->CoInitializeSecurityParam)
232 pOptions->AuthenticationLevel =
dwData;
242 pOptions->ImpersonationLevel =
dwData;
248 pOptions->AuthenticationCapabilities = EOAC_NO_CUSTOM_MARSHAL |
253 pOptions->AuthenticationCapabilities =
dwData;
260 pOptions->DefaultRpcStackSize =
dwData;
266 pOptions->SystemCritical =
dwData;
287 L"Software\\Microsoft\\Windows NT\\CurrentVersion\\Svchost",
307 pszServiceName +=
lstrlenW(pszServiceName) + 1;
326 pszServiceName +=
lstrlenW(pszServiceName) + 1;
349 L"Software\\Microsoft\\Windows NT\\CurrentVersion\\Svchost",
361 DebugBreakOn =
Data != 0;
389 L"System\\CurrentControlSet\\Services",
432 ASSERT(pService->cServiceActiveThreadCount > 0);
433 pService->cServiceActiveThreadCount--;
440 L"ServiceDllUnloadOnStop",
450 if (pService->cServiceActiveThreadCount != 0)
453 DBG_TRACE(
"Skip Unload dll %ws for service %ws, "
454 "active threads %d\n",
455 pService->pDll->pszDllPath,
456 pService->pszServiceName,
457 pService->cServiceActiveThreadCount);
462 DBG_TRACE(
"Unload dll %ws for service %ws\n",
463 pService->pDll->pszDllPath,
464 pService->pszServiceName);
468 pService->pDll->hModule =
NULL;
504 DBG_TRACE(
"Call stop callback for service %ws, active threads %d\n",
507 pfnStopCallback(pSvcsStopCbContext->
pContext, TimerOrWaitFired);
533 if ((phNewWaitObject ==
NULL) ||
536 (pfnStopCallback ==
NULL))
562 DBG_ERR(
"Service %ws missing or already registered for callback, "
571 if (pSvcsStopCbContext ==
NULL)
575 DBG_ERR(
"MemAlloc for context block for service %ws failed, status "
583 pSvcsStopCbContext->
pContext = pContext;
584 pSvcsStopCbContext->
pService = pService;
595 DBG_TRACE(
"Registered stop callback for service %ws, active threads %d\n",
603 DBG_ERR(
"Registration for stop callback for service %ws failed, "
644 DBG_ERR(
"AbortSvchostService: SetServiceStatus error %ld\n",
651 DBG_ERR(
"AbortSvchostService: RegisterServiceCtrlHandler failed %d\n",
673 DBG_ERR(
"ActivateActCtx for %ws failed. Error %d.\n",
691 DBG_ERR(
"LoadLibrary (%ws) failed. Error %d.\n",
704 if (!lpAddress && lpdwError)
708 DBG_ERR(
"GetProcAddress (%s) failed on DLL %ws. Error %d.\n",
750 pNextEntry = pNextEntry->
Flink;
768 ULONG nDllPathLength, nManifestPathLength;
773 nDllPathLength =
lstrlenW(pszDllPath);
774 nManifestPathLength =
lstrlenW(pszManifestPath);
779 (nDllPathLength + nManifestPathLength) *
sizeof(
WCHAR) +
797 sizeof(
WCHAR) * nDllPathLength);
800 sizeof(
WCHAR) * nManifestPathLength);
826 DWORD dwError, cbDllLength, cbData, dwType;
837 actCtx.cbSize =
sizeof(actCtx);
850 pDll = pService->pDll;
851 if (pDll !=
NULL)
goto HaveDll;
857 *lpdwError = dwError;
882 *lpdwError = dwError;
883 DBG_ERR(
"RegQueryValueEx for the ServiceDll parameter of the %ws "
884 "service returned %u\n",
885 pService->pszServiceName,
895 DBG_ERR(
"The ServiceDll parameter for the %ws service is not of type "
897 pService->pszServiceName);
920 *lpdwError = dwError;
921 DBG_ERR(
"RegQueryValueEx for the ServiceManifest parameter of the "
922 "%ws service returned %u\n",
923 pService->pszServiceName,
936 pszDllPath = szDllBuffer;
945 DBG_ERR(
"The ServiceManifest parameter for the %ws service is not "
946 "of type REG_EXPAND_SZ\n",
947 pService->pszServiceName);
962 cbDllLength =
lstrlenW(szDllBuffer);
966 if (szDllBuffer[cbDllLength] ==
'\\' || szDllBuffer[cbDllLength] ==
'/')
969 pszDllPath = &szDllBuffer[cbDllLength + 1];
979 pDll =
FindDll(szManifestBuffer, pszDllPath, pService);
986 actCtx.lpSource = szManifestBuffer;
992 DBG_ERR(
"CreateActCtxW(%ws) for the %ws service returned %u\n",
994 pService->pszServiceName,
1001 pDll =
AddDll(szManifestBuffer, pszDllPath, pService, lpdwError);
1012 pService->pDll = pDll;
1018 &pService->pszServiceMain);
1021 if (!pService->pDll)
1031 pService->pszServiceMain ?
1032 pService->pszServiceMain :
1038 "SvchostPushServiceGlobals",
1065 lpServiceName = *lpServiceArgVectors;
1087 DBG_TRACE(
"Attaching debugger before getting ServiceMain for %ws...\n",
1095 (
PVOID*)&ServiceInitGlobals,
1100 (ServiceInitGlobals !=
NULL) &&
1119 if (ServiceInitGlobals !=
NULL)
1131 if (lpServiceName !=
NULL)
1140 else if (lpServiceName !=
NULL)
1151 DBG_TRACE(
"Calling ServiceMain for %ws...\n", lpServiceName);
1152 ServiceMain(dwNumServicesArgs, lpServiceArgVectors);
1157 else if (lpServiceName !=
NULL)
1187 DBG_TRACE(
"Added service table entry for %ws\n",
1188 pServiceTable[
i].lpServiceName);
1194 return pServiceTable;
1207 if (pOptions->CoInitializeSecurityParam != 0)
1211 pOptions->AuthenticationLevel,
1212 pOptions->ImpersonationLevel,
1213 pOptions->AuthenticationCapabilities);
1218 if (pOptions->DefaultRpcStackSize != 0)
1235 if (pOptions->SystemCritical !=
FALSE)
1269 if (lpOptions ==
NULL)
1272 DBG_TRACE(
"Calling ExitProcess for %ws\n", pszCmdLine);
1281 if (pServiceTable ==
NULL)
1292 DBG_ERR(
"%s",
"CallPerInstanceInitFunctions failed -- exiting!\n");
static SERVICE_STATUS_HANDLE(WINAPI *pRegisterServiceCtrlHandlerExA)(LPCSTR
BOOL MemFree(IN PVOID lpMem)
PVOID MemAlloc(IN DWORD dwFlags, IN SIZE_T dwBytes)
VOID CALLBACK ServiceMain(DWORD argc, LPWSTR argv)
static WCHAR ServiceName[]
static SERVICE_STATUS ServiceStatus
VOID WINAPI MemInit(_In_ HANDLE Heap)
PSVCHOST_GLOBAL_DATA g_pSvchostSharedGlobals
VOID WINAPI SvchostBuildSharedGlobals(VOID)
VOID WINAPI SvchostCharLowerW(_In_ LPCWSTR lpSrcStr)
DWORD WINAPI RegQueryStringA(_In_ HKEY hKey, _In_ LPCWSTR pszValueName, _In_ DWORD dwExpectedType, _Out_ LPCSTR *ppszData)
DWORD WINAPI RegQueryString(_In_ HKEY hKey, _In_ LPCWSTR pszValueName, _In_ DWORD dwExpectedType, _Out_ PBYTE *ppbData)
DWORD WINAPI RegQueryDword(_In_ HKEY hKey, _In_ LPCWSTR pszValueName, _Out_ PDWORD pdwValue)
#define RegCloseKey(hKey)
#define ERROR_NOT_ENOUGH_MEMORY
LONG WINAPI RegOpenKeyExW(HKEY hKey, LPCWSTR lpSubKey, DWORD ulOptions, REGSAM samDesired, PHKEY phkResult)
LONG WINAPI RegQueryValueExW(_In_ HKEY hkeyorg, _In_ LPCWSTR name, _In_ LPDWORD reserved, _In_ LPDWORD type, _In_ LPBYTE data, _In_ LPDWORD count)
#define ERROR_INVALID_PARAMETER
#define GetProcAddress(x, y)
#define INVALID_HANDLE_VALUE
VOID WINAPI ReleaseActCtx(IN HANDLE hActCtx)
BOOL WINAPI DeactivateActCtx(IN DWORD dwFlags, IN ULONG_PTR ulCookie)
BOOL WINAPI ActivateActCtx(IN HANDLE hActCtx, OUT PULONG_PTR ulCookie)
DWORD WINAPI ExpandEnvironmentStringsW(IN LPCWSTR lpSrc, IN LPWSTR lpDst, IN DWORD nSize)
UINT WINAPI SetErrorMode(IN UINT uMode)
LPTOP_LEVEL_EXCEPTION_FILTER WINAPI DECLSPEC_HOTPATCH SetUnhandledExceptionFilter(IN LPTOP_LEVEL_EXCEPTION_FILTER lpTopLevelExceptionFilter)
HINSTANCE WINAPI DECLSPEC_HOTPATCH LoadLibraryExW(LPCWSTR lpLibFileName, HANDLE hFile, DWORD dwFlags)
VOID WINAPI ExitProcess(IN UINT uExitCode)
LPWSTR WINAPI GetCommandLineW(VOID)
HANDLE WINAPI CreateActCtxW(PCACTCTXW pActCtx)
int WINAPI lstrcmpW(LPCWSTR str1, LPCWSTR str2)
int WINAPI lstrcmpiW(LPCWSTR str1, LPCWSTR str2)
#define InsertTailList(ListHead, Entry)
#define InitializeListHead(ListHead)
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
#define memcpy(s1, s2, n)
#define ERROR_FILE_NOT_FOUND
static HANDLE ULONG_PTR dwData
NTSYSAPI NTSTATUS __cdecl RtlSetProcessIsCritical(_In_ BOOLEAN NewValue, _Out_opt_ PBOOLEAN OldValue, _In_ BOOLEAN NeedBreaks)
#define SEM_FAILCRITICALERRORS
RPC_STATUS WINAPI RpcMgmtSetServerStackSize(ULONG ThreadStackSize)
#define RPC_C_AUTHN_LEVEL_PKT
#define RPC_C_IMP_LEVEL_IDENTIFY
BOOL WINAPI StartServiceCtrlDispatcherW(const SERVICE_TABLE_ENTRYW *lpServiceStartTable)
SERVICE_STATUS_HANDLE WINAPI RegisterServiceCtrlHandlerW(LPCWSTR lpServiceName, LPHANDLER_FUNCTION lpHandlerProc)
BOOL WINAPI SetServiceStatus(SERVICE_STATUS_HANDLE hServiceStatus, LPSERVICE_STATUS lpServiceStatus)
WAITORTIMERCALLBACK PSVCHOST_STOP_CALLBACK
LONG NTAPI RtlUnhandledExceptionFilter(IN struct _EXCEPTION_POINTERS *ExceptionInfo)
BOOL WINAPI InitializeSecurity(_In_ DWORD dwParam, _In_ DWORD dwAuthnLevel, _In_ DWORD dwImpLevel, _In_ DWORD dwCapabilities)
struct _LIST_ENTRY * Flink
DWORD dwServiceSpecificExitCode
LPSERVICE_MAIN_FUNCTIONW lpServiceProc
PSVCHOST_SERVICE pService
struct _SVCHOST_SERVICE * pService
LONG cServiceActiveThreadCount
PSVCHOST_STOP_CALLBACK pfnStopCallback
PSVCHOST_OPTIONS WINAPI BuildCommandOptions(_In_ LPWSTR pszCmdLine)
__callback LONG WINAPI SvchostUnhandledExceptionFilter(_In_ struct _EXCEPTION_POINTERS *ExceptionInfo)
PSVCHOST_SERVICE ServiceArray
VOID WINAPI DummySvchostCtrlHandler(_In_ DWORD dwControl)
VOID WINAPI GetServiceMainFunctions(_In_ PSVCHOST_SERVICE pService, _Out_ PVOID *pServiceMain, _Out_ PVOID *pPushServiceGlobals, _Out_ PDWORD lpdwError)
VOID WINAPI AbortSvchostService(_In_ LPCWSTR lpServiceName, _In_ DWORD dwExitCode)
PVOID WINAPI GetServiceDllFunction(_In_ PSVCHOST_DLL pDll, _In_ LPCSTR lpProcName, _Out_ PDWORD lpdwError)
PSVCHOST_DLL WINAPI FindDll(_In_ LPCWSTR pszManifestPath, _In_ LPCWSTR pszDllPath, _In_ PSVCHOST_SERVICE pService)
VOID WINAPI ServiceStarter(_In_ DWORD dwNumServicesArgs, _In_ LPWSTR *lpServiceArgVectors)
BOOL WINAPI FDebugBreakForService(_In_ LPCWSTR ServiceName)
CRITICAL_SECTION ListLock
VOID WINAPI BuildServiceArray(_In_ PSVCHOST_OPTIONS lpOptions)
DWORD WINAPI OpenServiceParametersKey(_In_ LPCWSTR lpSubKey, _Out_ PHKEY phKey)
VOID __cdecl wmainCRTStartup(VOID)
PSVCHOST_DLL WINAPI AddDll(_In_ LPCWSTR pszManifestPath, _In_ LPCWSTR pszDllPath, _In_ PSVCHOST_SERVICE pService, _Out_ PDWORD lpdwError)
DWORD WINAPI SvcRegisterStopCallback(_Out_ PHANDLE phNewWaitObject, _In_ PCWSTR ServiceName, _In_ HANDLE hObject, _In_ PSVCHOST_STOP_CALLBACK pfnStopCallback, _In_ PVOID pContext, _In_ ULONG dwFlags)
VOID WINAPI SvchostStopCallback(_In_ PVOID Context, _In_ BOOLEAN TimerOrWaitFired)
SERVICE_TABLE_ENTRYW *WINAPI BuildServiceTable(VOID)
DWORD WINAPI ReadPerInstanceRegistryParameters(_In_ HKEY hKey, _In_ PSVCHOST_OPTIONS pOptions)
VOID WINAPI UnloadServiceDll(_In_ PSVCHOST_SERVICE pService)
BOOLEAN WINAPI CallPerInstanceInitFunctions(_In_ PSVCHOST_OPTIONS pOptions)
VOID(WINAPI * PSVCHOST_INIT_GLOBALS)(_In_ PSVCHOST_GLOBAL_DATA Globals)
#define DBG_TRACE(fmt,...)
VOID WINAPI InitializeCriticalSection(OUT LPCRITICAL_SECTION lpCriticalSection)
BOOL WINAPI RegisterWaitForSingleObject(OUT PHANDLE phNewWaitObject, IN HANDLE hObject, IN WAITORTIMERCALLBACK Callback, IN PVOID Context, IN ULONG dwMilliseconds, IN ULONG dwFlags)
#define RtlZeroMemory(Destination, Length)
#define CONTAINING_RECORD(address, type, field)
DWORD WINAPI GetLastError(void)
void WINAPI LeaveCriticalSection(LPCRITICAL_SECTION)
void WINAPI DebugBreak(void)
#define LOAD_WITH_ALTERED_SEARCH_PATH
void WINAPI EnterCriticalSection(LPCRITICAL_SECTION)
_In_ PCCERT_CONTEXT _In_ DWORD dwFlags
#define ERROR_PATH_NOT_FOUND
#define ERROR_INVALID_DATA
#define HKEY_LOCAL_MACHINE
void(WINAPI * LPSERVICE_MAIN_FUNCTIONW)(DWORD, LPWSTR *)
#define SERVICE_QUERY_CONFIG