Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenservice.c
Go to the documentation of this file.
00001 /* 00002 * msiexec.exe implementation 00003 * 00004 * Copyright 2007 Google (James Hawkins) 00005 * 00006 * This library is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU Lesser General Public 00008 * License as published by the Free Software Foundation; either 00009 * version 2.1 of the License, or (at your option) any later version. 00010 * 00011 * This library is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00014 * Lesser General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU Lesser General Public 00017 * License along with this library; if not, write to the Free Software 00018 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 00019 */ 00020 00021 #define WIN32_LEAN_AND_MEAN 00022 00023 #include <windows.h> 00024 #include <stdio.h> 00025 00026 #include "wine/debug.h" 00027 00028 WINE_DEFAULT_DEBUG_CHANNEL(msiexec); 00029 00030 static SERVICE_STATUS_HANDLE hstatus; 00031 00032 static HANDLE thread; 00033 static HANDLE kill_event; 00034 00035 static void KillService(void) 00036 { 00037 WINE_TRACE("Killing service\n"); 00038 SetEvent(kill_event); 00039 } 00040 00041 static BOOL UpdateSCMStatus(DWORD dwCurrentState, DWORD dwWin32ExitCode, 00042 DWORD dwServiceSpecificExitCode) 00043 { 00044 SERVICE_STATUS status; 00045 00046 status.dwServiceType = SERVICE_WIN32_OWN_PROCESS; 00047 status.dwCurrentState = dwCurrentState; 00048 00049 if (dwCurrentState == SERVICE_START_PENDING) 00050 status.dwControlsAccepted = 0; 00051 else 00052 { 00053 status.dwControlsAccepted = SERVICE_ACCEPT_STOP | 00054 SERVICE_ACCEPT_PAUSE_CONTINUE | 00055 SERVICE_ACCEPT_SHUTDOWN; 00056 } 00057 00058 if (dwServiceSpecificExitCode == 0) 00059 { 00060 status.dwWin32ExitCode = dwWin32ExitCode; 00061 } 00062 else 00063 { 00064 status.dwWin32ExitCode = ERROR_SERVICE_SPECIFIC_ERROR; 00065 } 00066 00067 status.dwServiceSpecificExitCode = dwServiceSpecificExitCode; 00068 status.dwCheckPoint = 0; 00069 status.dwWaitHint = 0; 00070 00071 if (!SetServiceStatus(hstatus, &status)) 00072 { 00073 fprintf(stderr, "Failed to set service status\n"); 00074 KillService(); 00075 return FALSE; 00076 } 00077 00078 return TRUE; 00079 } 00080 00081 static void WINAPI ServiceCtrlHandler(DWORD code) 00082 { 00083 WINE_TRACE("%d\n", code); 00084 00085 switch (code) 00086 { 00087 case SERVICE_CONTROL_SHUTDOWN: 00088 case SERVICE_CONTROL_STOP: 00089 UpdateSCMStatus(SERVICE_STOP_PENDING, NO_ERROR, 0); 00090 KillService(); 00091 return; 00092 default: 00093 fprintf(stderr, "Unhandled service control code: %d\n", code); 00094 break; 00095 } 00096 00097 UpdateSCMStatus(SERVICE_RUNNING, NO_ERROR, 0); 00098 } 00099 00100 static DWORD WINAPI ServiceExecutionThread(LPVOID param) 00101 { 00102 while (TRUE) 00103 { 00104 /* do nothing */ 00105 } 00106 00107 return 0; 00108 } 00109 00110 static BOOL StartServiceThread(void) 00111 { 00112 DWORD id; 00113 00114 thread = CreateThread(0, 0, ServiceExecutionThread, 0, 0, &id); 00115 if (!thread) 00116 { 00117 fprintf(stderr, "Failed to create thread\n"); 00118 return FALSE; 00119 } 00120 00121 return TRUE; 00122 } 00123 00124 static void WINAPI ServiceMain(DWORD argc, LPSTR *argv) 00125 { 00126 hstatus = RegisterServiceCtrlHandlerA("MSIServer", ServiceCtrlHandler); 00127 if (!hstatus) 00128 { 00129 fprintf(stderr, "Failed to register service ctrl handler\n"); 00130 return; 00131 } 00132 00133 UpdateSCMStatus(SERVICE_START_PENDING, NO_ERROR, 0); 00134 00135 kill_event = CreateEventW(0, TRUE, FALSE, 0); 00136 if (!kill_event) 00137 { 00138 fprintf(stderr, "Failed to create event\n"); 00139 KillService(); 00140 return; 00141 } 00142 00143 if (!StartServiceThread()) 00144 { 00145 KillService(); 00146 return; 00147 } 00148 00149 UpdateSCMStatus(SERVICE_RUNNING, NO_ERROR, 0); 00150 00151 WaitForSingleObject(kill_event, INFINITE); 00152 KillService(); 00153 } 00154 00155 DWORD DoService(void) 00156 { 00157 char service_name[] = "MSIServer"; 00158 00159 const SERVICE_TABLE_ENTRYA service[] = 00160 { 00161 {service_name, ServiceMain}, 00162 {NULL, NULL}, 00163 }; 00164 00165 WINE_TRACE("Starting MSIServer service\n"); 00166 00167 if (!StartServiceCtrlDispatcherA(service)) 00168 { 00169 fprintf(stderr, "Failed to start MSIServer service\n"); 00170 return 1; 00171 } 00172 00173 return 0; 00174 } Generated on Wed May 23 2012 04:16:51 for ReactOS by
1.7.6.1
|