--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/videofeeds/clientapi/src/ciptvsecureprovisioningparameters.cpp Mon Jan 18 20:21:12 2010 +0200
@@ -0,0 +1,543 @@
+/*
+* Copyright (c) 2007-2008 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of the License "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description:
+*
+*/
+
+
+
+
+
+// INCLUDE FILES
+#include "IptvDebug.h"
+#include <sysutil.h>
+
+#include <3des.h> // For C3DES
+#include <centralrepository.h> // link against centralrepository.lib
+#include <e32math.h>
+#include <mmtsy_names.h>
+
+#include "ciptvsecureprovisioningparameters.h"
+
+// EXTERNAL DATA STRUCTURES
+
+// EXTERNAL FUNCTION PROTOTYPES
+
+// CONSTANTS
+const TUid KCRUidPnpUtil = {0x1020433A};
+const TInt KMaxKeyInfoLength = 20;
+const TInt KNonceLength = 8;
+const TUint32 KPnPUtilNonce = 0x00000002;
+const TUint32 KPnPUtilHomeMcc = 0x00000004;
+const TUint32 KPnPUtilHomeMnc = 0x00000005;
+const TUint32 KPnPUtilKeyInfo = 0x00000008;
+_LIT8( K3DesKey, "111111111111111111111111" );
+
+// MACROS
+
+// LOCAL CONSTANTS AND MACROS
+
+// MODULE DATA STRUCTURES
+
+// LOCAL FUNCTION PROTOTYPES
+
+// FORWARD DECLARATIONS
+
+// ============================= LOCAL FUNCTIONS ===============================
+
+// ============================ MEMBER FUNCTIONS ===============================
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::ConstructL
+// Symbian 2nd phase constructor can leave.
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::ConstructL()
+ {
+ User::LeaveIfError( iServer.Connect() );
+ User::LeaveIfError( iServer.LoadPhoneModule( KMmTsyModuleName ) );
+ User::LeaveIfError( iPhone.Open( iServer, KMmTsyPhoneName ) );
+ User::LeaveIfError( iPhone.Initialise() );
+
+ iRepository = CRepository::NewL( KCRUidPnpUtil );
+
+#ifndef __WINS__ // calling C3DESEncryptor::NewL crashes emulator
+ iEncryptor = C3DESEncryptor::NewL( K3DesKey );
+#endif
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::NewL
+// Two-phased constructor.
+// -----------------------------------------------------------------------------
+//
+CIptvSecureProvisioningParameters* CIptvSecureProvisioningParameters::NewL()
+ {
+ CIptvSecureProvisioningParameters* self = new( ELeave ) CIptvSecureProvisioningParameters;
+
+ CleanupStack::PushL( self );
+ self->ConstructL();
+ CleanupStack::Pop(self);
+
+ return self;
+ }
+
+
+// Destructor
+CIptvSecureProvisioningParameters::~CIptvSecureProvisioningParameters()
+ {
+ delete iRepository;
+#ifndef __WINS__
+ delete iEncryptor;
+#endif
+ iPhone.Close();
+ iServer.Close();
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::SecureProvisioningUrlParametersL()
+// -----------------------------------------------------------------------------
+//
+HBufC* CIptvSecureProvisioningParameters::SecureProvisioningUrlParametersL()
+ {
+ IPTVLOGSTRING_LOW_LEVEL("CIptvService::SecureProvisioningUrlParametersL() start");
+
+ // home country code and home network id
+
+ FetchHomeNetworkInfoL();
+
+ RMobilePhone::TMobilePhoneNetworkCountryCode homeMcc = HomeMccL();
+ RMobilePhone::TMobilePhoneNetworkIdentity homeMnc = HomeMncL();
+
+ const TInt HomeCountryCodeLength = 4;
+ const TInt HomeNetworkCodeLength = 8;
+ TBuf<HomeCountryCodeLength> hmcc16;
+ TBuf<HomeNetworkCodeLength> hmnc16;
+ hmcc16.Copy( homeMcc );
+ hmnc16.Copy( homeMnc );
+
+ // keyinfo, nonce
+ TBuf8<KMaxKeyInfoLength> keyInfo;
+ TBuf<KMaxKeyInfoLength> keyInfo16;
+ GetKeyInfoL( keyInfo );
+ keyInfo16.Copy( keyInfo );
+ TBuf8<KNonceLength> nonce;
+ TBuf<KNonceLength> nonce16;
+ TInt timeout( 0 );
+ CreateNewNonceL( timeout, nonce );
+ nonce16.Copy( nonce );
+
+ // product model
+ TBuf8<KSysUtilVersionTextLength> deviceinfo;
+ TBuf<KSysUtilVersionTextLength> deviceinfo16;
+ FetchProductModelL( deviceinfo );
+ deviceinfo16.Copy( deviceinfo );
+
+ // 1. Keyinfo
+ // 2. Nonce
+ // 3. Home MCC
+ // 4. Home MNC
+ // 5. Network (current) MCC
+ // 6. Network MNC
+ // 7. Version
+ // 8. deviceinfo
+
+ _LIT( KVersionDes, "NPnP-MSS60-1.01" );
+ const TInt KVersionDesLength = 16;
+
+ TBuf<KVersionDesLength> version16;
+ version16 = KVersionDes;
+
+ // These are for the test service, comments kept here until we get the real thing up.
+ //version16 = _L("email-0.1");
+ //deviceinfo16 = _L("n80");
+
+ _LIT(KParameterFormatDes,
+ "?sType=4&Key=%S&Nonce=%S&MCC=%S&MNC=%S&cVersion=%S&deviceinfo=%S&VCSW=1&action=activate");
+ const TInt KParameterFormatDesLength = 150;
+
+ HBufC* parameters = HBufC::NewL(
+ KParameterFormatDesLength +
+ keyInfo16.Length() +
+ nonce16.Length() +
+ hmcc16.Length() +
+ hmnc16.Length() +
+ KVersionDesLength +
+ deviceinfo16.Length() );
+
+ TPtr parametersPtr( parameters->Des() );
+
+ parametersPtr.Format(
+ KParameterFormatDes,
+ &keyInfo16,
+ &nonce16,
+ &hmcc16,
+ &hmnc16,
+ &version16,
+ &deviceinfo16);
+
+ IPTVLOGSTRING2_HIGH_LEVEL( "%S", ¶metersPtr );
+
+ IPTVLOGSTRING_LOW_LEVEL("CIptvService::SecureProvisioningUrlParametersL() exit");
+ return parameters;
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::FetchProductModelL()
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::FetchProductModelL( TDes8& aModel )
+ {
+ HBufC* tmpVersion = HBufC::NewLC( KSysUtilVersionTextLength );
+ TPtr ptr( tmpVersion->Des() );
+ User::LeaveIfError( SysUtil::GetSWVersion( ptr ) );
+
+ _LIT(KVerStrStart,"V ");
+ _LIT(KVerStrEnd,"\n");
+
+ TInt pos1 = tmpVersion->Find(KVerStrStart);
+ TInt pos2 = tmpVersion->Find(KVerStrEnd);
+ TInt verlen = ((TDesC)(KVerStrStart)).Length();
+
+ // Example version string:
+ // V 10.0.053
+ // 21-09-07
+ // RM-179
+ // (c) Nokia N81 (92.03)
+
+ // RM-179 is extracted from it
+
+ if( pos1==KErrNotFound) // Version does not start with "V "
+ {
+ pos1=0;
+ verlen=0;
+ }
+
+ if( (pos1!=KErrNotFound)
+ && (pos2!=KErrNotFound)
+ && (pos2 > (pos1 + verlen) )
+ )
+ {
+ TPtrC ptrSeek(ptr);
+ pos1 = ptrSeek.Find(KVerStrEnd);
+ if(pos1>=0)
+ {
+ ptrSeek.Set(ptrSeek.Mid(pos1+1)); //removes "V 10.0.053"
+ pos1 = ptrSeek.Find(KVerStrEnd);
+ if( pos1 >= 0 )
+ {
+ ptrSeek.Set(ptrSeek.Mid(pos1+1)); // removes "21-09-07"
+ pos1 = ptrSeek.Find(KVerStrEnd);
+ if( pos1 < 0 )
+ {
+ ptrSeek.Set(ptrSeek.Mid(1));
+ aModel.Copy(ptrSeek);
+ }
+ else if( pos1 > 0 )
+ {
+ ptrSeek.Set(ptrSeek.Mid(1,pos1-1));
+ aModel.Copy(ptrSeek);
+ }
+ }
+ }
+ }
+ CleanupStack::PopAndDestroy();
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::FetchHomeNetworkInfoL
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::FetchHomeNetworkInfoL()
+ {
+ // Get home (sim) MCC&MNC info
+ RMobilePhone::TMobilePhoneNetworkInfoV1 info;
+ RMobilePhone::TMobilePhoneNetworkInfoV1Pckg infoPckg( info );
+#ifndef __WINS__
+ TRequestStatus status( KRequestPending );
+ iPhone.GetHomeNetwork( status, infoPckg );
+ User::WaitForRequest( status );
+ User::LeaveIfError( status.Int() );
+#else
+ info.iCountryCode.Copy( _L("244") );
+ info.iNetworkId.Copy( _L("05") );
+#endif
+
+ RMobilePhone::TMobilePhoneNetworkIdentity formattedMnc;
+ FormatMncCodeL( info.iCountryCode, info.iNetworkId, formattedMnc );
+ SetHomeMncL( formattedMnc );
+ SetHomeMccL( info.iCountryCode );
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::FormatMncCodeL
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::FormatMncCodeL(
+ const RMobilePhone::TMobilePhoneNetworkCountryCode aMcc,
+ const RMobilePhone::TMobilePhoneNetworkIdentity aUnformattedMnc,
+ RMobilePhone::TMobilePhoneNetworkIdentity& aFormattedMnc )
+ {
+ RMobilePhone::TMobilePhoneNetworkIdentity formattedMnc;
+
+ // Check that codes only contain valid characters
+ TInt mncValue(0);
+ TInt mccValue(0);
+
+ TLex mncParser( aUnformattedMnc );
+ TInt err = mncParser.Val( mncValue );
+ if( err != KErrNone )
+ {
+ User::Leave( KErrCorrupt );
+ }
+
+ TLex mccParser( aMcc );
+ err = mccParser.Val( mccValue );
+ if( err != KErrNone )
+ {
+ User::Leave( KErrCorrupt );
+ }
+
+ // In N7610 the MNC given by RMobilePhone::GetHomeNetwork is
+ // always three digits
+ // But for example in N6630 the MNC seems to be correctly formatted
+
+ // The initial value is the given MNC:
+ formattedMnc.Copy( aUnformattedMnc );
+
+ // Reformat only if needed
+ if( aUnformattedMnc.Length() == 3 )
+ {
+ // Assume two digits, exceptions follow
+ formattedMnc.Copy( aUnformattedMnc.Left(2) );
+
+ if( aMcc.Compare( _L("302") ) == 0 ||
+ aMcc.Compare( _L("346") ) == 0 ||
+ aMcc.Compare( _L("348") ) == 0 ||
+ aMcc.Compare( _L("356") ) == 0 ||
+ aMcc.Compare( _L("365") ) == 0 ||
+ aMcc.Compare( _L("376") ) == 0 ||
+ aMcc.Compare( _L("467") ) == 0 ||
+ aMcc.Compare( _L("732") ) == 0 )
+ {
+ // MNC should be three digits
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ else if( aMcc.Compare( _L("310") ) == 0 )
+ {
+ // MNC is always three digits in this case
+ // For example: 000, 011, 110, 020, 200, ...
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ else if( aMcc.Compare( _L("311") ) == 0 )
+ {
+ // 3 digit (USA) some exceptions
+
+ // See previous case for comments
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+
+ else if( aMcc.Compare( _L("338") ) == 0 )
+ {
+ // 2 digit, but 3 digit if 180 (JAM)
+ if( aUnformattedMnc.Compare( _L("180") ) == 0 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("342") ) == 0 )
+ {
+ // 2 digit, but 3 digit if larger than 510
+ if( mncValue >= 510 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("344") ) == 0 )
+ {
+ // 2 digit, but 3 digit if larger than 310
+ if( mncValue >= 310 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("352") ) == 0 )
+ {
+ // 2 digit, but 3 digit if smaller than 300
+ if( mncValue < 300 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("358") ) == 0 )
+ {
+ // 2 digit, but 3 digit if smaller than 300
+ if( mncValue < 300 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("360") ) == 0 )
+ {
+ // 2 digit, but 3 digit if 110
+ if( aUnformattedMnc.Compare( _L("110") ) == 0 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("362") ) == 0 )
+ {
+ // 2 digit, but 3 digit if larger than 920
+ if( mncValue >= 920 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("366") ) == 0 )
+ {
+ // 2 digit, but 3 digit if 110
+ if( aUnformattedMnc.Compare( _L("110") ) == 0 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ else if( aMcc.Compare( _L("722") ) == 0 )
+ {
+ // 2 digit, but 3 digit if 310
+ if( aUnformattedMnc.Compare( _L("310") ) == 0 )
+ {
+ formattedMnc.Copy( aUnformattedMnc );
+ }
+ }
+ }
+ aFormattedMnc.Copy( formattedMnc );
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::HomeMccL
+// -----------------------------------------------------------------------------
+//
+const RMobilePhone::TMobilePhoneNetworkCountryCode CIptvSecureProvisioningParameters::HomeMccL()
+ {
+ RMobilePhone::TMobilePhoneNetworkIdentity mcc;
+ User::LeaveIfError( iRepository->Get( KPnPUtilHomeMcc, mcc ) );
+
+ return mcc;
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::SetHomeMncL
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::SetHomeMncL( const RMobilePhone::TMobilePhoneNetworkIdentity aMnc )
+ {
+ User::LeaveIfError( iRepository->Set( KPnPUtilHomeMnc, aMnc ) );
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::HomeMncL
+// -----------------------------------------------------------------------------
+//
+const RMobilePhone::TMobilePhoneNetworkIdentity CIptvSecureProvisioningParameters::HomeMncL()
+ {
+ RMobilePhone::TMobilePhoneNetworkIdentity mnc;
+ User::LeaveIfError( iRepository->Get( KPnPUtilHomeMnc, mnc ) );
+ return mnc;
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::SetHomeMccL
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::SetHomeMccL( const RMobilePhone::TMobilePhoneNetworkCountryCode aMcc )
+ {
+ User::LeaveIfError( iRepository->Set( KPnPUtilHomeMcc, aMcc ) );
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::GetKeyInfoL
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::GetKeyInfoL( TDes8& aKeyInfo )
+ {
+ if( aKeyInfo.MaxLength() < KMaxKeyInfoLength )
+ {
+ User::Leave( KErrArgument );
+ }
+ // read keyinfo from cenrep
+ TBuf<KMaxKeyInfoLength> buffer;
+ User::LeaveIfError( iRepository->Get( KPnPUtilKeyInfo, buffer) );
+ aKeyInfo.Copy( buffer );
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::CreateNewNonceL
+// -----------------------------------------------------------------------------
+//
+void CIptvSecureProvisioningParameters::CreateNewNonceL( const TUint /*aTimeOut*/, TDes8& aNonce )
+ {
+ if( aNonce.MaxLength() < KNonceLength )
+ {
+ User::Leave( KErrArgument );
+ }
+
+ TBuf8<KNonceLength> buffer;
+
+ TTime time;
+ time.HomeTime();
+ TInt64 seed = time.Int64();
+ for( TInt i(0); i < KNonceLength; i++ )
+ {
+ TChar character( RandomCharacter( seed ) );
+ buffer.Append( character );
+ }
+
+ aNonce.Copy( buffer );
+
+ // Encrypt
+#ifndef __WINS__
+ iEncryptor->Transform( buffer );
+#endif
+
+ // Save the nonce
+ User::LeaveIfError( iRepository->Set( KPnPUtilNonce, buffer ) );
+ }
+
+// -----------------------------------------------------------------------------
+// CIptvSecureProvisioningParameters::RandomCharacter
+// -----------------------------------------------------------------------------
+//
+TUint CIptvSecureProvisioningParameters::RandomCharacter( TInt64& aSeed )
+ {
+ // Create random number value for token
+ TInt value = Math::Rand( aSeed );
+ if( value < 0 )
+ {
+ value = -value;
+ }
+ value %= 61; // [0,61]
+ value += 48; // [48,109]
+ // split the range to ranges [48,57],[65,90] and [97,122]
+ // that is: the ascii codes for numbers from 0 to 9,
+ // capital alphabets from A to Z and alphabets from a to z
+ if( value > 57 )
+ {
+ value += 8; // [65,90]
+ if( value > 90 )
+ {
+ value += 6; // [97,122]
+ }
+ }
+ return value;
+ }