Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

320 lines
7.5 KiB

  1. /*++
  2. Copyright (c) 1997-1999 Microsoft Corporation
  3. Module Name:
  4. wmiexe.c
  5. Abstract:
  6. WMI exe scaffolding
  7. Author:
  8. 16-Jan-1997 AlanWar
  9. Revision History:
  10. --*/
  11. #include "wmiump.h"
  12. #if DBG
  13. BOOLEAN WmipLoggingEnabled;
  14. #endif
  15. #ifdef MEMPHIS
  16. typedef (*RSPAPI)(DWORD, DWORD);
  17. #define RSP_SIMPLE_SERVICE 1
  18. #define RSP_UNREGISTER_SERVICE 0
  19. int WinMain(
  20. HINSTANCE hInstance,
  21. HINSTANCE hPrevInstance,
  22. LPSTR lpCmdLine,
  23. int nCmdShow
  24. )
  25. {
  26. ULONG Status;
  27. HMODULE Module;
  28. RSPAPI RspApi;
  29. HANDLE HackEvent;
  30. HANDLE EventHandle;
  31. HackEvent = CreateEvent(NULL,
  32. TRUE,
  33. FALSE,
  34. "WMI_UNIQUE_EVENT_NAME");
  35. if (HackEvent == NULL)
  36. {
  37. Status = GetLastError();
  38. WmipDebugPrint(("WMI: Couldn't create WMI_UNIQUE_EVENT_NAME %d\n",
  39. Status));
  40. return(Status);
  41. }
  42. if ((HackEvent != NULL) &&
  43. (GetLastError() == ERROR_ALREADY_EXISTS))
  44. {
  45. CloseHandle(HackEvent);
  46. WmipDebugPrint(("WMI: Previous instance of WMIEXE running, exiting...\n"));
  47. #ifndef RUN_AS_SERVICE
  48. MessageBox(NULL, "Another copy of WMIEXE.EXE is already running\n",
  49. "WMI", MB_OK);
  50. #endif
  51. return(0);
  52. }
  53. Status = WmiInitializeService();
  54. if (Status != ERROR_SUCCESS)
  55. {
  56. WmipDebugPrint(("WMI: WmiInitializeService failed %d\n", Status));
  57. } else {
  58. EventHandle = (HANDLE)atoi(lpCmdLine);
  59. if (EventHandle != NULL)
  60. {
  61. SetEvent(EventHandle);
  62. CloseHandle(EventHandle);
  63. }
  64. #ifdef RUN_AS_SERVICE
  65. Module = GetModuleHandle("Kernel32");
  66. if (Module == NULL)
  67. {
  68. WmipDebugPrint(("WMI: Kernel32 not loaded\n"));
  69. return(GetLastError());
  70. }
  71. RspApi = (RSPAPI)GetProcAddress(Module, "RegisterServiceProcess");
  72. if (RspApi == NULL)
  73. {
  74. WmipDebugPrint(("WMI: RspApi not loaded\n"));
  75. return(GetLastError());
  76. }
  77. (*RspApi)(GetCurrentProcessId(), RSP_SIMPLE_SERVICE);
  78. #endif
  79. Status = WmiRunService(
  80. 0
  81. #ifdef MEMPHIS
  82. , hInstance
  83. #endif
  84. );
  85. if (Status != ERROR_SUCCESS)
  86. {
  87. WmipDebugPrint(("WMI: WmiRunService failed %d\n", Status));
  88. }
  89. WmiDeinitializeService();
  90. }
  91. CloseHandle(HackEvent);
  92. return(Status);
  93. }
  94. #else
  95. void
  96. WmiServiceMain(
  97. DWORD argc,
  98. LPWSTR *argv
  99. );
  100. void
  101. WmiServiceCtrlHandler(
  102. DWORD Opcode
  103. );
  104. SERVICE_STATUS WmiServiceStatus;
  105. SERVICE_STATUS_HANDLE WmiServiceStatusHandle;
  106. int _cdecl main(int argc, WCHAR *argv[])
  107. {
  108. #ifdef RUN_AS_SERVICE
  109. SERVICE_TABLE_ENTRY DispatchTable[] =
  110. {
  111. { L"Wmi", WmiServiceMain },
  112. { NULL, NULL }
  113. };
  114. if (!StartServiceCtrlDispatcher( DispatchTable))
  115. {
  116. WmipDebugPrint(("WMI: StartServiceCtrlDispatcher error = %d\n",
  117. GetLastError()));
  118. }
  119. return(0);
  120. #else
  121. DWORD Status;
  122. //
  123. // Initialize the WMI service
  124. Status = WmiInitializeService();
  125. if (Status != ERROR_SUCCESS)
  126. {
  127. return(Status);
  128. }
  129. //
  130. // All set to start doing the real work of the service
  131. Status = WmiRunService(0);
  132. WmiDeinitializeService();
  133. return(Status);
  134. #endif
  135. }
  136. void WmiServiceMain(DWORD argc, LPWSTR *argv)
  137. {
  138. DWORD Status;
  139. WmiServiceStatus.dwServiceType = SERVICE_WIN32;
  140. WmiServiceStatus.dwCurrentState = SERVICE_START_PENDING;
  141. WmiServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP;
  142. WmiServiceStatus.dwWin32ExitCode = 0;
  143. WmiServiceStatus.dwServiceSpecificExitCode = 0;
  144. WmiServiceStatus.dwCheckPoint = 0;
  145. WmiServiceStatus.dwWaitHint = 0;
  146. WmiServiceStatusHandle = RegisterServiceCtrlHandler(L"Wmi",
  147. WmiServiceCtrlHandler);
  148. if (WmiServiceStatusHandle == (SERVICE_STATUS_HANDLE)NULL)
  149. {
  150. WmipDebugPrint(("WMI: RegisterServiceCtrlHandler failed %d\n", GetLastError()));
  151. return;
  152. }
  153. //
  154. // Initialize the WMI service
  155. Status = WmiInitializeService();
  156. if (Status != ERROR_SUCCESS)
  157. {
  158. //
  159. // If an error occurs we just stop ourselves
  160. WmiServiceStatus.dwCurrentState = SERVICE_STOPPED;
  161. WmiServiceStatus.dwCheckPoint = 0;
  162. WmiServiceStatus.dwWaitHint = 0;
  163. WmiServiceStatus.dwWin32ExitCode = Status;
  164. WmiServiceStatus.dwServiceSpecificExitCode = Status;
  165. SetServiceStatus (WmiServiceStatusHandle, &WmiServiceStatus);
  166. return;
  167. }
  168. // Initialization complete - report running status.
  169. WmiServiceStatus.dwCurrentState = SERVICE_RUNNING;
  170. WmiServiceStatus.dwCheckPoint = 0;
  171. WmiServiceStatus.dwWaitHint = 0;
  172. if (!SetServiceStatus (WmiServiceStatusHandle, &WmiServiceStatus))
  173. {
  174. Status = GetLastError();
  175. WmipDebugPrint(("WMI: SetServiceStatus error %ld\n",Status));
  176. }
  177. //
  178. // All set to start doing the real work of the service
  179. Status = WmiRunService(0);
  180. WmiDeinitializeService();
  181. WmiServiceStatus.dwCurrentState = SERVICE_STOPPED;
  182. WmiServiceStatus.dwCheckPoint = 0;
  183. WmiServiceStatus.dwWaitHint = 0;
  184. WmiServiceStatus.dwWin32ExitCode = Status;
  185. WmiServiceStatus.dwServiceSpecificExitCode = Status;
  186. SetServiceStatus (WmiServiceStatusHandle, &WmiServiceStatus);
  187. return;
  188. }
  189. void WmiServiceCtrlHandler (DWORD Opcode)
  190. {
  191. ULONG Status;
  192. switch(Opcode)
  193. {
  194. case SERVICE_CONTROL_PAUSE:
  195. {
  196. WmipDebugPrint(("WMI: service does not support Pause\n"));
  197. break;
  198. }
  199. case SERVICE_CONTROL_CONTINUE:
  200. {
  201. WmipDebugPrint(("WMI: service does not support Continue\n"));
  202. break;
  203. }
  204. case SERVICE_CONTROL_STOP:
  205. {
  206. // TODO: Do something to stop main service thread
  207. WmiServiceStatus.dwWin32ExitCode = 0;
  208. WmiServiceStatus.dwCurrentState = SERVICE_STOP_PENDING;
  209. WmiServiceStatus.dwCheckPoint = 0;
  210. WmiServiceStatus.dwWaitHint = 0;
  211. if (!SetServiceStatus (WmiServiceStatusHandle,
  212. &WmiServiceStatus))
  213. {
  214. Status = GetLastError();
  215. WmipDebugPrint(("WMI: SetServiceStatus error %ld\n", Status));
  216. }
  217. WmiTerminateService();
  218. WmipDebugPrint(("WMI: Leaving Service\n"));
  219. return;
  220. }
  221. case SERVICE_CONTROL_INTERROGATE:
  222. {
  223. // Fall through to send current status.
  224. break;
  225. }
  226. default:
  227. {
  228. WmipDebugPrint(("WMI: Unrecognized opcode %ld\n", Opcode));
  229. break;
  230. }
  231. }
  232. //
  233. // Send current status.
  234. if (!SetServiceStatus (WmiServiceStatusHandle, &WmiServiceStatus))
  235. {
  236. Status = GetLastError();
  237. WmipDebugPrint(("WMI: SetServiceStatus error %ld\n",Status));
  238. }
  239. return;
  240. }
  241. #endif
  242. #ifdef MEMPHIS
  243. #if DBG
  244. void __cdecl DebugOut(char *Format, ...)
  245. {
  246. char Buffer[1024];
  247. va_list pArg;
  248. ULONG i;
  249. va_start(pArg, Format);
  250. i = _vsnprintf(Buffer, sizeof(Buffer), Format, pArg);
  251. OutputDebugString(Buffer);
  252. }
  253. #endif
  254. #endif