mmsharing/mmshengine/src/musengmceoutsession.cpp
changeset 0 f0cf47e981f9
child 2 b31261fd4e04
equal deleted inserted replaced
-1:000000000000 0:f0cf47e981f9
       
     1 /*
       
     2 * Copyright (c) 2005 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: 
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 // USER
       
    20 #include "musengmceoutsession.h"
       
    21 #include "musengoutsessionobserver.h"
       
    22 #include "musenglivesessionobserver.h"
       
    23 #include "mussettings.h"
       
    24 #include "musengmceutils.h"
       
    25 #include "musenguriparser.h"
       
    26 #include "musenglogger.h"
       
    27 #include "mussesseioninformationapi.h"
       
    28 #include "mussipprofilehandler.h"
       
    29 
       
    30 // SYSTEM
       
    31 #include <mcestreambundle.h>
       
    32 #include <mcemediastream.h>
       
    33 #include <mceoutsession.h>
       
    34 #include <mcevideostream.h>
       
    35 #include <mcemediasource.h>
       
    36 #include <mcefilesource.h>
       
    37 #include <mcemediasink.h>
       
    38 #include <mcertpsink.h>
       
    39 #include <mcespeakersink.h>
       
    40 #include <mcedisplaysink.h>
       
    41 #include <mcevideocodec.h>
       
    42 #include <mceaudiocodec.h>
       
    43 
       
    44 #include <sipprofile.h>
       
    45 #include <sipextensionheader.h>
       
    46 #include <sipaddress.h>
       
    47 #include <uri8.h>
       
    48 #include <e32property.h>
       
    49 
       
    50 
       
    51 
       
    52 const TInt KMusEngSipReasonCodeBadRequest = 400;
       
    53 const TInt KMusEngSipReasonCodeUnauthorized = 401;
       
    54 const TInt KMusEngSipReasonCodePaymentRequired = 402;
       
    55 const TInt KMusEngSipReasonCodeRecipientNotFound  = 404;
       
    56 const TInt KMusEngSipReasonCodeProxyAuthenticationRequired = 407;
       
    57 const TInt KMusEngSipReasonCodeRequestTimeout = 408;
       
    58 const TInt KMusEngSipReasonCodeUnsupportedMediaType = 415;
       
    59 const TInt KMusEngSipReasonCodeUnsupportedUriScheme = 416;
       
    60 const TInt KMusEngSipReasonCodeTemporarilyNotAvailable = 480;
       
    61 const TInt KMusEngSipReasonCodeBusyHere = 486;
       
    62 const TInt KMusEngSipReasonCodeRequestCancelled = 487;
       
    63 const TInt KMusEngSipReasonCodeNotAcceptableHere = 488;
       
    64 const TInt KMusEngSipReasonCodeDecline = 603;
       
    65 const TInt KMusEngSipReasonCodeNotAcceptable = 606;
       
    66 // The next code represents unofficial sip error code
       
    67 // "479 Regretfuly, we were not able to process the URI (479/SL)
       
    68 const TInt KMusEngSipReasonCode479NotAbleToProcessURI = 479;
       
    69 
       
    70 const TUint8 KMusEngPayloadTypeVideoH263 = 96;
       
    71 const TUint8 KMusEngPayloadTypeAudio = 97;
       
    72 const TUint8 KMusEngPayloadTypeVideoAvc = 98;
       
    73 
       
    74 using namespace NMusSessionInformationApi;
       
    75 
       
    76 // -----------------------------------------------------------------------------
       
    77 //
       
    78 // -----------------------------------------------------------------------------
       
    79 //
       
    80 CMusEngMceOutSession::~CMusEngMceOutSession()
       
    81     {
       
    82     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::~CMusEngMceOutSession()" )
       
    83 
       
    84     delete iRecipient;
       
    85     delete iVideoCodecList;
       
    86     
       
    87     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::~CMusEngMceOutSession()" )
       
    88     }
       
    89 
       
    90 
       
    91 // -----------------------------------------------------------------------------
       
    92 //
       
    93 // -----------------------------------------------------------------------------
       
    94 //
       
    95 EXPORT_C void CMusEngMceOutSession::InviteL( const TDesC& aRecipient )
       
    96     {
       
    97     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::InviteL()")
       
    98 
       
    99     if ( iSession )
       
   100         {
       
   101         MUS_ENG_LOG_SESSION_STATE( *iSession ) 
       
   102 
       
   103         if ( iSession->State() == CMceSession::EIdle ||
       
   104              iSession->State() == CMceSession::ETerminated )
       
   105             {
       
   106             // This is the case when last invite has ended up to an error,
       
   107             // last sharing has ended normally, or construction of the session
       
   108             // stucture has not been completed. Delete old session and try to
       
   109             // continue normally.
       
   110             delete iSession;
       
   111             iSession = NULL;
       
   112             MUS_LOG( "mus: [ENGINE]     Existing session deleted")
       
   113             }
       
   114         else
       
   115             {
       
   116             // Session is already ongoing. Leave.
       
   117             User::Leave( KErrAlreadyExists );
       
   118             }
       
   119 
       
   120         }
       
   121 
       
   122     MUS_LOG_TDESC( "mus: [ENGINE]      CMusEngMceOutSession::InviteL() recipient=",
       
   123                    aRecipient )
       
   124 
       
   125     // delete possibly existing recipient
       
   126     delete iRecipient;
       
   127     iRecipient = NULL;  
       
   128     
       
   129     TMusEngUriParser parser( aRecipient ); 
       
   130     parser.ParseUriL();    
       
   131     iRecipient = parser.GetUri8L();
       
   132 
       
   133     CreateMceSessionStructureL();
       
   134 
       
   135     EstablishSessionL();
       
   136 
       
   137     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::InviteL()")
       
   138     }
       
   139 
       
   140 
       
   141 // -----------------------------------------------------------------------------
       
   142 //
       
   143 // -----------------------------------------------------------------------------
       
   144 //
       
   145 EXPORT_C void CMusEngMceOutSession::CancelInviteL()
       
   146     {
       
   147     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::CancelInviteL()" )
       
   148 
       
   149     __ASSERT_ALWAYS( iSession, User::Leave( KErrNotReady ) );
       
   150     
       
   151     MUS_ENG_LOG_SESSION_STATE( *iSession ) 
       
   152 
       
   153     if( iSession->State() == CMceSession::EOffering )
       
   154         {
       
   155         MUS_LOG( "mus: [ENGINE]     CMceOutSession->CancelL()" )
       
   156         static_cast<CMceOutSession*>( iSession )->CancelL();
       
   157         }
       
   158 
       
   159     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::CancelInviteL()" )
       
   160     }
       
   161 
       
   162 
       
   163 // -----------------------------------------------------------------------------
       
   164 //
       
   165 // -----------------------------------------------------------------------------
       
   166 //
       
   167 EXPORT_C void CMusEngMceOutSession::SetSupportedVideoCodecListL( 
       
   168                                                 const TDesC& aVideoCodecs )
       
   169     {
       
   170     MUS_LOG_TDESC( "mus: [ENGINE]  -> CMusEngMceOutSession::SetSupportedVideoCodecListL: ",
       
   171                    aVideoCodecs )
       
   172 
       
   173     HBufC8* newVideoCodecList = 
       
   174                     CnvUtfConverter::ConvertFromUnicodeToUtf8L( aVideoCodecs );
       
   175     delete iVideoCodecList;
       
   176     iVideoCodecList = newVideoCodecList;
       
   177 
       
   178     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::SetSupportedVideoCodecListL" )
       
   179     }
       
   180 
       
   181 
       
   182 // -----------------------------------------------------------------------------
       
   183 // Calls MCE function EstablishL with feature tag in Accept-Contact header.
       
   184 // Adjusts stream and codec values.
       
   185 // -----------------------------------------------------------------------------
       
   186 //
       
   187 void CMusEngMceOutSession::EstablishSessionL()
       
   188     {
       
   189     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::EstablishSessionL()" )
       
   190     
       
   191     __ASSERT_ALWAYS( iSession, User::Leave( KErrNotReady ) );
       
   192     
       
   193     AdjustStreamsAndCodecsL();
       
   194     
       
   195     CDesC8Array* headers = new ( ELeave ) CDesC8ArrayFlat( 1 );
       
   196     CleanupStack::PushL( headers );
       
   197     headers->AppendL( KMusEngAcceptContactHeader() );
       
   198     headers->AppendL( KMusAcceptHeader() ); 
       
   199     if ( iOperatorVariant )
       
   200         {
       
   201         CUri8* originator = iSipProfileHandler->UserFromProfileLC();
       
   202         
       
   203         CSIPExtensionHeader* header = CSIPExtensionHeader::NewLC( 
       
   204                     KMusPPreferredIdentity, originator->Uri().UriDes() );
       
   205         HBufC8* headInText = header->ToTextL();
       
   206         MUS_LOG_TDESC8( " mus: [ENGINE] P-Preferred-Identity header : ", headInText->Des() );
       
   207         CleanupStack::PopAndDestroy( header );
       
   208         CleanupStack::PopAndDestroy( originator );
       
   209         CleanupStack::PushL( headInText );
       
   210         headers->AppendL( *headInText );
       
   211         CleanupStack::PopAndDestroy( headInText );
       
   212         }
       
   213       
       
   214      /* Add the privacy header if cs call privacy setting is switched on */
       
   215     if ( iPrivate && iPrivateNumber )
       
   216         {
       
   217         AddPrivacyHeaderL( *headers );
       
   218         }
       
   219     static_cast<CMceOutSession*>( iSession )->EstablishL( 0, headers );
       
   220     CleanupStack::Pop( headers );
       
   221     
       
   222     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::EstablishSessionL()" )
       
   223     }
       
   224 
       
   225 
       
   226 // -----------------------------------------------------------------------------
       
   227 // Handle MCE session termination. Called by MCE observer function of the
       
   228 // base class.
       
   229 // -----------------------------------------------------------------------------
       
   230 //
       
   231 void CMusEngMceOutSession::HandleTermination( TInt aStatusCode,
       
   232                                               const TDesC8& aReasonPhrase )
       
   233     {
       
   234     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::HandleTermination()" )
       
   235 
       
   236     switch ( aStatusCode )
       
   237         {
       
   238 
       
   239         case KMusEngSipReasonCodeBadRequest :
       
   240             {
       
   241             iOutSessionObserver.SessionBadRequest();
       
   242             break;
       
   243             }
       
   244         case KMusEngSipReasonCodeUnauthorized :
       
   245             {
       
   246             iOutSessionObserver.SessionUnauthorized();
       
   247             break;
       
   248             }
       
   249         case KMusEngSipReasonCodePaymentRequired :
       
   250             {
       
   251             iOutSessionObserver.SessionPaymentRequired();
       
   252             break;
       
   253             }
       
   254         case KMusEngSipReasonCodeRecipientNotFound : 
       
   255             //lint -fallthrough
       
   256         case KMusEngSipReasonCode479NotAbleToProcessURI:
       
   257             //lint -fallthrough
       
   258         case KMusEngSipReasonCodeUnsupportedUriScheme : 
       
   259             {
       
   260             iOutSessionObserver.SessionRecipientNotFound();
       
   261             break;
       
   262             }
       
   263         case KMusEngSipReasonCodeProxyAuthenticationRequired :
       
   264             {
       
   265             iOutSessionObserver.SessionProxyAuthenticationRequired();
       
   266             break;
       
   267             }
       
   268         case KMusEngSipReasonCodeRequestTimeout :
       
   269             {
       
   270             iOutSessionObserver.SessionRequestTimeOut();
       
   271             break;
       
   272             }
       
   273         case KMusEngSipReasonCodeUnsupportedMediaType :
       
   274             //lint -fallthrough
       
   275         case KMusEngSipReasonCodeNotAcceptableHere:
       
   276             //lint -fallthrough
       
   277         case KMusEngSipReasonCodeNotAcceptable:
       
   278             {
       
   279             iOutSessionObserver.SessionUnsupportedMediaType();
       
   280             break;
       
   281             }
       
   282         case KMusEngSipReasonCodeBusyHere :
       
   283             {
       
   284             // Operator variant uses 486 to rejection instead of 603
       
   285             if ( iOperatorVariant )
       
   286                 {
       
   287                 iOutSessionObserver.SessionRejected();
       
   288                 }
       
   289             else
       
   290                 {
       
   291                 iOutSessionObserver.SessionBusyHere();
       
   292                 }
       
   293             break;
       
   294             }
       
   295         case KMusEngSipReasonCodeRequestCancelled :  
       
   296             {
       
   297             iOutSessionObserver.SessionRequestCancelled();
       
   298             break;
       
   299             }
       
   300         case KMusEngSipReasonCodeDecline :
       
   301             {
       
   302             iOutSessionObserver.SessionRejected();
       
   303             break;
       
   304             }
       
   305         case KMusEngSipReasonCodeTemporarilyNotAvailable :
       
   306             {
       
   307             iOutSessionObserver.SessionTemporarilyNotAvailable();
       
   308             break;
       
   309             }
       
   310         default:
       
   311             {
       
   312             // Termination reason is not outsession specific.
       
   313             // Let the base class to handle the termination.
       
   314             CMusEngMceSession::HandleTermination( aStatusCode, aReasonPhrase );
       
   315             }
       
   316         }
       
   317 
       
   318 
       
   319     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::HandleTermination()" )
       
   320     }
       
   321 
       
   322 
       
   323 // -----------------------------------------------------------------------------
       
   324 // Sets payload type and calls overridden base class version
       
   325 // -----------------------------------------------------------------------------
       
   326 //
       
   327 void CMusEngMceOutSession::AdjustVideoCodecL( CMceVideoCodec& aVideoCodec )
       
   328     {
       
   329     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::AdjustVideoCodecL()" )
       
   330     
       
   331     CMusEngMceSession::AdjustVideoCodecL( aVideoCodec );
       
   332     
       
   333     if ( aVideoCodec.SdpName() == KMceSDPNameH263() ||
       
   334          aVideoCodec.SdpName() == KMceSDPNameH2632000() )
       
   335         {
       
   336         User::LeaveIfError( 
       
   337                 aVideoCodec.SetPayloadType( KMusEngPayloadTypeVideoH263 ) );
       
   338         }
       
   339     else if ( aVideoCodec.SdpName() == KMceSDPNameH264() )
       
   340         {
       
   341         User::LeaveIfError(
       
   342                 aVideoCodec.SetPayloadType( KMusEngPayloadTypeVideoAvc ) );
       
   343         }
       
   344     else
       
   345         {
       
   346         // NOP
       
   347         }
       
   348     
       
   349     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::AdjustVideoCodecL()" )
       
   350     }
       
   351 
       
   352 
       
   353 // -----------------------------------------------------------------------------
       
   354 // Sets payload type and calls overridden base class version
       
   355 // -----------------------------------------------------------------------------
       
   356 //        
       
   357 void CMusEngMceOutSession::AdjustAudioCodecL( CMceAudioCodec& aAudioCodec )
       
   358     {
       
   359     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::AdjustAudioCodecL()" )
       
   360     
       
   361     CMusEngMceSession::AdjustAudioCodecL( aAudioCodec );
       
   362     
       
   363     User::LeaveIfError( aAudioCodec.SetPayloadType( KMusEngPayloadTypeAudio ) );
       
   364     
       
   365     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::AdjustAudioCodecL()" )
       
   366     }
       
   367         
       
   368 
       
   369 // -----------------------------------------------------------------------------
       
   370 //
       
   371 // -----------------------------------------------------------------------------
       
   372 //
       
   373 CMusEngMceOutSession::CMusEngMceOutSession( 
       
   374                                 const TRect& aRect,
       
   375                                 MMusEngSessionObserver& aSessionObserver,
       
   376                                 MMusEngOutSessionObserver& aOutSessionObserver )
       
   377     : CMusEngMceSession( aRect, aSessionObserver ),      
       
   378       iOutSessionObserver( aOutSessionObserver )
       
   379     {
       
   380     }
       
   381 
       
   382 
       
   383 // -----------------------------------------------------------------------------
       
   384 //
       
   385 // -----------------------------------------------------------------------------
       
   386 //
       
   387 void CMusEngMceOutSession::ConstructL( TUint aSipProfileId )
       
   388     {
       
   389     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::ConstructL()" )
       
   390 
       
   391     CMusEngMceSession::ConstructL();
       
   392     iSipProfileHandler->CreateProfileL( aSipProfileId );
       
   393     
       
   394     // Check if feature specific behavior is expected
       
   395     iPrivate = ( MultimediaSharingSettings::PrivacySetting());
       
   396         
       
   397     NMusSessionInformationApi::TMusClirSetting clir;
       
   398     // Ignore RProperty::Get return value.Incase of error it should behave default.
       
   399     RProperty::Get( NMusSessionInformationApi::KCategoryUid,
       
   400                     NMusSessionInformationApi::KMusClirSetting,
       
   401                     reinterpret_cast<TInt&>( clir ) );
       
   402     iPrivateNumber = ( clir == NMusSessionInformationApi::ESendOwnNumber )? EFalse: ETrue;
       
   403       
       
   404     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::ConstructL()" )
       
   405     }
       
   406 
       
   407 
       
   408 // -----------------------------------------------------------------------------
       
   409 //
       
   410 // -----------------------------------------------------------------------------
       
   411 //
       
   412 void CMusEngMceOutSession::CreateMceSessionStructureL()
       
   413     {
       
   414     MUS_LOG( "mus: [ENGINE]  -> CMusEngMceOutSession::CreateMceSessionStructureL()" )
       
   415 
       
   416  	CSIPProfile* profile = iSipProfileHandler->Profile();
       
   417     __ASSERT_ALWAYS( profile != NULL, User::Leave( KErrNotReady ) );
       
   418 
       
   419     // Create session
       
   420     if ( iPrivate && iPrivateNumber )
       
   421         {
       
   422         HBufC8* originator = KMusAnonymousHeader().AllocLC();
       
   423         iSession = CMceOutSession::NewL( *iManager, *profile, *iRecipient, originator );
       
   424         CleanupStack::Pop();
       
   425         }
       
   426     else
       
   427         {
       
   428         iSession = CMceOutSession::NewL( *iManager, *profile, *iRecipient );
       
   429         }
       
   430 
       
   431 
       
   432     // Remove QoS-lines if needed
       
   433     if ( profile->Type().iSIPProfileClass == 
       
   434          TSIPProfileTypeInfo::EInternet ||
       
   435          MultimediaSharingSettings::ForceInternetSignalingSettingL() ==
       
   436          MusSettingsKeys::EForceInternetSignaling ||
       
   437          iOperatorVariant)
       
   438         {
       
   439         iSession->SetModifierL( KMcePreconditions, KMcePreconditionsNotUsed );
       
   440         MUS_LOG( "mus: [ENGINE]     Usage of preconditions denied" )
       
   441         }
       
   442         
       
   443     SetSessionSdpLinesL( *iSession );
       
   444 
       
   445     // Create bundle for local streams
       
   446     
       
   447     CMceStreamBundle* localBundle = 
       
   448                         CMceStreamBundle::NewLC( CMceStreamBundle::ELS );
       
   449 
       
   450     // To complete session structure, let the sibling classes add video out
       
   451     // and possibly needed audio streams
       
   452     CompleteSessionStructureL( *localBundle );
       
   453 
       
   454     // Create stream to display and share source with video outstream
       
   455     CMceVideoStream* streamForDisplay = CMceVideoStream::NewLC();
       
   456 
       
   457     CMceVideoStream* videoOut = MusEngMceUtils::GetVideoOutStreamL( *iSession );
       
   458     
       
   459     SetMediaSdpLinesL( *videoOut );
       
   460 		
       
   461     streamForDisplay->SetSourceL( videoOut->Source() );
       
   462 
       
   463     MusEngMceUtils::AddDisplayL( *streamForDisplay, *iManager, Rect() );
       
   464 
       
   465     iSession->AddStreamL( streamForDisplay );
       
   466     CleanupStack::Pop( streamForDisplay );    
       
   467 
       
   468     // Check if there are audio streams to bundle with
       
   469     if ( localBundle->Streams().Count() > 0 ) 
       
   470         {
       
   471         localBundle->AddStreamL( *streamForDisplay );
       
   472         iSession->AddBundleL( localBundle );
       
   473         CleanupStack::Pop( localBundle );
       
   474         }
       
   475     else
       
   476         {
       
   477         CleanupStack::PopAndDestroy( localBundle );
       
   478         }
       
   479 
       
   480     MUS_LOG( "mus: [ENGINE]  <- CMusEngMceOutSession::CreateMceSessionStructureL()" )
       
   481     }
       
   482 
       
   483 
       
   484 // -----------------------------------------------------------------------------
       
   485 // Add Privacy header if own phone number/id should not be sent to remote party
       
   486 // -----------------------------------------------------------------------------
       
   487 //
       
   488 void CMusEngMceOutSession::AddPrivacyHeaderL( CDesC8Array& aHeaders )
       
   489     {
       
   490     MUS_LOG( "mus: [ENGINE]  -> AddPrivacyHeaderL()" )
       
   491     _LIT8( KMusPrivacyHeaderValue, "id" );
       
   492     CSIPExtensionHeader* header = CSIPExtensionHeader::NewLC( 
       
   493                                   KMusPrivacyHeader, KMusPrivacyHeaderValue );
       
   494     HBufC8* headInText = header->ToTextL();
       
   495     MUS_LOG_TDESC8( " mus: [ENGINE] Privacy header : ", headInText->Des() );
       
   496     CleanupStack::PopAndDestroy( header );
       
   497     CleanupStack::PushL( headInText );
       
   498     aHeaders.AppendL( *headInText );
       
   499     CleanupStack::PopAndDestroy( headInText );
       
   500     MUS_LOG( "mus: [ENGINE]  <- AddPrivacyHeaderL()" )
       
   501     }