1 karl 1.11 //%2006////////////////////////////////////////////////////////////////////////
|
2 kumpf 1.1 //
|
3 karl 1.3 // 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.3 // 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.5 // Copyright (c) 2005 Hewlett-Packard Development Company, L.P.; IBM Corp.;
10 // EMC Corporation; VERITAS Software Corporation; The Open Group.
|
11 karl 1.11 // Copyright (c) 2006 Hewlett-Packard Development Company, L.P.; IBM Corp.;
12 // EMC Corporation; Symantec Corporation; The Open Group.
|
13 kumpf 1.1 //
14 // Permission is hereby granted, free of charge, to any person obtaining a copy
15 // of this software and associated documentation files (the "Software"), to
16 // deal in the Software without restriction, including without limitation the
17 // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
18 // sell copies of the Software, and to permit persons to whom the Software is
19 // furnished to do so, subject to the following conditions:
|
20 r.kieninger 1.15 //
|
21 kumpf 1.1 // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
22 // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
23 // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
24 // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
25 // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
26 // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
27 // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 //
30 //==============================================================================
31 //
32 //%/////////////////////////////////////////////////////////////////////////////
33
34 #include <Pegasus/Common/Config.h>
35 #include <Pegasus/Common/Constants.h>
36 #include <Pegasus/Common/Tracer.h>
37
38 #include "IndicationConstants.h"
39 #include "IndicationService.h"
40 #include "SubscriptionTable.h"
41
|
42 yi.zhou 1.17 #ifdef PEGASUS_ENABLE_INDICATION_COUNT
43 # include "ProviderIndicationCountTable.h"
44 #endif
45
|
46 kumpf 1.1 PEGASUS_USING_STD;
47
48 PEGASUS_NAMESPACE_BEGIN
49
50 SubscriptionTable::SubscriptionTable (
51 SubscriptionRepository * subscriptionRepository)
52 : _subscriptionRepository (subscriptionRepository)
53 {
54 }
55
56 SubscriptionTable::~SubscriptionTable ()
57 {
58 }
59
60 Boolean SubscriptionTable::getSubscriptionEntry (
61 const CIMObjectPath & subscriptionPath,
|
62 carolann.graves 1.9 ActiveSubscriptionsTableEntry & tableValue) const
|
63 kumpf 1.1 {
64 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
65 "SubscriptionTable::getSubscriptionEntry");
66
67 Boolean succeeded = false;
|
68 r.kieninger 1.15 String activeSubscriptionsKey = _generateActiveSubscriptionsKey
|
69 kumpf 1.1 (subscriptionPath);
|
70 carolann.graves 1.9 if (_lockedLookupActiveSubscriptionsEntry
|
71 kumpf 1.1 (activeSubscriptionsKey, tableValue))
72 {
73 succeeded = true;
74 }
75 else
76 {
77 //
78 // Subscription not found in Active Subscriptions table
79 //
|
80 marek 1.21 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL, Tracer::LEVEL1,
|
81 r.kieninger 1.15 "Subscription (" + activeSubscriptionsKey +
|
82 kumpf 1.1 ") not found in ActiveSubscriptionsTable");
83 }
84
85 PEG_METHOD_EXIT ();
86 return succeeded;
87 }
88
89 Array <CIMInstance> SubscriptionTable::getMatchingSubscriptions (
90 const CIMName & supportedClass,
91 const Array <CIMNamespaceName> nameSpaces,
92 const Boolean checkProvider,
|
93 aruran.ms 1.7 const CIMInstance & provider) const
|
94 kumpf 1.1 {
95 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
96 "SubscriptionTable::getMatchingSubscriptions");
97
98 Array <CIMInstance> matchingSubscriptions;
99 Array <CIMInstance> subscriptions;
100
101 for (Uint32 i = 0; i < nameSpaces.size (); i++)
102 {
103 //
|
104 carolann.graves 1.9 // Look up the indicationClass-sourceNamespace pair in the
|
105 kumpf 1.1 // Subscription Classes table
106 //
|
107 carolann.graves 1.9 String subscriptionClassesKey = _generateSubscriptionClassesKey
|
108 kumpf 1.1 (supportedClass, nameSpaces [i]);
|
109 kumpf 1.22 SubscriptionClassesTableEntry scTableValue;
110 if (_lockedLookupSubscriptionClassesEntry(
111 subscriptionClassesKey, scTableValue))
|
112 kumpf 1.1 {
|
113 kumpf 1.22 subscriptions = scTableValue.subscriptions;
|
114 kumpf 1.1 for (Uint32 j = 0; j < subscriptions.size (); j++)
115 {
116 Boolean match = true;
117
118 if (checkProvider)
119 {
120 //
|
121 carolann.graves 1.9 // Check if the provider who generated this indication
|
122 kumpf 1.1 // accepted this subscription
123 //
|
124 r.kieninger 1.15 String activeSubscriptionsKey =
|
125 kumpf 1.1 _generateActiveSubscriptionsKey
|
126 carolann.graves 1.10 (subscriptions [j].getPath ());
|
127 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
128 if (_lockedLookupActiveSubscriptionsEntry(
129 activeSubscriptionsKey, asTableValue))
|
130 kumpf 1.1 {
131 //
132 // If provider is not in list, it did not accept the
133 // subscription
134 //
|
135 kumpf 1.22 if ((providerInList(provider, asTableValue)) ==
136 PEG_NOT_FOUND)
|
137 kumpf 1.1 {
138 match = false;
139 break;
140 }
141 }
142 }
143
144 if (match)
145 {
146 //
147 // Add current subscription to list
148 //
149 matchingSubscriptions.append (subscriptions [j]);
150 }
151 }
152 }
153 }
154
155 PEG_METHOD_EXIT ();
156 return matchingSubscriptions;
157 }
158 kumpf 1.1
|
159 carolann.graves 1.12 Array <CIMInstance> SubscriptionTable::reflectProviderDisable (
|
160 aruran.ms 1.8 const CIMInstance & provider)
|
161 kumpf 1.1 {
162 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
|
163 carolann.graves 1.12 "SubscriptionTable::reflectProviderDisable");
|
164 kumpf 1.1
165 Array <CIMInstance> providerSubscriptions;
166
167 //
168 // Iterate through the subscription table to find subscriptions served by
169 // the provider
|
170 carolann.graves 1.9 // NOTE: updating entries (remove and insert) while iterating through the
|
171 kumpf 1.1 // table does not work reliably, and it is not clear if that is supposed to
|
172 carolann.graves 1.9 // work; for now, the SubscriptionTable first iterates through the
173 // active subscriptions table to find subscriptions served by the
174 // provider, then looks up and updates each affected subscription
|
175 kumpf 1.1 //
176 {
177 //
|
178 carolann.graves 1.9 // Acquire and hold the write lock during the entire
179 // lookup/remove/insert process, allowing competing threads to apply
180 // their logic over a consistent view of the data.
|
181 kumpf 1.14 // Do not call any other methods that need
|
182 carolann.graves 1.9 // _activeSubscriptionsTableLock.
|
183 kumpf 1.1 //
|
184 carolann.graves 1.9 WriteLock lock (_activeSubscriptionsTableLock);
|
185 kumpf 1.1
186 for (ActiveSubscriptionsTable::Iterator i =
187 _activeSubscriptionsTable.start (); i; i++)
188 {
189 //
190 // If provider matches, append subscription to the list
191 //
|
192 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue = i.value();
193 for (Uint32 j = 0; j < asTableValue.providers.size(); j++)
|
194 kumpf 1.1 {
|
195 kumpf 1.22 if (asTableValue.providers[j].provider.getPath().identical(
196 provider.getPath()))
|
197 kumpf 1.1 {
198 //
199 // Add the subscription to the list
200 //
|
201 kumpf 1.22 providerSubscriptions.append(asTableValue.subscription);
|
202 kumpf 1.1 break;
203 }
204 }
205 }
206
207 //
|
208 carolann.graves 1.9 // Look up and update hash table entry for each affected subscription
|
209 kumpf 1.1 //
|
210 carolann.graves 1.9 for (Uint32 k = 0; k < providerSubscriptions.size (); k++)
|
211 kumpf 1.1 {
212 //
|
213 carolann.graves 1.9 // Update the entry in the active subscriptions hash table
|
214 kumpf 1.1 //
|
215 r.kieninger 1.15 String activeSubscriptionsKey =
|
216 carolann.graves 1.10 _generateActiveSubscriptionsKey
217 (providerSubscriptions [k].getPath ());
|
218 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
219 if (_activeSubscriptionsTable.lookup(
220 activeSubscriptionsKey, asTableValue))
|
221 kumpf 1.1 {
|
222 carolann.graves 1.9 //
223 // Remove the provider from the list of providers serving the
224 // subscription
225 //
|
226 kumpf 1.22 Uint32 providerIndex = providerInList(provider, asTableValue);
|
227 carolann.graves 1.9 if (providerIndex != PEG_NOT_FOUND)
|
228 kumpf 1.1 {
|
229 kumpf 1.22 asTableValue.providers.remove(providerIndex);
|
230 carolann.graves 1.12
|
231 kumpf 1.22 _updateSubscriptionProviders(
232 activeSubscriptionsKey,
233 asTableValue.subscription,
234 asTableValue.providers);
|
235 carolann.graves 1.9 }
236 else
237 {
238 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
239 Tracer::LEVEL2,
240 "Provider (" + provider.getPath().toString() +
241 ") not found in list for Subscription (" +
|
242 r.kieninger 1.15 activeSubscriptionsKey +
|
243 carolann.graves 1.9 ") in ActiveSubscriptionsTable");
|
244 kumpf 1.1 }
245 }
246 else
247 {
|
248 kumpf 1.14 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
|
249 carolann.graves 1.9 Tracer::LEVEL2,
|
250 r.kieninger 1.15 "Subscription (" + activeSubscriptionsKey +
|
251 carolann.graves 1.9 ") not found in ActiveSubscriptionsTable");
252 //
253 // The subscription may have been deleted in the mean time
254 // If so, no further update is required
255 //
|
256 kumpf 1.1 }
257 }
258 }
259
260 PEG_METHOD_EXIT ();
261 return providerSubscriptions;
262 }
263
|
264 carolann.graves 1.12 Array <ActiveSubscriptionsTableEntry>
265 SubscriptionTable::reflectProviderModuleFailure
266 (const String & moduleName,
267 const String & userName,
268 Boolean authenticationEnabled)
269 {
270 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
271 "SubscriptionTable::reflectProviderModuleFailure");
272
273 Array <ActiveSubscriptionsTableEntry> providerModuleSubscriptions;
274
275 //
276 // Iterate through the subscription table to find subscriptions served by
277 // a provider in the specified module, with the specified userName as the
278 // subscription creator
279 // NOTE: updating entries (remove and insert) while iterating through the
280 // table is not allowed
281 // The SubscriptionTable first iterates through the active subscriptions
282 // table to find matching subscriptions served by a provider in the
283 // specified module, then looks up and updates each affected subscription
284 //
285 carolann.graves 1.12 {
286 //
287 // Acquire and hold the write lock during the entire
288 // lookup/remove/insert process, allowing competing threads to apply
289 // their logic over a consistent view of the data.
|
290 kumpf 1.14 // Do not call any other methods that need
|
291 carolann.graves 1.12 // _activeSubscriptionsTableLock.
292 //
293 WriteLock lock (_activeSubscriptionsTableLock);
294
295 for (ActiveSubscriptionsTable::Iterator i =
296 _activeSubscriptionsTable.start (); i; i++)
297 {
|
298 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
|
299 carolann.graves 1.12 //
300 // Get subscription creator
301 //
|
302 kumpf 1.22 asTableValue = i.value();
|
303 carolann.graves 1.12 String creator;
|
304 kumpf 1.22 CIMValue creatorValue = asTableValue.subscription.getProperty(
305 asTableValue.subscription.findProperty(
306 PEGASUS_PROPERTYNAME_INDSUB_CREATOR)).getValue();
|
307 carolann.graves 1.12 creatorValue.get (creator);
308
309 Array <ProviderClassList> failedProviderList;
|
310 kumpf 1.22 for (Uint32 j = 0; j < asTableValue.providers.size(); j++)
|
311 carolann.graves 1.12 {
312 //
313 // Get provider module name
314 //
315 String providerModuleName;
316 CIMValue nameValue =
|
317 kumpf 1.22 asTableValue.providers[j].providerModule.getProperty(
318 asTableValue.providers[j].providerModule.findProperty(
319 PEGASUS_PROPERTYNAME_NAME)).getValue();
|
320 carolann.graves 1.12 nameValue.get (providerModuleName);
321
322 //
323 // Get module user context setting
324 //
325 Uint16 moduleContext = PEGASUS_DEFAULT_PROV_USERCTXT;
|
326 kumpf 1.14 CIMValue contextValue =
|
327 kumpf 1.22 asTableValue.providers[j].providerModule.getProperty(
328 asTableValue.providers [j].providerModule.findProperty(
329 PEGASUS_PROPERTYNAME_MODULE_USERCONTEXT)).
330 getValue();
|
331 carolann.graves 1.12 if (!contextValue.isNull ())
332 {
333 contextValue.get (moduleContext);
334 }
335
336 //
|
337 kumpf 1.14 // If provider module name matches,
|
338 carolann.graves 1.12 // add provider to the list of failed providers
339 //
340 if (providerModuleName == moduleName)
341 {
342 //
343 // If authentication is enabled, and module was run as
344 // requestor, subscription creator must also match module
345 // user context name, to add provider to the list of
346 // failed providers
347 //
348 if ((moduleContext != PG_PROVMODULE_USERCTXT_REQUESTOR) ||
349 (!authenticationEnabled) || (creator == userName))
350 {
351 //
352 // Add the provider to the list
353 //
|
354 kumpf 1.22 failedProviderList.append(asTableValue.providers[j]);
|
355 carolann.graves 1.12 }
356 } // if provider module name matches
357 } // for each subscription provider
358
359 //
360 // If there were any failed providers, add the subscription
361 // entry to the list of affected subscriptions
362 //
363 if (failedProviderList.size () > 0)
364 {
365 ActiveSubscriptionsTableEntry subscription;
|
366 kumpf 1.22 subscription.subscription = asTableValue.subscription;
|
367 carolann.graves 1.12 subscription.providers = failedProviderList;
368 providerModuleSubscriptions.append (subscription);
369 }
370 }
371
372 //
373 // Look up and update hash table entry for each affected subscription
374 //
375 for (Uint32 k = 0; k < providerModuleSubscriptions.size (); k++)
376 {
377 //
378 // Update the entry in the active subscriptions hash table
379 //
|
380 r.kieninger 1.15 String activeSubscriptionsKey =
|
381 carolann.graves 1.12 _generateActiveSubscriptionsKey
382 (providerModuleSubscriptions [k].subscription.getPath ());
|
383 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
384 if (_activeSubscriptionsTable.lookup(
385 activeSubscriptionsKey, asTableValue))
|
386 carolann.graves 1.12 {
|
387 kumpf 1.14 Array <ProviderClassList> updatedProviderList;
|
388 kumpf 1.22 for (Uint32 l = 0; l < asTableValue.providers.size(); l++)
|
389 carolann.graves 1.12 {
390 String providerModuleName;
391 CIMValue nameValue =
|
392 kumpf 1.22 asTableValue.providers[l].providerModule.getProperty(
393 asTableValue.providers[l].providerModule.
394 findProperty(PEGASUS_PROPERTYNAME_NAME)).getValue();
|
395 carolann.graves 1.12 nameValue.get (providerModuleName);
396 if (providerModuleName != moduleName)
397 {
398 //
399 // Provider is not in the failed module
400 // Append provider to list of providers still serving
401 // the subscription
402 //
|
403 kumpf 1.22 updatedProviderList.append(asTableValue.providers[l]);
|
404 carolann.graves 1.12 }
405 }
406
|
407 kumpf 1.22 _updateSubscriptionProviders(
408 activeSubscriptionsKey,
409 asTableValue.subscription,
410 updatedProviderList);
|
411 carolann.graves 1.12 }
412 }
413 }
414
415 PEG_METHOD_EXIT ();
416 return providerModuleSubscriptions;
417 }
418
|
419 r.kieninger 1.15 String SubscriptionTable::_generateActiveSubscriptionsKey (
|
420 kumpf 1.1 const CIMObjectPath & subscription) const
421 {
422 //
|
423 carolann.graves 1.10 // Get filter and handler object paths from subscription Filter and Handler
424 // reference property values
|
425 kumpf 1.1 //
426 Array<CIMKeyBinding> subscriptionKB = subscription.getKeyBindings ();
|
427 r.kieninger 1.15 String filterPath;
428 String handlerPath;
|
429 kumpf 1.1 for (Uint32 i = 0; i < subscriptionKB.size (); i++)
430 {
|
431 w.otsuka 1.13 if ((subscriptionKB [i].getName () == PEGASUS_PROPERTYNAME_FILTER) &&
|
432 kumpf 1.1 (subscriptionKB [i].getType () == CIMKeyBinding::REFERENCE))
433 {
|
434 carolann.graves 1.10 filterPath = subscriptionKB [i].getValue ();
|
435 kumpf 1.1 }
|
436 r.kieninger 1.15 else
|
437 w.otsuka 1.13 if ((subscriptionKB [i].getName () == PEGASUS_PROPERTYNAME_HANDLER) &&
|
438 kumpf 1.1 (subscriptionKB [i].getType () == CIMKeyBinding::REFERENCE))
439 {
|
440 carolann.graves 1.10 handlerPath = subscriptionKB [i].getValue ();
|
441 kumpf 1.1 }
442 }
443
444 //
|
445 r.kieninger 1.15 // Construct subscription key from handler and filter.
446 // To avoid ambiguity, the hostname part is removed, since the
447 // hostname can only point to the local machine anyway.
|
448 kumpf 1.1 //
|
449 r.kieninger 1.15 const Char16 slash = '/';
450 if ((filterPath[0]==slash) && (filterPath[1]==slash))
451 {
452 Uint32 index = filterPath.find(2,slash);
453 filterPath = filterPath.subString(index+1);
454 }
455
456 if ((handlerPath[0]==slash) && (handlerPath[1]==slash))
457 {
458 Uint32 index = handlerPath.find(2,slash);
459 handlerPath = handlerPath.subString(index+1);
460 }
461
462 //
463 // Assuming that most subscriptions will differ in the filter and handler
|
464 yi.zhou 1.18 // names, the namespace and classname of the subscription are added at the
|
465 r.kieninger 1.15 // end of the key.
466 //
467 String activeSubscriptionsKey(filterPath);
468 activeSubscriptionsKey.append(handlerPath);
469 activeSubscriptionsKey.append(slash);
470 activeSubscriptionsKey.append(subscription.getNameSpace().getString());
471 activeSubscriptionsKey.append(slash);
472 activeSubscriptionsKey.append(subscription.getClassName().getString());
|
473 kumpf 1.1
474 return activeSubscriptionsKey;
475 }
476
477 Boolean SubscriptionTable::_lockedLookupActiveSubscriptionsEntry (
|
478 r.kieninger 1.15 const String & key,
|
479 aruran.ms 1.7 ActiveSubscriptionsTableEntry & tableEntry) const
|
480 kumpf 1.1 {
481 ReadLock lock(_activeSubscriptionsTableLock);
482
483 return (_activeSubscriptionsTable.lookup (key, tableEntry));
484 }
485
486 void SubscriptionTable::_insertActiveSubscriptionsEntry (
487 const CIMInstance & subscription,
|
488 aruran.ms 1.8 const Array <ProviderClassList> & providers)
|
489 kumpf 1.1 {
490 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
491 "SubscriptionTable::_insertActiveSubscriptionsEntry");
492
|
493 r.kieninger 1.15 String activeSubscriptionsKey = _generateActiveSubscriptionsKey
|
494 kumpf 1.1 (subscription.getPath ());
495 ActiveSubscriptionsTableEntry entry;
496 entry.subscription = subscription;
497 entry.providers = providers;
498
|
499 carolann.graves 1.10 //
500 // Insert returns true on success, false if duplicate key
501 //
502 Boolean succeeded = _activeSubscriptionsTable.insert
503 (activeSubscriptionsKey, entry);
504 PEGASUS_ASSERT (succeeded);
|
505 kumpf 1.1
506 #ifdef PEGASUS_INDICATION_HASHTRACE
507 String traceString;
508 traceString.append (activeSubscriptionsKey);
509 traceString.append (" Providers: ");
510 for (Uint32 i = 0; i < providers.size (); i++)
511 {
|
512 carolann.graves 1.9 String providerName = providers [i].provider.getProperty
513 (providers [i].provider.findProperty
|
514 w.otsuka 1.13 (PEGASUS_PROPERTYNAME_NAME)).getValue ().toString ();
|
515 kumpf 1.1 traceString.append (providerName);
516 traceString.append (" Classes: ");
517 for (Uint32 j = 0; j < providers[i].classList.size (); j++)
518 {
|
519 carolann.graves 1.9 traceString.append (providers[i].classList[j].getString());
|
520 kumpf 1.1 traceString.append (" ");
521 }
522 }
|
523 carolann.graves 1.9
|
524 marek 1.21 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL, Tracer::LEVEL4,
|
525 kumpf 1.1 "INSERTED _activeSubscriptionsTable entry: " + traceString);
526 #endif
527
528 PEG_METHOD_EXIT ();
529 }
530
531 void SubscriptionTable::_removeActiveSubscriptionsEntry (
|
532 r.kieninger 1.15 const String & key)
|
533 kumpf 1.1 {
534 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
535 "SubscriptionTable::_removeActiveSubscriptionsEntry");
536
|
537 carolann.graves 1.10 //
538 // Remove returns true on success, false if not found
539 //
540 Boolean succeeded = _activeSubscriptionsTable.remove (key);
541 PEGASUS_ASSERT (succeeded);
542
|
543 kumpf 1.1 #ifdef PEGASUS_INDICATION_HASHTRACE
|
544 carolann.graves 1.9 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
|
545 marek 1.21 Tracer::LEVEL4,
|
546 carolann.graves 1.10 "REMOVED _activeSubscriptionsTable entry: " +
|
547 kumpf 1.20 key);
|
548 kumpf 1.1 #endif
549
550 PEG_METHOD_EXIT ();
551 }
552
553 String SubscriptionTable::_generateSubscriptionClassesKey (
554 const CIMName & indicationClassName,
555 const CIMNamespaceName & sourceNamespaceName) const
556 {
557 String subscriptionClassesKey;
558
559 //
560 // Append indication class name to key
561 //
562 subscriptionClassesKey.append (indicationClassName.getString ());
563
564 //
565 // Append source namespace name to key
566 //
567 subscriptionClassesKey.append (sourceNamespaceName.getString ());
568
569 kumpf 1.1 return subscriptionClassesKey;
570 }
571
572 Boolean SubscriptionTable::_lockedLookupSubscriptionClassesEntry (
573 const String & key,
|
574 aruran.ms 1.7 SubscriptionClassesTableEntry & tableEntry) const
|
575 kumpf 1.1 {
576 ReadLock lock(_subscriptionClassesTableLock);
577
578 return (_subscriptionClassesTable.lookup (key, tableEntry));
579 }
580
|
581 carolann.graves 1.9 void SubscriptionTable::_insertSubscriptionClassesEntry (
|
582 kumpf 1.1 const CIMName & indicationClassName,
583 const CIMNamespaceName & sourceNamespaceName,
584 const Array <CIMInstance> & subscriptions)
585 {
586 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
|
587 carolann.graves 1.9 "SubscriptionTable::_insertSubscriptionClassesEntry");
|
588 kumpf 1.1
589 String subscriptionClassesKey = _generateSubscriptionClassesKey
590 (indicationClassName, sourceNamespaceName);
591 SubscriptionClassesTableEntry entry;
592 entry.indicationClassName = indicationClassName;
593 entry.sourceNamespaceName = sourceNamespaceName;
594 entry.subscriptions = subscriptions;
|
595 carolann.graves 1.9
|
596 carolann.graves 1.10 //
597 // Insert returns true on success, false if duplicate key
598 //
599 Boolean succeeded = _subscriptionClassesTable.insert
600 (subscriptionClassesKey, entry);
601 PEGASUS_ASSERT (succeeded);
|
602 kumpf 1.1
603 #ifdef PEGASUS_INDICATION_HASHTRACE
604 String traceString;
605 traceString.append (subscriptionClassesKey);
606 traceString.append (" Subscriptions: ");
607 for (Uint32 i = 0; i < subscriptions.size (); i++)
608 {
|
609 carolann.graves 1.9 traceString.append (subscriptions [i].getPath ().toString());
|
610 kumpf 1.1 traceString.append (" ");
611 }
|
612 carolann.graves 1.9
|
613 marek 1.21 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL, Tracer::LEVEL4,
|
614 kumpf 1.1 "INSERTED _subscriptionClassesTable entry: " + traceString);
615 #endif
616
617 PEG_METHOD_EXIT ();
618 }
619
|
620 carolann.graves 1.9 void SubscriptionTable::_removeSubscriptionClassesEntry (
|
621 kumpf 1.1 const String & key)
622 {
623 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
|
624 carolann.graves 1.9 "SubscriptionTable::_removeSubscriptionClassesEntry");
|
625 kumpf 1.1
|
626 carolann.graves 1.10 //
627 // Remove returns true on success, false if not found
628 //
629 Boolean succeeded = _subscriptionClassesTable.remove (key);
630 PEGASUS_ASSERT (succeeded);
|
631 kumpf 1.1
632 #ifdef PEGASUS_INDICATION_HASHTRACE
|
633 marek 1.21 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL, Tracer::LEVEL4,
|
634 kumpf 1.1 "REMOVED _subscriptionClassesTable entry: " + key);
635 #endif
636
637 PEG_METHOD_EXIT ();
638 }
639
|
640 carolann.graves 1.12 void SubscriptionTable::_updateSubscriptionProviders
|
641 r.kieninger 1.15 (const String & activeSubscriptionsKey,
|
642 carolann.graves 1.12 const CIMInstance & subscription,
643 const Array <ProviderClassList> & updatedProviderList)
644 {
645 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
646 "SubscriptionTable::_updateSubscriptionProviders");
647
648 if (updatedProviderList.size () > 0)
649 {
650 //
651 // At least one provider is still serving the
652 // subscription
653 // Update entry in Active Subscriptions table
654 //
655 _removeActiveSubscriptionsEntry (activeSubscriptionsKey);
656 _insertActiveSubscriptionsEntry (subscription, updatedProviderList);
657 }
658 else
659 {
660 //
661 // The disabled or failed provider(s) was (were) the only provider(s)
662 // serving the subscription
663 carolann.graves 1.12 // Implement the subscription's On Fatal Error Policy
664 //
665 Boolean removedOrDisabled =
666 _subscriptionRepository->reconcileFatalError (subscription);
667 _removeActiveSubscriptionsEntry (activeSubscriptionsKey);
668 if (!removedOrDisabled)
669 {
670 //
671 // If subscription was not disabled or deleted
672 // Update entry in Active Subscriptions table
673 // Note that in this case the updatedProviderList is
674 // empty - no providers are serving the subscription
675 // currently
676 //
677 _insertActiveSubscriptionsEntry (subscription,
678 updatedProviderList);
679 }
|
680 s.kodali 1.19 else
681 {
682 // Delete subscription entries from SubscriptionClassesTable.
683 WriteLock lock(_subscriptionClassesTableLock);
|
684 kumpf 1.22 Array<SubscriptionClassesTableEntry> scTableValues;
|
685 s.kodali 1.19 for (SubscriptionClassesTable::Iterator i =
686 _subscriptionClassesTable.start(); i; i++)
687 {
688 SubscriptionClassesTableEntry value = i.value();
689 for (Uint32 j = 0, n = value.subscriptions.size(); j < n; ++j)
690 {
691 if (value.subscriptions[j].getPath().identical(
692 subscription.getPath()))
693 {
694 value.subscriptions.remove(j);
|
695 kumpf 1.22 scTableValues.append(value);
|
696 s.kodali 1.19 break;
697 }
698 }
699 }
|
700 kumpf 1.22 for (Uint32 i = 0, n = scTableValues.size(); i < n; ++i)
|
701 s.kodali 1.19 {
702 String subscriptionClassesKey = _generateSubscriptionClassesKey(
|
703 kumpf 1.22 scTableValues[i].indicationClassName,
704 scTableValues[i].sourceNamespaceName);
|
705 s.kodali 1.19 // If this is the only subscription for this class-namespace
706 // pair delete the entry else update the subscription list
707 // for this class-namespace pair.
|
708 kumpf 1.22 if (scTableValues[i].subscriptions.size())
|
709 s.kodali 1.19 {
710 SubscriptionClassesTableEntry *entry = 0;
711 _subscriptionClassesTable.lookupReference(
712 subscriptionClassesKey,
713 entry);
714 PEGASUS_ASSERT(entry);
|
715 kumpf 1.22 entry->subscriptions = scTableValues[i].subscriptions;
|
716 s.kodali 1.19 }
717 else
718 {
719 _removeSubscriptionClassesEntry(subscriptionClassesKey);
720 }
721 }
722 }
|
723 carolann.graves 1.12 }
724
725 PEG_METHOD_EXIT ();
726 }
727
|
728 carolann.graves 1.6 void SubscriptionTable::insertSubscription (
|
729 kumpf 1.1 const CIMInstance & subscription,
730 const Array <ProviderClassList> & providers,
731 const Array <CIMName> & indicationSubclassNames,
732 const CIMNamespaceName & sourceNamespaceName)
733 {
734 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
735 "SubscriptionTable::insertSubscription");
736
737 //
|
738 carolann.graves 1.9 // Insert entry into active subscriptions table
|
739 kumpf 1.1 //
740 {
741 WriteLock lock(_activeSubscriptionsTableLock);
742
|
743 yi.zhou 1.17 _insertActiveSubscriptionsEntry(subscription, providers);
|
744 kumpf 1.1 }
745
746 //
|
747 carolann.graves 1.9 // Insert or update entries in subscription classes table
|
748 kumpf 1.1 //
749 {
|
750 carolann.graves 1.9 //
751 // Acquire and hold the write lock during the entire
752 // lookup/remove/insert process, allowing competing threads to apply
753 // their logic over a consistent view of the data.
|
754 kumpf 1.14 // Do not call any other methods that need
|
755 carolann.graves 1.9 // _subscriptionClassesTableLock.
756 //
757 WriteLock lock (_subscriptionClassesTableLock);
758 for (Uint32 i = 0; i < indicationSubclassNames.size (); i++)
|
759 kumpf 1.1 {
|
760 carolann.graves 1.9 String subscriptionClassesKey = _generateSubscriptionClassesKey
761 (indicationSubclassNames [i], sourceNamespaceName);
|
762 kumpf 1.22 SubscriptionClassesTableEntry scTableValue;
763 if (_subscriptionClassesTable.lookup(
764 subscriptionClassesKey, scTableValue))
|
765 carolann.graves 1.9 {
766 //
767 // If entry exists for this IndicationClassName-SourceNamespace
768 // pair, remove old entry and insert new entry
769 //
|
770 kumpf 1.22 Array<CIMInstance> subscriptions = scTableValue.subscriptions;
|
771 carolann.graves 1.9 subscriptions.append (subscription);
772 _removeSubscriptionClassesEntry (subscriptionClassesKey);
773 _insertSubscriptionClassesEntry (indicationSubclassNames [i],
774 sourceNamespaceName, subscriptions);
775 }
776 else
777 {
778 //
779 // If no entry exists for this
780 // IndicationClassName-SourceNamespace pair, insert new entry
781 //
782 Array <CIMInstance> subscriptions;
783 subscriptions.append (subscription);
784 _insertSubscriptionClassesEntry (indicationSubclassNames [i],
785 sourceNamespaceName, subscriptions);
786 }
|
787 kumpf 1.1 }
788 }
789
790 PEG_METHOD_EXIT ();
791 }
792
|
793 carolann.graves 1.6 void SubscriptionTable::updateProviders (
|
794 kumpf 1.1 const CIMObjectPath & subscriptionPath,
795 const ProviderClassList & provider,
796 Boolean addProvider)
797 {
798 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
799 "SubscriptionTable::updateProviders");
800
|
801 r.kieninger 1.15 String activeSubscriptionsKey = _generateActiveSubscriptionsKey
|
802 kumpf 1.1 (subscriptionPath);
|
803 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
|
804 kumpf 1.1 {
|
805 carolann.graves 1.9 //
806 // Acquire and hold the write lock during the entire
807 // lookup/remove/insert process, allowing competing threads to apply
808 // their logic over a consistent view of the data.
|
809 kumpf 1.14 // Do not call any other methods that need
|
810 carolann.graves 1.9 // _activeSubscriptionsTableLock.
811 //
812 WriteLock lock (_activeSubscriptionsTableLock);
|
813 kumpf 1.22 if (_activeSubscriptionsTable.lookup(
814 activeSubscriptionsKey, asTableValue))
|
815 kumpf 1.1 {
|
816 kumpf 1.22 Uint32 providerIndex =
817 providerInList(provider.provider, asTableValue);
|
818 carolann.graves 1.9 if (addProvider)
|
819 kumpf 1.1 {
|
820 carolann.graves 1.9 if (providerIndex == PEG_NOT_FOUND)
821 {
|
822 kumpf 1.22 asTableValue.providers.append(provider);
823 _removeActiveSubscriptionsEntry(activeSubscriptionsKey);
824 _insertActiveSubscriptionsEntry(
825 asTableValue.subscription,
826 asTableValue.providers);
|
827 carolann.graves 1.9 }
828 else
829 {
830 CIMInstance p = provider.provider;
831 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
832 Tracer::LEVEL2,
|
833 kumpf 1.14 "Provider " +
|
834 carolann.graves 1.9 IndicationService::getProviderLogString (p) +
835 " already in list for Subscription (" +
|
836 r.kieninger 1.15 activeSubscriptionsKey +
|
837 carolann.graves 1.9 ") in ActiveSubscriptionsTable");
838 }
|
839 kumpf 1.1 }
840 else
841 {
|
842 carolann.graves 1.9 if (providerIndex != PEG_NOT_FOUND)
843 {
|
844 kumpf 1.22 asTableValue.providers.remove(providerIndex);
845 _removeActiveSubscriptionsEntry(activeSubscriptionsKey);
846 _insertActiveSubscriptionsEntry(
847 asTableValue.subscription,
848 asTableValue.providers);
|
849 carolann.graves 1.9 }
850 else
851 {
852 CIMInstance p = provider.provider;
853 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
854 Tracer::LEVEL2,
|
855 kumpf 1.14 "Provider " +
|
856 carolann.graves 1.9 IndicationService::getProviderLogString (p) +
857 " not found in list for Subscription (" +
|
858 r.kieninger 1.15 activeSubscriptionsKey +
|
859 carolann.graves 1.9 ") in ActiveSubscriptionsTable");
860 }
|
861 kumpf 1.1 }
862 }
863 else
864 {
|
865 carolann.graves 1.9 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL, Tracer::LEVEL2,
|
866 r.kieninger 1.15 "Subscription (" + activeSubscriptionsKey +
|
867 carolann.graves 1.9 ") not found in ActiveSubscriptionsTable");
|
868 kumpf 1.14
|
869 carolann.graves 1.9 //
870 // The subscription may have been deleted in the mean time
871 // If so, no further update is required
872 //
|
873 kumpf 1.1 }
874 }
875
876 PEG_METHOD_EXIT ();
877 }
878
879 void SubscriptionTable::updateClasses (
880 const CIMObjectPath & subscriptionPath,
881 const CIMInstance & provider,
882 const CIMName & className)
883 {
884 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
885 "SubscriptionTable::updateClasses");
886
|
887 r.kieninger 1.15 String activeSubscriptionsKey = _generateActiveSubscriptionsKey
|
888 kumpf 1.1 (subscriptionPath);
|
889 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
|
890 kumpf 1.1
891 {
|
892 carolann.graves 1.9 //
893 // Acquire and hold the write lock during the entire
894 // lookup/remove/insert process, allowing competing threads to apply
895 // their logic over a consistent view of the data.
|
896 kumpf 1.14 // Do not call any other methods that need
|
897 carolann.graves 1.9 // _activeSubscriptionsTableLock.
898 //
899 WriteLock lock (_activeSubscriptionsTableLock);
|
900 kumpf 1.22 if (_activeSubscriptionsTable.lookup(
901 activeSubscriptionsKey, asTableValue))
|
902 kumpf 1.1 {
|
903 kumpf 1.22 Uint32 providerIndex = providerInList(provider, asTableValue);
|
904 carolann.graves 1.9 if (providerIndex != PEG_NOT_FOUND)
|
905 kumpf 1.1 {
|
906 kumpf 1.22 Uint32 classIndex = classInList(
907 className, asTableValue.providers[providerIndex]);
|
908 carolann.graves 1.9 if (classIndex == PEG_NOT_FOUND)
909 {
|
910 kumpf 1.22 asTableValue.providers[providerIndex].classList.append(
911 className);
|
912 carolann.graves 1.9 }
913 else // classIndex != PEG_NOT_FOUND
914 {
|
915 kumpf 1.22 asTableValue.providers[providerIndex].classList.remove(
916 classIndex);
|
917 carolann.graves 1.9 }
918
|
919 kumpf 1.22 _removeActiveSubscriptionsEntry(activeSubscriptionsKey);
920 _insertActiveSubscriptionsEntry(
921 asTableValue.subscription,
922 asTableValue.providers);
|
923 kumpf 1.1 }
|
924 carolann.graves 1.9 else
|
925 kumpf 1.1 {
|
926 kumpf 1.14 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
|
927 carolann.graves 1.9 Tracer::LEVEL2,
928 "Provider (" + provider.getPath ().toString () +
929 ") not found in list for Subscription (" +
|
930 r.kieninger 1.15 activeSubscriptionsKey +
|
931 carolann.graves 1.9 ") in ActiveSubscriptionsTable");
|
932 kumpf 1.1 }
933 }
934 else
935 {
|
936 carolann.graves 1.9 //
937 // Subscription not found in Active Subscriptions table
938 //
|
939 kumpf 1.1 }
940 }
941
942 PEG_METHOD_EXIT ();
943 }
944
|
945 carolann.graves 1.6 void SubscriptionTable::removeSubscription (
|
946 kumpf 1.1 const CIMInstance & subscription,
947 const Array <CIMName> & indicationSubclassNames,
948 const CIMNamespaceName & sourceNamespaceName,
949 const Array <ProviderClassList> & providers)
950 {
951 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
952 "SubscriptionTable::removeSubscription");
953
954 //
|
955 carolann.graves 1.9 // Remove entry from active subscriptions table
|
956 kumpf 1.1 //
957 {
958 WriteLock lock(_activeSubscriptionsTableLock);
959
960 _removeActiveSubscriptionsEntry (
961 _generateActiveSubscriptionsKey (subscription.getPath ()));
962 }
963
964 //
|
965 carolann.graves 1.9 // Remove or update entries in subscription classes table
|
966 kumpf 1.1 //
967 {
|
968 carolann.graves 1.9 //
969 // Acquire and hold the write lock during the entire
970 // lookup/remove/insert process, allowing competing threads to apply
971 // their logic over a consistent view of the data.
|
972 kumpf 1.14 // Do not call any other methods that need
|
973 carolann.graves 1.9 // _subscriptionClassesTableLock.
974 //
975 WriteLock lock (_subscriptionClassesTableLock);
976 for (Uint32 i = 0; i < indicationSubclassNames.size (); i++)
|
977 kumpf 1.1 {
|
978 carolann.graves 1.9 String subscriptionClassesKey = _generateSubscriptionClassesKey
979 (indicationSubclassNames [i], sourceNamespaceName);
|
980 kumpf 1.22 SubscriptionClassesTableEntry scTableValue;
981 if (_subscriptionClassesTable.lookup(
982 subscriptionClassesKey, scTableValue))
|
983 carolann.graves 1.9 {
984 //
985 // If entry exists for this IndicationClassName-SourceNamespace
986 // pair, remove subscription from the list
987 //
|
988 kumpf 1.22 Array<CIMInstance> subscriptions = scTableValue.subscriptions;
|
989 carolann.graves 1.9 for (Uint32 j = 0; j < subscriptions.size (); j++)
990 {
991 if (subscriptions [j].getPath().identical
992 (subscription.getPath()))
993 {
994 subscriptions.remove (j);
995 }
996 }
|
997 kumpf 1.14
|
998 carolann.graves 1.9 //
999 // Remove the old entry
1000 //
1001 _removeSubscriptionClassesEntry (subscriptionClassesKey);
|
1002 kumpf 1.14
|
1003 carolann.graves 1.9 //
1004 // If there are still subscriptions in the list, insert the
1005 // new entry
1006 //
1007 if (subscriptions.size () > 0)
|
1008 kumpf 1.1 {
|
1009 carolann.graves 1.9 _insertSubscriptionClassesEntry (
1010 indicationSubclassNames [i],
1011 sourceNamespaceName, subscriptions);
|
1012 kumpf 1.1 }
1013 }
|
1014 carolann.graves 1.9 else
|
1015 kumpf 1.1 {
|
1016 carolann.graves 1.9 //
1017 // Entry not found in Subscription Classes table
1018 //
|
1019 kumpf 1.14 PEG_TRACE_STRING (TRC_INDICATION_SERVICE_INTERNAL,
|
1020 carolann.graves 1.9 Tracer::LEVEL2,
|
1021 kumpf 1.14 "Indication subclass and namespace (" +
|
1022 carolann.graves 1.9 subscriptionClassesKey +
1023 ") not found in SubscriptionClassesTable");
|
1024 kumpf 1.1 }
1025 }
1026 }
1027
1028 PEG_METHOD_EXIT ();
1029 }
1030
|
1031 carolann.graves 1.9 Uint32 SubscriptionTable::providerInList
1032 (const CIMInstance & provider,
|
1033 kumpf 1.1 const ActiveSubscriptionsTableEntry & tableValue) const
1034 {
1035 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
1036 "SubscriptionTable::providerInList");
1037
1038 //
1039 // Look for the provider in the list
1040 //
1041 for (Uint32 i = 0; i < tableValue.providers.size (); i++)
1042 {
|
1043 carolann.graves 1.9 if (tableValue.providers [i].provider.getPath ().identical
|
1044 kumpf 1.1 (provider.getPath ()))
1045 {
|
1046 gs.keenan 1.4 PEG_METHOD_EXIT ();
|
1047 kumpf 1.1 return i;
1048 }
1049 }
1050
|
1051 gs.keenan 1.4 PEG_METHOD_EXIT ();
|
1052 kumpf 1.1 return PEG_NOT_FOUND;
1053 }
1054
1055
|
1056 carolann.graves 1.9 Uint32 SubscriptionTable::classInList
1057 (const CIMName & className,
|
1058 kumpf 1.1 const ProviderClassList & providerClasses) const
1059 {
1060 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE, "SubscriptionTable::classInList");
1061
1062 //
1063 // Look for the class in the list
1064 //
1065 for (Uint32 i = 0; i < providerClasses.classList.size (); i++)
1066 {
1067 if (providerClasses.classList [i].equal (className))
1068 {
|
1069 gs.keenan 1.4 PEG_METHOD_EXIT ();
|
1070 kumpf 1.1 return i;
1071 }
1072 }
1073
|
1074 gs.keenan 1.4 PEG_METHOD_EXIT ();
|
1075 kumpf 1.1 return PEG_NOT_FOUND;
1076 }
1077
|
1078 kumpf 1.2 void SubscriptionTable::clear ()
1079 {
1080 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE, "SubscriptionTable::clear");
1081
1082 {
1083 WriteLock lock (_activeSubscriptionsTableLock);
1084 _activeSubscriptionsTable.clear ();
1085 }
1086 {
1087 WriteLock lock (_subscriptionClassesTableLock);
1088 _subscriptionClassesTable.clear ();
1089 }
1090
1091 PEG_METHOD_EXIT ();
1092 }
1093
|
1094 yi.zhou 1.17 void SubscriptionTable::getMatchingClassNamespaceSubscriptions(
|
1095 yi.zhou 1.16 const CIMName & supportedClass,
1096 const CIMNamespaceName & nameSpace,
|
1097 yi.zhou 1.17 const CIMInstance& provider,
1098 Array<CIMInstance>& matchingSubscriptions,
1099 Array<String>& matchingSubscriptionKeys)
|
1100 yi.zhou 1.16 {
1101 PEG_METHOD_ENTER (TRC_INDICATION_SERVICE,
1102 "SubscriptionTable::getMatchingClassNamespaceSubscriptions");
1103
1104 Array <CIMInstance> subscriptions;
|
1105 yi.zhou 1.17 matchingSubscriptions.clear();
1106 matchingSubscriptionKeys.clear();
|
1107 yi.zhou 1.16
1108 //
1109 // Look up the indicationClass-sourceNamespace pair in the
1110 // Subscription Classes table
1111 //
1112 String subscriptionClassesKey = _generateSubscriptionClassesKey
1113 (supportedClass, nameSpace);
|
1114 kumpf 1.22 SubscriptionClassesTableEntry scTableValue;
1115 if (_lockedLookupSubscriptionClassesEntry(
1116 subscriptionClassesKey, scTableValue))
|
1117 yi.zhou 1.16 {
|
1118 kumpf 1.22 subscriptions = scTableValue.subscriptions;
|
1119 yi.zhou 1.16 for (Uint32 j = 0; j < subscriptions.size (); j++)
1120 {
1121 //
1122 // Check if the provider who generated this indication
1123 // accepted this subscription
1124 //
1125 String activeSubscriptionsKey =
1126 _generateActiveSubscriptionsKey
1127 (subscriptions [j].getPath ());
|
1128 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
1129 if (_lockedLookupActiveSubscriptionsEntry(
1130 activeSubscriptionsKey, asTableValue))
|
1131 yi.zhou 1.16 {
1132 //
1133 // If provider is in list, the subscription is acceptted
1134 //
|
1135 kumpf 1.22 if ((providerInList(provider, asTableValue)) != PEG_NOT_FOUND)
|
1136 yi.zhou 1.16 {
1137 //
1138 // Add current subscription to list
1139 //
|
1140 yi.zhou 1.17 matchingSubscriptions.append(subscriptions[j]);
1141 matchingSubscriptionKeys.append(activeSubscriptionsKey);
|
1142 yi.zhou 1.16 }
1143 }
1144 }
1145 }
1146
|
1147 yi.zhou 1.17 PEGASUS_ASSERT(
1148 matchingSubscriptions.size() == matchingSubscriptionKeys.size());
|
1149 yi.zhou 1.16 PEG_METHOD_EXIT ();
1150 }
1151
|
1152 yi.zhou 1.17 #ifdef PEGASUS_ENABLE_INDICATION_COUNT
1153
1154 void SubscriptionTable::updateMatchedIndicationCounts(
1155 const CIMInstance & providerInstance,
1156 const Array<String>& activeSubscriptionsKeys)
1157 {
1158 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1159 "SubscriptionTable::updateMatchedIndicationCounts");
1160
1161 WriteLock lock(_activeSubscriptionsTableLock);
1162
1163 for (Uint32 i = 0; i < activeSubscriptionsKeys.size(); i++)
1164 {
1165 ActiveSubscriptionsTableEntry* entry = 0;
1166 if (_activeSubscriptionsTable.lookupReference(
1167 activeSubscriptionsKeys[i], entry))
1168 {
1169 Uint32 providerIndex = providerInList(providerInstance, *entry);
1170 if (providerIndex != PEG_NOT_FOUND)
1171 {
1172 entry->providers[providerIndex].
1173 yi.zhou 1.17 matchedIndCountPerSubscription++;
1174 }
1175 }
1176 else
1177 {
1178 // The subscription may have been deleted in the mean time.
1179 // If so, no further update is required.
1180 PEG_TRACE((TRC_INDICATION_SERVICE_INTERNAL, Tracer::LEVEL2,
1181 "Subscription %s not found in ActiveSubscriptionsTable",
1182 (const char *) activeSubscriptionsKeys[i].getCString()));
1183 }
1184 }
1185 PEG_METHOD_EXIT();
1186 }
1187
1188 Array<ActiveSubscriptionsTableEntry>
1189 SubscriptionTable::_getAllActiveSubscriptionEntries()
1190 {
1191 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1192 "SubscriptionTable::_getAllActiveSubscriptionEntries");
1193
1194 yi.zhou 1.17 Array <ActiveSubscriptionsTableEntry> subscriptionsEntries;
1195
1196 //
1197 // Iterate through the ActiveSubscriptions table to get all active
1198 // subscriptions table entries
1199 //
1200
1201 ReadLock lock(_activeSubscriptionsTableLock);
1202
1203 for (ActiveSubscriptionsTable::Iterator i =
1204 _activeSubscriptionsTable.start(); i; i++)
1205 {
1206 subscriptionsEntries.append(i.value());
1207 }
1208
1209 PEG_METHOD_EXIT();
1210 return subscriptionsEntries;
1211 }
1212
1213 Array<CIMInstance>
1214 SubscriptionTable::enumerateSubscriptionIndicationDataInstances()
1215 yi.zhou 1.17 {
1216 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1217 "SubscriptionTable::enumerateSubscriptionIndicationDataInstances");
1218
1219 Array<CIMInstance> instances;
1220
1221 //
1222 // Get all active subscriptions table entries
1223 //
1224 Array<ActiveSubscriptionsTableEntry> activeSubscriptionEntries =
1225 _getAllActiveSubscriptionEntries();
1226
1227 for (Uint32 i = 0; i < activeSubscriptionEntries.size(); i++)
1228 {
1229 //
1230 // Gets filter name and handler name of the subscription
1231 //
1232 CIMInstance subscription = activeSubscriptionEntries[i].subscription;
1233 String sourceNS = subscription.getPath().getNameSpace().getString();
1234
1235 String filterName;
1236 yi.zhou 1.17 String handlerName;
1237 _getFilterAndHandlerNames(subscription, filterName, handlerName);
1238
1239 Array<ProviderClassList> providers =
1240 activeSubscriptionEntries[i].providers;
1241
1242 for (Uint32 j = 0; j < providers.size(); j++)
1243 {
|
1244 yi.zhou 1.18 //
1245 // Gets provider name and provider module name
1246 //
1247 String providerName, providerModuleName;
1248 ProviderIndicationCountTable::getProviderKeys(
1249 providers[j].provider,
1250 providerModuleName,
1251 providerName);
1252
1253 CIMInstance subscriptionIndDataInstance =
1254 _buildSubscriptionIndDataInstance(
1255 filterName,
1256 handlerName,
1257 sourceNS,
1258 providerModuleName,
1259 providerName,
1260 providers[j].matchedIndCountPerSubscription);
1261
1262 instances.append(subscriptionIndDataInstance);
1263 }
1264 }
1265 yi.zhou 1.18
1266 PEG_METHOD_EXIT();
1267 return instances;
1268 }
1269
1270 Array<CIMObjectPath>
1271 SubscriptionTable::enumerateSubscriptionIndicationDataInstanceNames()
1272 {
1273 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1274 "SubscriptionTable::enumerateSubscriptionIndicationDataInstanceNames");
1275
1276 Array<CIMObjectPath> instanceNames;
1277
1278 //
1279 // Get all active subscriptions table entries
1280 //
1281 Array<ActiveSubscriptionsTableEntry> activeSubscriptionEntries =
1282 _getAllActiveSubscriptionEntries();
1283
1284 for (Uint32 i = 0; i < activeSubscriptionEntries.size(); i++)
1285 {
1286 yi.zhou 1.18 //
1287 // Gets filter name and handler name of the subscription
1288 //
1289 CIMInstance subscription = activeSubscriptionEntries[i].subscription;
1290 String sourceNS = subscription.getPath().getNameSpace().getString();
1291
1292 String filterName;
1293 String handlerName;
1294 _getFilterAndHandlerNames(subscription, filterName, handlerName);
|
1295 yi.zhou 1.17
|
1296 yi.zhou 1.18 Array<ProviderClassList> providers =
1297 activeSubscriptionEntries[i].providers;
|
1298 yi.zhou 1.17
|
1299 yi.zhou 1.18 for (Uint32 j = 0; j < providers.size(); j++)
1300 {
|
1301 yi.zhou 1.17 //
|
1302 yi.zhou 1.18 // Gets provider name and provider module name
|
1303 yi.zhou 1.17 //
1304 String providerName, providerModuleName;
1305 ProviderIndicationCountTable::getProviderKeys(
|
1306 yi.zhou 1.18 providers[j].provider,
1307 providerModuleName,
1308 providerName);
1309
1310 CIMObjectPath path = _buildSubscriptionIndDataInstanceName(
1311 filterName,
1312 handlerName,
1313 sourceNS,
|
1314 yi.zhou 1.17 providerModuleName,
1315 providerName);
1316
|
1317 yi.zhou 1.18 instanceNames.append(path);
1318 }
1319 }
|
1320 yi.zhou 1.17
|
1321 yi.zhou 1.18 PEG_METHOD_EXIT();
1322 return instanceNames;
1323 }
1324
1325 CIMInstance SubscriptionTable::getSubscriptionIndicationDataInstance(
1326 const CIMObjectPath& instanceName)
1327 {
1328 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1329 "SubscriptionTable::getSubscriptionIndicationDataInstance");
1330
1331 String filterName;
1332 String handlerName;
1333 String sourceNS;
1334 String specifiedProviderModuleName;
1335 String specifiedProviderName;
1336
1337 //
1338 // Gets handler name, filter name, source namespace, provider module name,
1339 // and provider name from a PG_SubscriptionIndicationData instanceName
1340 //
1341 _getSubscriptionIndicationDataKeys(
1342 yi.zhou 1.18 instanceName,
1343 filterName,
1344 handlerName,
1345 sourceNS,
1346 specifiedProviderModuleName,
1347 specifiedProviderName);
1348
1349 // Builds the PG_Provider object path
1350 CIMObjectPath providerName = _buildProviderPath(
1351 specifiedProviderModuleName, specifiedProviderName);
1352
1353 //
1354 // Builds subscription path by using the specified parameters
1355 //
1356 CIMObjectPath subscriptionPath = _buildSubscriptionPath(
1357 filterName, handlerName, sourceNS);
1358
1359 //
1360 // Look up the subscription in the active subscriptions table
1361 //
|
1362 kumpf 1.22 ActiveSubscriptionsTableEntry asTableValue;
1363 if (getSubscriptionEntry(subscriptionPath, asTableValue))
|
1364 yi.zhou 1.18 {
|
1365 kumpf 1.22 Array<ProviderClassList> providers = asTableValue.providers;
|
1366 yi.zhou 1.18 for (Uint32 i = 0; i < providers.size(); i++)
1367 {
1368 if (providerName.identical(providers[i].provider.getPath()))
1369 {
1370 CIMInstance subIndDataInstance =
1371 _buildSubscriptionIndDataInstance(
1372 filterName,
1373 handlerName,
1374 sourceNS,
1375 specifiedProviderModuleName,
1376 specifiedProviderName,
1377 providers[i].matchedIndCountPerSubscription);
1378
1379 PEG_METHOD_EXIT();
1380 return subIndDataInstance;
1381 }
|
1382 yi.zhou 1.17 }
1383 }
1384
1385 PEG_METHOD_EXIT();
|
1386 yi.zhou 1.18 throw CIMObjectNotFoundException(instanceName.toString());
|
1387 yi.zhou 1.17 }
1388
1389 void SubscriptionTable::_getFilterAndHandlerNames(
1390 const CIMInstance& subscription,
1391 String& filterName,
1392 String& handlerName)
1393 {
1394 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1395 "SubscriptionTable::_getFilterAndHandlerNames");
1396
1397 CIMObjectPath filterPath;
1398 CIMObjectPath handlerPath;
1399
1400 subscription.getProperty(subscription.findProperty(
1401 PEGASUS_PROPERTYNAME_FILTER)).getValue().get(filterPath);
1402 subscription.getProperty(subscription.findProperty(
1403 PEGASUS_PROPERTYNAME_HANDLER)).getValue().get(handlerPath);
1404
1405 //
1406 // Get Filter namespace - if not set in Filter reference property
1407 // value, namespace is the namespace of the subscription
1408 yi.zhou 1.17 //
1409 CIMNamespaceName filterNS = filterPath.getNameSpace();
1410 if (filterNS.isNull())
1411 {
1412 filterNS = subscription.getPath().getNameSpace();
1413 }
1414
1415 //
1416 // Get filter name
1417 //
1418 Array<CIMKeyBinding> filterKeyBindings = filterPath.getKeyBindings();
1419 for (Uint32 i = 0; i < filterKeyBindings.size(); i++)
1420 {
1421 if (filterKeyBindings[i].getName().equal(PEGASUS_PROPERTYNAME_NAME))
1422 {
1423 filterName.append(filterNS.getString());
1424 filterName.append(":");
1425 filterName.append(filterKeyBindings[i].getValue());
1426 break;
1427 }
1428 }
1429 yi.zhou 1.17
1430 //
1431 // Get handler namespace - if not set in handler reference property
1432 // value, namespace is the namespace of the subscription
1433 //
1434 CIMNamespaceName handlerNS = handlerPath.getNameSpace();
1435 if (handlerNS.isNull())
1436 {
1437 handlerNS = subscription.getPath().getNameSpace();
1438 }
1439
1440 //
1441 // Get handler name
1442 //
1443 Array<CIMKeyBinding> handlerKeyBindings = handlerPath.getKeyBindings();
1444 for (Uint32 i = 0; i < handlerKeyBindings.size(); i++)
1445 {
1446 if (handlerKeyBindings[i].getName().equal(PEGASUS_PROPERTYNAME_NAME))
1447 {
1448 handlerName.append(handlerNS.getString());
1449 handlerName.append(":");
1450 yi.zhou 1.17 handlerName.append(handlerPath.getClassName().getString());
1451 handlerName.append(".");
1452 handlerName.append(handlerKeyBindings[i].getValue());
1453 break;
1454 }
1455 }
1456
1457 PEG_METHOD_EXIT();
1458 }
1459
|
1460 yi.zhou 1.18 void SubscriptionTable::_getSubscriptionIndicationDataKeys(
1461 const CIMObjectPath& instanceName,
1462 String& filterName,
1463 String& handlerName,
1464 String& sourceNS,
1465 String& providerModuleName,
1466 String& providerName)
1467 {
1468 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1469 "SubscriptionTable::_getSubscriptionIndicationDataKeys");
1470
1471 Array<CIMKeyBinding> keys = instanceName.getKeyBindings();
1472 for (Uint32 i = 0; i < keys.size(); i++)
1473 {
1474 if (keys[i].getName() == "FilterName")
1475 {
1476 filterName = keys[i].getValue();
1477 }
1478 else if (keys[i].getName() == "HandlerName")
1479 {
1480 handlerName = keys[i].getValue();
1481 yi.zhou 1.18 }
1482 else if (keys[i].getName() == "SourceNamespace")
1483 {
1484 sourceNS = keys[i].getValue();
1485 }
1486 else if (keys[i].getName() == "ProviderModuleName")
1487 {
1488 providerModuleName = keys[i].getValue();
1489 }
1490 else if (keys[i].getName() == "ProviderName")
1491 {
1492 providerName = keys[i].getValue();
1493 }
1494 }
1495
1496 PEG_METHOD_EXIT();
1497 }
1498
1499
1500 CIMObjectPath SubscriptionTable::_buildFilterPath(const String& filterName)
1501 {
1502 yi.zhou 1.18 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1503 "SubscriptionTable::_buildFilterPath");
1504
1505 //
1506 // creates filter object path from input string filterName
1507 // (namespace:filtername)
1508 //
1509 String name;
1510 Uint32 colonIndex = filterName.find(':');
1511
1512 if (colonIndex != PEG_NOT_FOUND)
1513 {
1514 name = filterName.subString(colonIndex + 1);
1515 }
1516
1517 Array<CIMKeyBinding> filterKeys;
1518 filterKeys.append(CIMKeyBinding(
1519 "SystemCreationClassName",
1520 System::getSystemCreationClassName(),
1521 CIMKeyBinding::STRING));
1522 filterKeys.append(CIMKeyBinding(
1523 yi.zhou 1.18 "SystemName",
1524 System::getFullyQualifiedHostName(),
1525 CIMKeyBinding::STRING));
1526 filterKeys.append(CIMKeyBinding(
1527 "CreationClassName",
1528 PEGASUS_CLASSNAME_INDFILTER.getString(),
1529 CIMKeyBinding::STRING));
1530 filterKeys.append(CIMKeyBinding(
1531 "Name",
1532 name,
1533 CIMKeyBinding::STRING));
1534
1535 CIMObjectPath filterPath = CIMObjectPath(
1536 String::EMPTY,
1537 CIMNamespaceName(),
1538 PEGASUS_CLASSNAME_INDFILTER,
1539 filterKeys);
1540
1541 PEG_METHOD_EXIT();
1542 return filterPath;
1543 }
1544 yi.zhou 1.18
1545 CIMObjectPath SubscriptionTable::_buildHandlerPath(const String& handlerName)
1546 {
1547 PEG_METHOD_ENTER(TRC_INDICATION_SERVICE,
1548 "SubscriptionTable::_buildHandlerPath");
1549
1550 //
1551 // creates handler object path from input string handlerName
1552 // (namespace:classname.handlername)
1553 //
1554 String name;
1555 String classname;
1556 Uint32 colonIndex = handlerName.find(':');
1557 Uint32 dotIndex = handlerName.find('.');
1558
1559 if (colonIndex != PEG_NOT_FOUND)
1560 {
1561 if ((dotIndex != PEG_NOT_FOUND) && (dotIndex > colonIndex))
1562 {
1563 classname = handlerName.subString(
1564 colonIndex + 1, dotIndex - 1 - colonIndex);
1565 yi.zhou 1.18 name = handlerName.subString(dotIndex + 1);
1566 }
1567 }
1568
1569 Array<CIMKeyBinding> handlerKeys;
1570 handlerKeys.append(CIMKeyBinding(
1571 "SystemCreationClassName",
1572 System::getSystemCreationClassName(),
1573 CIMKeyBinding::STRING));
1574 handlerKeys.append(CIMKeyBinding(
1575 "SystemName",
1576 System::getFullyQualifiedHostName(),
1577 CIMKeyBinding::STRING));
1578 handlerKeys.append(CIMKeyBinding(
1579 "CreationClassName",
1580 classname,
1581 CIMKeyBinding::STRING));
1582 handlerKeys.append(CIMKeyBinding(
1583 "Name",
1584 name,
1585 CIMKeyBinding::STRING));
1586 yi.zhou 1.18
1587 CIMObjectPath handlerPath = CIMObjectPath(
1588 String::EMPTY,
1589 CIMNamespaceName(),
1590 classname,
1591 handlerKeys);
1592
1593 PEG_METHOD_EXIT();
1594 return handlerPath;
1595 }
1596
1597 CIMObjectPath SubscriptionTable::_buildSubscriptionPath(
1598 const String& filterName,
1599 const String& handlerName,
1600 const String& sourceNS)
1601 {
1602 CIMObjectPath filterPath = _buildFilterPath(filterName);
1603 CIMObjectPath handlerPath = _buildHandlerPath(handlerName);
1604
1605 CIMObjectPath subscriptionPath;
1606 Array<CIMKeyBinding> keyBindings;
1607 yi.zhou 1.18 keyBindings.append(CIMKeyBinding(
1608 PEGASUS_PROPERTYNAME_FILTER,
1609 filterPath.toString(),
1610 CIMKeyBinding::REFERENCE));
1611 keyBindings.append(CIMKeyBinding(
1612 PEGASUS_PROPERTYNAME_HANDLER,
1613 handlerPath.toString(),
1614 CIMKeyBinding::REFERENCE));
1615
1616 subscriptionPath.setClassName(PEGASUS_CLASSNAME_INDSUBSCRIPTION);
1617 subscriptionPath.setNameSpace(sourceNS);
1618 subscriptionPath.setKeyBindings(keyBindings);
1619
1620 return subscriptionPath;
1621 }
1622
1623 CIMInstance SubscriptionTable::_buildSubscriptionIndDataInstance(
1624 const String& filterName,
1625 const String& handlerName,
1626 const String& sourceNS,
1627 const String& providerModuleName,
1628 yi.zhou 1.18 const String& providerName,
1629 Uint32 matchedIndicationCount)
1630 {
1631 CIMInstance subscriptionIndDataInstance(
1632 PEGASUS_CLASSNAME_SUBSCRIPTIONINDDATA);
1633 subscriptionIndDataInstance.addProperty(CIMProperty(
1634 CIMName("FilterName"), filterName));
1635 subscriptionIndDataInstance.addProperty(CIMProperty(
1636 CIMName("HandlerName"), handlerName));
1637 subscriptionIndDataInstance.addProperty(CIMProperty(
1638 CIMName("SourceNamespace"), sourceNS));
1639 subscriptionIndDataInstance.addProperty(CIMProperty(
1640 CIMName("ProviderModuleName"), providerModuleName));
1641 subscriptionIndDataInstance.addProperty(CIMProperty(
1642 CIMName("ProviderName"), providerName));
1643 subscriptionIndDataInstance.addProperty(CIMProperty(
1644 CIMName("MatchedIndicationCount"),
1645 matchedIndicationCount));
1646
1647 CIMObjectPath path = _buildSubscriptionIndDataInstanceName(
1648 filterName,
1649 yi.zhou 1.18 handlerName,
1650 sourceNS,
1651 providerModuleName,
1652 providerName);
1653 subscriptionIndDataInstance.setPath(path);
1654
1655 return subscriptionIndDataInstance;
1656 }
1657
1658 CIMObjectPath SubscriptionTable::_buildSubscriptionIndDataInstanceName(
1659 const String& filterName,
1660 const String& handlerName,
1661 const String& sourceNS,
1662 const String& providerModuleName,
1663 const String& providerName)
1664 {
1665 CIMObjectPath path;
1666 Array<CIMKeyBinding> keyBindings;
1667 keyBindings.append(CIMKeyBinding(
1668 "FilterName",
1669 filterName,
1670 yi.zhou 1.18 CIMKeyBinding::STRING));
1671 keyBindings.append(CIMKeyBinding(
1672 "HandlerName",
1673 handlerName,
1674 CIMKeyBinding::STRING));
1675 keyBindings.append(CIMKeyBinding(
1676 "SourceNamespace",
1677 sourceNS,
1678 CIMKeyBinding::STRING));
1679 keyBindings.append(CIMKeyBinding(
1680 "ProviderModuleName",
1681 providerModuleName,
1682 CIMKeyBinding::STRING));
1683 keyBindings.append(CIMKeyBinding(
1684 "ProviderName",
1685 providerName,
1686 CIMKeyBinding::STRING));
1687
1688 path.setClassName(PEGASUS_CLASSNAME_SUBSCRIPTIONINDDATA);
1689 path.setKeyBindings(keyBindings);
1690
1691 yi.zhou 1.18 return path;
1692 }
1693
1694 CIMObjectPath SubscriptionTable::_buildProviderPath(
1695 const String& providerModuleName,
1696 const String& providerName)
1697 {
1698 CIMObjectPath path;
1699 Array<CIMKeyBinding> keyBindings;
1700 keyBindings.append(CIMKeyBinding(
1701 _PROPERTY_PROVIDERMODULENAME,
1702 providerModuleName,
1703 CIMKeyBinding::STRING));
1704 keyBindings.append(CIMKeyBinding(
1705 PEGASUS_PROPERTYNAME_NAME,
1706 providerName,
1707 CIMKeyBinding::STRING));
1708
1709 path.setClassName(PEGASUS_CLASSNAME_PROVIDER);
1710 path.setKeyBindings(keyBindings);
1711
1712 yi.zhou 1.18 return path;
1713 }
1714
|
1715 yi.zhou 1.17 #endif
1716
|
1717 kumpf 1.1 PEGASUS_NAMESPACE_END
|