void BasicProviderManagerRouter::unloadIdleProviders() { PEG_METHOD_ENTER(TRC_PROVIDERMANAGER, "BasicProviderManagerRouter::unloadIdleProviders"); // // Save pointers to the ProviderManagerContainers so we don't hold the // _providerManagerTableLock while unloading idle providers // Array<ProviderManagerContainer*> pmcs; { ReadLock tableLock(_providerManagerTableLock); for (Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++) { pmcs.append(_providerManagerTable[i]); } } // // Unload idle providers in each of the active ProviderManagers // _providerManagerTableLock while unloading idle providers // for (Uint32 i = 0; i < pmcs.size(); i++) { pmcs[i]->getProviderManager()->unloadIdleProviders(); } PEG_METHOD_EXIT(); }
bool FMallocBinned::validateHeap() { #ifdef USE_COARSE_GRAIN_LOCKS FScopeLock ScopedLock(&AccessGuard); #endif for( int32_t i = 0; i < PoolCount; i++ ) { FPoolTable* table = &poolTable[i]; #ifdef USE_FINE_GRAIN_LOCKS std::lock_guard<std::mutex> tableLock(table->mutex); #endif for( FPoolInfo** poolPtr = &table->firstPool; *poolPtr; poolPtr = &(*poolPtr)->next ) { FPoolInfo* pool = *poolPtr; FAssert(pool->prevLink == poolPtr); FAssert(!!pool->firstMem); for( FFreeMem* free = pool->firstMem; free; free = free->next ) { FAssert(free->numFreeBlocks > 0); } } for( FPoolInfo** poolPtr = &table->exhaustedPool; *poolPtr; poolPtr = &(*poolPtr)->next ) { FPoolInfo* pool = *poolPtr; FAssert(pool->prevLink == poolPtr); FAssert(!pool->firstMem); } } return true; }
Boolean BasicProviderManagerRouter::hasActiveProviders() { PEG_METHOD_ENTER(TRC_PROVIDERMANAGER, "BasicProviderManagerRouter::hasActiveProviders"); ReadLock tableLock(_providerManagerTableLock); for (Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++) { ProviderManagerContainer* pmc = _providerManagerTable[i]; if (pmc->getProviderManager()->hasActiveProviders()) { PEG_METHOD_EXIT(); return true; } } PEG_METHOD_EXIT(); return false; }
void* FMallocBinned::malloc(size_t size, uint32_t alignment) { #ifdef USE_COARSE_GRAIN_LOCKS FScopeLock ScopedLock(&AccessGuard); #endif flushPendingFrees(); // Handle DEFAULT_ALIGNMENT for binned allocator. if (alignment == DefaultAlignment) { alignment = default_binned_allocator_alignment; } FAssert(alignment <= pageSize); alignment = std::max<uint32_t>(alignment, default_binned_allocator_alignment); size = std::max<size_t>(alignment, FAlign(size, alignment)); MEM_TIME(MemTime -= FPlatformTime::Seconds()); STAT(currentAllocs++); STAT(totalAllocs++); FFreeMem* free = nullptr; if( size < binnedSizeLimit ) { // Allocate from pool. FPoolTable* table = memSizeToPoolTable[size]; #ifdef USE_FINE_GRAIN_LOCKS std::lock_guard<std::mutex> tableLock(table->mutex); #endif FAssert(size <= table->blockSize); trackStats(table, (uint32_t)size); FPoolInfo* pool = table->firstPool; if( !pool ) { pool = allocatePoolMemory(table, binned_alloc_pool_size/*PageSize*/, size); } free = allocateBlockFromPool(table, pool); } else if ( ((size >= binnedSizeLimit && size <= pagePoolTable[0].blockSize) || (size > pageSize && size <= pagePoolTable[1].blockSize)) && alignment == default_binned_allocator_alignment ) { // Bucket in a pool of 3*PageSize or 6*PageSize uint32_t binType = size < pageSize ? 0 : 1; uint32_t pageCount = 3 * binType + 3; FPoolTable* table = &pagePoolTable[binType]; #ifdef USE_FINE_GRAIN_LOCKS std::lock_guard<std::mutex> tableLock(table->mutex); #endif FAssert(size <= table->blockSize); trackStats(table, (uint32_t)size); FPoolInfo* pool = table->firstPool; if( !pool ) { pool = allocatePoolMemory(table, pageCount * pageSize, binnedSizeLimit + binType); } free = allocateBlockFromPool(table, pool); } else { // Use OS for large allocations. UIntPtr_t alignedSize = FAlign(size, pageSize); size_t actualPoolSize; //TODO: use this to reduce waste? free = (FFreeMem*)osAlloc(alignedSize, actualPoolSize); if( !free ) { outOfMemory(alignedSize); } FAssert(!((size_t)free & (pageSize - 1))); // Create indirect. FPoolInfo* pool; { #ifdef USE_FINE_GRAIN_LOCKS std::lock_guard<std::mutex> poolInfoLock(accessGuard); #endif pool = getPoolInfo((UIntPtr_t)free); } pool->setAllocationSizes((uint32_t)size, alignedSize, (uint32_t)binnedOSTableIndex, (uint32_t)binnedOSTableIndex); STAT(osPeak = std::max(osPeak, osCurrent += alignedSize)); STAT(usedPeak = std::max(usedPeak, usedCurrent += size)); STAT(wastePeak = std::max(wastePeak, wasteCurrent += alignedSize - size)); } MEM_TIME(MemTime += FPlatformTime::Seconds()); return free; }
// ATTN: May need to add interfaceVersion parameter to further constrain lookup ProviderManager* BasicProviderManagerRouter::_getProviderManager( const String& interfaceType, const String& providerModuleName, const String& providerManagerPath) { PEG_METHOD_ENTER(TRC_PROVIDERMANAGER, "BasicProviderManagerRouter::_getProviderManager"); // // Search for this InterfaceType in the table of loaded ProviderManagers // { ReadLock tableLock(_providerManagerTableLock); ProviderManager* pm = _lookupProviderManager(interfaceType); if (pm) { PEG_METHOD_EXIT(); return pm; } } // // Load the ProviderManager for this InterfaceType and add it to the table // { WriteLock tableLock(_providerManagerTableLock); ProviderManager* pm = _lookupProviderManager(interfaceType); if (pm) { PEG_METHOD_EXIT(); return pm; } // The DefaultProviderManager is now statically linked rather than // dynamically loaded. This code is no longer used but remains for // reference purposes. #if defined(PEGASUS_ENABLE_DEFAULT_PROVIDER_MANAGER) if (interfaceType == "C++Default" && _createDefaultProviderManagerCallback) { pm = (*_createDefaultProviderManagerCallback)(); ProviderManagerContainer* pmc = new ProviderManagerContainer( "C++Default", _indicationCallback, _responseChunkCallback, _subscriptionInitComplete, pm); _providerManagerTable.append(pmc); PEG_METHOD_EXIT(); return pmc->getProviderManager(); } #endif ProviderManagerContainer* pmc = new ProviderManagerContainer( providerManagerPath, interfaceType, interfaceType, _indicationCallback, _responseChunkCallback, _subscriptionInitComplete); _providerManagerTable.append(pmc); PEG_METHOD_EXIT(); return pmc->getProviderManager(); } }
Message* BasicProviderManagerRouter::processMessage(Message * message) { PEG_METHOD_ENTER(TRC_PROVIDERMANAGER, "BasicProviderManagerRouter::processMessage"); CIMRequestMessage* request = dynamic_cast<CIMRequestMessage *>(message); PEGASUS_ASSERT(request != 0); Message* response = 0; Boolean remoteNameSpaceRequest=false; // // Retrieve the ProviderManager routing information // CIMInstance providerModule; if ((dynamic_cast<CIMOperationRequestMessage*>(request) != 0) || (request->getType() == CIM_EXPORT_INDICATION_REQUEST_MESSAGE)) { // Provider information is in OperationContext ProviderIdContainer pidc = (ProviderIdContainer) request->operationContext.get(ProviderIdContainer::NAME); providerModule = pidc.getModule(); remoteNameSpaceRequest=pidc.isRemoteNameSpace(); } else if (dynamic_cast<CIMIndicationRequestMessage*>(request) != 0) { // Provider information is in CIMIndicationRequestMessage CIMIndicationRequestMessage* indReq = dynamic_cast<CIMIndicationRequestMessage*>(request); ProviderIdContainer pidc = indReq->operationContext.get(ProviderIdContainer::NAME); providerModule = pidc.getModule(); } else if (request->getType() == CIM_ENABLE_MODULE_REQUEST_MESSAGE) { // Provider information is in CIMEnableModuleRequestMessage CIMEnableModuleRequestMessage* emReq = dynamic_cast<CIMEnableModuleRequestMessage*>(request); providerModule = emReq->providerModule; } else if (request->getType() == CIM_DISABLE_MODULE_REQUEST_MESSAGE) { // Provider information is in CIMDisableModuleRequestMessage CIMDisableModuleRequestMessage* dmReq = dynamic_cast<CIMDisableModuleRequestMessage*>(request); providerModule = dmReq->providerModule; } else if ((request->getType() == CIM_STOP_ALL_PROVIDERS_REQUEST_MESSAGE) || (request->getType() == CIM_SUBSCRIPTION_INIT_COMPLETE_REQUEST_MESSAGE) || (request->getType() == CIM_INDICATION_SERVICE_DISABLED_REQUEST_MESSAGE) || (request->getType() == CIM_NOTIFY_CONFIG_CHANGE_REQUEST_MESSAGE)) { // This operation is not provider-specific } else { // Error: Unrecognized message type. PEGASUS_ASSERT(0); CIMResponseMessage* resp = request->buildResponse(); resp->cimException = PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED, "Unknown message type."); response = resp; } // // Forward the request to the appropriate ProviderManager(s) // if ((request->getType() == CIM_STOP_ALL_PROVIDERS_REQUEST_MESSAGE) || (request->getType() == CIM_SUBSCRIPTION_INIT_COMPLETE_REQUEST_MESSAGE) || (request->getType() == CIM_INDICATION_SERVICE_DISABLED_REQUEST_MESSAGE)) { if (request->getType() == CIM_INDICATION_SERVICE_DISABLED_REQUEST_MESSAGE) { _subscriptionInitComplete = false; } else { _subscriptionInitComplete = true; } // Send CIMStopAllProvidersRequestMessage or // CIMIndicationServiceDisabledRequestMessage or // CIMSubscriptionInitCompleteRequestMessage to all ProviderManagers ReadLock tableLock(_providerManagerTableLock); for (Uint32 i = 0, n = _providerManagerTable.size(); i < n; i++) { ProviderManagerContainer* pmc=_providerManagerTable[i]; Message* resp = pmc->getProviderManager()->processMessage(request); delete resp; } response = request->buildResponse(); } else if (request->getType() == CIM_NOTIFY_CONFIG_CHANGE_REQUEST_MESSAGE) { // Do not need to forward this request to in-process provider // managers response = request->buildResponse(); } else { // Retrieve the provider interface type String interfaceType; CIMValue itValue = providerModule.getProperty( providerModule.findProperty("InterfaceType")).getValue(); itValue.get(interfaceType); // Get ProviderModule name. String providerModuleName; CIMValue nameValue = providerModule.getProperty( providerModule.findProperty(PEGASUS_PROPERTYNAME_NAME)).getValue(); nameValue.get(providerModuleName); // Get providerManager path String provMgrPath; if (request->operationContext.contains(ProviderIdContainer::NAME)) { ProviderIdContainer pidc = (ProviderIdContainer) request->operationContext.get(ProviderIdContainer::NAME); provMgrPath = pidc.getProvMgrPath(); } ProviderManager* pm = 0; Boolean gotError = false; try { // Look up the appropriate ProviderManager by InterfaceType pm = _getProviderManager(interfaceType, providerModuleName, provMgrPath); } catch (const CIMException& e) { // This is not an error incase of CIMEnableModuleRequestMessage or // CIMDisableModuleRequestMessage. This means there is no provider // to enable or disable. if (request->getType() == CIM_ENABLE_MODULE_REQUEST_MESSAGE) { CIMEnableModuleResponseMessage* emResponse = dynamic_cast<CIMEnableModuleResponseMessage*>( request->buildResponse()); emResponse->operationalStatus.append( CIM_MSE_OPSTATUS_VALUE_OK); response = emResponse; } else if (request->getType() == CIM_DISABLE_MODULE_REQUEST_MESSAGE) { CIMDisableModuleResponseMessage* dmResponse = dynamic_cast<CIMDisableModuleResponseMessage*>( request->buildResponse()); dmResponse->operationalStatus.append( CIM_MSE_OPSTATUS_VALUE_STOPPED); response = dmResponse; } else { CIMResponseMessage *cimResponse = request->buildResponse(); cimResponse->cimException = e; response = cimResponse; } gotError = true; } if (!gotError && remoteNameSpaceRequest && !pm->supportsRemoteNameSpaces()) { CIMResponseMessage* resp = request->buildResponse(); resp->cimException = PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED, "Remote Namespace operations not supported for interface type " + interfaceType); response = resp; gotError = true; } if (!gotError) { response = pm->processMessage(request); } } PEG_METHOD_EXIT(); return response; }
// ATTN: May need to add interfaceVersion parameter to further constrain lookup ProviderManager* BasicProviderManagerRouter::_getProviderManager( const String& interfaceType, const String& providerManagerPath, Boolean loadProviderManager) { PEG_METHOD_ENTER(TRC_PROVIDERMANAGER, "BasicProviderManagerRouter::_getProviderManager"); // // Search for this InterfaceType in the table of loaded ProviderManagers // { ReadLock tableLock(_providerManagerTableLock); ProviderManager* pm = _lookupProviderManager(interfaceType); if (pm) { PEG_TRACE((TRC_PROVIDERMANAGER, Tracer::LEVEL4, "Provider Manager for interfaceType '%s' already loaded.", (const char*)interfaceType.getCString())); PEG_METHOD_EXIT(); return pm; } } // // If requested, do not load the ProviderManger. // if (!loadProviderManager) { PEG_TRACE((TRC_PROVIDERMANAGER, Tracer::LEVEL4, "Requested not to load the Provider Manager " "for interfaceType '%s'.", (const char*)interfaceType.getCString())); PEG_METHOD_EXIT(); return 0; } // // Load the ProviderManager for this InterfaceType and add it to the table // { WriteLock tableLock(_providerManagerTableLock); ProviderManager* pm = _lookupProviderManager(interfaceType); if (pm) { PEG_TRACE((TRC_PROVIDERMANAGER, Tracer::LEVEL4, "Provider Manager for interfaceType '%s' already loaded.", (const char*)interfaceType.getCString())); PEG_METHOD_EXIT(); return pm; } // The DefaultProviderManager is now statically linked rather than // dynamically loaded. This code is no longer used but remains for // reference purposes. #if defined(PEGASUS_ENABLE_DEFAULT_PROVIDER_MANAGER) if (interfaceType == "C++Default" && _createDefaultProviderManagerCallback) { pm = (*_createDefaultProviderManagerCallback)(); ProviderManagerContainer* pmc = new ProviderManagerContainer( "C++Default", _indicationCallback, _responseChunkCallback, _subscriptionInitComplete, pm); _providerManagerTable.append(pmc); PEG_METHOD_EXIT(); return pmc->getProviderManager(); } #endif PEG_TRACE((TRC_PROVIDERMANAGER, Tracer::LEVEL4, "Crating new Provider Manager for interfaceType '%s', " "providerManagerPath '%s'.", (const char*)interfaceType.getCString(), (const char*)providerManagerPath.getCString())); ProviderManagerContainer* pmc = new ProviderManagerContainer( providerManagerPath, interfaceType, interfaceType, _indicationCallback, _responseChunkCallback, _subscriptionInitComplete); _providerManagerTable.append(pmc); PEG_METHOD_EXIT(); return pmc->getProviderManager(); } }