sipvoipprovider/svphold/src/svpholdoutestablishingstate.cpp
branchRCL_3
changeset 22 d38647835c2e
parent 0 a4daefaec16c
equal deleted inserted replaced
21:f742655b05bf 22:d38647835c2e
       
     1 /*
       
     2 * Copyright (c) 2006-2008 Nokia Corporation and/or its subsidiary(-ies).
       
     3 * All rights reserved.
       
     4 * This component and the accompanying materials are made available
       
     5 * under the terms of "Eclipse Public License v1.0"
       
     6 * which accompanies this distribution, and is available
       
     7 * at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8 *
       
     9 * Initial Contributors:
       
    10 * Nokia Corporation - initial contribution.
       
    11 *
       
    12 * Contributors:
       
    13 *
       
    14 * Description:  Outgoing request establishing state for hold state machine.
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 #include    <badesca.h>
       
    20 #include    "mcesession.h"
       
    21 #include    "mcemediastream.h"
       
    22 #include    "mceaudiostream.h"
       
    23 #include    "svpholdoutestablishingstate.h"
       
    24 #include    "svpholdcontext.h"
       
    25 #include    "svpholdcontroller.h"
       
    26 #include    "svpholdattributehandler.h"
       
    27 #include    "svpholdobserver.h"
       
    28 #include    "svplogger.h"
       
    29 
       
    30 
       
    31 // ---------------------------------------------------------------------------
       
    32 // CSVPHoldOutEstablishingState::CSVPHoldOutEstablishingState
       
    33 // ---------------------------------------------------------------------------
       
    34 CSVPHoldOutEstablishingState::CSVPHoldOutEstablishingState()
       
    35     {
       
    36     }
       
    37 
       
    38 // ---------------------------------------------------------------------------
       
    39 // CSVPHoldOutEstablishingState::NewLC
       
    40 // ---------------------------------------------------------------------------
       
    41 CSVPHoldOutEstablishingState* CSVPHoldOutEstablishingState::NewLC()
       
    42     {
       
    43     CSVPHoldOutEstablishingState* self = 
       
    44         new ( ELeave ) CSVPHoldOutEstablishingState;
       
    45     CleanupStack::PushL( self );
       
    46     return self;
       
    47     }
       
    48 
       
    49 
       
    50 // ---------------------------------------------------------------------------
       
    51 // CSVPHoldOutEstablishingState::~CSVPHoldOutEstablishingState
       
    52 // ---------------------------------------------------------------------------
       
    53 CSVPHoldOutEstablishingState::~CSVPHoldOutEstablishingState()
       
    54     {
       
    55     }
       
    56 
       
    57 // ---------------------------------------------------------------------------
       
    58 // CSVPHoldOutEstablishingState::DoApplyL
       
    59 // ---------------------------------------------------------------------------
       
    60 //
       
    61 void CSVPHoldOutEstablishingState::DoApplyL( CSVPHoldContext& aContext )
       
    62     {
       
    63     SVPDEBUG1( "CSVPHoldOutEstablishingState::DoApply" );
       
    64     
       
    65     TSVPHoldStateIndex nextState = KSVPHoldEstablishingStateIndex; 
       
    66     CMceSession* session = aContext.SessionObject();
       
    67     const RPointerArray< CMceMediaStream >& streams = session->Streams();
       
    68     TInt streamCount = streams.Count();
       
    69     
       
    70     // Hold / Resume handling depends on the response received from network and
       
    71     // timers; any differences from normal handled in SpecialResponseHandling:
       
    72     if ( !aContext.SpecialResponseHandling( nextState ) )
       
    73         {
       
    74         for ( TInt i = 0; i < streamCount; i++ )
       
    75             {
       
    76             CMceMediaStream* mediaStream = streams[ i ];
       
    77             TMceMediaType mediaType = mediaStream->Type();
       
    78             if ( KMceAudio == mediaType )
       
    79                 {
       
    80                 // This media is audio stream. Handling depends on the request
       
    81                 switch ( aContext.HoldRequest() )
       
    82                     {
       
    83                     case ESVPLocalHold:
       
    84                     case ESVPLocalResume:
       
    85                     case ESVPLocalDoubleHold:
       
    86                     case ESVPLocalDoubleHoldResume:
       
    87                         {
       
    88                         HandleLocalHoldL( aContext, mediaStream, nextState );
       
    89                         break;
       
    90                         }
       
    91                     
       
    92                     case ESVPRemoteHold:
       
    93                     case ESVPRemoteResume:
       
    94                     case ESVPRemoteDoubleHold:
       
    95                     case ESVPRemoteDoubleHoldResume:
       
    96                         {
       
    97                         SVPDEBUG1(
       
    98                         "CSVPHoldOutEstablishingState::DoApply\
       
    99                          - Remote action - State Error" );                   
       
   100                         User::Leave( KErrSVPHoldStateError );
       
   101                         }
       
   102                         
       
   103                     default:
       
   104                         {
       
   105                         // Error in request solving
       
   106                         SVPDEBUG2(
       
   107                         "CSVPHoldOutEstablishingState::CSVPHoldOutEstablishingState\
       
   108                          - Error, request %i",
       
   109                         aContext.HoldRequest() );
       
   110                         break;
       
   111                         }
       
   112                     }
       
   113                 }
       
   114             }    
       
   115         }
       
   116     
       
   117     aContext.SetCurrentStateL( aContext, nextState );
       
   118     SVPDEBUG1( "CSVPHoldOutEstablishingState::DoApply - Handled" );
       
   119     }
       
   120     
       
   121 // ---------------------------------------------------------------------------
       
   122 // CSVPHoldOutEstablishingState::DoEnter
       
   123 // ---------------------------------------------------------------------------
       
   124 //
       
   125 void CSVPHoldOutEstablishingState::DoEnter( CSVPHoldContext& /*aContext*/ )
       
   126     {
       
   127     SVPDEBUG1( "CSVPHoldOutEstablishingState::DoEnter" );
       
   128     }
       
   129 
       
   130 // ---------------------------------------------------------------------------
       
   131 // CSVPHoldOutEstablishingState::IsOutEstablishingStateActive
       
   132 // ---------------------------------------------------------------------------
       
   133 //
       
   134 TBool CSVPHoldOutEstablishingState::IsOutEstablishingStateActive()
       
   135     {
       
   136     return ETrue;
       
   137     }
       
   138     
       
   139 // ---------------------------------------------------------------------------
       
   140 // CSVPHoldOutEstablishingState::HandleLocalHoldL
       
   141 // ---------------------------------------------------------------------------
       
   142 //
       
   143 void CSVPHoldOutEstablishingState::
       
   144 HandleLocalHoldL( CSVPHoldContext& aContext,
       
   145                   CMceMediaStream* aMediaStream,
       
   146                   TSVPHoldStateIndex& aNextState )
       
   147     {
       
   148     switch ( aContext.HoldRequest() )
       
   149         {
       
   150         case ESVPLocalHold:
       
   151             {
       
   152             // From Connected state
       
   153             HandleLocalHoldingL( aContext,
       
   154                                  aMediaStream,
       
   155                                  aNextState );
       
   156             break;
       
   157             }
       
   158             
       
   159         case ESVPLocalResume:
       
   160             {
       
   161             // From Out state
       
   162             HandleLocalResumingL( aContext,
       
   163                                   aMediaStream,
       
   164                                   aNextState );
       
   165             break;
       
   166             }
       
   167 
       
   168         case ESVPLocalDoubleHold:
       
   169             {
       
   170             // From In state
       
   171             HandleLocalHoldingL( aContext,
       
   172                                  aMediaStream,
       
   173                                  aNextState,
       
   174                                  KSVPHoldDHStateIndex );
       
   175             break;
       
   176             }
       
   177 
       
   178          case ESVPLocalDoubleHoldResume:
       
   179             {
       
   180             // From Doublehold state
       
   181             HandleLocalResumingL( aContext,
       
   182                                   aMediaStream,
       
   183                                   aNextState,
       
   184                                   KSVPHoldInStateIndex );
       
   185             break;
       
   186             }       
       
   187         }
       
   188     }
       
   189 
       
   190 // ---------------------------------------------------------------------------
       
   191 // CSVPHoldOutEstablishingState::HandleLocalHoldingL
       
   192 // ---------------------------------------------------------------------------
       
   193 //
       
   194 void CSVPHoldOutEstablishingState::
       
   195 HandleLocalHoldingL( CSVPHoldContext& aContext,
       
   196                      CMceMediaStream* mediaStream,
       
   197                      TSVPHoldStateIndex& aNextState,
       
   198                      TSVPHoldStateIndex aState )
       
   199     {
       
   200     SVPDEBUG1(
       
   201     "CSVPHoldOutEstablishingState::HandleLocalHoldingL" );
       
   202     
       
   203     MDesC8Array* attributeLines = mediaStream->MediaAttributeLinesL();
       
   204     CleanupDeletePushL( attributeLines );
       
   205 
       
   206     if ( KSVPHoldDHStateIndex == aState )
       
   207         {
       
   208         SVPDEBUG1(
       
   209         "CSVPHoldOutEstablishingState::HandleLocalHoldingL\
       
   210          - Next KSVPHoldDHStateIndex" );
       
   211         //aNextState = KSVPHoldDHStateIndex;
       
   212         KSVPHoldAttributeIndex neededAttribute = KSVPHoldInactiveIndex;
       
   213         CheckAttributeL( attributeLines,
       
   214                          neededAttribute,
       
   215                          aNextState,
       
   216                          aContext );
       
   217         }
       
   218     else
       
   219         {
       
   220         SVPDEBUG1(
       
   221         "CSVPHoldOutEstablishingState::HandleLocalHoldingL\
       
   222          - Next KSVPHoldOutStateIndex" );
       
   223         //aNextState = KSVPHoldOutStateIndex;
       
   224         KSVPHoldAttributeIndex neededAttribute = KSVPHoldRecvonlyIndex;
       
   225         CheckAttributeL( attributeLines,
       
   226                          neededAttribute,
       
   227                          aNextState,
       
   228                          aContext );
       
   229         }
       
   230 
       
   231     CleanupStack::PopAndDestroy( attributeLines );
       
   232     
       
   233     SVPDEBUG1( "CSVPHoldOutEstablishingState::HandleLocalHoldingL - Done" );
       
   234     }
       
   235 
       
   236 // ---------------------------------------------------------------------------
       
   237 // CSVPHoldOutEstablishingState::HandleLocalResumingL
       
   238 // ---------------------------------------------------------------------------
       
   239 //
       
   240 void CSVPHoldOutEstablishingState::
       
   241 HandleLocalResumingL( CSVPHoldContext& aContext,
       
   242                       CMceMediaStream* mediaStream,
       
   243                       TSVPHoldStateIndex& aNextState,
       
   244                       TSVPHoldStateIndex aState )
       
   245     {
       
   246     SVPDEBUG1(
       
   247     "CSVPHoldOutEstablishingState::HandleLocalResumingL" );
       
   248     
       
   249     MDesC8Array* attributeLines = mediaStream->MediaAttributeLinesL();
       
   250     CleanupDeletePushL( attributeLines );
       
   251     
       
   252     if ( KSVPHoldInStateIndex == aState )
       
   253         {
       
   254         // Resume from doublehold:
       
   255         SVPDEBUG1(
       
   256         "CSVPHoldOutEstablishingState::HandleLocalResumingL\
       
   257          - Next KSVPHoldInStateIndex" );
       
   258         //aNextState = KSVPHoldInStateIndex;
       
   259         KSVPHoldAttributeIndex neededAttribute = KSVPHoldSendonlyIndex;
       
   260         CheckAttributeL( attributeLines,
       
   261                          neededAttribute,
       
   262                          aNextState,
       
   263                          aContext );    
       
   264         }
       
   265         
       
   266     else
       
   267         {
       
   268         // Basic resume:
       
   269         SVPDEBUG1(
       
   270         "CSVPHoldOutEstablishingState::HandleLocalResumingL\
       
   271          - Next KSVPHoldConnectedStateIndex" );
       
   272         //aNextState = KSVPHoldConnectedStateIndex;
       
   273         KSVPHoldAttributeIndex neededAttribute = KSVPHoldSendrecvIndex;
       
   274         CheckAttributeL( attributeLines,
       
   275                          neededAttribute,
       
   276                          aNextState,
       
   277                          aContext );                                  
       
   278         }
       
   279         
       
   280     CleanupStack::PopAndDestroy( attributeLines );
       
   281 
       
   282     SVPDEBUG1(
       
   283     "CSVPHoldOutEstablishingState::HandleLocalResumingL - Done" );
       
   284     }
       
   285     
       
   286 // ---------------------------------------------------------------------------
       
   287 // CSVPHoldOutEstablishingState::CheckAttributeL
       
   288 // ---------------------------------------------------------------------------
       
   289 //
       
   290 TInt CSVPHoldOutEstablishingState::
       
   291 CheckAttributeL( MDesC8Array* aAttributeLines,
       
   292                 KSVPHoldAttributeIndex aNeededAttribute,
       
   293                 TSVPHoldStateIndex& aNextState,
       
   294                 CSVPHoldContext& aContext )
       
   295     {
       
   296     SVPDEBUG1( "CSVPHoldOutEstablishingState::CheckAttributeL" );
       
   297 
       
   298     KSVPHoldAttributeIndex responseAttribute =
       
   299         aContext.AttributeHandler().FindDirectionAttribute( aAttributeLines );
       
   300 
       
   301     if ( KErrNotFound == responseAttribute )
       
   302         {
       
   303         SVPDEBUG1( "CSVPHoldOutEstablishingState::CheckAttributeL - Session level" );
       
   304         
       
   305         MDesC8Array* sessionAttributeLines =
       
   306             aContext.SessionObject()->SessionSDPLinesL();
       
   307         
       
   308         responseAttribute =
       
   309             aContext.AttributeHandler().FindDirectionAttribute(
       
   310                 sessionAttributeLines );
       
   311         
       
   312         aContext.SessionObject()->SetSessionSDPLinesL(
       
   313             static_cast<CDesC8Array*>( sessionAttributeLines ) );
       
   314         
       
   315         SVPDEBUG1( "CSVPHoldOutEstablishingState::CheckAttributeL - Session level done" );
       
   316         }
       
   317         
       
   318     if ( aNeededAttribute == responseAttribute || 
       
   319          KErrNotFound == responseAttribute )
       
   320         {
       
   321         // If there is no attributes in response; but 200Ok is received;
       
   322         // state change is done based to default cases.
       
   323         return DefineDefaultCaseStateChange( aContext, aNextState );
       
   324         }
       
   325         
       
   326     else if ( KSVPHoldSendrecvIndex == aNeededAttribute &&
       
   327               KErrNotFound == responseAttribute )
       
   328         {
       
   329         // If there is no direction attribute at all, default is sendrecv
       
   330         SVPDEBUG1(
       
   331         "CSVPHoldOutEstablishingState::CheckAttributeL - No attribute" );
       
   332         aNextState = KSVPHoldConnectedStateIndex;
       
   333         return KErrNone;
       
   334         }
       
   335 
       
   336     else if ( KSVPHoldSendrecvIndex == aNeededAttribute &&
       
   337               KSVPHoldRecvonlyIndex == responseAttribute )
       
   338         {
       
   339         // Radvision client fix (it responds to resume with recvonly)
       
   340         SVPDEBUG1(
       
   341         "CSVPHoldOutEstablishingState::CheckAttributeL - recvonly to resume.." );
       
   342         aNextState = KSVPHoldConnectedStateIndex;
       
   343         return KErrNone;
       
   344         }
       
   345     
       
   346     else if ( KSVPHoldRecvonlyIndex == aNeededAttribute &&
       
   347               KSVPHoldInactiveIndex == responseAttribute )
       
   348         {
       
   349         // Inactive response to local hold is allowed
       
   350         SVPDEBUG1(
       
   351         "CSVPHoldOutEstablishingState::CheckAttributeL - No attribute" );
       
   352         aNextState = KSVPHoldOutStateIndex;
       
   353         return KErrNone;
       
   354         }
       
   355         
       
   356     else if( KSVPHoldSendonlyIndex == responseAttribute &&
       
   357              KSVPHoldInactiveIndex == aNeededAttribute )
       
   358         {
       
   359         // Sendonly response to local DH (accept for IOP)
       
   360         SVPDEBUG1(
       
   361         "CSVPHoldOutEstablishingState::CheckAttributeL - Sendonly to Inactive request" );
       
   362         aNextState = KSVPHoldDHStateIndex;
       
   363         return KErrNone;        
       
   364         }
       
   365 
       
   366     else if( KSVPHoldSendonlyIndex == aNeededAttribute &&
       
   367              KSVPHoldInactiveIndex == responseAttribute )
       
   368         {
       
   369         // Inactive response to local DH resume (accept for IOP)
       
   370         SVPDEBUG1(
       
   371         "CSVPHoldOutEstablishingState::CheckAttributeL - Inactive to DH resume request" );
       
   372         aNextState = KSVPHoldInStateIndex;
       
   373         return KErrNone;        
       
   374         }   
       
   375     
       
   376     else if ( KSVPHoldSendrecvIndex == responseAttribute )
       
   377         {
       
   378         // Response has sendrecv -attribute
       
   379         return ResolveStateFromSendRecvIndex( aNeededAttribute, aNextState );
       
   380         }
       
   381 
       
   382     else
       
   383         {
       
   384         SVPDEBUG1(
       
   385         "CSVPHoldOutEstablishingState::CheckAttributeL - else" );
       
   386         return KErrNone;
       
   387         }        
       
   388     }
       
   389     
       
   390 // ---------------------------------------------------------------------------
       
   391 // CSVPHoldOutEstablishingState::DefineDefaultCaseStateChange
       
   392 // ---------------------------------------------------------------------------
       
   393 //
       
   394 TInt CSVPHoldOutEstablishingState::
       
   395 DefineDefaultCaseStateChange( CSVPHoldContext& aContext,
       
   396                               TSVPHoldStateIndex& aNextState )
       
   397     {
       
   398     SVPDEBUG1( "CSVPHoldOutEstablishingState::DefineDefaultCaseStateChange" );
       
   399     // Basic cases (e.g for holding "sendonly" answer has "recvonly")
       
   400     switch ( aContext.HoldRequest() )
       
   401         {
       
   402         case ESVPLocalHold:
       
   403             {
       
   404             SVPDEBUG1( "    ESVPLocalHold" );
       
   405             aNextState = KSVPHoldOutStateIndex;
       
   406             return KErrNone;
       
   407             }
       
   408              
       
   409         case ESVPLocalResume:
       
   410             {
       
   411             SVPDEBUG1( "    ESVPLocalResume" );
       
   412             aNextState = KSVPHoldConnectedStateIndex;
       
   413             return KErrNone;
       
   414             }
       
   415             
       
   416         case ESVPLocalDoubleHold:
       
   417             {
       
   418             SVPDEBUG1( "    ESVPLocalDoubleHold" );
       
   419             aNextState = KSVPHoldDHStateIndex;
       
   420             return KErrNone;
       
   421             }
       
   422             
       
   423         case ESVPLocalDoubleHoldResume:
       
   424             {
       
   425             SVPDEBUG1( "    ESVPLocalDoubleHoldResume" );
       
   426             aNextState = KSVPHoldInStateIndex;
       
   427             return KErrNone;
       
   428             }
       
   429             
       
   430         default:
       
   431             {
       
   432             SVPDEBUG1(
       
   433             "CSVPHoldOutEstablishingState::DefineDefaultCaseStateChange" );
       
   434              return KErrNone;
       
   435             }
       
   436         }    
       
   437     }
       
   438 
       
   439 // ---------------------------------------------------------------------------
       
   440 // CSVPHoldOutEstablishingState::ResolveStateFromSendRecvIndex
       
   441 // ---------------------------------------------------------------------------
       
   442 //
       
   443 TInt CSVPHoldOutEstablishingState::
       
   444 ResolveStateFromSendRecvIndex( KSVPHoldAttributeIndex aNeededAttribute,
       
   445                                TSVPHoldStateIndex& aNextState )
       
   446     {
       
   447     SVPDEBUG1( "CSVPHoldOutEstablishingState::ResolveStateFromSendRecvIndex" );
       
   448     switch ( aNeededAttribute )
       
   449         {
       
   450         case KSVPHoldRecvonlyIndex:
       
   451             {
       
   452             aNextState = KSVPHoldOutStateIndex;
       
   453             return KErrNone;
       
   454             }
       
   455 
       
   456         case KSVPHoldInactiveIndex:
       
   457             {
       
   458             aNextState = KSVPHoldDHStateIndex;
       
   459             return KErrNone;
       
   460             }
       
   461 
       
   462         case KSVPHoldSendonlyIndex:
       
   463             {
       
   464             aNextState = KSVPHoldInStateIndex;
       
   465             return KErrNone;
       
   466             }
       
   467         
       
   468         default:
       
   469             {
       
   470             SVPDEBUG1(
       
   471             "CSVPHoldOutEstablishingState::CheckAttributeL - Last default" );
       
   472             return KErrNone;
       
   473             }
       
   474         }
       
   475     }    
       
   476 
       
   477