omadrm/drmplugins/drmudtmodule/src/DrmUdtHandler.cpp
changeset 0 95b198f216e5
equal deleted inserted replaced
-1:000000000000 0:95b198f216e5
       
     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:  Implementation of the User Data Transfer module
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 // INCLUDE FILES
       
    20 #include "DrmUdtHandler.h"
       
    21 #include "DrmUdtConn.h"
       
    22 #include "RoapStorageClient.h"
       
    23 #include "DrmRightsClient.h"
       
    24 #include "DrmUdtObserver.h"
       
    25 
       
    26 #include <hash.h>
       
    27 #include <stringpool.h>
       
    28 #include <http/thttphdrval.h>
       
    29 #include <etelmm.h> 
       
    30 #include <mmtsy_names.h>
       
    31 
       
    32 #ifdef _DEBUG
       
    33 #define LOGGING
       
    34 #endif
       
    35 
       
    36 #define LOGGING
       
    37 
       
    38 #ifdef LOGGING
       
    39 _LIT(KLogDir, "DRM");
       
    40 _LIT(KLogName, "UDT.log");
       
    41 #include "flogger.h"
       
    42 #define LOG(string) \
       
    43 	RFileLogger::Write(KLogDir, KLogName, \
       
    44 		EFileLoggingModeAppend, string);
       
    45 #define LOGINT(string, val) \
       
    46 	RFileLogger::WriteFormat(KLogDir, KLogName, \
       
    47 		EFileLoggingModeAppend, string, val);
       
    48 #define LOGHEX(buffer) \
       
    49 	RFileLogger::HexDump(KLogDir, KLogName, \
       
    50 		EFileLoggingModeAppend, _S(""), _S(""), \
       
    51 		buffer.Ptr(), buffer.Length());
       
    52 #else
       
    53 #define LOG
       
    54 #define LOGHEX        
       
    55 #endif
       
    56 
       
    57 using namespace Roap;
       
    58 
       
    59 // ================= CONSTANTS ======================
       
    60 
       
    61 // The time out value in HTTP, 30 sec
       
    62 LOCAL_D const TInt KUdtTimeoutValue = 30000000;
       
    63 
       
    64 LOCAL_D const TInt KMaxSerNumLength = 64;
       
    65 LOCAL_D const TInt KRdbKeyLength = 256;
       
    66 LOCAL_D const TInt KVersionSize = 1;
       
    67 LOCAL_D const TInt KMessageIdSize = 1;
       
    68 LOCAL_D const TInt KLengthSize = 4;
       
    69 LOCAL_D const TInt KSignatureLength = 128;
       
    70 
       
    71 LOCAL_D const TInt KVersion = 0;
       
    72 
       
    73 LOCAL_D const TInt KPadding255 = 1;
       
    74 
       
    75 _LIT8( KUdtContentType, "application/binary" );
       
    76 
       
    77 // UDT message identifiers
       
    78 LOCAL_D const TUint8 KUdtRequestId = 0;
       
    79 LOCAL_D const TUint8 KUdtResponseId = 1;
       
    80 LOCAL_D const TUint8 KStatusResponseId = 3;
       
    81 LOCAL_D const TUint8 KErrorResponseId = 4;
       
    82 LOCAL_D const TUint8 KServerErrorValue = 0;
       
    83 LOCAL_D const TUint8 KClientErrorValue = 1;
       
    84 
       
    85 
       
    86 LOCAL_D const TInt KUdtResponseSize = 129;
       
    87 
       
    88 NONSHARABLE_STRUCT( TUnloadModule )
       
    89     {
       
    90     RTelServer* iServer;
       
    91     const TDesC* iName;
       
    92     };
       
    93 
       
    94 // ================= LOCAL FUNCTIONS =========================
       
    95 
       
    96 LOCAL_C void WriteIntToBlock( TInt aValue, TDes8& aBlock, TInt aOffset )
       
    97     {
       
    98     aBlock.SetLength(4);
       
    99     aBlock[aOffset] =     (aValue & 0xff000000) >> 24;
       
   100     aBlock[aOffset + 1] = (aValue & 0x00ff0000) >> 16;
       
   101     aBlock[aOffset + 2] = (aValue & 0x0000ff00) >> 8;
       
   102     aBlock[aOffset + 3] = (aValue & 0x000000ff);
       
   103     }
       
   104 
       
   105 template<class S>
       
   106 void PointerArrayResetDestroyAndClose(TAny* aPtr)
       
   107     {
       
   108     (reinterpret_cast<RPointerArray<S>*>(aPtr))->ResetAndDestroy();
       
   109     (reinterpret_cast<RPointerArray<S>*>(aPtr))->Close();
       
   110     }
       
   111     
       
   112 LOCAL_C void DoUnloadPhoneModule( TAny* aAny )
       
   113     {
       
   114     __ASSERT_DEBUG( aAny, User::Invariant() );
       
   115     TUnloadModule* module = ( TUnloadModule* ) aAny;
       
   116     module->iServer->UnloadPhoneModule( *( module->iName ) );
       
   117     } 
       
   118 
       
   119 // ================= MEMBER FUNCTIONS =======================
       
   120 
       
   121 // ---------------------------------------------------------
       
   122 // CDrmUdtHandler::NewL()
       
   123 // ---------------------------------------------------------
       
   124 //
       
   125 EXPORT_C CDrmUdtHandler* CDrmUdtHandler::NewL( )
       
   126     {
       
   127     LOG( _L("CDrmUdtHandler:NewL:") );
       
   128     CDrmUdtHandler* handler = new( ELeave ) CDrmUdtHandler();
       
   129     CleanupStack::PushL( handler );
       
   130     handler->ConstructL();
       
   131     CleanupStack::Pop( handler );
       
   132     return handler;
       
   133     }
       
   134 
       
   135 // ---------------------------------------------------------
       
   136 // CDrmUdtHandler::~CDrmUdtModule()
       
   137 // ---------------------------------------------------------
       
   138 //
       
   139 CDrmUdtHandler::~CDrmUdtHandler()
       
   140     {
       
   141     LOG( _L("CDrmUdtHandler::~CDrmUdtHandler") );
       
   142     Cancel();
       
   143 	iSession.Close();
       
   144 	delete iConnection;
       
   145 	delete iUri;
       
   146 	delete iTimeout;
       
   147     delete iOneTimePassword;
       
   148     delete iUdtRequest;
       
   149     delete iUdtResponse;
       
   150     }
       
   151     
       
   152 // ---------------------------------------------------------
       
   153 // CDrmUdtHandler::ConstructL()
       
   154 // ---------------------------------------------------------
       
   155 //
       
   156 void CDrmUdtHandler::ConstructL() 
       
   157     {
       
   158     LOG( _L("CDrmUdtHandler::ConstructL") );
       
   159     iConnection = CDrmUdtConn::NewL();
       
   160     iTimeout = CPeriodic::NewL( CActive::EPriorityUserInput );
       
   161     iRequestType = EUdtRequest;
       
   162     iUdtError = EUdtOk;
       
   163     iStateInfo.iState = TUdtStateInfo::EUdtNotStarted;
       
   164     iStateInfo.iProgress = 0;
       
   165     iStateInfo.iError = EUdtOk;
       
   166     }
       
   167     
       
   168 // -----------------------------------------------------------------------------
       
   169 // CDrmUdtHandler::DoUserDataTransferL()
       
   170 // -----------------------------------------------------------------------------
       
   171 //
       
   172 EXPORT_C void CDrmUdtHandler::DoUserDataTransferL( const TDesC8& aOneTimePassword,
       
   173                                                    const TDesC8& aServiceUrl,
       
   174                                                    MDrmUdtObserver* aObserver,
       
   175                                                    TRequestStatus& aStatus )
       
   176     {
       
   177     LOG( _L("CDrmUdtHandler::DoUserDataTransferL") );
       
   178     __ASSERT_ALWAYS( iState == EInit, User::Invariant() );
       
   179     
       
   180     /*
       
   181     1. fetch original RDB data from the rights client (serial number and key)
       
   182     2. create UDT package with the original RDB data, the one time password,
       
   183        our serial number and our certificate
       
   184     3. open a connection to the service URL
       
   185     4. do a POST to the service URL, sending our UDT package
       
   186     5. receive the anwser with the re-encrypted RDB key
       
   187     6. tell the rights client to do a restore, using the re-encrypted RDB key
       
   188     7. do a POST to the service URL, sendind a success or error notification
       
   189     */
       
   190 
       
   191     iOneTimePassword = aOneTimePassword.AllocLC();
       
   192     iUri = aServiceUrl.AllocL();
       
   193     iObserver = aObserver;
       
   194     
       
   195     LOG( _L8("Password: ") );
       
   196     LOG( aOneTimePassword );
       
   197     LOG( _L8("URL: ") );
       
   198     LOG( aServiceUrl );
       
   199     
       
   200     iParentStatus = &aStatus;    
       
   201     *iParentStatus = KRequestPending;
       
   202     iState = EStart;
       
   203     TRequestStatus* ownStatus = &iStatus;    
       
   204     *ownStatus = KRequestPending;
       
   205     iRequestType = EUdtRequest;
       
   206     
       
   207     SetActive();
       
   208     User::RequestComplete( ownStatus, KErrNone );      
       
   209     CleanupStack::Pop(); // iOneTimePassword    
       
   210     }
       
   211     
       
   212 // ---------------------------------------------------------
       
   213 // CDrmUdtHandler::SetPreferredIap()
       
   214 // ---------------------------------------------------------
       
   215 EXPORT_C void CDrmUdtHandler::SetPreferredIap( TUint32 aPreferredIap )
       
   216     {
       
   217     LOG( _L("CDrmUdtHandler::SetPreferredIap") );
       
   218     iPreferredIap = aPreferredIap;
       
   219     }    
       
   220 
       
   221 // ---------------------------------------------------------
       
   222 // CDrmUdtHandler::DoCancel()
       
   223 // ---------------------------------------------------------
       
   224 //
       
   225 void CDrmUdtHandler::DoCancel()
       
   226     {
       
   227     LOG( _L("CDrmUdtHandler::DoCancel") );
       
   228     switch ( iState )
       
   229         {
       
   230         case EStart:
       
   231         case EConnect:
       
   232             {
       
   233             iConnection->Cancel();
       
   234             break;
       
   235             }
       
   236         case EResponseReceived:
       
   237             {
       
   238             iTransaction.Close();
       
   239             SelfComplete( iError );
       
   240             break;
       
   241             }
       
   242         default:
       
   243             {
       
   244             break;
       
   245             }
       
   246         }
       
   247 	iError = KErrCancel;
       
   248 	Complete();
       
   249     }
       
   250 
       
   251 // ---------------------------------------------------------
       
   252 // CDrmUdtHandler::RunL()
       
   253 // ---------------------------------------------------------
       
   254 //
       
   255 void CDrmUdtHandler::RunL()
       
   256     {
       
   257     LOG( _L("CDrmUdtHandler::RunL") );
       
   258     User::LeaveIfError( iStatus.Int() );
       
   259 
       
   260     switch ( iState )
       
   261         {
       
   262         case EStart:
       
   263             {
       
   264             ConnectL();
       
   265             break;
       
   266             }        
       
   267         case EConnect:
       
   268             {
       
   269             CreateSessionL();
       
   270             break;
       
   271             }
       
   272         case ESendMessage:
       
   273             {
       
   274             SendUdtMessageL();
       
   275             break;
       
   276             }
       
   277         case EResponseReceived:
       
   278             {
       
   279             ResponseReceivedL();
       
   280             break;
       
   281             }
       
   282         case EComplete:
       
   283             {
       
   284             iState = EInit;
       
   285     		Complete();
       
   286             break;
       
   287             }
       
   288         case EInit:
       
   289         default:
       
   290             {
       
   291             break;
       
   292             }
       
   293         }
       
   294     }
       
   295 
       
   296 // ---------------------------------------------------------
       
   297 // CDrmUdtHandler::RunError()
       
   298 // ---------------------------------------------------------
       
   299 //
       
   300 TInt CDrmUdtHandler::RunError( TInt aError )
       
   301     {
       
   302     LOG( _L("CDrmUdtHandler::RunError") );
       
   303     iError = aError;
       
   304     iState = EInit;
       
   305     Complete();
       
   306     return KErrNone;
       
   307     }
       
   308 
       
   309 // ---------------------------------------------------------
       
   310 // CDrmUdtHandler::ConnectL()
       
   311 // ---------------------------------------------------------
       
   312 //
       
   313 void CDrmUdtHandler::ConnectL()
       
   314     {
       
   315     LOG( _L("CDrmUdtHandler::ConnectL") );
       
   316     __ASSERT_ALWAYS( iState == EStart, User::Invariant() );
       
   317     
       
   318     iConnection->ConnectL( iPreferredIap, iObserver, &iStatus );
       
   319     iState = EConnect;
       
   320     iError = EUdtOk;
       
   321     SetActive();
       
   322     }
       
   323 
       
   324 // ---------------------------------------------------------
       
   325 // CDrmUdtHandler::CreateSessionL()
       
   326 // ---------------------------------------------------------
       
   327 //
       
   328 void CDrmUdtHandler::CreateSessionL()
       
   329     {
       
   330     LOG( _L("CDrmUdtHandler::CreateSessionL") );
       
   331     __ASSERT_ALWAYS( iState == EConnect, User::Invariant() );
       
   332     
       
   333     TUint32 ap;
       
   334 
       
   335     if( !iConnection->IsConnected( ap ) )
       
   336         {
       
   337         User::Leave( KErrGeneral );
       
   338         }
       
   339     
       
   340     iSession.Close();
       
   341     iSession.OpenL();
       
   342 
       
   343     RStringPool strPool = iSession.StringPool();
       
   344 
       
   345     // Remove first session properties just in case.
       
   346     RHTTPConnectionInfo connInfo = iSession.ConnectionInfo();
       
   347     
       
   348     // Clear RConnection and Socket Server instances
       
   349     connInfo.RemoveProperty(strPool.StringF(HTTP::EHttpSocketServ,RHTTPSession::GetTable()));
       
   350     connInfo.RemoveProperty(strPool.StringF(HTTP::EHttpSocketConnection,RHTTPSession::GetTable()));
       
   351     
       
   352 #ifdef __WINS__    
       
   353     // Clear the proxy settings
       
   354     RStringF proxy;
       
   355     proxy = strPool.OpenFStringL(_L8("172.22.168.15"));
       
   356     connInfo.SetPropertyL
       
   357         ( 
       
   358         strPool.StringF( HTTP::EProxyAddress, RHTTPSession::GetTable() ), 
       
   359         THTTPHdrVal( proxy ) 
       
   360         );
       
   361     proxy.Close();
       
   362     connInfo.SetPropertyL
       
   363         ( 
       
   364         strPool.StringF( HTTP::EProxyUsage, RHTTPSession::GetTable() ), 
       
   365         THTTPHdrVal( strPool.StringF(HTTP::EUseProxy, RHTTPSession::GetTable() ) )
       
   366         );
       
   367 
       
   368 #else
       
   369     THTTPHdrVal proxyUsage(strPool.StringF(HTTP::EUseProxy,RHTTPSession::GetTable()));
       
   370     connInfo.RemoveProperty(strPool.StringF(HTTP::EProxyUsage,RHTTPSession::GetTable()));
       
   371     connInfo.RemoveProperty(strPool.StringF(HTTP::EProxyAddress,RHTTPSession::GetTable()));
       
   372 #endif
       
   373 
       
   374     connInfo.SetPropertyL
       
   375         (
       
   376         strPool.StringF( HTTP::EHttpSocketServ, RHTTPSession::GetTable() ),
       
   377         THTTPHdrVal( iConnection->SocketServ().Handle() )
       
   378         );
       
   379 
       
   380     connInfo.SetPropertyL
       
   381         ( 
       
   382         strPool.StringF( HTTP::EHttpSocketConnection, RHTTPSession::GetTable() ), 
       
   383         THTTPHdrVal( REINTERPRET_CAST( TInt, &iConnection->Conn() ) )
       
   384         );
       
   385 
       
   386     InstallHttpFiltersL();
       
   387 
       
   388     // Complete requests
       
   389     TRequestStatus* ownStatus = &iStatus;    
       
   390     *ownStatus = KRequestPending;
       
   391     iState = ESendMessage;
       
   392     SetActive();
       
   393     User::RequestComplete( ownStatus, KErrNone );
       
   394     }
       
   395 
       
   396 
       
   397 // ---------------------------------------------------------
       
   398 // CDrmUdtModule::InstallHttpFilters()
       
   399 // ---------------------------------------------------------
       
   400 //
       
   401 void CDrmUdtHandler::InstallHttpFiltersL()
       
   402     {
       
   403     LOG( _L("CDrmUdtHandler::InstallHttpFiltersL") );
       
   404  // CHttpUAProfFilterInterface::InstallFilterL( iSession );
       
   405  // CHttpCookieFilter::InstallFilterL( iSession );
       
   406  // InstallAuthenticationL( iSession );
       
   407  // CHttpFilterProxyInterface::InstallFilterL( iSession );
       
   408     }
       
   409 
       
   410 
       
   411 // ---------------------------------------------------------
       
   412 // CDrmUdtHandler::SendUdtMessageL()
       
   413 // ---------------------------------------------------------
       
   414 //
       
   415 void CDrmUdtHandler::SendUdtMessageL()
       
   416     {
       
   417     LOG( _L("CDrmUdtHandler::SendUdtMessageL") );
       
   418     __ASSERT_ALWAYS( iState == ESendMessage, User::Invariant() );
       
   419     
       
   420     TUriParser8 uri;
       
   421     
       
   422     if ( iRequestType == EUdtRequest )
       
   423         {
       
   424         CreateUdtRequestL();
       
   425         }
       
   426     else if( iRequestType == EStatusNotification )
       
   427         {
       
   428         CreateStatusNotificationL();
       
   429         }
       
   430     
       
   431     User::LeaveIfError( uri.Parse( *iUri ) );
       
   432     RStringF POST;
       
   433     POST = iSession.StringPool().StringF( HTTP::EPOST, RHTTPSession::GetTable() );
       
   434     iTransaction = iSession.OpenTransactionL( uri, *this, POST );
       
   435 
       
   436     // Set required headers
       
   437     RHTTPHeaders hdrs = iTransaction.Request().GetHeaderCollection();
       
   438     
       
   439     SetHeaderL(hdrs, HTTP::EAccept, KUdtContentType() );
       
   440     
       
   441     SetHeaderL(hdrs, HTTP::EContentType, KUdtContentType() );
       
   442     
       
   443     // Add request body
       
   444     MHTTPDataSupplier* ds = this;
       
   445     iTransaction.Request().SetBody(*ds);
       
   446     
       
   447     iTransaction.SubmitL();
       
   448 
       
   449     iState = EResponseReceived;
       
   450     iStatus = KRequestPending;
       
   451     SetActive();
       
   452 
       
   453     iTimeout->Cancel();
       
   454     iTimeout->Start( KUdtTimeoutValue,
       
   455     				 KUdtTimeoutValue,
       
   456     				 TCallBack( StaticTimeOut,this ) );
       
   457     }
       
   458     
       
   459     
       
   460 // ---------------------------------------------------------
       
   461 // CDrmUdtHandler::CreateUdtRequestL()
       
   462 // ---------------------------------------------------------
       
   463 //    
       
   464 void CDrmUdtHandler::CreateUdtRequestL()
       
   465     {
       
   466     RRoapStorageClient client;
       
   467     RPointerArray< HBufC8 > certChain;
       
   468     TCleanupItem listCleanup( PointerArrayResetDestroyAndClose< HBufC8 >,
       
   469         &certChain );
       
   470     HBufC8* certBlock;
       
   471     TInt i;
       
   472     TInt n;
       
   473     TPtr8 ptr( NULL, 0 );
       
   474     TBuf8< sizeof ( TUint32 ) > intBuf;
       
   475     TBuf8< KMaxSerNumLength > targetSer;
       
   476     TBuf8< KRdbKeyLength > rdb_data;
       
   477     TBuf8< KSignatureLength > hash;
       
   478     HBufC8* signature = NULL;
       
   479     TInt udtVersion;
       
   480     CSHA1* hasher = NULL;
       
   481     
       
   482     LOG( _L("CDrmUdtHandler::CreateUdtRequestL") );
       
   483     delete iUdtRequest;
       
   484     
       
   485     if ( iObserver )
       
   486         {
       
   487         iStateInfo.iState = TUdtStateInfo::EUdtReguest;
       
   488         iStateInfo.iProgress = 0;
       
   489         iObserver->UdtProgressInfoL( iStateInfo );
       
   490         }
       
   491     
       
   492     hasher = CSHA1::NewL();
       
   493     CleanupStack::PushL( hasher );
       
   494     User::LeaveIfError( client.Connect() );
       
   495     CleanupClosePushL( client );
       
   496     client.SelectTrustedRootL( KNullDesC8 );
       
   497 
       
   498     LOG( _L("  Getting cert chain") );
       
   499     User::LeaveIfError( client.GetDeviceCertificateChainL( certChain ) );
       
   500     CleanupStack::PushL( listCleanup );
       
   501 
       
   502     LOG( _L("  Getting UDT data") );
       
   503     ReadUdtDataL( targetSer, udtVersion, rdb_data );
       
   504 
       
   505     LOG(_L8("RDB data:"));    
       
   506     LOGHEX(rdb_data)
       
   507     
       
   508     n = 0;
       
   509     for ( i = 0; i < certChain.Count(); i++ )
       
   510         {
       
   511         n = n + KLengthSize + certChain[i]->Size();
       
   512         }
       
   513     certBlock = HBufC8::NewL( n );
       
   514     CleanupStack::PushL( certBlock );
       
   515     ptr.Set( certBlock->Des() );
       
   516     for ( i = 0; i < certChain.Count(); i++ )
       
   517         {
       
   518         WriteIntToBlock( certChain[i]->Size(), intBuf, 0 );
       
   519         ptr.Append( intBuf );
       
   520         ptr.Append( *certChain[i] );
       
   521         }
       
   522 
       
   523     n = KVersionSize + 
       
   524         KMessageIdSize + 
       
   525         KLengthSize + 
       
   526         iOneTimePassword->Size() + 
       
   527         KLengthSize +
       
   528         certBlock->Size() + 
       
   529         KLengthSize +
       
   530         targetSer.Size() +
       
   531         rdb_data.Size() + 
       
   532         KLengthSize + 
       
   533         KSignatureLength;
       
   534         
       
   535     iUdtRequest = HBufC8::NewL( n );
       
   536     ptr.Set( iUdtRequest->Des() );
       
   537     WriteIntToBlock( n - (KVersionSize + KMessageIdSize + 
       
   538                      KLengthSize + KSignatureLength), intBuf, 0 );
       
   539     
       
   540     ptr.Append( KVersion );             // 1. version
       
   541     ptr.Append( KUdtRequestId );        // 2. request id
       
   542     ptr.Append( intBuf );               // 3. request length
       
   543     ptr.Append( *iOneTimePassword );    // 4. password
       
   544     WriteIntToBlock( certBlock->Size(), intBuf, 0 );
       
   545     ptr.Append( intBuf );               // 5. ceritificate block length
       
   546     ptr.Append( *certBlock );           // 6. ceritificate block
       
   547     WriteIntToBlock( targetSer.Size(), intBuf, 0 );
       
   548     ptr.Append( intBuf );               // 7. serial number length
       
   549     ptr.Append( targetSer );            // 8. original serial number
       
   550     ptr.Append( rdb_data );             // 9. RDB data
       
   551     WriteIntToBlock( udtVersion, intBuf, 0 );
       
   552     ptr.Append( intBuf );               // 10. UDT key version
       
   553     
       
   554     hasher->Update( ptr );
       
   555     hash.Append( 0 );
       
   556     hash.Append( KPadding255 );
       
   557     for ( i = 2; i < KSignatureLength - SHA1_HASH - 1; i++ )
       
   558         {
       
   559         hash.Append( 255 );
       
   560         }
       
   561     hash.Append( 0 );
       
   562     hash.Append( hasher->Final() );
       
   563     LOG(_L8("Hash:"));
       
   564     LOGHEX(hash);
       
   565     client.RsaSignL( hash, signature );
       
   566     CleanupStack::PushL(signature);
       
   567     ptr.Append( *signature );           // 11. signature
       
   568     LOG(_L8("Signature:"));
       
   569     LOGHEX((*signature));
       
   570     
       
   571     CleanupStack::PopAndDestroy( 5 );   // certBlock, listCleanup,
       
   572                                         // client, hasher, signature
       
   573     if ( iObserver )
       
   574         {
       
   575         iStateInfo.iState = TUdtStateInfo::EUdtReguest;
       
   576         iStateInfo.iProgress += 20;
       
   577         iObserver->UdtProgressInfoL( iStateInfo );
       
   578         }
       
   579         
       
   580     LOG(_L8("Request:"));
       
   581     LOGHEX((*iUdtRequest));
       
   582     }
       
   583     
       
   584     
       
   585 // ---------------------------------------------------------
       
   586 // CDrmUdtHandler::CreateStatusNotificationL()
       
   587 // ---------------------------------------------------------
       
   588 //    
       
   589 void CDrmUdtHandler::CreateStatusNotificationL()
       
   590     {
       
   591     LOG( _L("CDrmUdtHandler::CreateStatusNotificationL") );
       
   592     
       
   593     if ( iObserver )
       
   594         {
       
   595         iStateInfo.iState = TUdtStateInfo::EUdtStatusNotification;
       
   596         iStateInfo.iProgress += 20;
       
   597         iObserver->UdtProgressInfoL( iStateInfo );
       
   598         }
       
   599     
       
   600     delete iUdtRequest;
       
   601     iUdtRequest = NULL;
       
   602     iUdtRequest = HBufC8::NewL(64);
       
   603     TPtr8 ptr = iUdtRequest->Des();
       
   604     ptr.Append(0);
       
   605     ptr.Append(2);
       
   606     ptr.Append(*iOneTimePassword);
       
   607     iUdtError == EUdtOk ? ptr.Append(1) : ptr.Append(0);
       
   608     }
       
   609     
       
   610     
       
   611 // ---------------------------------------------------------
       
   612 // CDrmUdtHandler::ResponseReceivedL()
       
   613 // ---------------------------------------------------------
       
   614 //    
       
   615 void CDrmUdtHandler::ResponseReceivedL()
       
   616     {
       
   617     LOG( _L("CDrmUdtHandler::ResponseReceivedL") );
       
   618     __ASSERT_ALWAYS( iState == EResponseReceived, User::Invariant() );
       
   619     __ASSERT_ALWAYS( iUdtResponse, User::Invariant() );
       
   620     
       
   621     TPtrC8 udtRespPtr( *iUdtResponse );
       
   622     HBufC8* origDBKey = NULL;
       
   623     TPtrC8 origDBKeyPtr( KNullDesC8 );
       
   624     RDRMRightsClient rightsClient;
       
   625     TInt error = EUdtOk;
       
   626         
       
   627     LOGHEX((*iUdtResponse));
       
   628     
       
   629     // check response type
       
   630     switch ( udtRespPtr[1] )
       
   631         {
       
   632         case KUdtResponseId:
       
   633             {
       
   634             if ( iObserver )
       
   635                 {
       
   636                 iStateInfo.iState = TUdtStateInfo::EUdtKeyRestore;
       
   637                 iStateInfo.iProgress += 20;
       
   638                 iObserver->UdtProgressInfoL( iStateInfo );
       
   639                 }
       
   640             
       
   641             if ( udtRespPtr.Length() < KUdtResponseSize )
       
   642                 {
       
   643                 User::Leave( KErrCorrupt );
       
   644                 }
       
   645             origDBKeyPtr.Set( udtRespPtr.Mid( 2 ) );
       
   646             origDBKey = origDBKeyPtr.AllocLC();
       
   647             
       
   648             iUdtError = rightsClient.Connect();
       
   649             CleanupClosePushL( rightsClient );
       
   650             
       
   651             if ( !iUdtError )
       
   652                 {
       
   653                 iUdtError = rightsClient.InitiateUdt( origDBKeyPtr );
       
   654                 }
       
   655          
       
   656             CleanupStack::PopAndDestroy( 2 ); // origDBKey, rightsClient
       
   657             
       
   658             iRequestType = EStatusNotification;
       
   659             iState = ESendMessage;
       
   660             iStatus = KRequestPending;
       
   661             SetActive();
       
   662             SelfComplete( KErrNone );
       
   663             break;
       
   664             }
       
   665         case KStatusResponseId:
       
   666             {
       
   667             if ( iObserver )
       
   668                 {
       
   669                 iStateInfo.iState = TUdtStateInfo::EUdtStatusNotification;
       
   670                 iStateInfo.iProgress += 20;
       
   671                 iObserver->UdtProgressInfoL( iStateInfo );
       
   672                 }
       
   673             
       
   674             iState = EComplete;
       
   675             iStatus = KRequestPending;
       
   676             SetActive();
       
   677             
       
   678             if ( iUdtError )
       
   679                 {
       
   680                 error = EUdtKeyRestoreFailed;
       
   681                 iUdtError = EUdtOk;
       
   682                 }
       
   683             SelfComplete( error );
       
   684             break;
       
   685             }
       
   686         case KErrorResponseId:
       
   687             {
       
   688             if ( udtRespPtr.Length() >= 3 && udtRespPtr[2] == KClientErrorValue )
       
   689                 {
       
   690                 error = EUdtClientError;
       
   691                 }
       
   692             else
       
   693                 {
       
   694                 error = EUdtServerError;
       
   695                 }
       
   696             
       
   697             iState = EComplete;
       
   698             iStatus = KRequestPending;            
       
   699             SetActive();
       
   700             SelfComplete( error );
       
   701             break;
       
   702             }
       
   703         default:
       
   704             {
       
   705             User::Leave( KErrNotSupported );
       
   706             }
       
   707         }  
       
   708     }
       
   709     
       
   710 // ---------------------------------------------------------
       
   711 // CDrmUdtHandler::SetHeaderL()
       
   712 // ---------------------------------------------------------
       
   713 //
       
   714 void CDrmUdtHandler::SetHeaderL(RHTTPHeaders aHeaders, TInt aHdrField, const TDesC8& aHdrValue)
       
   715 	{
       
   716     LOG( _L("CDrmUdtHandler::SetHeaderL") );
       
   717     RStringF valStr = iSession.StringPool().OpenFStringL(aHdrValue);
       
   718     THTTPHdrVal val(valStr);
       
   719     aHeaders.SetFieldL(iSession.StringPool().StringF(aHdrField,RHTTPSession::GetTable()), val);
       
   720     valStr.Close();
       
   721 	}
       
   722     
       
   723 
       
   724 // ---------------------------------------------------------
       
   725 // CDrmUdtHandler::Complete()
       
   726 // ---------------------------------------------------------
       
   727 //
       
   728 void CDrmUdtHandler::Complete()
       
   729     {
       
   730     LOG( _L("CDrmUdtHandler::Complete") );
       
   731     
       
   732     delete iUri;
       
   733     iUri = NULL;
       
   734     delete iUdtResponse;
       
   735     iUdtResponse = NULL;
       
   736     delete iUdtRequest;
       
   737     iUdtRequest = NULL;
       
   738     delete iOneTimePassword;
       
   739     iOneTimePassword = NULL;
       
   740     
       
   741     if( iTimeout )
       
   742     	{
       
   743     	iTimeout->Cancel();
       
   744     	}
       
   745     	
       
   746     if ( iObserver )
       
   747         {
       
   748         iStateInfo.iState = TUdtStateInfo::EUdtComplete;
       
   749         iStateInfo.iProgress = 100;
       
   750         iStateInfo.iError = iError;
       
   751         TRAPD(ignore, iObserver->UdtProgressInfoL( iStateInfo ));
       
   752         }  
       
   753     
       
   754     User::RequestComplete( iParentStatus, iError );
       
   755     iParentStatus = NULL;
       
   756     }
       
   757 
       
   758 
       
   759 // ---------------------------------------------------------
       
   760 // CDrmUdtHandler::CDrmUdtModule()
       
   761 // ---------------------------------------------------------
       
   762 //
       
   763 CDrmUdtHandler::CDrmUdtHandler(): CActive( CActive::EPriorityStandard )
       
   764     {
       
   765     LOG( _L("CDrmUdtHandler::CDrmUdtHandler") );
       
   766     CActiveScheduler::Add( this );
       
   767     }
       
   768 
       
   769 
       
   770 // ---------------------------------------------------------
       
   771 // CDrmUdtHandler::SelfComplete()
       
   772 // ---------------------------------------------------------
       
   773 //
       
   774 void CDrmUdtHandler::SelfComplete( TInt aResult )
       
   775     {
       
   776     LOG( _L("CDrmUdtHandler::SelfComplete") );
       
   777     if ( iStatus == KRequestPending )
       
   778         {
       
   779         TRequestStatus* ownStatus = &iStatus;
       
   780         User::RequestComplete( ownStatus, aResult );
       
   781         }
       
   782     else
       
   783         {
       
   784         if ( aResult != KErrNone )
       
   785             {
       
   786             iStatus = aResult;
       
   787             }
       
   788         }
       
   789     }
       
   790 
       
   791 
       
   792 // ---------------------------------------------------------
       
   793 // CDrmUdtHandler::MHFRunL()
       
   794 // ---------------------------------------------------------
       
   795 //
       
   796 void CDrmUdtHandler::MHFRunL( RHTTPTransaction  /*aTransaction */, 
       
   797 								const THTTPEvent& aEvent )
       
   798     {
       
   799     LOGINT( _L("CDrmUdtHandler::MHFRunL: %d"), aEvent.iStatus );
       
   800     iTimeout->Cancel();
       
   801     iTimeout->Start( KUdtTimeoutValue,
       
   802     				 KUdtTimeoutValue, 
       
   803     				 TCallBack( StaticTimeOut,this ) );    				 
       
   804 
       
   805     switch ( aEvent.iStatus )
       
   806         {
       
   807         case THTTPEvent::EGotResponseHeaders:
       
   808             {
       
   809             HandleResponseHeadersL( iTransaction.Response() );
       
   810             break;
       
   811             }
       
   812 
       
   813         case THTTPEvent::EGotResponseBodyData:
       
   814             {
       
   815             TInt ret( KErrNone );
       
   816             MHTTPDataSupplier* body = iTransaction.Response().Body();
       
   817             TPtrC8 ptr;
       
   818             body->GetNextDataPart( ptr );
       
   819 			ret = AppendResponseData( ptr );
       
   820             body->ReleaseData();
       
   821             User::LeaveIfError( ret );
       
   822             break;
       
   823             }
       
   824 
       
   825         case THTTPEvent::EFailed:
       
   826             {
       
   827             if ( iError == KErrNone )
       
   828                 {
       
   829                 iError = EUdtServerError;
       
   830                 }
       
   831         	iTransaction.Close();
       
   832             SelfComplete( iError );
       
   833             break;
       
   834             }
       
   835 
       
   836         case THTTPEvent::ESucceeded:
       
   837             {        
       
   838             iTransaction.Close();
       
   839             SelfComplete( iError );
       
   840             break;
       
   841             }
       
   842 
       
   843         case THTTPEvent::ERedirectRequiresConfirmation:
       
   844             {
       
   845             iTransaction.SubmitL();
       
   846             }
       
   847 
       
   848         default:
       
   849             {
       
   850             if( aEvent.iStatus == KErrHttpRedirectUseProxy )
       
   851                 {
       
   852                 }
       
   853             else
       
   854                 {                
       
   855                 User::LeaveIfError( aEvent.iStatus );
       
   856                 }
       
   857             break;
       
   858             }
       
   859         }
       
   860 
       
   861     }
       
   862 
       
   863 // ---------------------------------------------------------
       
   864 // CDrmUdtHandler::MHFRunError()
       
   865 // ---------------------------------------------------------
       
   866 //
       
   867 TInt CDrmUdtHandler::MHFRunError (
       
   868         TInt aError,
       
   869         RHTTPTransaction /* aTransaction */,
       
   870         const THTTPEvent& /* aEvent */
       
   871         )
       
   872     {
       
   873     LOG( _L("CDrmUdtHandler::MHFRunError") );
       
   874     iTransaction.Close();
       
   875     iError = aError;
       
   876     SelfComplete( iError );
       
   877     return KErrNone;
       
   878     }
       
   879 
       
   880 // ---------------------------------------------------------
       
   881 // CDrmUdtHandler::HandleResponseHeadersL()
       
   882 // ---------------------------------------------------------
       
   883 //
       
   884 void CDrmUdtHandler::HandleResponseHeadersL( RHTTPResponse aHttpResponse )
       
   885     {
       
   886     LOG( _L("CDrmUdtHandler::HandleResponseHeadersL") );
       
   887     RHTTPHeaders headers = aHttpResponse.GetHeaderCollection();
       
   888     
       
   889     TInt httpCode = aHttpResponse.StatusCode();
       
   890     TBool status;
       
   891     
       
   892     status = CheckHttpCode( httpCode );
       
   893     
       
   894     if ( status )
       
   895     	{
       
   896         RStringF contentTypeStr;
       
   897         THTTPHdrVal contentTypeVal;
       
   898         TPtrC8 ptrContentType(KNullDesC8);
       
   899 		RStringPool srtPool;
       
   900 		srtPool = iSession.StringPool();
       
   901         
       
   902         contentTypeStr = srtPool.StringF( HTTP::EContentType, RHTTPSession::GetTable() );										
       
   903     	User::LeaveIfError( headers.GetField( contentTypeStr, 0, contentTypeVal ) );
       
   904     	
       
   905     	if ( contentTypeVal.StrF().DesC().CompareF( KUdtContentType() ) != KErrNone )
       
   906     	    {
       
   907 			User::Leave( KErrNotSupported );
       
   908     	    }
       
   909        
       
   910     	}
       
   911     if ( aHttpResponse.HasBody() )
       
   912         {
       
   913         TInt dataSize = aHttpResponse.Body()->OverallDataSize();
       
   914         if ( dataSize >= 0 )
       
   915             {
       
   916             HBufC8* buf = HBufC8::NewL( dataSize );
       
   917             delete iUdtResponse;
       
   918             iUdtResponse = buf;
       
   919             }
       
   920         }
       
   921     }
       
   922      
       
   923 // ---------------------------------------------------------
       
   924 // CDrmUdtHandler::CheckHttpCode()
       
   925 // ---------------------------------------------------------
       
   926 //
       
   927 TBool CDrmUdtHandler::CheckHttpCode( TInt aHttpStatus )
       
   928 	{
       
   929 	LOGINT(_L("CDrmUdtHandler::CheckHttpCode: %d"), aHttpStatus);
       
   930     if ( HTTPStatus::IsInformational( aHttpStatus ) )
       
   931         {
       
   932         // 1xx
       
   933         // Informational messages.
       
   934         iError = EUdtServerError;
       
   935         return EFalse;  
       
   936         }
       
   937     else if ( aHttpStatus == HTTPStatus::EOk ||
       
   938               aHttpStatus == HTTPStatus::ENonAuthoritativeInfo )
       
   939         {
       
   940         // 200 OK
       
   941         // 203 Non-Authoritative Information
       
   942         iError = EUdtOk;
       
   943         return ETrue;        
       
   944         }
       
   945     else if ( HTTPStatus::IsSuccessful( aHttpStatus ) )
       
   946         {
       
   947         // 2xx
       
   948         // Success codes without an usable body.
       
   949         iError = EUdtServerError;
       
   950         return EFalse; 
       
   951         }
       
   952     else if ( aHttpStatus == HTTPStatus::EUnauthorized ||
       
   953               aHttpStatus == HTTPStatus::EProxyAuthenticationRequired )
       
   954         {
       
   955         // 401 Unauthorized
       
   956         // 407 Proxy authentication required
       
   957         iError = EUdtInvalidServerAddress;
       
   958         return EFalse; 
       
   959         }
       
   960     else if ( aHttpStatus == HTTPStatus::ENotFound ||
       
   961               aHttpStatus == HTTPStatus::EGone )
       
   962         {
       
   963         // 404 Not found
       
   964         // 410 Gone
       
   965         iError = EUdtInvalidServerAddress;
       
   966         return EFalse; 
       
   967         }
       
   968     else if ( HTTPStatus::IsClientError( aHttpStatus ) )
       
   969         {
       
   970         // 4xx
       
   971         iError = EUdtInvalidServerAddress;
       
   972         return EFalse; 
       
   973         }
       
   974     else if ( aHttpStatus == HTTPStatus::EHTTPVersionNotSupported )
       
   975         {
       
   976         // 505 HTTP Version Not Supported
       
   977         iError = EUdtServerError;
       
   978         return EFalse; 
       
   979         }
       
   980     else if ( HTTPStatus::IsServerError( aHttpStatus ) )
       
   981         {
       
   982         // 5xx
       
   983         iError = EUdtServerError;
       
   984         return EFalse; 
       
   985         }
       
   986     else 
       
   987         {
       
   988         // Everything else.
       
   989         iError = EUdtServerError;
       
   990         }
       
   991     return EFalse; 
       
   992 	}
       
   993 
       
   994 
       
   995 // ---------------------------------------------------------
       
   996 // CDrmUdtModule::AppendResponseData()
       
   997 // ---------------------------------------------------------
       
   998 //
       
   999 TInt CDrmUdtHandler::AppendResponseData( const TDesC8& aDataChunk )
       
  1000     {
       
  1001     LOG( _L("CDrmUdtHandler::AppendResponseData") );
       
  1002     TInt needed = iUdtResponse->Des().Length() + aDataChunk.Length();
       
  1003     if ( iUdtResponse->Des().MaxLength() < needed )
       
  1004         {
       
  1005         HBufC8* buf = iUdtResponse->ReAlloc( needed );
       
  1006         if ( buf )
       
  1007             {
       
  1008             iUdtResponse = buf;
       
  1009             }
       
  1010         else
       
  1011             {
       
  1012             return KErrNoMemory;
       
  1013             }
       
  1014         }
       
  1015     iUdtResponse->Des().Append( aDataChunk );
       
  1016     return KErrNone;
       
  1017     }
       
  1018     
       
  1019 // -----------------------------------------------------------------------------
       
  1020 // CDrmUdtHandler::StaticTimeOut()
       
  1021 // -----------------------------------------------------------------------------
       
  1022 //
       
  1023 TInt CDrmUdtHandler::StaticTimeOut( TAny* aPointer )
       
  1024     {  
       
  1025     LOG( _L("CDrmUdtHandler::StaticTimeOut") );
       
  1026     CDrmUdtHandler* itself = STATIC_CAST(CDrmUdtHandler*, aPointer);
       
  1027     if(itself)
       
  1028         {
       
  1029         itself->TimeOut();
       
  1030         }
       
  1031     return KErrNone;
       
  1032     }
       
  1033  
       
  1034     
       
  1035 // -----------------------------------------------------------------------------
       
  1036 // CDrmUdtHandler::TimeOut()
       
  1037 // -----------------------------------------------------------------------------
       
  1038 //
       
  1039 void CDrmUdtHandler::TimeOut()
       
  1040     {
       
  1041     LOG( _L("CDrmUdtHandler::TimeOut") );
       
  1042     iTransaction.Close();
       
  1043     iError = KErrTimedOut;
       
  1044     SelfComplete( iError );
       
  1045     }
       
  1046 
       
  1047 
       
  1048 // ---------------------------------------------------------
       
  1049 // CDrmUdtHandler::GetNextDataPart()
       
  1050 // ---------------------------------------------------------
       
  1051 //
       
  1052 TBool CDrmUdtHandler::GetNextDataPart( TPtrC8& aDataPart )
       
  1053     {
       
  1054     LOG( _L("CDrmUdtHandler::GetNextDataPart") );
       
  1055     aDataPart.Set( iUdtRequest->Des() );
       
  1056     return ETrue;
       
  1057     }
       
  1058 
       
  1059 // ---------------------------------------------------------
       
  1060 // CDrmUdtHandler::ReleaseData()
       
  1061 // ---------------------------------------------------------
       
  1062 //
       
  1063 void CDrmUdtHandler::ReleaseData()
       
  1064     {
       
  1065     LOG( _L("CDrmUdtHandler::ReleaseData") );
       
  1066     }
       
  1067 
       
  1068 // ---------------------------------------------------------
       
  1069 // CDrmUdtHandler::OverallDataSize()
       
  1070 // ---------------------------------------------------------
       
  1071 //
       
  1072 TInt CDrmUdtHandler::OverallDataSize()
       
  1073     {
       
  1074     LOG( _L("CDrmUdtHandler::OverallDataSize") );
       
  1075     return iUdtRequest->Des().Size();
       
  1076     }
       
  1077 
       
  1078 // ---------------------------------------------------------
       
  1079 // CDrmUdtHandler::Reset()
       
  1080 // ---------------------------------------------------------
       
  1081 //
       
  1082 TInt CDrmUdtHandler::Reset()
       
  1083     {
       
  1084     LOG( _L("CDrmUdtHandler::Reset") );
       
  1085     return KErrNone;
       
  1086     }
       
  1087 
       
  1088 // ---------------------------------------------------------
       
  1089 // CDrmUdtHandler::ReadUdtDataL
       
  1090 //
       
  1091 // ---------------------------------------------------------
       
  1092 //
       
  1093 void CDrmUdtHandler::ReadUdtDataL(
       
  1094     TDes8& aTargetSerialNumber,
       
  1095     TInt& aUdtKeyVersion,
       
  1096     TDes8& aEncryptedRdbData )
       
  1097     {
       
  1098     RDRMRightsClient rightsClient;
       
  1099     HBufC* serialNum = NULL;
       
  1100 
       
  1101     LOG( _L("CDrmUdtHandler::ReadUdtDataL") );
       
  1102     User::LeaveIfError( rightsClient.Connect() );
       
  1103     CleanupClosePushL( rightsClient );
       
  1104     serialNum = SerialNumberL();
       
  1105     
       
  1106     aTargetSerialNumber.Copy( *serialNum );
       
  1107 
       
  1108     aUdtKeyVersion = 0;
       
  1109     User::LeaveIfError( rightsClient.GetUdtData( aEncryptedRdbData ) );
       
  1110     if( !aEncryptedRdbData.Length() )
       
  1111         {
       
  1112         User::Leave( KErrNotFound );
       
  1113         }
       
  1114     CleanupStack::PopAndDestroy(); // rightsClient
       
  1115     }
       
  1116     
       
  1117 // ---------------------------------------------------------
       
  1118 // CDrmUdtHandler::ReadUdtDataL
       
  1119 //
       
  1120 // ---------------------------------------------------------
       
  1121 //    
       
  1122 HBufC* CDrmUdtHandler::SerialNumberL()
       
  1123     {
       
  1124     TInt error( KErrNone );
       
  1125     TInt count( 0 );
       
  1126     TInt count2( 0 );
       
  1127     TUint32 caps( 0 );
       
  1128     HBufC* imei = NULL;
       
  1129 
       
  1130 #ifndef __WINS__
       
  1131     LOG( _L("CDrmUdtHandler::SerialNumberL") );
       
  1132 
       
  1133     RTelServer etelServer;
       
  1134     RMobilePhone phone;
       
  1135     
       
  1136     for ( TUint8 i = 0; i < 3; ++i )
       
  1137         {
       
  1138         error = etelServer.Connect();
       
  1139         if ( error )
       
  1140             {
       
  1141             User::After( TTimeIntervalMicroSeconds32( 100000 ) );
       
  1142             }
       
  1143         }
       
  1144     
       
  1145     User::LeaveIfError( error );
       
  1146     CleanupClosePushL( etelServer );
       
  1147 
       
  1148     LOG( _L("  Connected to ETEL") );
       
  1149     
       
  1150     User::LeaveIfError( etelServer.LoadPhoneModule( KMmTsyModuleName ) );
       
  1151     
       
  1152     LOG( _L("  Phone Module loaded") );
       
  1153 
       
  1154     TUnloadModule unload;
       
  1155     unload.iServer = &etelServer;
       
  1156     unload.iName = &KMmTsyModuleName;
       
  1157     
       
  1158     TCleanupItem item( DoUnloadPhoneModule, &unload );
       
  1159     CleanupStack::PushL( item );
       
  1160     
       
  1161     User::LeaveIfError( etelServer.EnumeratePhones( count ) );
       
  1162     
       
  1163     LOG( _L("  Phones enumerated") );
       
  1164 
       
  1165     for ( count2 = 0; count2 < count; ++count2 )
       
  1166         {
       
  1167         RTelServer::TPhoneInfo phoneInfo;
       
  1168         User::LeaveIfError( etelServer.GetTsyName( count2, phoneInfo.iName ) );
       
  1169         
       
  1170         LOG( _L("    Got TSY module") );
       
  1171         LOG( phoneInfo.iName );
       
  1172         if ( phoneInfo.iName.CompareF( KMmTsyModuleName ) == 0 )
       
  1173             {
       
  1174             User::LeaveIfError( etelServer.GetPhoneInfo( count2, phoneInfo ) );
       
  1175             LOG( _L("    Got phone info") );
       
  1176             User::LeaveIfError( phone.Open( etelServer, phoneInfo.iName ) );
       
  1177             LOG( _L("    Opened phone") );
       
  1178             CleanupClosePushL( phone );
       
  1179             break;
       
  1180             }
       
  1181         }
       
  1182         
       
  1183     if ( count2 == count )
       
  1184         {
       
  1185         // Not found.
       
  1186         LOG( _L("  No phone found") );
       
  1187         User::Leave( KErrNotFound );
       
  1188         }
       
  1189     
       
  1190     LOG( _L("  Got phone") );
       
  1191 
       
  1192     User::LeaveIfError( phone.GetIdentityCaps( caps ) );
       
  1193 
       
  1194     LOG( _L("  Got Caps") );
       
  1195 
       
  1196     if ( caps & RMobilePhone::KCapsGetSerialNumber )
       
  1197         {
       
  1198         RMobilePhone::TMobilePhoneIdentityV1 id;
       
  1199         TRequestStatus status;
       
  1200         
       
  1201         phone.GetPhoneId( status, id );
       
  1202         User::WaitForRequest( status );
       
  1203         
       
  1204         User::LeaveIfError( status.Int() );
       
  1205         
       
  1206         imei = id.iSerialNumber.AllocL();
       
  1207         
       
  1208         LOG( _L("  Got serial number") );
       
  1209 
       
  1210         CleanupStack::PopAndDestroy( 3 ); // phone, item, etelServer
       
  1211         
       
  1212         return imei;
       
  1213         }
       
  1214     
       
  1215     User::Leave( KErrNotFound );
       
  1216     
       
  1217     // Never happens...
       
  1218     return imei;
       
  1219 
       
  1220 #else
       
  1221     _LIT( KDefaultSerialNumber, "123456789123456789" );
       
  1222     imei = KDefaultSerialNumber().AllocL();
       
  1223         
       
  1224     return imei;
       
  1225 #endif
       
  1226     }
       
  1227  
       
  1228