kernel/eka/drivers/resourceman/resourcecontrol_extended.cpp
changeset 31 56f325a607ea
parent 0 a41df078684a
child 244 a77889bee936
equal deleted inserted replaced
15:4122176ea935 31:56f325a607ea
    42 			return KErrNoMemory;
    42 			return KErrNoMemory;
    43 		for(TUint count = 0;count<(TUint)(allocCount);count++)
    43 		for(TUint count = 0;count<(TUint)(allocCount);count++)
    44 			LIST_PUSH(iResourceLevelPool, &pCL[count], iNextInList);
    44 			LIST_PUSH(iResourceLevelPool, &pCL[count], iNextInList);
    45 		iResourceLevelPoolCount= (TUint16)(iResourceLevelPoolCount + (iStaticResDependencyCount / 2));
    45 		iResourceLevelPoolCount= (TUint16)(iResourceLevelPoolCount + (iStaticResDependencyCount / 2));
    46 #ifdef PRM_INSTRUMENTATION_MACRO
    46 #ifdef PRM_INSTRUMENTATION_MACRO
    47 		TUint size = allocCount * 4;
    47 		TUint size = allocCount * sizeof(SPowerResourceClientLevel);
    48 		PRM_MEMORY_USAGE_TRACE
    48 		PRM_MEMORY_USAGE_TRACE
    49 #endif
    49 #endif
    50 		}
    50 		}
    51 	return KErrNone;
    51 	return KErrNone;
    52 	}
    52 	}
   298 		aPDRes->Lock();
   298 		aPDRes->Lock();
   299 		//Increment dynamic resource count in client
   299 		//Increment dynamic resource count in client
   300 		aClientPtr->iDynamicResCount++;
   300 		aClientPtr->iDynamicResCount++;
   301 		}
   301 		}
   302 	__KTRACE_OPT(KRESMANAGER, Kern::Printf("<DExtendedResourceController::RegisterDynamicResource, resource ID = 0x%x", 
   302 	__KTRACE_OPT(KRESMANAGER, Kern::Printf("<DExtendedResourceController::RegisterDynamicResource, resource ID = 0x%x", 
   303 		                                                                                  aDynamicResourceId));
   303 		                                                                                  *aDynamicResourceId));
   304 #ifdef PRM_INSTRUMENTATION_MACRO
   304 #ifdef PRM_INSTRUMENTATION_MACRO
   305 	PRM_REGISTER_DYNAMIC_RESOURCE_TRACE
   305 	PRM_REGISTER_DYNAMIC_RESOURCE_TRACE
   306 #endif
   306 #endif
   307 	return r;
   307 	return r;
   308 	}
   308 	}
   499 Default implementation, PSL re-implements this if features supported.
   499 Default implementation, PSL re-implements this if features supported.
   500 */
   500 */
   501 TInt DPowerResourceController::DoRegisterStaticResourcesDependency(DStaticPowerResourceD**& aStaticResourceDArray, 
   501 TInt DPowerResourceController::DoRegisterStaticResourcesDependency(DStaticPowerResourceD**& aStaticResourceDArray, 
   502 																    TUint16& aStaticResourceDCount)
   502 																    TUint16& aStaticResourceDCount)
   503 	{
   503 	{
   504 	__KTRACE_OPT(KRESMANAGER, Kern::Printf("DExtendedResourceController::DoRegisterStaticResourcesDependency default \
   504 	__KTRACE_OPT(KRESMANAGER, Kern::Printf("DExtendedResourceController::DoRegisterStaticResourcesDependency default implementation"));
   505 		                                                               implementation"));
       
   506 	aStaticResourceDArray = NULL;
   505 	aStaticResourceDArray = NULL;
   507 	aStaticResourceDCount = 0;
   506 	aStaticResourceDCount = 0;
   508 	return KErrNone;
   507 	return KErrNone;
   509 	}
   508 	}
   510 
   509 
   921 This propagates the change to all of its dependents.
   920 This propagates the change to all of its dependents.
   922 This function takes Originator name and id as parameter as this needs to be passed for custom sense function.
   921 This function takes Originator name and id as parameter as this needs to be passed for custom sense function.
   923 */
   922 */
   924 TInt DStaticPowerResourceD::HandleChangePropagation(TPowerRequest aRequest, TPropagation aProp, TUint aOriginatorId, const TDesC8& aOriginatorName)
   923 TInt DStaticPowerResourceD::HandleChangePropagation(TPowerRequest aRequest, TPropagation aProp, TUint aOriginatorId, const TDesC8& aOriginatorName)
   925 	{
   924 	{
       
   925 	TInt result = KErrNone;
       
   926 	result = PowerResourceController->HandleResourceChange(aRequest, aProp, aOriginatorId, aOriginatorName, this);
       
   927 	return result;
       
   928 	}
       
   929 //Function to change the resource state of dependency resource. 
       
   930 TInt DPowerResourceController::HandleResourceChange(TPowerRequest &aRequest, TPropagation aProp, TUint aOriginatorId, 
       
   931 													const TDesC8& aOriginatorName, DStaticPowerResourceD* aResource)
       
   932 	{
   926 	static TUint16 clientLevelCount = 0;
   933 	static TUint16 clientLevelCount = 0;
   927 	DStaticPowerResourceD* pDR = (DStaticPowerResourceD*)aRequest.Resource();
   934 	DStaticPowerResourceD* pDR = (DStaticPowerResourceD*)aRequest.Resource();
       
   935 	DStaticPowerResourceD* pDepRes = NULL;
       
   936 	SNode* dependencyList = NULL;
       
   937 	TPowerRequest depRequest;
   928 	TInt result = KErrNone;
   938 	TInt result = KErrNone;
   929 	TInt resState;
   939 	TInt resState;
   930 	TPowerRequest depRequest;
       
   931 	depRequest.ReqType() = TPowerRequest::EChange;
   940 	depRequest.ReqType() = TPowerRequest::EChange;
   932 	depRequest.ResourceCb() = NULL;
   941 	depRequest.ResourceCb() = NULL;
   933 	depRequest.ReturnCode() = KErrNone;
   942 	depRequest.ReturnCode() = KErrNone;
   934 	depRequest.RequiresChange() = EFalse;
   943 	depRequest.RequiresChange() = EFalse;
   935 	DStaticPowerResourceD* pDepRes = NULL;
   944 
   936 	TBool traceEnabled = EFalse;
   945 	if(pDR->iResourceId & KIdMaskDynamic)
       
   946 		dependencyList = ((DDynamicPowerResourceD*)pDR)->iDependencyList;
       
   947 	else
       
   948 		dependencyList = pDR->iDependencyList;
       
   949 	switch(aProp)																									
       
   950 		{																											
       
   951 		case EChangeStart:																							
       
   952 			{
       
   953 			if(!dependencyList) /*No dependents so change state of the resource*/
       
   954 				{																									
       
   955 				aRequest.ReturnCode() = pDR->DoRequest(aRequest);													
       
   956 				if(aRequest.ReturnCode() == KErrNone)																
       
   957 					{																								
       
   958 					aResource->iCachedLevel = aRequest.Level();																
       
   959 					aResource->iLevelOwnerId = aRequest.ClientId();															
       
   960 					if(aResource->iIdleListEntry)																				
       
   961 						{																							
       
   962 						aResource->iIdleListEntry->iCurrentLevel = aRequest.Level();											
       
   963 						aResource->iIdleListEntry->iLevelOwnerId = aRequest.ClientId();										
       
   964 						}			
       
   965 					CompleteNotifications(aRequest.ClientId(), pDR,									
       
   966 							aRequest.Level(), aRequest.ReturnCode(), aRequest.ClientId());							
       
   967 					}																								
       
   968 					break;																		
       
   969 				}					
       
   970 			depRequest.ResourceId() = aRequest.ResourceId();														
       
   971 			depRequest.ClientId() = aRequest.ResourceId();															
       
   972 			depRequest.Level() = aRequest.Level();																	
       
   973 			depRequest.Resource() = pDR;
       
   974 			result = pDR->HandleChangePropagation(depRequest, ECheckChangeAllowed, aOriginatorId, aOriginatorName);	
       
   975 			if(result != KErrNone)																					
       
   976 				return result;																						
       
   977 			/*Adjust resource client level*/																		
       
   978 			if(clientLevelCount)																					
       
   979 				{					
       
   980 				result = ReserveClientLevelPoolCount(clientLevelCount);								
       
   981 				if(result != KErrNone)																				
       
   982 					return result;																					
       
   983 				}																									
       
   984 			/*Resource change of dependents */																		
       
   985 			pDR->HandleChangePropagation(aRequest, ERequestStateChange, aOriginatorId, aOriginatorName);				
       
   986 			/*Notification to dependents */																			
       
   987 			pDR->HandleChangePropagation(aRequest, EIssueNotifications, aOriginatorId, aOriginatorName);				
       
   988 			break;																									
       
   989 			}																										
       
   990 		case ECheckChangeAllowed:																					
       
   991 			{																										
       
   992 			TChangePropagationStatus status;																		
       
   993 			for(SNode* depNode = dependencyList; depNode != NULL; depNode = depNode->iNext)					
       
   994 				{																									
       
   995 				pDepRes = depNode->iResource;													
       
   996 				if((aRequest.ClientId() & KIdMaskResourceWithDependencies) &&										
       
   997 						(pDepRes->iResourceId == (TUint)aRequest.ClientId()))										
       
   998 					continue;	
       
   999 				/*Resource need not change if it is already in that state, so continue with							
       
  1000 						another dependent state.*/																	
       
  1001 				if(pDepRes->iResourceId & KIdMaskDynamic)															
       
  1002 					status = ((DDynamicPowerResourceD*)pDepRes)->TranslateDependentState(aRequest.ResourceId(),		
       
  1003 																				aRequest.Level(), resState);		
       
  1004 				else																								
       
  1005 					status = ((DStaticPowerResourceD*)pDepRes)->TranslateDependentState(aRequest.ResourceId(),		
       
  1006 																					aRequest.Level(), resState);	
       
  1007 				if((status == ENoChange) || (pDepRes->iCachedLevel == resState))									
       
  1008 					{																								
       
  1009 					depNode->iRequiresChange = EFalse;																
       
  1010 					continue;																						
       
  1011 					}																								
       
  1012 				if(status == EChangeNotAccepted)																	
       
  1013 					return KErrPermissionDenied;	
       
  1014 				depRequest.ResourceId() = pDepRes->iResourceId;														
       
  1015 				depRequest.ClientId() = aRequest.ResourceId(); /*ID of the dependent resource */					
       
  1016 				depRequest.Level() = resState;																		
       
  1017 				depRequest.Resource() = pDepRes;		
       
  1018 				/*Check resource client list and resource list to see whether change is allowed.*/					
       
  1019 				if(pDepRes->Sense() == DStaticPowerResource::ECustom)												
       
  1020 					{																								
       
  1021 					/*Call custom function to check whether change is allowed.*/									
       
  1022 					if(pDepRes->iResourceId & KIdMaskDynamic)														
       
  1023 						depRequest.RequiresChange() = ((DDynamicPowerResourceD*)pDepRes)->iDepCustomFunction(depRequest.ClientId(),	
       
  1024 							aOriginatorName, depRequest.ResourceId(), EClientRequestLevel, depRequest.Level(), (TAny*)&pDepRes->iClientList,		
       
  1025 									(TAny*)&((DDynamicPowerResourceD*)pDepRes)->iResourceClientList, NULL);				
       
  1026 					else																							
       
  1027 						depRequest.RequiresChange() = ((DStaticPowerResourceD*)pDepRes)->iDepCustomFunction(depRequest.ClientId(),		
       
  1028 							aOriginatorName, depRequest.ResourceId(), EClientRequestLevel, depRequest.Level(), (TAny*)&pDepRes->iClientList,		
       
  1029 									(TAny*)&((DStaticPowerResourceD*)pDepRes)->iResourceClientList, NULL);				
       
  1030 					if(!depRequest.RequiresChange())																
       
  1031 						return KErrPermissionDenied;																
       
  1032 					}						
       
  1033 				SPowerResourceClientLevel*pN=NULL;																	
       
  1034 				for(SDblQueLink* pNL=pDepRes->iClientList.First();pNL!=&pDepRes->iClientList.iA; pNL=pNL->iNext)	
       
  1035 					{																								
       
  1036 					pN = (SPowerResourceClientLevel*)pNL;															
       
  1037 					if(pDepRes->Sense() == DStaticPowerResource::EPositive)											
       
  1038 						{																							
       
  1039 						if(pN->iLevel > depRequest.Level())															
       
  1040 							return KErrPermissionDenied;															
       
  1041 						}																							
       
  1042 					else if(pDepRes->Sense() == DStaticPowerResource::ENegative)									
       
  1043 						{																							
       
  1044 						if(pN->iLevel < depRequest.Level())															
       
  1045 							return KErrPermissionDenied;															
       
  1046 						}																							
       
  1047 					}																								
       
  1048 				/*check through the resource client level */														
       
  1049 				SPowerResourceClientLevel*pCL = NULL;																
       
  1050 				if(pDepRes->iResourceId & KIdMaskDynamic)															
       
  1051 					pCL = ((DDynamicPowerResourceD*)pDepRes)->iResourceClientList;									
       
  1052 				else																								
       
  1053 					pCL = ((DStaticPowerResourceD*)pDepRes)->iResourceClientList;									
       
  1054 				for(; pCL != NULL; pCL = pCL->iNextInList)															
       
  1055 					{																								
       
  1056 					if(pCL->iClientId == pDR->iResourceId)															
       
  1057 						break;																						
       
  1058 					}																								
       
  1059 				if(!pCL)																							
       
  1060 					clientLevelCount++;																				
       
  1061 				/*check dependent resource client list & resource list to see whether change is allowed */			
       
  1062 				if(pDepRes->iResourceId & KIdMaskDynamic)															
       
  1063 					result = ((DDynamicPowerResourceD*)pDepRes)->HandleChangePropagation(depRequest,				
       
  1064 																ECheckChangeAllowed, aOriginatorId, aOriginatorName);	
       
  1065 				else																								
       
  1066 					result = ((DStaticPowerResourceD*)pDepRes)->HandleChangePropagation(depRequest,					
       
  1067 											ECheckChangeAllowed, aOriginatorId, aOriginatorName);						
       
  1068 				if(result != KErrNone)																				
       
  1069 					return result;																					
       
  1070 				depNode->iPropagatedLevel = resState;																
       
  1071 				depNode->iRequiresChange = ETrue;																	
       
  1072 				}																									
       
  1073 			break;																									
       
  1074 			}																										
       
  1075 		case ERequestStateChange:																					
       
  1076 			{																										
       
  1077 			SPowerResourceClientLevel* pCL = NULL;																	
       
  1078 			for(SNode* depNode = dependencyList; depNode != NULL; depNode = depNode->iNext)					
       
  1079 				{																									
       
  1080 				pDepRes = depNode->iResource;													
       
  1081 				if((!depNode->iRequiresChange) || (pDepRes->iResourceId == (TUint)aRequest.ClientId()))				
       
  1082 					continue;																						
       
  1083 				depRequest.ResourceId() = pDepRes->iResourceId;														
       
  1084 				depRequest.ClientId() = aRequest.ResourceId();														
       
  1085 				depRequest.Level() = depNode->iPropagatedLevel;														
       
  1086 				depRequest.Resource() = pDepRes;									
       
  1087 				if(pDepRes->iResourceId & KIdMaskDynamic)															
       
  1088 					((DDynamicPowerResourceD*)pDepRes)->HandleChangePropagation(depRequest, ERequestStateChange,	
       
  1089 																					aOriginatorId, aOriginatorName);	
       
  1090 				else																								
       
  1091 					((DStaticPowerResourceD*)pDepRes)->HandleChangePropagation(depRequest, ERequestStateChange,		
       
  1092 																					aOriginatorId, aOriginatorName);	
       
  1093 				/*Update level if resource client level is already present for this resource.*/						
       
  1094 				if(pDepRes->iResourceId & KIdMaskDynamic)															
       
  1095 					pCL = ((DDynamicPowerResourceD*)pDepRes)->iResourceClientList;									
       
  1096 				else																								
       
  1097 					pCL = ((DStaticPowerResourceD*)pDepRes)->iResourceClientList;									
       
  1098 				for(; pCL != NULL; pCL = pCL->iNextInList)															
       
  1099 					{																								
       
  1100 					if(pCL->iClientId == pDR->iResourceId)															
       
  1101 						{																							
       
  1102 						pCL->iLevel = depNode->iPropagatedLevel;													
       
  1103 						break;																						
       
  1104 						}																							
       
  1105 					}																								
       
  1106 				if(!pCL) /*Create a new resource client level*/														
       
  1107 					{																								
       
  1108 					RemoveClientLevelFromPool(pCL);													
       
  1109 					pCL->iClientId = pDR->iResourceId;																
       
  1110 					pCL->iResourceId = pDepRes->iResourceId;														
       
  1111 					pCL->iLevel = depNode->iPropagatedLevel;														
       
  1112 					if(pDepRes->iResourceId & KIdMaskDynamic)														
       
  1113 						{																							
       
  1114 						LIST_PUSH(((DDynamicPowerResourceD*)pDepRes)->iResourceClientList, pCL, iNextInList);		
       
  1115 						}																							
       
  1116 					else																							
       
  1117 						{																							
       
  1118 						LIST_PUSH(((DStaticPowerResourceD*)pDepRes)->iResourceClientList, pCL, iNextInList);		
       
  1119 						}																							
       
  1120 					clientLevelCount--;																				
       
  1121 					}																								
       
  1122 				}	
       
  1123 #ifdef PRM_INSTRUMENTATION_MACRO			
       
  1124 			if(aRequest.ClientId() & KIdMaskResourceWithDependencies)								
       
  1125 				{																									
       
  1126 				SPowerResourceClient res;																			
       
  1127 				SPowerResourceClient* pC = &res;																	
       
  1128 				pC->iClientId = aRequest.ClientId();																
       
  1129 				pC->iName = &KParentResource;																		
       
  1130 				DStaticPowerResource*pR = (DStaticPowerResource*)pDR;												
       
  1131 				TUint aResourceId = pDR->iResourceId;																
       
  1132 				TInt aNewState = aRequest.Level();																	
       
  1133 				PRM_CLIENT_CHANGE_STATE_START_TRACE																	
       
  1134 				}																									
       
  1135 #endif
       
  1136 				aResource->DoRequest(aRequest);																				
   937 #ifdef PRM_INSTRUMENTATION_MACRO
  1137 #ifdef PRM_INSTRUMENTATION_MACRO
   938 	traceEnabled = ETrue;
  1138 			if(aRequest.ClientId() & KIdMaskResourceWithDependencies)								
   939 #endif
  1139 				{																									
   940 	HANDLE_CHANGE_PROPAGATION(PowerResourceController, DStaticPowerResourceD*, traceEnabled, aOriginatorId, aOriginatorName)
  1140 				SPowerResourceClient res;																			
   941 	}
  1141 				SPowerResourceClient* pC = &res;																	
   942 
  1142 				pC->iClientId = aRequest.ClientId();																
   943 
  1143 				pC->iName = &KParentResource;																		
       
  1144 				DStaticPowerResource*pR = (DStaticPowerResource*)pDR;												
       
  1145 				TUint aResourceId = pDR->iResourceId;																
       
  1146 				TInt aNewState = aRequest.Level();																	
       
  1147 				TInt r = KErrNone;																					
       
  1148 				PRM_CLIENT_CHANGE_STATE_END_TRACE																	
       
  1149 				}													
       
  1150 #endif												
       
  1151 			pDR->iCachedLevel = aRequest.Level();																	
       
  1152 			pDR->iLevelOwnerId = aRequest.ClientId();																
       
  1153 			if(pDR->iIdleListEntry)																					
       
  1154 				{																									
       
  1155 				pDR->iIdleListEntry->iCurrentLevel = aRequest.Level();												
       
  1156 				pDR->iIdleListEntry->iLevelOwnerId = aRequest.ClientId();											
       
  1157 				}									
       
  1158 			break;																									
       
  1159 			}																										
       
  1160 		case EIssueNotifications:																					
       
  1161 			{																										
       
  1162 			for(SNode* depNode = dependencyList; depNode != NULL; depNode = depNode->iNext)					
       
  1163 				{																									
       
  1164 				pDepRes = depNode->iResource;													
       
  1165 				if((!depNode->iRequiresChange) || (pDepRes->iResourceId == (TUint)aRequest.ClientId()))				
       
  1166 					continue;																						
       
  1167 				depRequest.ResourceId() = pDepRes->iResourceId;														
       
  1168 				depRequest.ClientId() = pDepRes->iLevelOwnerId;														
       
  1169 				depRequest.Level() = pDepRes->iCachedLevel;															
       
  1170 				depRequest.Resource() = pDepRes;																	
       
  1171 				if(pDepRes->iResourceId & KIdMaskDynamic)															
       
  1172 					((DDynamicPowerResourceD*)pDepRes)->HandleChangePropagation(depRequest, EIssueNotifications,	
       
  1173 																					aOriginatorId, aOriginatorName);	
       
  1174 				else																								
       
  1175 					((DStaticPowerResourceD*)pDepRes)->HandleChangePropagation(depRequest, EIssueNotifications,		
       
  1176 																					aOriginatorId, aOriginatorName);	
       
  1177 				}							
       
  1178 			CompleteNotifications(aRequest.ClientId(), pDR, aRequest.Level(), KErrNone,				
       
  1179 																					aRequest.ClientId());			
       
  1180 			break;																									
       
  1181 			}																										
       
  1182 		default:																									
       
  1183 			return KErrNotSupported;																				
       
  1184 		}																											
       
  1185 	return result;
       
  1186 	}
       
  1187 
       
  1188