1 /* 2 * PROJECT: ReactOS Secondary Logon Service 3 * LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+) 4 * PURPOSE: Secondary Logon service RPC server 5 * COPYRIGHT: Eric Kohl 2022 <eric.kohl@reactos.org> 6 */ 7 8 /* INCLUDES *****************************************************************/ 9 10 #include "precomp.h" 11 12 WINE_DEFAULT_DEBUG_CHANNEL(seclogon); 13 14 15 /* GLOBALS ******************************************************************/ 16 17 HINSTANCE hDllInstance; 18 PSVCHOST_GLOBAL_DATA lpServiceGlobals; 19 20 static WCHAR ServiceName[] = L"seclogon"; 21 22 static SERVICE_STATUS_HANDLE ServiceStatusHandle; 23 static SERVICE_STATUS ServiceStatus; 24 25 26 /* FUNCTIONS *****************************************************************/ 27 28 static 29 VOID 30 UpdateServiceStatus( 31 _In_ DWORD dwState) 32 { 33 ServiceStatus.dwServiceType = SERVICE_WIN32_SHARE_PROCESS; 34 ServiceStatus.dwCurrentState = dwState; 35 36 if (dwState == SERVICE_PAUSED || dwState == SERVICE_RUNNING) 37 ServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP | 38 SERVICE_ACCEPT_SHUTDOWN | 39 SERVICE_ACCEPT_PAUSE_CONTINUE; 40 else 41 ServiceStatus.dwControlsAccepted = 0; 42 43 ServiceStatus.dwWin32ExitCode = 0; 44 ServiceStatus.dwServiceSpecificExitCode = 0; 45 ServiceStatus.dwCheckPoint = 0; 46 47 if (dwState == SERVICE_START_PENDING || 48 dwState == SERVICE_STOP_PENDING || 49 dwState == SERVICE_PAUSE_PENDING || 50 dwState == SERVICE_CONTINUE_PENDING) 51 ServiceStatus.dwWaitHint = 10000; 52 else 53 ServiceStatus.dwWaitHint = 0; 54 55 SetServiceStatus(ServiceStatusHandle, 56 &ServiceStatus); 57 } 58 59 60 static 61 DWORD 62 WINAPI 63 ServiceControlHandlerEx( 64 _In_ DWORD dwControl, 65 _In_ DWORD dwEventType, 66 _In_ LPVOID lpEventData, 67 _In_ LPVOID lpContext) 68 { 69 TRACE("ServiceControlHandlerEx()\n"); 70 71 switch (dwControl) 72 { 73 case SERVICE_CONTROL_STOP: 74 TRACE(" SERVICE_CONTROL_STOP received\n"); 75 UpdateServiceStatus(SERVICE_STOP_PENDING); 76 StopRpcServer(); 77 UpdateServiceStatus(SERVICE_STOPPED); 78 return ERROR_SUCCESS; 79 80 case SERVICE_CONTROL_PAUSE: 81 TRACE(" SERVICE_CONTROL_PAUSE received\n"); 82 UpdateServiceStatus(SERVICE_PAUSE_PENDING); 83 StopRpcServer(); 84 UpdateServiceStatus(SERVICE_PAUSED); 85 return ERROR_SUCCESS; 86 87 case SERVICE_CONTROL_CONTINUE: 88 TRACE(" SERVICE_CONTROL_CONTINUE received\n"); 89 UpdateServiceStatus(SERVICE_CONTINUE_PENDING); 90 StartRpcServer(); 91 UpdateServiceStatus(SERVICE_RUNNING); 92 return ERROR_SUCCESS; 93 94 case SERVICE_CONTROL_INTERROGATE: 95 TRACE(" SERVICE_CONTROL_INTERROGATE received\n"); 96 SetServiceStatus(ServiceStatusHandle, 97 &ServiceStatus); 98 return ERROR_SUCCESS; 99 100 case SERVICE_CONTROL_SHUTDOWN: 101 TRACE(" SERVICE_CONTROL_SHUTDOWN received\n"); 102 UpdateServiceStatus(SERVICE_STOP_PENDING); 103 StopRpcServer(); 104 UpdateServiceStatus(SERVICE_STOPPED); 105 return ERROR_SUCCESS; 106 107 default : 108 TRACE(" Control %lu received\n", dwControl); 109 return ERROR_CALL_NOT_IMPLEMENTED; 110 } 111 } 112 113 114 VOID 115 WINAPI 116 SvchostPushServiceGlobals( 117 _In_ PSVCHOST_GLOBAL_DATA lpGlobals) 118 { 119 TRACE("SvchostPushServiceGlobals(%p)\n", lpGlobals); 120 lpServiceGlobals = lpGlobals; 121 } 122 123 124 VOID 125 WINAPI 126 SvcEntry_Seclogon( 127 _In_ INT ArgCount, 128 _In_ PWSTR *ArgVector) 129 { 130 DWORD dwError; 131 132 UNREFERENCED_PARAMETER(ArgCount); 133 UNREFERENCED_PARAMETER(ArgVector); 134 135 TRACE("ServiceMain(%d %p)\n", ArgCount, ArgVector); 136 137 ServiceStatusHandle = RegisterServiceCtrlHandlerExW(ServiceName, 138 ServiceControlHandlerEx, 139 NULL); 140 if (!ServiceStatusHandle) 141 { 142 ERR("RegisterServiceCtrlHandlerExW() failed! (Error %lu)\n", GetLastError()); 143 return; 144 } 145 146 UpdateServiceStatus(SERVICE_START_PENDING); 147 148 dwError = StartRpcServer(); 149 if (dwError != ERROR_SUCCESS) 150 { 151 ERR("Service stopped (dwError: %lu\n", dwError); 152 UpdateServiceStatus(SERVICE_STOPPED); 153 return; 154 } 155 156 UpdateServiceStatus(SERVICE_RUNNING); 157 } 158 159 160 BOOL 161 WINAPI 162 DllMain( 163 _In_ HINSTANCE hinstDLL, 164 _In_ DWORD fdwReason, 165 _In_ PVOID pvReserved) 166 { 167 UNREFERENCED_PARAMETER(pvReserved); 168 169 switch (fdwReason) 170 { 171 case DLL_PROCESS_ATTACH: 172 DisableThreadLibraryCalls(hinstDLL); 173 hDllInstance = hinstDLL; 174 break; 175 176 case DLL_PROCESS_DETACH: 177 break; 178 } 179 180 return TRUE; 181 } 182 183 /* EOF */ 184