diff -r dfb7c4ff071f -r 21d2ab05f085 datacommsserver/esockserver/ssock/ss_conn.cpp --- a/datacommsserver/esockserver/ssock/ss_conn.cpp Thu Dec 17 09:22:25 2009 +0200 +++ b/datacommsserver/esockserver/ssock/ss_conn.cpp Thu Jan 07 13:34:53 2010 +0200 @@ -303,7 +303,6 @@ } - namespace ConnectionGoingDownActivity { DECLARE_DEFINE_CUSTOM_NODEACTIVITY(ECFActivityGoneDown, ConnectionGoingDown, TCFControlClient::TGoneDown, PRActivities::CGoneDownActivity::NewL) @@ -311,9 +310,10 @@ THROUGH_NODEACTIVITY_ENTRY(KNoTag, ConnectionGoingDownActivity::TStoreGoneDownError, MeshMachine::TNoTag) THROUGH_NODEACTIVITY_ENTRY(KNoTag, CoreNetStates::TCancelAndCloseZone0ClientExtIfaces, MeshMachine::TNoTag) THROUGH_NODEACTIVITY_ENTRY(KNoTag, ConnStates::TCancelAllLegacyRMessage2Activities, ConnStates::TNoTagBlockedByLegacyRMessage2Activities) + THROUGH_NODEACTIVITY_ENTRY(KNoTag, ConnStates::TGenerateConnectionDownProgress, MeshMachine::TNoTag) NODEACTIVITY_ENTRY(KNoTag, CoreNetStates::TSendClientLeavingRequestToServiceProviders, MeshMachine::TAwaitingLeaveComplete, MeshMachine::TNoTag) NODEACTIVITY_ENTRY(KNoTag, CoreNetStates::TSetIdleIfNoServiceProviders, MeshMachine::TAwaitingLeaveComplete, ConnectionCleanupActivities::TNoTagOrNoTagBackwards) - LAST_NODEACTIVITY_ENTRY(KNoTag, ConnStates::TGenerateConnectionDownProgress) + LAST_NODEACTIVITY_ENTRY(KNoTag, MeshMachine::TDoNothing) NODEACTIVITY_END() } @@ -402,6 +402,8 @@ : CMMSockSubSession(ConnectionActivities::connectionActivities::Self(), aSession, aPlayer, aSubSessionUniqueId), ASubSessionPlatsecApiExt(UniqueId()), TIfStaticFetcherNearestInHierarchy(this), + iLastProgress(KConnectionUninitialised, KErrNone), + iLastProgressError(KConnectionUninitialised, KErrNone), iTierId(aTierId), iLegacyConnection(*this) { @@ -516,6 +518,18 @@ Main body of CConnection::NewL(CSockSession* aSession, const CConnection& aExistingConnection) */ { + // will need to be brought over + iLastProgress = aExistingConnection.iLastProgress; + iLastProgressError = aExistingConnection.iLastProgressError; + iProgressQueue = aExistingConnection.iProgressQueue; + + /** + The first commented in section of code here is incorrect. It only clones one of the service providers and not them + all. This means that certain calls, GetIntSetting being one, does not work on cloned connections. Unfortunately, + some code now relies on this being broken (browser). This code needs to be fixed before the first section of code + is removed and the proper code reinstated. + */ +#if 1 // BAD CODE RNodeInterface* sp = aExistingConnection.ServiceProvider(); if (sp) { @@ -529,6 +543,59 @@ LOG( ESockLog::Printf(KESockConnectionTag, _L8("CConnection %08x CloneL KErrNotReady"), this) ); User::Leave(KErrNotReady); } + +#else // PROPER CODE + /* + This function looks like it'd be better to do in one loop. dont do this though. All fallible parts need to be done before + sending the messages to ourselves, otherwise the mesh machine will panic. + */ + TInt numSP = 0; + TClientIter iter = aExistingConnection.GetClientIter(TClientType(TCFClientType::EServProvider), + Messages::TClientType(TCFClientType::EServProvider, Messages::TClientType::ELeaving)); + + /** + Add clients to client list. If this fails at any point, remove anything we've added. + Makes assumption that we are the only thing adding service providers. + */ + RNodeInterface* sp = iter++; + while (sp) + { + TRAPD(err, AddClientL(sp->RecipientId(), sp->ClientType())); + if (err != KErrNone) + { + sp = GetFirstClient(TClientType(TCFClientType::EServProvider)); + while (sp) + { + RemoveClient(sp->RecipientId()); + sp = GetFirstClient(TClientType(TCFClientType::EServProvider)); + } + User::Leave(err); + } + + sp = iter++; + numSP++; + } + + /** + If we managed to add anything, post messages to them so that we get added as control clients + */ + if (numSP == 0) + { + LOG( ESockLog::Printf(KESockConnectionTag, _L8("CConnection %08x CloneL KErrNotReady"), this) ); + User::Leave(KErrNotReady); + } + else + { + TClientIter iter = GetClientIter(TClientType(TCFClientType::EServProvider)); + sp = iter++; + while (sp) + { + // TODO IK: This is the wrong message to be using here, should use JoinRequest/Complete handshake + sp->PostMessage(Id(), TCFFactory::TPeerFoundOrCreated(Id(), 0).CRef()); + sp = iter++; + } + } +#endif } @@ -791,7 +858,9 @@ void CConnection::ProgressL() { - if (iLastProgress.iStage != KConnectionUp && iLastProgress.iStage != KConnectionDown) + if (iLastProgress.iStage != KConnectionUp + && iLastProgress.iStage != KConnectionDown + && iLastProgress.iStage != KConnectionUninitialised) { RNodeInterface* sp = ServiceProvider(); User::LeaveIfError(sp? KErrNone : KErrNotReady); @@ -812,7 +881,9 @@ void CConnection::LastProgressErrorL() { - if (iLastProgress.iStage != KConnectionUp && iLastProgress.iStage != KConnectionDown) + if (iLastProgress.iStage != KConnectionUp + && iLastProgress.iStage != KConnectionDown + && iLastProgress.iStage != KConnectionUninitialised) { RNodeInterface* sp = ServiceProvider(); User::LeaveIfError(sp? KErrNone : KErrNotReady); @@ -997,10 +1068,9 @@ // Enqueue the notification and wait for the next one - we loop here forever NODEACTIVITY_ENTRY(KNoTag, TEnqueueNotification, TAwaitingLinkNotification, CoreStates::TCancelOrErrorOrTag) - THROUGH_TRIPLE_ENTRY(KErrorTag, MeshMachine::TStoreError, MeshMachine::TTag) // If we received a TCancel from CConnection, reply with TError to complete shutdown handshake. - THROUGH_NODEACTIVITY_ENTRY(KCancelTag, TSendErrorToConnection, MeshMachine::TTag) - NODEACTIVITY_ENTRY(KCancelTag, TCancelLinkNotification, TAwaitingLinkNotificationError, MeshMachine::TNoTag) + NODEACTIVITY_ENTRY(KCancelTag, TCancelLinkNotification, TAwaitingLinkNotificationError, MeshMachine::TTag) + THROUGH_TRIPLE_ENTRY(KErrorTag, TSendErrorToConnection, MeshMachine::TNoTag) LAST_NODEACTIVITY_ENTRY(KNoTag, TLeaveTierManager) // no other sessions with tier so can safely fire & forget this NODEACTIVITY_END() }