(file) Return to cimserver_windows.cpp CVS log (file) (dir) Up to [Pegasus] / pegasus / src / WMIMapper / WMIServer

  1 kumpf 1.1 //%/////////////////////////////////////////////////////////////////////////////
  2           //
  3           // Copyright (c) 2000, 2001, 2002 BMC Software, Hewlett-Packard Company, IBM,
  4           // The Open Group, Tivoli Systems
  5           //
  6           // Permission is hereby granted, free of charge, to any person obtaining a copy
  7           // of this software and associated documentation files (the "Software"), to
  8           // deal in the Software without restriction, including without limitation the
  9           // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
 10           // sell copies of the Software, and to permit persons to whom the Software is
 11           // furnished to do so, subject to the following conditions:
 12           // 
 13           // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
 14           // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
 15           // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
 16           // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
 17           // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 18           // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
 19           // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
 20           // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 21           //
 22 kumpf 1.1 //==============================================================================
 23           //
 24           // Author: Mike Day (mdday@us.ibm.com)
 25           //
 26           // Modified By: Mary Hinton (m.hinton@verizon.net)
 27           //              Sushma Fernandes (sushma_fernandes@hp.com)
 28           //
 29           //%/////////////////////////////////////////////////////////////////////////////
 30           
 31           #include <windows.h>
 32           #include <process.h>    /* _beginthread, _endthread */
 33           #include <tchar.h>
 34           #include <direct.h>
 35           
 36           
 37           PEGASUS_USING_PEGASUS;
 38           PEGASUS_USING_STD;
 39           
 40           static DWORD dieNow = 0;
 41           String *runPath;
 42           CIMServer *server_windows;
 43 kumpf 1.1 static SERVICE_STATUS pegasus_status;
 44           static SERVICE_STATUS_HANDLE pegasus_status_handle;
 45           
 46           VOID WINAPI  cimserver_windows_main(int argc, char **argv) ;
 47           VOID WINAPI cimserver_service_start(DWORD, LPTSTR *);
 48           VOID WINAPI cimserver_service_ctrl_handler(DWORD ); 
 49           DWORD cimserver_initialization(DWORD, LPTSTR *, DWORD *) ;
 50           
 51           void GetOptions(
 52               ConfigManager* cm,
 53               int& argc,
 54               char** argv,
 55               const String& pegasusHome);
 56           
 57           void cim_server_service(int argc, char **argv ) { cimserver_windows_main(argc, argv); exit(0); }
 58           int cimserver_fork( ) { return(0); }
 59           int cimserver_kill( ) { return(0); }
 60           Boolean isCIMServerRunning( ) { return(false); }
 61           
 62           static void __cdecl cimserver_windows_thread(void *parm) 
 63           {
 64 kumpf 1.1 
 65               // Get options (from command line and from configuration file); this
 66               // removes corresponding options and their arguments fromt he command
 67               // line.
 68           
 69               ConfigManager* configManager = ConfigManager::getInstance();
 70               int dummy = 0;
 71               String pegasusHome;
 72           
 73               try
 74               {
 75           	GetOptions(configManager, dummy, NULL, pegasusHome);
 76               }
 77               catch (Exception&)
 78               {
 79                 exit(1);
 80               }
 81           
 82               //
 83               // Check the trace options and set global variable
 84               //
 85 kumpf 1.1     Boolean pegasusIOTrace = false;
 86           
 87               if (String::equal(configManager->getCurrentValue("trace"), "true"))
 88               {
 89                   pegasusIOTrace = true;
 90               }
 91           
 92               //
 93               // Check the log trace options and set global variable
 94               //
 95               Boolean pegasusIOLog = false;
 96           
 97               if (String::equal(configManager->getCurrentValue("logtrace"), "true"))
 98               {
 99                   pegasusIOLog = true;
100               }
101               Boolean useSSL = false;
102               
103               if (String::equal(configManager->getCurrentValue("SSL"), "true"))
104               {
105                  useSSL =  true;
106 kumpf 1.1     }
107           
108               // mdh: need to get the environment for the Windows Service to run 
109               const char* tmp = getenv("PEGASUS_HOME");
110               if (tmp)
111               {
112                   pegasusHome = tmp;
113               }    
114               ConfigManager::setPegasusHome(pegasusHome);
115           
116               // Grab the port otpion:
117           
118               String portOption;
119           
120               if (useSSL)
121               {
122                   portOption = configManager->getCurrentValue("httpsPort");
123               }
124               else
125               {
126                   portOption = configManager->getCurrentValue("httpPort");
127 kumpf 1.1     }
128               CString address = portOption.getCString();
129           
130               // Set up the Logger
131               Logger::setHomeDirectory("./logs");
132           
133               // Put server start message to the logger
134               Logger::put(Logger::STANDARD_LOG, "CIMServer", Logger::INFORMATION,
135           	"Start $0 %1 port $2 $3 ", 88, PEGASUS_NAME, PEGASUS_VERSION,
136           		(const char*)address, (pegasusIOTrace ? " Tracing": " "));
137                // try loop to bind the address, and run the server
138               try
139               {
140           	Monitor monitor;
141                   
142                  	CIMServer server(&monitor, useSSL);
143           	server_windows = &server;
144           
145           	char* end = 0;
146           	long portNumber = strtol(address, &end, 10);
147           	assert(end != 0 && *end == '\0');
148 kumpf 1.1 	
149           	server_windows->bind(portNumber);
150           
151           	while(!server_windows->terminated())
152           	{
153           	    server_windows->runForever();
154           	}
155               }
156               catch(Exception& e)
157               {
158           	PEGASUS_STD(cerr) << "Error: " << e.getMessage() << PEGASUS_STD(endl);
159               }
160           
161               _endthreadex(NULL);
162           }
163           
164           
165           /////////////////////////////////////////////////////////////////
166           //  Windows NT Service Control Code 
167           /////////////////////////////////////////////////////////////////
168           
169 kumpf 1.1 
170           
171           
172           VOID WINAPI  cimserver_windows_main(int argc, char **argv) 
173           {
174             int ccode;
175             SERVICE_TABLE_ENTRY dispatch_table[] = 
176             {
177               {"cimserver", cimserver_service_start},
178               {NULL, NULL}
179             };
180           
181              /* let everyone know we are running (or trying to run) as an NT service */
182             if(!(ccode =  StartServiceCtrlDispatcher(dispatch_table))) 
183               {
184                 ccode = GetLastError();
185                 // Put server start message to the logger
186                 Logger::put(Logger::STANDARD_LOG, "CIMServer_Windows", Logger::INFORMATION,
187           		  "Started as a Windows Service");
188               }
189             return;
190 kumpf 1.1 }
191           
192           /////////////////////////////////////////////////////////////////
193           //
194           // called by the NT service control manager to start the SLP service
195           //
196           /////////////////////////////////////////////////////////////////
197           
198           VOID WINAPI cimserver_service_start(DWORD argc, LPTSTR *argv) 
199           {
200           
201             DWORD status;
202             DWORD specificError;
203             pegasus_status.dwServiceType = SERVICE_WIN32;
204             pegasus_status.dwCurrentState = SERVICE_START_PENDING;
205             pegasus_status.dwControlsAccepted 
206                 = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN ;
207             pegasus_status.dwWin32ExitCode = 0;
208             pegasus_status.dwServiceSpecificExitCode = 0;
209             pegasus_status.dwCheckPoint = 0;
210             pegasus_status.dwWaitHint = 0;
211 kumpf 1.1 
212             pegasus_status_handle = RegisterServiceCtrlHandler("cimserver", cimserver_service_ctrl_handler);
213             if( pegasus_status_handle == (SERVICE_STATUS_HANDLE)0) 
214               {
215                 Logger::put(Logger::STANDARD_LOG, "CIMServer_Windows", Logger::INFORMATION,
216           		  "Error installing service handler");
217                 return;
218               }
219           
220             // mdday -- I need to replace this hack with registry code
221           
222             // this is an ugly hack because we should really be getting this data 
223             // out of the registry. We are essentially forcing pegasus to be run 
224             // from its build tree. i.e.: 
225             // PEGASUS_HOME = binary_exe_path minus  "\bin\cimserver.exe"
226           
227             // so if my build environment is in "c:\my-programs\pegasus\ 
228             // I will install the service binary path as "c:\my-programs\pegasus\bin\cimserver.exe"
229             // Therefore I will derive PEGASUS_HOME as "c:\my-programs\pegasus"
230             
231             // If I do something wierd and run pegasus from "c:\winnt" then this hack will break 
232 kumpf 1.1   // the service will think its running but the CIMServer object will never have been instantiated. 
233            
234             SC_HANDLE service_handle, sc_manager;
235             if(NULL != (sc_manager = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS))) 
236               {
237                 if(NULL != (service_handle = OpenService(sc_manager, 
238           					       "cimserver",
239           					       SERVICE_ALL_ACCESS)))
240           
241           	{
242           	  DWORD bytes_needed = 0;
243           	  QUERY_SERVICE_CONFIG *svc_config = NULL;
244           	  
245           	  QueryServiceConfig(service_handle, svc_config, sizeof(svc_config), &bytes_needed);
246           	  if(bytes_needed > 0) 
247           	    {
248           	      if(NULL != ( svc_config = (QUERY_SERVICE_CONFIG *) malloc(bytes_needed))) 
249           		{
250           		  if(TRUE == QueryServiceConfig(service_handle, svc_config, bytes_needed, &bytes_needed)) 
251           		    {
252           		      Uint32 position;
253 kumpf 1.1 		      runPath = new String(svc_config->lpBinaryPathName);
254           		      if(PEG_NOT_FOUND != (position = runPath->reverseFind('\\'))) 
255           			{
256           			  Uint32 len = runPath->size();
257           			  runPath->remove(position, len - position);
258           			  position = runPath->reverseFind('\\');
259           			  len = runPath->size();
260           			  runPath->remove(position, len - position);
261           			}
262           		    }
263           		  free(svc_config);
264           		}
265           	    }
266           	  CloseServiceHandle(service_handle);
267           	}
268                 CloseServiceHandle(sc_manager);
269               }
270           
271             status = cimserver_initialization(argc, argv, &specificError);
272             if(status < 0) 
273               {
274 kumpf 1.1       pegasus_status.dwCurrentState = SERVICE_STOPPED;
275                 pegasus_status.dwCheckPoint = 0;
276                 pegasus_status.dwWaitHint = 0;
277                 pegasus_status.dwWin32ExitCode = status;
278                 pegasus_status.dwServiceSpecificExitCode = specificError;
279                 SetServiceStatus(pegasus_status_handle, &pegasus_status);
280                 Logger::put(Logger::STANDARD_LOG, "CIMServer_Windows", Logger::INFORMATION,
281           		  "Error starting Cim Server");
282               return;
283               }
284           
285             pegasus_status.dwCurrentState = SERVICE_RUNNING;
286             pegasus_status.dwCheckPoint = 0;
287             pegasus_status.dwWaitHint = 0;
288           
289             if(!SetServiceStatus(pegasus_status_handle, &pegasus_status)) 
290               {
291                 if(server_windows != NULL)
292           	server_windows->shutdown();
293               }
294           
295 kumpf 1.1   return;
296           }
297           
298           VOID WINAPI cimserver_service_ctrl_handler(DWORD opcode) 
299           {
300           
301             switch(opcode) {
302             case SERVICE_CONTROL_STOP:
303             case SERVICE_CONTROL_SHUTDOWN:
304               if(server_windows != NULL)
305                 server_windows->shutdown();
306               pegasus_status.dwCurrentState = SERVICE_STOPPED;
307               pegasus_status.dwCheckPoint = 0;
308               pegasus_status.dwWaitHint = 0;
309               pegasus_status.dwWin32ExitCode = 0;
310               SetServiceStatus(pegasus_status_handle, &pegasus_status);
311               return;
312               break;
313               default:
314                 break;
315             }
316 kumpf 1.1   SetServiceStatus(pegasus_status_handle, &pegasus_status);
317             return;
318           }
319           
320           DWORD cimserver_initialization(DWORD argc, LPTSTR *argv, DWORD *specificError) 
321           {
322             
323             return( _beginthread(cimserver_windows_thread, 0, NULL ));
324           }
325            
326           
327           Uint32 cimserver_install_nt_service(String &pegasusHome ) 
328           {
329             SC_HANDLE service_handle, sc_manager;
330             Uint32 ccode = 0;
331             pegasusHome.append("\\bin\\cimserver.exe");
332             CString pegHome = pegasusHome.getCString() ;
333             LPCSTR path_name = (const char*) pegHome;
334             if(NULL != (sc_manager = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS))) 
335               {
336                 if(NULL != (service_handle = CreateService(sc_manager, 
337 kumpf 1.1 						 "cimserver",
338           						 "Pegasus CIM Object Manager",
339           						 SERVICE_ALL_ACCESS,
340           						 SERVICE_WIN32_OWN_PROCESS,
341           						 SERVICE_DEMAND_START,
342           						 SERVICE_ERROR_NORMAL, 
343           						 path_name,
344           						 NULL, NULL, NULL, NULL, NULL))) 
345           	{
346           	  ccode = (Uint32)service_handle;
347           	}
348                 CloseServiceHandle(service_handle);
349               }
350             
351             return(ccode);
352           }
353           
354           Uint32 cimserver_remove_nt_service(void) 
355           {
356           
357             SC_HANDLE service_handle, sc_manager;
358 kumpf 1.1   int ccode = 0;
359             if(NULL != (sc_manager = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS))) 
360               {
361                 if(NULL != (service_handle = OpenService(sc_manager, "cimserver", DELETE))) 
362           	{
363           	  DeleteService(service_handle);
364           	  CloseServiceHandle(service_handle);
365           	  ccode = 1;
366           	} 
367                 CloseServiceHandle(sc_manager);
368               } 
369             return(ccode);
370           }

No CVS admin address has been configured
Powered by
ViewCVS 0.9.2