1 karl 1.15 //%2005////////////////////////////////////////////////////////////////////////
|
2 kumpf 1.1 //
|
3 karl 1.14 // Copyright (c) 2000, 2001, 2002 BMC Software; Hewlett-Packard Development
4 // Company, L.P.; IBM Corp.; The Open Group; Tivoli Systems.
5 // Copyright (c) 2003 BMC Software; Hewlett-Packard Development Company, L.P.;
|
6 kumpf 1.1 // IBM Corp.; EMC Corporation, The Open Group.
|
7 karl 1.14 // Copyright (c) 2004 BMC Software; Hewlett-Packard Development Company, L.P.;
8 // IBM Corp.; EMC Corporation; VERITAS Software Corporation; The Open Group.
|
9 karl 1.15 // Copyright (c) 2005 Hewlett-Packard Development Company, L.P.; IBM Corp.;
10 // EMC Corporation; VERITAS Software Corporation; The Open Group.
|
11 kumpf 1.1 //
12 // Permission is hereby granted, free of charge, to any person obtaining a copy
13 // of this software and associated documentation files (the "Software"), to
14 // deal in the Software without restriction, including without limitation the
15 // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
16 // sell copies of the Software, and to permit persons to whom the Software is
17 // furnished to do so, subject to the following conditions:
|
18 karl 1.14 //
|
19 kumpf 1.1 // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
20 // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
21 // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
22 // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
23 // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
24 // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
25 // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
26 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
27 //
28 //==============================================================================
29 //
30 // Author: Chip Vincent (cvincent@us.ibm.com)
31 // Roger Kumpf, Hewlett-Packard Company (roger_kumpf@hp.com)
32 //
|
33 se.gupta 1.9 // Modified By: Seema Gupta(gseema@in.ibm.com) for PEP135
|
34 gs.keenan 1.16 // Sean Keenan, Hewlett-Packard Company (sean.keenan@hp.com)
|
35 carolann.graves 1.17 // Carol Ann Krug Graves, Hewlett-Packard Company
36 // (carolann_graves@hp.com)
|
37 kumpf 1.1 //
38 //%/////////////////////////////////////////////////////////////////////////////
39
40 #include "BasicProviderManagerRouter.h"
41
42 #include <Pegasus/Common/Config.h>
|
43 se.gupta 1.9 #include <Pegasus/Common/OperationContextInternal.h>
|
44 kumpf 1.1 #include <Pegasus/Common/CIMMessage.h>
45 #include <Pegasus/Common/Tracer.h>
|
46 kumpf 1.12 #include <Pegasus/Common/FileSystem.h>
47 #include <Pegasus/Config/ConfigManager.h>
|
48 kumpf 1.1 #include <Pegasus/ProviderManager2/OperationResponseHandler.h>
49 #include <Pegasus/ProviderManager2/ProviderManagerModule.h>
50 #include <Pegasus/ProviderManager2/ProviderManager.h>
51
52 // ProviderManager library names. Should these be defined elsewhere?
53 #if defined(PEGASUS_OS_OS400)
|
54 humberto 1.19 # define LIBRARY_NAME_DEFAULTPM "QSYS/QYCMPMDE00"
|
55 kumpf 1.1 # define LIBRARY_NAME_CMPIPM "QSYS/QYCMCMPIPM"
56 # define LIBRARY_NAME_JMPIPM "QSYS/QYCMJMPIPM"
57 #else
58 # define LIBRARY_NAME_DEFAULTPM "DefaultProviderManager"
59 # define LIBRARY_NAME_CMPIPM "CMPIProviderManager"
60 # define LIBRARY_NAME_JMPIPM "JMPIProviderManager"
61 #endif
62
63 PEGASUS_NAMESPACE_BEGIN
64
65 // BEGIN TEMP SECTION
66 class ProviderManagerContainer
67 {
68 public:
69 ProviderManagerContainer()
70 : _manager(0)
71 {
72 }
73
74 ProviderManagerContainer(const ProviderManagerContainer & container)
75 : _manager(0)
76 kumpf 1.1 {
77 *this = container;
78 }
79
80 ProviderManagerContainer(
81 const String& physicalName,
82 const String& logicalName,
83 const String& interfaceName,
|
84 carolann.graves 1.17 PEGASUS_INDICATION_CALLBACK indicationCallback,
85 Boolean subscriptionInitComplete)
|
86 kumpf 1.1 : _manager(0)
87 {
|
88 gs.keenan 1.16 #if defined (PEGASUS_OS_VMS)
89 _physicalName = FileSystem::buildLibraryFileName(physicalName);
|
90 humberto 1.19 #elif defined (PEGASUS_OS_OS400)
91 _physcialName = physicalName;
|
92 gs.keenan 1.16 #else
|
93 kumpf 1.12 _physicalName = ConfigManager::getHomedPath(PEGASUS_DEST_LIB_DIR) +
|
94 kumpf 1.13 String("/") + FileSystem::buildLibraryFileName(physicalName);
|
95 gs.keenan 1.16 #endif
|
96 kumpf 1.1
97 _logicalName = logicalName;
98 _interfaceName = interfaceName;
99
100 _module = ProviderManagerModule(_physicalName);
101 _module.load();
102
103 _manager = _module.getProviderManager(_logicalName);
104 PEGASUS_ASSERT(_manager != 0);
105
106 _manager->setIndicationCallback(indicationCallback);
|
107 carolann.graves 1.17
108 _manager->setSubscriptionInitComplete (subscriptionInitComplete);
|
109 kumpf 1.1 }
110
111 ~ProviderManagerContainer()
112 {
113 _module.unload();
114 }
115
116 ProviderManagerContainer& operator=(
117 const ProviderManagerContainer & container)
118 {
119 if (this == &container)
120 {
121 return *this;
122 }
123
124 _logicalName = container._logicalName;
125 _physicalName = container._physicalName;
126 _interfaceName = container._interfaceName;
127
128 _module = container._module;
129 _manager = container._manager;
130 kumpf 1.1
131 return *this;
132 }
133
134 ProviderManager* getProviderManager()
135 {
136 return _manager;
137 }
138
139 const String& getPhysicalName() const
140 {
141 return _physicalName;
142 }
143
144 const String& getLogicalName() const
145 {
146 return _logicalName;
147 }
148
149 const String& getInterfaceName() const
150 {
151 kumpf 1.1 return _interfaceName;
152 }
153
154 private:
155 String _physicalName;
156 String _logicalName;
157 String _interfaceName;
158
159 ProviderManagerModule _module;
160 ProviderManager* _manager;
161 };
162 // END TEMP SECTION
163
164
165 PEGASUS_INDICATION_CALLBACK BasicProviderManagerRouter::_indicationCallback = 0;
166
167 // Private, unimplemented constructor
168 BasicProviderManagerRouter::BasicProviderManagerRouter()
169 {
170 }
171
172 kumpf 1.1 BasicProviderManagerRouter::BasicProviderManagerRouter(
173 PEGASUS_INDICATION_CALLBACK indicationCallback)
174 {
175 PEG_METHOD_ENTER(TRC_PROVIDERMANAGER,
176 "BasicProviderManagerRouter::BasicProviderManagerRouter");
177
178 _indicationCallback = indicationCallback;
|
179 carolann.graves 1.17 _subscriptionInitComplete = false;
|
180 kumpf 1.1
181 PEG_METHOD_EXIT();
182 }
183
184 BasicProviderManagerRouter::~BasicProviderManagerRouter()
185 {
186 PEG_METHOD_ENTER(TRC_PROVIDERMANAGER,
187 "BasicProviderManagerRouter::~BasicProviderManagerRouter");
188 PEG_METHOD_EXIT();
189 }
190
191 Message* BasicProviderManagerRouter::processMessage(Message * message)
192 {
193 PEG_METHOD_ENTER(TRC_PROVIDERMANAGER,
194 "BasicProviderManagerRouter::processMessage");
195
196 CIMRequestMessage* request = dynamic_cast<CIMRequestMessage *>(message);
197 PEGASUS_ASSERT(request != 0);
198
199 Message* response = 0;
|
200 schuur 1.7 Boolean remoteNameSpaceRequest=false;
|
201 kumpf 1.1
202 //
203 // Retrieve the ProviderManager routing information
204 //
205
206 CIMInstance providerModule;
207
208 if ((dynamic_cast<CIMOperationRequestMessage*>(request) != 0) ||
|
209 kumpf 1.4 (request->getType() == CIM_EXPORT_INDICATION_REQUEST_MESSAGE) ||
210 (request->getType() == CIM_INITIALIZE_PROVIDER_REQUEST_MESSAGE))
|
211 kumpf 1.1 {
212 // Provider information is in OperationContext
213 ProviderIdContainer pidc = (ProviderIdContainer)
214 request->operationContext.get(ProviderIdContainer::NAME);
215 providerModule = pidc.getModule();
|
216 schuur 1.7 remoteNameSpaceRequest=pidc.isRemoteNameSpace();
|
217 kumpf 1.1 }
218 else if (dynamic_cast<CIMIndicationRequestMessage*>(request) != 0)
219 {
220 // Provider information is in CIMIndicationRequestMessage
221 CIMIndicationRequestMessage* indReq =
222 dynamic_cast<CIMIndicationRequestMessage*>(request);
|
223 se.gupta 1.9 ProviderIdContainer pidc = indReq->operationContext.get(ProviderIdContainer::NAME);
224 providerModule = pidc.getModule();
|
225 kumpf 1.1 }
226 else if (request->getType() == CIM_ENABLE_MODULE_REQUEST_MESSAGE)
227 {
228 // Provider information is in CIMEnableModuleRequestMessage
229 CIMEnableModuleRequestMessage* emReq =
230 dynamic_cast<CIMEnableModuleRequestMessage*>(request);
231 providerModule = emReq->providerModule;
232 }
233 else if (request->getType() == CIM_DISABLE_MODULE_REQUEST_MESSAGE)
234 {
235 // Provider information is in CIMDisableModuleRequestMessage
236 CIMDisableModuleRequestMessage* dmReq =
237 dynamic_cast<CIMDisableModuleRequestMessage*>(request);
238 providerModule = dmReq->providerModule;
239 }
|
240 kumpf 1.6 else if ((request->getType() == CIM_STOP_ALL_PROVIDERS_REQUEST_MESSAGE) ||
|
241 carolann.graves 1.17 (request->getType() ==
242 CIM_SUBSCRIPTION_INIT_COMPLETE_REQUEST_MESSAGE) ||
|
243 kumpf 1.6 (request->getType() == CIM_NOTIFY_CONFIG_CHANGE_REQUEST_MESSAGE))
|
244 kumpf 1.1 {
245 // This operation is not provider-specific
246 }
247 else
248 {
249 // Error: Unrecognized message type.
250 PEGASUS_ASSERT(0);
|
251 kumpf 1.6 CIMResponseMessage* resp = request->buildResponse();
|
252 schuur 1.7 resp->cimException = PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
|
253 kumpf 1.6 "Unknown message type.");
|
254 kumpf 1.1 response = resp;
255 }
256
257 //
258 // Forward the request to the appropriate ProviderManager(s)
259 //
260
|
261 carolann.graves 1.17 if ((request->getType() == CIM_STOP_ALL_PROVIDERS_REQUEST_MESSAGE) ||
262 (request->getType() ==
263 CIM_SUBSCRIPTION_INIT_COMPLETE_REQUEST_MESSAGE))
|
264 kumpf 1.1 {
|
265 carolann.graves 1.17 _subscriptionInitComplete = true;
266
267 // Send CIMStopAllProvidersRequestMessage or
268 // CIMSubscriptionInitCompleteRequestMessage to all ProviderManagers
|
269 kumpf 1.5 ReadLock tableLock(_providerManagerTableLock);
|
270 kumpf 1.1 for (Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++)
271 {
272 ProviderManagerContainer* pmc=_providerManagerTable[i];
273 Message* resp = pmc->getProviderManager()->processMessage(request);
274 if (resp)
275 {
|
276 kumpf 1.3 delete resp;
|
277 kumpf 1.1 }
278 }
|
279 kumpf 1.3
|
280 schuur 1.7 response = request->buildResponse();
|
281 kumpf 1.6 }
282 else if(request->getType() == CIM_NOTIFY_CONFIG_CHANGE_REQUEST_MESSAGE)
283 {
|
284 schuur 1.7 // Do not need to forward this request to in-process provider
|
285 kumpf 1.6 // managers
|
286 schuur 1.7 response = request->buildResponse();
|
287 kumpf 1.1 }
288 else
289 {
290 // Retrieve the provider interface type
291 String interfaceType;
292 CIMValue itValue = providerModule.getProperty(
293 providerModule.findProperty("InterfaceType")).getValue();
294 itValue.get(interfaceType);
295
296 // Look up the appropriate ProviderManager by InterfaceType
297 ProviderManager* pm = _lookupProviderManager(interfaceType);
|
298 schuur 1.7 if (remoteNameSpaceRequest && !pm->supportsRemoteNameSpaces()) {
299 CIMResponseMessage* resp = request->buildResponse();
300 resp->cimException = PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
301 "Remote Namespace operations not supported for interface type "+interfaceType);
302 response = resp;
303 }
304 else response = pm->processMessage(request);
|
305 kumpf 1.1 }
306
307 // preserve message key
308 response->setKey(request->getKey());
309
310 // set HTTP method in response from request
311 response->setHttpMethod(request->getHttpMethod());
312
313 PEG_METHOD_EXIT();
314 return response;
315 }
316
317 // ATTN: May need to add interfaceVersion parameter to further constrain lookup
318 ProviderManager* BasicProviderManagerRouter::_lookupProviderManager(
319 const String& interfaceType)
320 {
321 PEG_METHOD_ENTER(TRC_PROVIDERMANAGER,
322 "BasicProviderManagerRouter::_lookupProviderManager");
323
324 //
325 // Search for this InterfaceType in the table of loaded ProviderManagers
326 kumpf 1.1 //
327 {
328 ReadLock tableLock(_providerManagerTableLock);
329
330 // find provider manager for specified provider interface type
331 for(Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++)
332 {
333 if (interfaceType == _providerManagerTable[i]->getInterfaceName())
334 {
335 ProviderManagerContainer* pmc=_providerManagerTable[i];
336 PEG_METHOD_EXIT();
337 return pmc->getProviderManager();
338 }
339 }
340 }
341
342 //
343 // Load the ProviderManager for this InterfaceType and add it to the table
344 //
345 {
346 WriteLock tableLock(_providerManagerTableLock);
347 kumpf 1.1
348 // ATTN: this section is a temporary solution to populate the list of
349 // enabled provider managers for a given distribution. It includes
350 // another temporary solution for converting a generic file name into
351 // a file name useable by each platform.
352
|
353 se.gupta 1.10 #if defined(PEGASUS_ENABLE_DEFAULT_PROVIDER_MANAGER)
|
354 kumpf 1.1 if (interfaceType == "C++Default")
355 {
356 ProviderManagerContainer* pmc = new ProviderManagerContainer(
357 LIBRARY_NAME_DEFAULTPM, "DEFAULT", "C++Default",
|
358 carolann.graves 1.17 _indicationCallback, _subscriptionInitComplete);
|
359 kumpf 1.1 _providerManagerTable.append(pmc);
360 return pmc->getProviderManager();
361 }
362 #endif
363
|
364 se.gupta 1.11 #if defined(PEGASUS_ENABLE_CMPI_PROVIDER_MANAGER)
|
365 kumpf 1.1 if (interfaceType == "CMPI")
366 {
367 ProviderManagerContainer* pmc = new ProviderManagerContainer(
|
368 kumpf 1.18 LIBRARY_NAME_CMPIPM, "CMPI", "CMPI", _indicationCallback,
369 _subscriptionInitComplete);
|
370 kumpf 1.1 _providerManagerTable.append(pmc);
371 return pmc->getProviderManager();
372 }
373 #endif
374
|
375 se.gupta 1.11 #if defined(PEGASUS_ENABLE_JMPI_PROVIDER_MANAGER)
|
376 kumpf 1.1 if (interfaceType == "JMPI")
377 {
378 ProviderManagerContainer* pmc = new ProviderManagerContainer(
|
379 kumpf 1.18 LIBRARY_NAME_JMPIPM, "JMPI", "JMPI", _indicationCallback,
380 _subscriptionInitComplete);
|
381 kumpf 1.1 _providerManagerTable.append(pmc);
382 return pmc->getProviderManager();
383 }
384 #endif
385 // END TEMP SECTION
386 }
387
388 // Error: ProviderManager not found for the specified interface type
389 PEGASUS_ASSERT(0);
390 PEG_METHOD_EXIT();
391 return 0;
392 }
393
|
394 kumpf 1.5 Boolean BasicProviderManagerRouter::hasActiveProviders()
|
395 kumpf 1.1 {
396 PEG_METHOD_ENTER(TRC_PROVIDERMANAGER,
|
397 kumpf 1.5 "BasicProviderManagerRouter::hasActiveProviders");
|
398 kumpf 1.1
|
399 kumpf 1.5 ReadLock tableLock(_providerManagerTableLock);
|
400 kumpf 1.1 for(Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++)
401 {
402 ProviderManagerContainer* pmc = _providerManagerTable[i];
|
403 kumpf 1.5 if (pmc->getProviderManager()->hasActiveProviders())
404 {
405 PEG_METHOD_EXIT();
406 return true;
407 }
408 }
409
410 PEG_METHOD_EXIT();
411 return false;
412 }
413
414 void BasicProviderManagerRouter::unloadIdleProviders()
415 {
416 PEG_METHOD_ENTER(TRC_PROVIDERMANAGER,
417 "BasicProviderManagerRouter::unloadIdleProviders");
418
419 //
420 // Save pointers to the ProviderManagerContainers so we don't hold the
421 // _providerManagerTableLock while unloading idle providers
422 //
423 Array<ProviderManagerContainer*> pmcs;
424 kumpf 1.5 {
425 ReadLock tableLock(_providerManagerTableLock);
426 for(Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++)
427 {
428 pmcs.append(_providerManagerTable[i]);
429 }
430 }
431
432 //
433 // Unload idle providers in each of the active ProviderManagers
434 // _providerManagerTableLock while unloading idle providers
435 //
436 for (Uint32 i = 0; i < pmcs.size(); i++)
437 {
438 pmcs[i]->getProviderManager()->unloadIdleProviders();
|
439 kumpf 1.1 }
440
441 PEG_METHOD_EXIT();
442 }
443
444 PEGASUS_NAMESPACE_END
|