diff -r 000000000000 -r 5a93021fdf25 bearermanagement/S60MCPR/src/s60mpmrequests.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/bearermanagement/S60MCPR/src/s60mpmrequests.cpp Thu Dec 17 08:55:21 2009 +0200 @@ -0,0 +1,889 @@ +/* +* Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "Eclipse Public License v1.0" +* which accompanies this distribution, and is available +* at the URL "http://www.eclipse.org/legal/epl-v10.html". +* +* Initial Contributors: +* Nokia Corporation - initial contribution. +* +* Contributors: +* +* Description: Handling of the MPM interface. + * +*/ + + +/** + @file s60mpmrequests.cpp + Handling of the MPM interface. + */ + +// Project includes +#include "s60mpmrequests.h" +#include "s60mcpr.h" +#include "s60mpmnotifications.h" + +// Namespace +using namespace S60MCPRMPMOperations; + +// ============================ MEMBER FUNCTIONS =============================== +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::NewL +// ----------------------------------------------------------------------------- +// +CMPMPolicyRequests* CMPMPolicyRequests::NewL( MMPMPolicyNotificationUser& aUser ) + { + CMPMPolicyRequests* self = new ( ELeave ) CMPMPolicyRequests(); + CleanupStack::PushL( self ); + self->ConstructL( aUser ); + CleanupStack::Pop( self ); + return self; + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::PolicyNotification +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::PolicyNotification( TMpmNotification& aNotification ) + { + if ( !iCommitedToDeleteItself ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::PolicyNotification() forwarding call tocalling MCPR", this ) + iPolicyNotificationsUser->PolicyNotification( aNotification ); + } + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::RequestDelete +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::RequestDelete() + { + iCommitedToDeleteItself = ETrue; + // Either we have pending requests + // (we always have at least notifications if we're connected.) + // + if ( iPolicyRequests.Count() > 0 ) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::RequestDelete() %d pending requests, IssueRequest", this, iPolicyRequests.Count() ) + IssueRequest(); + } + // Or we are free to delete this. + // + else + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::RequestDelete() IssueDeleteRequest", this ) + IssueDeleteRequest(); + } + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::CMPMPolicyRequests +// ----------------------------------------------------------------------------- +// +CMPMPolicyRequests::CMPMPolicyRequests() : + CActive( EPriorityStandard ), + iCommitedToDeleteItself( EFalse ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CMPMPolicyRequests()", this ) + CActiveScheduler::Add( this ); + iConnId = (TConnectionId)this; + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::~CMPMPolicyRequests +// ----------------------------------------------------------------------------- +// +CMPMPolicyRequests::~CMPMPolicyRequests() + { + //LOG( ESockLog::Printf(KESockMetaConnectionTag, _L8("CMPMPolicyRequests<%x>::~CMPMPolicyRequests"), this ); ) + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::~CMPMPolicyRequests()", this ) + + __ASSERT_ALWAYS(!IsActive(), User::Panic(KS60MCprPanic, KPanicInvalidCActiveUsage)); + __ASSERT_DEBUG(iPolicyRequests.Count() == 0, User::Panic(KS60MCprPanic, KPanicInvalidCActiveUsage)); + + // Clean up all objects in the list + // Normally there shouldn't be any. + TInt count = iPolicyRequests.Count(); + for (TInt i = 0; i < count; i++) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::~CMPMPolicyRequests() deleting request %d", + this, (TInt)iPolicyRequests[i].iRequestType ) + // Delete prefs + delete iPolicyRequests[i].iConnPref; + delete iPolicyRequests[i].iPolicyPref; + // PolicyRequest owns this class and can delete it. + // MCPR must have cancelled its activity when this happens. + delete iPolicyRequests[i].iUser; + } + + // Reset the array. + iPolicyRequests.Close(); + + // Close the MPM handle + if ( iMpm.Connected() ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::~CMPMPolicyRequests() closing MPM session", this ) + iMpm.Close(); + } + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ConstructL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ConstructL( MMPMPolicyNotificationUser& aUser ) + { + // Force MPMNotifications to go through CMPMPolicyRequests + iPolicyNotificationsUser = &aUser; + iPolicyNotifications = CMPMPolicyNotifications::NewL( *(MMPMPolicyNotificationUser*)this, + iMpm ); + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::ConstructL() using iPolicyNotifications<%x>", + this, iPolicyNotifications ) + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::IAPConnectionStartedL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::IAPConnectionStartedL( const TUint32 aIapId ) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::IAPConnectionStartedL() IAP %d", this, aIapId ) + CreatePolicyRequestL( EPolicyRequestIAPConnectionStarted, aIapId ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::IAPConnectionStoppedL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::IAPConnectionStoppedL( const TUint32 aIapId ) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::IAPConnectionStoppedL() IAP %d", this, aIapId ) + CreatePolicyRequestL( EPolicyRequestIAPConnectionStopped, aIapId ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationJoinsConnectionL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationJoinsConnectionL( const TUint32 aIapId ) + { + // Can't use CreatePolicyRequest() here because this could + // be the first call to MPM. + + PolicyRequest policydata = PolicyRequest(); + policydata.iRequestType = EPolicyRequestApplicationJoinsConnection; + policydata.iConnId = iConnId; + policydata.iIapId = aIapId; + + // Add request to array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationJoinsConnectionL() IAP %d", this, aIapId ) + + // Submit it. + IssueRequest(); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationLeavesConnectionL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationLeavesConnectionL( const TUint32 aIapId ) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationLeavesConnectionL() IAP %d", this, aIapId ) + CreatePolicyRequestL( EPolicyRequestApplicationLeavesConnection, aIapId ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationLeavesConnectionL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationConnectionEndsL() + { + // This is only a notification. Thus, if the session doesn't exist, don't create one + if ( !iMpm.Connected() ) + { + return; + } + + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationConnectionEndsL() IAP %d", this ) + + PolicyRequest policydata = PolicyRequest(); + policydata.iRequestType = EPolicyRequestApplicationConnectionEnds; + policydata.iConnId = iConnId; +// policydata.iIapId = aIapId; + // Nothing to cleanup so it's ok to Leave in AppendL + + // Add request to array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + // Submit it. + IssueRequest(); + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::RegisterPreferredIAPNotificationL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::RegisterPreferredIAPNotificationL() + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::RegisterPreferredIAPNotificationL()", this ) + + PolicyRequest policydata = PolicyRequest(); + + policydata.iRequestType = EPolicyRequestRegisterPrefIAPNotif; + policydata.iConnId = iConnId; + + // Add request to array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + // Submit it. + IssueRequest(); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::UnregisterPreferredIAPNotificationL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::UnregisterPreferredIAPNotificationL() + { + // Sanity check that we're still in business. + if ( !iMpm.Connected() ) + { + return; + } + + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::UnregisterPreferredIAPNotificationL()", this ) + + PolicyRequest policydata = PolicyRequest(); + + policydata.iRequestType = EPolicyRequestUnregisterPrefIAPNotif; + policydata.iConnId = iConnId; + + // Add request to array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + // Submit it. + IssueRequest(); + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationIgnoredTheCarrierL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationIgnoredTheCarrierL( const TUint32 aIapId ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationIgnoredTheCarrierL()", this ) + CreatePolicyRequestL( EPolicyRequestApplicationIgnoredTheCarrier, aIapId ); + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationMigratesToCarrierL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationMigratesToCarrierL( const TUint32 aIapId ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationMigratesToCarrierL()", this ) + CreatePolicyRequestL( EPolicyRequestApplicationMigratesToCarrier, aIapId ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationRejectedTheCarrierL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationRejectedTheCarrierL( const TUint32 aIapId ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationRejectedTheCarrierL()", this ) + CreatePolicyRequestL( EPolicyRequestApplicationRejectedTheCarrier, aIapId ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ApplicationAcceptedTheCarrierL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ApplicationAcceptedTheCarrierL( const TUint32 aIapId) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ApplicationAcceptedTheCarrierL()", this ) + CreatePolicyRequestL( EPolicyRequestApplicationAcceptedTheCarrier, aIapId ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ChooseBestIAP +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ChooseBestIAPL( TConnPref* aConnPref, + const TUid& aAppUid, + TConnPref* aPolicyPref, + MMPMPolicyRequestsUser* aUser ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ChooseBestIAPL()", this ) + + // Define policydata + PolicyRequest policydata = PolicyRequest(); + policydata.iRequestType = EPolicyRequestChooseBestIAP; + policydata.iConnId = iConnId; + policydata.iAppUid = aAppUid; + + // Heap allocated objects + policydata.iConnPref = aConnPref; + policydata.iPolicyPref = aPolicyPref; + policydata.iUser = aUser; + + // Nothing to cleanup so it's ok to Leave in AppendL + // Heap allocated objects are on callers responsibility if we Leave. + + // Add it to the array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + IssueRequest(); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::CancelReselectBestIAP() +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::CancelReselectBestIAP() + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CancelReselectBestIAPL()", this ) + ASSERT( iPolicyRequests.Count() > 0 ); + CancelRequest( EMPMReselectBestIAP ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::CancelChooseBestIAPL() +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::CancelChooseBestIAPL() + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CancelChooseBestIAPL()", this ) + ASSERT( iPolicyRequests.Count() > 0 ); + CancelRequest( EMPMChooseBestIAP ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::CancelProcessError() +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::CancelProcessError() + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CancelProcessErrorL()", this ) + ASSERT( iPolicyRequests.Count() > 0 ); + CancelRequest( EMPMProcessError ); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ReselectIAPL() +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ReselectIAPL( TConnPref* aPolicyPref, + MMPMPolicyRequestsUser* aUser ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::ReselectIAPL()", this ) + //Call MPM to get the list of potential IAPs for the connection + // + PolicyRequest policydata = PolicyRequest(); + + policydata.iRequestType = EPolicyRequestReselectBestIAP; + policydata.iConnId = iConnId; + policydata.iPolicyPref = aPolicyPref; + policydata.iUser = aUser; + + // Add it to the array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + IssueRequest(); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::ProcessErrorL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::ProcessErrorL( TInt& anError, + MMPMPolicyRequestsUser* aUser ) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::ProcessErrorL() %d", this, anError ) + + // insert into array of pending policy request + PolicyRequest policydata = PolicyRequest(); + + policydata.iRequestType = EPolicyRequestProcessError; + policydata.iError = anError; + policydata.iConnId = iConnId; + policydata.iUser = aUser; + + // Add it to the array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + IssueRequest(); + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::IssueDeleteRequest +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::IssueDeleteRequest() + { + ASSERT( !IsActive() ); + // Always cancel & delete policynotifications. + if ( iMpm.Connected() && iPolicyNotifications->IsActive() ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::IssueDeleteRequest() Asynch", this ) + iPolicyNotifications->CancelRequestAndDestroyD( &iStatus ); + iPolicyNotifications = NULL; + SetActive(); + } + else if ( iPolicyNotifications ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::IssueDeleteRequest() Immediate", this ) + iPolicyNotifications->CancelRequestAndDestroyD(); + iPolicyNotifications = NULL; + delete this; + } + else + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::IssueDeleteRequest() Invalid state", this ) + } + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::IssueRequest +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::IssueRequest() + { + //__ASSERT_ALWAYS(IsActive() || iPolicyRequests.Count() > 0,User::Panic(KNetMCprPanic, KPanicInvalidCActiveUsage)); + + // If we have a pending request, back off. + // + if ( IsActive() || iPolicyRequests.Count() == 0 ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::IssueRequest() Unnecessary call, back off", this ) + return; + } + + if ( !iMpm.Connected() ) + { + PolicyRequest policydata = PolicyRequest(); + policydata.iRequestType = EPolicyRequestConnect; + // OK because default granularity is 8 and this is done when first request arrives. + iPolicyRequests.Insert(policydata, 0); + } + + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::IssueRequest() iRequestType %d", this, (TInt)iPolicyRequests[0].iRequestType ) + // + // else we submit a new one. + switch ( iPolicyRequests[0].iRequestType ) + { + case EPolicyRequestConnect: + { + iMpm.Connect( iStatus ); + SetActive(); + break; + } + case EPolicyRequestChooseBestIAP: + { + //LOG(ESockLog::Printf(KESockMetaConnectionTag, _L8("\tcall MPM ChooseBestIAP"))); + iMpm.ChooseBestIAP( ( *iPolicyRequests[0].iConnPref ), + iPolicyRequests[0].iConnId, + iPolicyRequests[0].iAppUid, + ( *iPolicyRequests[0].iPolicyPref ), + iStatus ); + SetActive(); + break; + } + case EPolicyRequestReselectBestIAP: + { + iMpm.ReselectBestIAP( iPolicyRequests[0].iConnId, + ( *iPolicyRequests[0].iPolicyPref ), + iStatus ); + SetActive(); + break; + } + case EPolicyRequestIAPConnectionStarted: + { + iMpm.IAPConnectionStarted( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestIAPConnectionStopped: + { + iMpm.IAPConnectionStopped( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationJoinsConnection: + { + iMpm.ApplicationJoinsConnection( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationLeavesConnection: + { + iMpm.ApplicationLeavesConnection( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationConnectionEnds: + { + iMpm.ApplicationConnectionEnds( iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestRegisterPrefIAPNotif: + { + iMpm.RegisterPrefIAPNotif( iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestUnregisterPrefIAPNotif: + { + iMpm.UnregisterPrefIAPNotif( iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationIgnoredTheCarrier: + { + iMpm.ApplicationIgnoredTheCarrier( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationMigratesToCarrier: + { + iMpm.ApplicationMigratesToCarrier( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationRejectedTheCarrier: + { + iMpm.ApplicationRejectedTheCarrier( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestApplicationAcceptedTheCarrier: + { + iMpm.ApplicationAcceptedTheCarrier( iPolicyRequests[0].iIapId, + iPolicyRequests[0].iConnId, + iStatus ); + SetActive(); + break; + } + case EPolicyRequestProcessError: + { + //LOG(ESockLog::Printf(KESockMetaConnectionTag, _L8("\tcall MPM ProcessError"))); + iMpm.ProcessError( iPolicyRequests[0].iError, + iPolicyRequests[0].iConnId, + iPolicyRequests[0].iNeededAction, + iStatus ); + SetActive(); + break; + } + default: + { +#ifdef _DEBUG + // In debug builds, panic + _LIT( KPanicMsg, "CMPMPolicyRequests::IssueRequestL: Invalid case" ); + User::Panic( KPanicMsg, KErrNotSupported ); +#endif + break; + } + } + } + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::RunL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::RunL() + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::RunL() iStatus %d", this, iStatus.Int() ) + + // If there's a request waiting and is now completed + // + if ( iPolicyRequests.Count() > 0 && !iCommitedToDeleteItself) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::RunL() Standard processing", this ) + PolicyRequest& policydata = iPolicyRequests[0]; + // Process the response + // + switch ( policydata.iRequestType ) + { + case EPolicyRequestConnect: + { + if ( iStatus.Int() != KErrNone ) + { + //-jl- MPM connection failed, set MPM connection required again. + iMpm.Close(); + //-jl- Go to RunError + User::Leave( iStatus.Int() ); + } + else + { + // Otherwise MPM ok and start listening for notifications + iPolicyNotifications->Activate(); + } + break; + } + case EPolicyRequestProcessError: + case EPolicyRequestChooseBestIAP: + case EPolicyRequestReselectBestIAP: + { + if ( policydata.iUser ) + { + // ChooseBest IAP is completed by iUser. + // + policydata.iStatus = iStatus.Int(); + policydata.iUser->PolicyResponse( policydata ); + } + break; + } + // With these messages we ignore the result. + case EPolicyRequestRegisterPrefIAPNotif: + case EPolicyRequestUnregisterPrefIAPNotif: + case EPolicyRequestApplicationIgnoredTheCarrier: + case EPolicyRequestApplicationMigratesToCarrier: + case EPolicyRequestApplicationRejectedTheCarrier: + case EPolicyRequestApplicationAcceptedTheCarrier: + case EPolicyRequestIAPConnectionStarted: + case EPolicyRequestIAPConnectionStopped: + case EPolicyRequestApplicationJoinsConnection: + case EPolicyRequestApplicationLeavesConnection: + case EPolicyRequestApplicationConnectionEnds: + { +#ifdef _DEBUG + if ( iStatus.Int() != KErrNone ) + { + S60MCPRLOGSTRING3( "S60MCPR::CMPMPolicyRequests<%x>::RunL() Request %d failed %d", + this, (TInt) policydata.iRequestType, iStatus.Int() ) + } +#endif // _DEBUG + break; + } + default: + { +#ifdef _DEBUG + // In debug builds, panic + _LIT( KPanicMsg, "CMPMPolicyRequests::RunL: Invalid case" ); + User::Panic( KPanicMsg, KErrNotSupported ); +#endif + break; + } + } + // Then cleanup + // + policydata.Cleanup(); + iPolicyRequests.Remove( 0 ); // remove request from the array + // And if there are still pending request, cotinue with the next one + // + if ( iPolicyRequests.Count() > 0 ) + { + IssueRequest(); + } + } + // We have pending requests but we have commited to delete itself + // + else if ( iPolicyRequests.Count() > 0 && iCommitedToDeleteItself ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::RunL() Processing pending requests before delete", this ) + // Submit pending requests to keep MPM in consistent state. + // First cleanup the old one + // + iPolicyRequests[0].Cleanup(); + iPolicyRequests.Remove( 0 ); // remove request from the array + // And if there are still pending request, cotinue with the next one + // + if ( iPolicyRequests.Count() > 0 ) + { + IssueRequest(); + } + // In this case we've processed everything and can close. + // + else + { + IssueDeleteRequest(); + } + } + else if ( iPolicyRequests.Count() == 0 && iCommitedToDeleteItself ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::RunL() About to delete itself", this ) + ASSERT( !iPolicyNotifications ); + delete this; + } + else + { + // INVALID STATE +#ifdef _DEBUG + // In debug builds, panic + _LIT( KPanicMsg, "CMPMPolicyRequests::RunL: Invalid state" ); + User::Panic( KPanicMsg, KErrNotSupported ); +#endif + // Even still, make sure we don't leak memory + // + iPolicyNotifications->CancelRequestAndDestroyD(); + iPolicyNotifications = NULL; + delete this; + } + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::DoCancel +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::DoCancel() + { + // Not allowed! Cancel() may cause deadlock! + _LIT( KPanicMsg, "CMPMPolicyRequests::DoCancel" ); + User::Panic( KPanicMsg, KErrNotSupported ); + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::RunError +// ----------------------------------------------------------------------------- +// +TInt CMPMPolicyRequests::RunError( TInt aError ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::RunError()", this ) + // Connect has failed, cleanup and deliver errors + TInt count = iPolicyRequests.Count(); + for ( TInt i = 0; i < count; i++ ) + { + if ( iPolicyRequests[i].iUser ) + { + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::RunError() Sending error %d in PolicyResponse", this, aError ) + iPolicyRequests[i].iStatus = aError; + iPolicyRequests[i].iUser->PolicyResponse( iPolicyRequests[i] ); + } + + // Delete prefs + iPolicyRequests[i].Cleanup(); + } + iPolicyRequests.Reset(); + + return KErrNone; + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::CancelRequest +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::CancelRequest( TMpmAsynchCodes aRequestCode ) + { + // Semantics of asynchronous cancellations: + // + // The biggest difference is that asynchronous cancellation will + // cause RunL() -call for original request. Because of this the + // PolicyResponse() calls must be prevented. + // + // Asynch Cancellation cannot be queued along with the other requests. + // Precondition for cancellation call to MPM is that there's an active request + // and that request code matches to the given parameter. + // + // Cancellation of the unsent requests is simple. Just remove it from the queue. + // + // Asynchronous cancellation adds message to MPMServer's IPC queue but since we + // queue all requests we can safely always call the SendCancelRequest() + + // If the cancelled request is the active one. + // + S60MCPRLOGSTRING2( "S60MCPR::CMPMPolicyRequests<%x>::CancelRequest() %d", this, (TInt)aRequestCode ) + if ( iPolicyRequests[0].iRequestType == aRequestCode ) + { + // Cancel the query if active + // + if ( IsActive() ) + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CancelRequest() Cancelling active request", this ) +#ifdef _DEBUG + TInt ret = iMpm.SendCancelRequest( aRequestCode ); +#else + iMpm.SendCancelRequest( aRequestCode ); +#endif + __ASSERT_DEBUG( ret == KErrNone, User::Panic( KS60MCprPanic, ret ) ); + // Prevent the callback. + iPolicyRequests[0].Cancel(); + } + // Completed or not started. Just remove the request. + // + else + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CancelRequest() Cancelling non-active request", this ) + iPolicyRequests[0].Cleanup(); + // remove it. + iPolicyRequests.Remove(0); + } + } + // Else we need to find it from the queue + // + else + { + S60MCPRLOGSTRING1( "S60MCPR::CMPMPolicyRequests<%x>::CancelRequest() Cancelling pending request", this ) + TInt count = iPolicyRequests.Count(); + for (TInt i = 1; i < count; i++) + { + if ( iPolicyRequests[i].iRequestType == aRequestCode ) + { + // Cancellable request found, clean it up + iPolicyRequests[i].Cleanup(); + // remove it. + iPolicyRequests.Remove(i); + break; // first occurence is enough. + } + } + } + } + + +// ----------------------------------------------------------------------------- +// CMPMPolicyRequests::CreatePolicyRequestL +// ----------------------------------------------------------------------------- +// +void CMPMPolicyRequests::CreatePolicyRequestL( TPolicyServerOperations aRequestCode, + const TUint32& aIapId ) + { + // Sanity check that we're still in business. + if ( !iMpm.Connected() ) + { + return; + } + + PolicyRequest policydata = PolicyRequest(); + + policydata.iRequestType = aRequestCode; + policydata.iConnId = iConnId; + policydata.iIapId = aIapId; + + // Add request to array of uncompleted requests + iPolicyRequests.AppendL( policydata ); + + // Submit it. + IssueRequest(); + } + + +// End of file