--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/ncdengine/engine/src/catalogsutils.cpp Thu Dec 17 08:51:10 2009 +0200
@@ -0,0 +1,1261 @@
+/*
+* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "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 "catalogsutils.h"
+
+#include <utf.h>
+#include <e32base.h>
+#include <f32file.h>
+#include <bautils.h>
+#include <s32strm.h>
+#include <s32mem.h>
+#include <sysutil.h>
+#include <pathinfo.h>
+
+#ifndef __S60_32__
+#include <platform/mw/languages.hrh>
+#endif
+
+#include "catalogsconstants.h"
+#include "catalogsbasemessage.h"
+
+#include "catalogsdebug.h"
+
+// Maximum length of a signed 16 bit integer when converted to a string
+const TInt K16BitIntAsDescLength = 6;
+
+// Maximum length of a signed 32 bit integer when converted to a string
+const TInt K32BitIntAsDescLength = 11;
+
+_LIT( KInitialSearchDrive, "Y:" );
+
+void TCatalogsVersion::ConvertL( TCatalogsVersion& aTarget, const TDesC& aVersion )
+ {
+ TUint16 major = 0;
+ TUint16 minor = 0;
+ TUint32 build = 0;
+
+ if ( aVersion.Length() )
+ {
+ DesToVersionL( aVersion, major, minor, build );
+ }
+
+ aTarget = TCatalogsVersion( major, minor, build );
+ }
+
+
+HBufC* TCatalogsVersion::ConvertLC( const TCatalogsVersion& aSource )
+ {
+ DLTRACEIN(("input: %u.%u.%u",
+ aSource.iMajor,
+ aSource.iMinor,
+ aSource.iBuild ));
+
+ _LIT( KFormatString, "%u.%u.%u");
+
+ HBufC* target = HBufC::NewLC(
+ // Length of major + minor
+ 2 * K16BitIntAsDescLength +
+ // length of build
+ K32BitIntAsDescLength +
+ // separators: '.'
+ 2 );
+
+ TPtr ptr( target->Des() );
+ ptr.Format(
+ KFormatString,
+ aSource.iMajor,
+ aSource.iMinor,
+ aSource.iBuild );
+
+ DLTRACEOUT(( _L("Output: %S"), target));
+ return target;
+ }
+
+
+TCatalogsVersion::TCatalogsVersion()
+ {
+ iMajor = 0;
+ iMinor = 0;
+ iBuild = 0;
+ }
+
+
+TCatalogsVersion::TCatalogsVersion( TUint16 aMajor,
+ TUint16 aMinor,
+ TUint32 aBuild )
+ {
+ iMajor = aMajor;
+ iMinor = aMinor;
+ iBuild = aBuild;
+ }
+
+TBool TCatalogsVersion::operator==( const TCatalogsVersion& aVersion ) const
+ {
+ return iMajor == aVersion.iMajor &&
+ iMinor == aVersion.iMinor &&
+ iBuild == aVersion.iBuild;
+ }
+
+TBool TCatalogsVersion::operator>( const TCatalogsVersion& aVersion ) const
+ {
+ return ( iMajor > aVersion.iMajor ) ||
+ ( iMajor == aVersion.iMajor && ( iMinor > aVersion.iMinor ||
+ ( iMinor == aVersion.iMinor && iBuild > aVersion.iBuild ) ) );
+ }
+
+TBool TCatalogsVersion::operator>=( const TCatalogsVersion& aVersion ) const
+ {
+ return operator==( aVersion ) || operator>( aVersion );
+ }
+
+
+
+
+#ifndef NCD_STORAGE_TESTING
+
+// ---------------------------------------------------------------------------
+// RCatalogsMessageReader
+// ---------------------------------------------------------------------------
+//
+
+RCatalogsMessageReader::RCatalogsMessageReader()
+ {
+ }
+
+void RCatalogsMessageReader::OpenL( MCatalogsBaseMessage& aMessage )
+ {
+ iBuf.CreateL( aMessage.InputLength() );
+ User::LeaveIfError( aMessage.ReadInput( iBuf ) );
+ iStream.Open( iBuf );
+ }
+
+
+void RCatalogsMessageReader::OpenLC( MCatalogsBaseMessage& aMessage )
+ {
+ CleanupClosePushL( *this );
+ OpenL( aMessage );
+ }
+
+
+void RCatalogsMessageReader::Close()
+ {
+ iStream.Close();
+ iBuf.Close();
+ }
+
+
+RCatalogsMessageReader::~RCatalogsMessageReader()
+ {
+ }
+
+#endif
+
+// ---------------------------------------------------------------------------
+// RCatalogsBufferWriter
+// ---------------------------------------------------------------------------
+//
+
+RCatalogsBufferWriter::RCatalogsBufferWriter() : iBuf( NULL )
+ {
+ }
+
+void RCatalogsBufferWriter::OpenL()
+ {
+ iBuf = CBufFlat::NewL( KBufExpandSize );
+ iStream.Open( *iBuf );
+ }
+
+
+void RCatalogsBufferWriter::OpenLC()
+ {
+ CleanupClosePushL( *this );
+ OpenL();
+ }
+
+
+void RCatalogsBufferWriter::Close()
+ {
+ iStream.Close();
+ delete iBuf;
+ iBuf = NULL;
+ }
+
+
+RCatalogsBufferWriter::~RCatalogsBufferWriter()
+ {
+ }
+
+
+// ---------------------------------------------------------------------------
+// Utility functions
+// ---------------------------------------------------------------------------
+//
+
+
+
+void AssignDesL( HBufC8*& aDes, const TDesC8& aSource )
+ {
+ delete aDes;
+ aDes = 0;
+ aDes = aSource.AllocL();
+ }
+
+
+void AssignDesL( HBufC16*& aDes, const TDesC16& aSource )
+ {
+ delete aDes;
+ aDes = 0;
+ aDes = aSource.AllocL();
+ }
+
+void AssignDesL( HBufC16*& aDes, const TDesC8& aSource )
+ {
+ delete aDes;
+ aDes = 0;
+ aDes = ConvertUtf8ToUnicodeL( aSource );
+ }
+
+HBufC16* ConvertUtf8ToUnicodeL( const TDesC8& aUtfText )
+ {
+ HBufC16* buffer = HBufC16::NewLC( aUtfText.Length() );
+ TPtr ptr( buffer->Des() );
+ User::LeaveIfError(
+ CnvUtfConverter::ConvertToUnicodeFromUtf8( ptr,
+ aUtfText ) );
+ CleanupStack::Pop( buffer );
+ return buffer;
+ }
+
+
+HBufC8* ConvertUnicodeToUtf8L( const TDesC16& aUnicodeText )
+ {
+ const TInt KConvertBufferSize = 32;
+
+ // Place converted data here, initial size double the conversion buffer.
+ HBufC8* convertedData = HBufC8::NewL( KConvertBufferSize * 2 );
+ CleanupStack::PushL( convertedData );
+ TPtr8 destination( convertedData->Des() );
+
+ // Create a small output buffer
+ TBuf8<KConvertBufferSize> outputBuffer;
+
+ // Create a buffer for the unconverted text - initialised with the
+ // input text
+ TPtrC16 remainderOfUnicodeText( aUnicodeText );
+
+ for ( ;; ) // conversion loop
+ {
+ // Start conversion. When the output buffer is full, return the
+ // number of characters that were not converted
+ const TInt returnValue
+ = CnvUtfConverter::ConvertFromUnicodeToUtf8( outputBuffer,
+ remainderOfUnicodeText );
+
+ // check to see that the descriptor isn’t corrupt - leave if it is
+ if ( returnValue == CnvUtfConverter::EErrorIllFormedInput )
+ {
+ User::Leave( KErrCorrupt );
+ }
+ else if ( returnValue < 0 ) // future-proof against "TError" expanding
+ {
+ User::Leave( KErrGeneral );
+ }
+
+ // Do something here to store the contents of the output buffer.
+ if ( destination.Length() + outputBuffer.Length() >=
+ destination.MaxLength() )
+ {
+ HBufC8* newBuffer = convertedData->ReAllocL(
+ ( destination.MaxLength() + outputBuffer.Length() ) * 2 );
+
+ CleanupStack::Pop( convertedData );
+ convertedData = newBuffer;
+ CleanupStack::PushL( convertedData );
+ destination.Set( convertedData->Des() );
+ }
+
+ destination.Append( outputBuffer );
+ outputBuffer.Zero();
+
+ // Finish conversion if there are no unconverted characters
+ // in the remainder buffer
+ if ( returnValue == 0 )
+ {
+ break;
+ }
+
+ // Remove the converted source text from the remainder buffer.
+ // The remainder buffer is then fed back into loop
+ remainderOfUnicodeText.Set(
+ remainderOfUnicodeText.Right( returnValue) );
+ }
+
+ CleanupStack::Pop( convertedData );
+ return convertedData;
+ }
+
+
+HBufC8* Des16ToDes8LC( const TDesC16& aDes )
+ {
+ HBufC8* buffer = HBufC8::NewLC( aDes.Length() );
+ buffer->Des().Copy( aDes );
+ return buffer;
+ }
+
+HBufC8* Des16ToDes8L( const TDesC16& aDes )
+ {
+ HBufC8* t = Des16ToDes8LC( aDes );
+ CleanupStack::Pop();
+ return t;
+ }
+
+HBufC16* Des8ToDes16LC( const TDesC8& aDes )
+ {
+ HBufC16* buffer = HBufC16::NewLC( aDes.Length() );
+ buffer->Des().Copy( aDes );
+ return buffer;
+ }
+
+HBufC16* Des8ToDes16L( const TDesC8& aDes )
+ {
+ HBufC16* t = Des8ToDes16LC( aDes );
+ CleanupStack::Pop();
+ return t;
+ }
+
+TInt DesDecToIntL( const TDesC& aDes )
+ {
+ TLex lex( aDes );
+ TInt value;
+ User::LeaveIfError( lex.Val( value ) );
+ return value;
+ }
+
+TInt DesDecToInt( const TDesC8& aDes, TInt& aValue )
+ {
+ TLex8 lex( aDes );
+ return lex.Val( aValue );
+ }
+
+TInt DesDecToInt( const TDesC16& aDes, TInt& aValue )
+ {
+ TLex16 lex( aDes );
+ return lex.Val( aValue );
+ }
+
+TInt DesHexToIntL( const TDesC& aDes )
+ {
+ TLex lex( aDes );
+ TInt position = aDes.LocateF( 'x' );
+ if ( position != KErrNotFound )
+ {
+ // Hex format is of type '0xABC' or 'xABC'
+ // Skip over the x-part.
+ lex.Assign( aDes.Mid( position+1 ) );
+ }
+ TUint value;
+ User::LeaveIfError( lex.Val( value, EHex ) );
+ return value;
+ }
+
+TInt Des8ToInt( const TDesC8& aDes )
+ {
+ return *(( TInt* )aDes.Ptr());
+ }
+
+TUint Des8ToUint( const TDesC8& aDes )
+ {
+ return *(( TUint* )aDes.Ptr());
+ }
+
+
+HBufC8* IntToDes8LC( TInt aInt )
+ {
+ HBufC8* buffer = HBufC8::NewMaxLC( sizeof( aInt ) );
+ TPtr8 ptr( buffer->Des() );
+ *(( TInt* )ptr.Ptr()) = aInt;
+ return buffer;
+ }
+
+HBufC8* IntToDes8L( TInt aInt )
+ {
+ HBufC8* t = IntToDes8LC( aInt );
+ CleanupStack::Pop();
+ return t;
+ }
+
+HBufC8* UintToDes8LC( TUint aUint )
+ {
+ HBufC8* buffer = HBufC8::NewMaxLC( sizeof( aUint ) );
+ TPtr8 ptr( buffer->Des() );
+ *(( TUint* )ptr.Ptr()) = aUint;
+ return buffer;
+ }
+
+HBufC8* UintToDes8L( TUint aUint )
+ {
+ HBufC8* t = UintToDes8LC( aUint );
+ CleanupStack::Pop();
+ return t;
+ }
+
+
+// ---------------------------------------------------------------------------
+// ExternalizeDesL
+// ---------------------------------------------------------------------------
+//
+void ExternalizeDesL( const TDesC16& aDes, RWriteStream& aStream )
+ {
+ aStream.WriteInt32L( aDes.Length() );
+ aStream.WriteL( aDes );
+ }
+
+
+// ---------------------------------------------------------------------------
+// InternalizeDesL
+// ---------------------------------------------------------------------------
+//
+TInt InternalizeDesL( HBufC16*& aDes, RReadStream& aStream )
+ {
+ //DLTRACEIN(("16bit"));
+ TInt length = aStream.ReadInt32L();
+ //DLTRACE(("length: %i", length));
+ if ( length > 0 )
+ {
+ HBufC* target = HBufC::NewLC( length );
+ TPtr ptr( target->Des() );
+
+ aStream.ReadL( ptr, length );
+ delete aDes;
+ aDes = target;
+ CleanupStack::Pop( target );
+ }
+ else
+ {
+ delete aDes;
+ aDes = KNullDesC16().AllocL();
+ }
+ //DLTRACEOUT((""));
+ return length;
+ }
+
+
+// ---------------------------------------------------------------------------
+// ExternalizeDesL
+// ---------------------------------------------------------------------------
+//
+void ExternalizeDesL( const TDesC8& aDes, RWriteStream& aStream )
+ {
+ aStream.WriteInt32L( aDes.Length() );
+ aStream.WriteL( aDes );
+ }
+
+
+// ---------------------------------------------------------------------------
+// InternalizeDesL
+// ---------------------------------------------------------------------------
+//
+TInt InternalizeDesL( HBufC8*& aDes, RReadStream& aStream )
+ {
+ //DLTRACEIN(("8bit"));
+ TInt length = aStream.ReadInt32L();
+ //DLTRACE(("length: %i", length));
+ if ( length > 0 )
+ {
+ HBufC8* target = HBufC8::NewLC( length );
+ TPtr8 ptr( target->Des() );
+
+ aStream.ReadL( ptr, length );
+ delete aDes;
+ aDes = target;
+ CleanupStack::Pop( target );
+ }
+ else
+ {
+ delete aDes;
+ aDes = KNullDesC8().AllocL();
+ }
+ //DLTRACEOUT((""));
+ return length;
+ }
+
+
+
+HBufC* FindEngineFileL( RFs& aFs, const TDesC& aFilename )
+ {
+ DLTRACEIN(( _L("Find: %S"), &aFilename ));
+ // Get engine's private path
+ RBuf target;
+ CleanupClosePushL( target );
+ target.CreateL( KMaxPath );
+ User::LeaveIfError( aFs.PrivatePath( target ) );
+
+ // Set Y: as the first drive to be searched instead of session
+ // path's drive which is C:
+ target.Insert( 0, KInitialSearchDrive );
+
+ DLTRACE(( _L("Path to search from: %S"), &target ));
+
+ // Find the file
+ TFindFile find( aFs );
+
+ User::LeaveIfError( find.FindByDir( aFilename, target ) );
+
+ CleanupStack::PopAndDestroy( &target );
+ DLTRACEOUT(( _L("Found the file from: %S"),
+ &find.File() ));
+
+ return find.File().AllocL();
+ }
+
+
+TBool IsRomDriveL( RFs& aFs, TChar aDriveChar )
+ {
+ DLTRACEIN((""));
+ TDriveInfo info;
+ TInt drive;
+ User::LeaveIfError( RFs::CharToDrive( aDriveChar, drive ) );
+ User::LeaveIfError( aFs.Drive( info, drive ) );
+ return info.iDriveAtt & KDriveAttRom;
+ }
+
+
+TChar DriveToCharL( TInt aDrive )
+ {
+ TChar c;
+ User::LeaveIfError( RFs::DriveToChar( aDrive, c ) );
+ return c;
+ }
+
+
+HBufC* DriveRootPathLC( RFs& aFs, const TChar& aDriveLetter )
+ {
+ DLTRACEIN((""));
+
+ HBufC* rootPath( NULL );
+
+ // Get the drive num that corresponds the given letter
+ TInt driveNum( EDriveA );
+ User::LeaveIfError( aFs.CharToDrive( aDriveLetter, driveNum ) );
+
+ // Get the information about the drive
+ TDriveInfo info;
+ User::LeaveIfError( aFs.Drive( info, driveNum ) );
+
+ // Compare drive information to check what is the correct root path
+ if ( info.iDriveAtt & KDriveAttRom )
+ {
+ DLINFO(("ROM drive"));
+ rootPath = PathInfo::RomRootPath().AllocLC();
+ }
+ else if ( info.iDriveAtt & KDriveAttRemovable )
+ {
+ DLINFO(("Memory card"));
+ // Memory card
+ rootPath = PathInfo::MemoryCardRootPath().AllocLC();
+ }
+ else
+ {
+ // Phone memory
+ DLINFO(("Phone memory"));
+ rootPath = PathInfo::PhoneMemoryRootPath().AllocLC();
+ }
+
+ HBufC* charDes( HBufC::NewLC( 1 ) );
+ charDes->Des().Append( aDriveLetter );
+ // Let us make sure that the drive letter is correct
+ // if there are multiple same kind of drives...
+ rootPath->Des().Replace( 0, 1, *charDes );
+ CleanupStack::PopAndDestroy( charDes );
+
+ DLTRACEOUT((""));
+ return rootPath;
+ }
+
+
+HBufC* LangCodeToDescLC( TLanguage aLang )
+ {
+ switch ( aLang )
+ {
+ case ELangEnglish:
+ return _L( "en_EN" ).AllocLC();
+ case ELangFrench:
+ return _L( "fr_FR" ).AllocLC();
+ case ELangGerman:
+ return _L( "de_DE" ).AllocLC();
+ case ELangSpanish:
+ return _L( "es_ES" ).AllocLC();
+ case ELangItalian:
+ return _L( "it_IT" ).AllocLC();
+ case ELangSwedish:
+ return _L( "sv_SE" ).AllocLC();
+ case ELangDanish:
+ return _L( "da_DK" ).AllocLC();
+ case ELangNorwegian:
+ return _L( "no_NO" ).AllocLC();
+ case ELangFinnish:
+ return _L( "fi_FI" ).AllocLC();
+ case ELangAmerican:
+ return _L( "en_US" ).AllocLC();
+ case ELangSwissFrench:
+ return _L( "fr_CH" ).AllocLC();
+ case ELangSwissGerman:
+ return _L( "de_CH" ).AllocLC();
+ case ELangPortuguese:
+ return _L( "pt_PT" ).AllocLC();
+ case ELangTurkish:
+ return _L( "tr_TR" ).AllocLC();
+ case ELangIcelandic:
+ return _L( "is_IS" ).AllocLC();
+ case ELangRussian:
+ return _L( "ru_RU" ).AllocLC();
+ case ELangHungarian:
+ return _L( "hu_HU" ).AllocLC();
+ case ELangDutch:
+ return _L( "nl_NL" ).AllocLC();
+ case ELangBelgianFlemish:
+ return _L( "nl_BE" ).AllocLC();
+ case ELangAustralian:
+ return _L( "en_AU" ).AllocLC();
+ case ELangBelgianFrench:
+ return _L( "fr_BE" ).AllocLC();
+ case ELangAustrian:
+ return _L( "de_AT" ).AllocLC();
+ case ELangNewZealand:
+ return _L( "en_NZ" ).AllocLC();
+ case ELangInternationalFrench:
+ return _L( "fr" ).AllocLC();
+ case ELangCzech:
+ return _L( "cs_CZ" ).AllocLC();
+ case ELangSlovak:
+ return _L( "sk_SK" ).AllocLC();
+ case ELangPolish:
+ return _L( "pl_PL" ).AllocLC();
+ case ELangSlovenian:
+ return _L( "sl_SI" ).AllocLC();
+ case ELangTaiwanChinese:
+ return _L( "zh_TW" ).AllocLC();
+ case ELangHongKongChinese:
+ return _L( "zh_HK" ).AllocLC();
+ case ELangPrcChinese:
+ return _L( "zh_CN" ).AllocLC();
+ case ELangJapanese:
+ return _L( "ja_JP" ).AllocLC();
+ case ELangThai:
+ return _L( "th_TH" ).AllocLC();
+ case ELangAfrikaans:
+ return _L( "af_ZA" ).AllocLC();
+ case ELangAlbanian:
+ return _L( "sq_AL" ).AllocLC();
+ case ELangAmharic:
+ return _L( "am_ET" ).AllocLC();
+ case ELangArabic:
+ return _L( "ar" ).AllocLC();
+ case ELangArmenian:
+ return _L( "hy_AM" ).AllocLC();
+ case ELangTagalog:
+ return _L( "tl" ).AllocLC();
+ case ELangBelarussian:
+ return _L( "be_BY" ).AllocLC();
+ case ELangBengali:
+ return _L( "bn_IN" ).AllocLC();
+ case ELangBulgarian:
+ return _L( "bg_BG" ).AllocLC();
+ case ELangBurmese:
+ return _L( "my_MM" ).AllocLC();
+ case ELangCatalan:
+ return _L( "ca_ES" ).AllocLC();
+ case ELangCroatian:
+ return _L( "hr_HR" ).AllocLC();
+ case ELangCanadianEnglish:
+ return _L( "en_CA" ).AllocLC();
+ case ELangInternationalEnglish:
+ return _L( "en" ).AllocLC();
+ case ELangSouthAfricanEnglish:
+ return _L( "en_ZA" ).AllocLC();
+ case ELangEstonian:
+ return _L( "et_EE" ).AllocLC();
+ case ELangFarsi:
+ return _L( "fa_IR" ).AllocLC();
+ case ELangCanadianFrench:
+ return _L( "fr_CA" ).AllocLC();
+ case ELangScotsGaelic:
+ return _L( "gd_GB" ).AllocLC();
+ case ELangGeorgian:
+ return _L( "ka_GE" ).AllocLC();
+ case ELangGreek:
+ return _L( "el_GR" ).AllocLC();
+ case ELangCyprusGreek:
+ return _L( "el_CY" ).AllocLC();
+ case ELangGujarati:
+ return _L( "gu_IN" ).AllocLC();
+ case ELangHebrew:
+ return _L( "he" ).AllocLC();
+ case ELangHindi:
+ return _L( "hi_IN" ).AllocLC();
+ case ELangIndonesian:
+ return _L( "id_ID" ).AllocLC();
+ case ELangIrish:
+ return _L( "ga_IE" ).AllocLC();
+ case ELangSwissItalian:
+ return _L( "it_CH" ).AllocLC();
+ case ELangKannada:
+ return _L( "kn_IN" ).AllocLC();
+ case ELangKazakh:
+ return _L( "kk_KZ" ).AllocLC();
+ case ELangKhmer:
+ return _L( "kh_KH" ).AllocLC();
+ case ELangKorean:
+ return _L( "ko_KR" ).AllocLC();
+ case ELangLao:
+ return _L( "lo_LA" ).AllocLC();
+ case ELangLatvian:
+ return _L( "lv_LV" ).AllocLC();
+ case ELangLithuanian:
+ return _L( "lt_LT" ).AllocLC();
+ case ELangMacedonian:
+ return _L( "mk_MK" ).AllocLC();
+ case ELangMalay:
+ return _L( "ms_MY" ).AllocLC();
+ case ELangMalayalam:
+ return _L( "ml_IN" ).AllocLC();
+ case ELangMarathi:
+ return _L( "mr_IN" ).AllocLC();
+ case ELangMoldavian:
+ return _L( "mo_MD" ).AllocLC();
+ case ELangMongolian:
+ return _L( "mn_MN" ).AllocLC();
+ case ELangNorwegianNynorsk:
+ return _L( "nn_NO" ).AllocLC();
+ case ELangBrazilianPortuguese:
+ return _L( "pt_BR" ).AllocLC();
+ case ELangPunjabi:
+ return _L( "pa_IN" ).AllocLC();
+ case ELangRomanian:
+ return _L( "ro_RO" ).AllocLC();
+ case ELangSerbian:
+ return _L( "sr" ).AllocLC();
+ case ELangSinhalese:
+ return _L( "si_LK" ).AllocLC();
+ case ELangSomali:
+ return _L( "so_SO" ).AllocLC();
+ case ELangInternationalSpanish:
+ return _L( "es" ).AllocLC();
+ case ELangLatinAmericanSpanish:
+ return _L( "esa" ).AllocLC();
+ case ELangSwahili:
+ return _L( "sw_KE" ).AllocLC();
+ case ELangFinlandSwedish:
+ return _L( "sv_FI" ).AllocLC();
+ case ELangTamil:
+ return _L( "ta_IN" ).AllocLC();
+ case ELangTelugu:
+ return _L( "te_IN" ).AllocLC();
+ case ELangTibetan:
+ return _L( "bo" ).AllocLC();
+ case ELangTigrinya:
+ return _L( "ti_ET" ).AllocLC();
+ case ELangCyprusTurkish:
+ return _L( "tr_CY" ).AllocLC();
+ case ELangTurkmen:
+ return _L( "tk_TM" ).AllocLC();
+ case ELangUkrainian:
+ return _L( "uk_UA" ).AllocLC();
+ case ELangUrdu:
+ return _L( "ur_PK" ).AllocLC();
+ case ELangVietnamese:
+ return _L( "vi_VN" ).AllocLC();
+ case ELangWelsh:
+ return _L( "cy_GB" ).AllocLC();
+ case ELangZulu:
+ return _L( "zu_ZA" ).AllocLC();
+
+#ifdef __S60_32__
+
+ case 129: // APAC English = 129
+ return _L( "en_APAC" ).AllocLC();
+ case 157: // APAC TW (a.k.a Chinese TW English) = 157
+ return _L( "en_TW" ).AllocLC();
+ case 158: // APAC HK = 158
+ return _L( "en_HK" ).AllocLC();
+ case 159: // APAC PRC = 159
+ return _L( "en_CN" ).AllocLC();
+ case 160: // Japanese English = 160
+ return _L( "en_JP" ).AllocLC();
+ case 161: // Thai English = 161
+ return _L( "en_TH" ).AllocLC();
+ case 326: // Bahasa Malay (Chinese) = 326
+ return _L( "ms_MY" ).AllocLC();
+ case 401: // Basque
+ return _L( "eu" ).AllocLC();
+ case 402: // Galician
+ return _L( "gl_ES" ).AllocLC();
+
+#else // __S60_32__
+
+ case KLangApacEnglish: // APAC English = 129
+ return _L( "en_APAC" ).AllocLC();
+ case KLangTaiwanEnglish: // APAC TW (a.k.a Chinese TW English) = 157
+ return _L( "en_TW" ).AllocLC();
+ case KLangHongKongEnglish: // APAC HK = 158
+ return _L( "en_HK" ).AllocLC();
+ case KLangPrcEnglish: // APAC PRC = 159
+ return _L( "en_CN" ).AllocLC();
+ case KLangJapaneseEnglish: // Japanese English = 160
+ return _L( "en_JP" ).AllocLC();
+ case KLangThaiEnglish: // Thai English = 161
+ return _L( "en_TH" ).AllocLC();
+ case KLangApacMalay: // Bahasa Malay (Chinese) = 326
+ return _L( "ms_MY" ).AllocLC();
+ case KLangBasque: // Basque = 102 on 5.0 platform
+ return _L( "eu" ).AllocLC();
+ case KLangGalician: // Galician = 103 on 5.0 platform
+ return _L( "gl_ES" ).AllocLC();
+
+#endif // __S60_32__
+
+ default:
+ return _L( "undef" ).AllocLC();
+ }
+ }
+
+
+// ---------------------------------------------------------------------------
+// CleanUidName
+// ---------------------------------------------------------------------------
+//
+TUidName CleanUidName( const TUid& aUid )
+ {
+ TUidName uidName( aUid.Name() );
+ DASSERT( uidName.Length() > 2 );
+ // Rip '[' and ']' out of uid name
+ return uidName.Mid( 1, uidName.Length() - 2 );
+ }
+
+// ---------------------------------------------------------------------------
+// Encodes a filename
+// ---------------------------------------------------------------------------
+//
+HBufC* EncodeFilenameLC( const TDesC& aFileName, RFs& aFs )
+ {
+ DLTRACEIN(( _L("Path: %S"), &aFileName ));
+ // If each character gets replaced with a number, it would quadruple the
+ // length: "abc" -> "xxxxyyyyzzzz". Multiply by 8 to be safe : )
+ HBufC* encoded = HBufC::NewLC( aFileName.Length() * 8 );
+ TPtr ptr( encoded->Des() );
+
+ // First some basic legality checks.
+ // It seems that RFs::IsValidName() acts very strangely in some cases
+ // ( returns 0x20 as badChar even though there is no such char in the desc )
+ // so it's better to do as much as we can by ourselves.
+
+ for ( TInt i = 0; i < aFileName.Length(); i++ )
+ {
+ TChar c = aFileName[i];
+ switch ( c )
+ {
+ // List partly from TNameChecker
+ case '"':
+ case '*':
+ case '/':
+ case ':':
+ case '<':
+ case '>':
+ case '?':
+ case '\'':
+ case '\000':
+ case '\\':
+ case '|':
+ case '.':
+ {
+ TBuf<8> num;
+ num.NumUC( c, EHex );
+ ptr.Append( num );
+ break;
+ }
+ default:
+ {
+ ptr.Append( c );
+ break;
+ }
+ };
+ }
+
+ // Then try with system's tools.
+ TText badChar = 0;
+ while ( ! aFs.IsValidName( ptr, badChar ) )
+ {
+ TInt position = ptr.Locate( badChar );
+ if ( position == KErrNotFound )
+ {
+ // This should not happen.
+ DLERROR(( _L("->encode filename abort! %S "),
+ &aFileName ));
+ break;
+ }
+ // Replace evil characters with uppercase numeric codes.
+ TBuf<8> num;
+ num.NumUC( badChar, EHex );
+ ptr.Replace( position, 1, num );
+ }
+
+
+ DLTRACEOUT(( _L("%S"), encoded ));
+ return encoded;
+ }
+
+
+// ---------------------------------------------------------------------------
+// Creates a private directory
+// ---------------------------------------------------------------------------
+//
+void CreatePrivatePathL( RFs& aFs, const TDesC& aDriveAndColon, TDes& aPath )
+ {
+ DLTRACEIN((""));
+ TInt driveNum;
+ User::LeaveIfError( aFs.CharToDrive( aDriveAndColon[0], driveNum ) );
+
+ DLTRACE(("Creating private path"));
+ User::LeaveIfError( aFs.CreatePrivatePath( driveNum ) );
+ User::LeaveIfError( aFs.PrivatePath( aPath ) );
+
+ aPath.Insert( 0, aDriveAndColon );
+ }
+
+
+// ---------------------------------------------------------------------------
+// Free disk space
+// ---------------------------------------------------------------------------
+//
+TInt64 FreeDiskSpaceL( RFs& aFs, TInt aDriveNumber )
+ {
+ DLTRACEIN((""));
+
+ TInt64 freeSpace = 0;
+ TVolumeInfo volumeInfo;
+
+ if ( aFs.Volume( volumeInfo, aDriveNumber ) == KErrNone)
+ {
+ freeSpace = volumeInfo.iFree;
+ }
+
+ DLTRACEOUT(( "Free space: %li", freeSpace ));
+ return freeSpace;
+ }
+
+
+ // Specialization for 64-bit integers
+template<>
+void IntToDes16<TInt64>( const TInt64& aInt, TDes& aDes )
+ {
+ DLTRACEIN(("Int: %Li, aDes.MaxLength() = %d", aInt, aDes.MaxLength() ));
+ DASSERT( aDes.MaxLength() > 3 );
+
+ IntToDes16( I64HIGH( aInt ), aDes );
+ aDes.SetLength( 4 );
+ TPtr16 ptr( aDes.MidTPtr( 2 ) );
+ TDes& des( ptr );
+ IntToDes16( I64LOW( aInt ), des );
+ DLTRACEOUT(( _L("High: %i, low: %i, Des: %S"),
+ I64HIGH( aInt ), I64LOW( aInt ), &aDes ));
+ }
+
+
+
+// Specialization for 64-bit integers
+template<>
+void Des16ToInt<TInt64>( const TDesC& aDes, TInt64& aInt )
+ {
+ DLTRACEIN(( _L("aDes: %S"), &aDes ));
+ DASSERT( aDes.Length() > 3 );
+ TUint32 high = 0;
+ Des16ToInt( aDes, high );
+
+ TUint32 low = 0;
+ Des16ToInt( aDes.Mid( 2 ), low );
+
+ aInt = MAKE_TINT64( high, low );
+ DLTRACEOUT(("Int: %Li, High: %i, low: %i", aInt, high, low ));
+ }
+
+// ---------------------------------------------------------------------------
+// Checks if the URI is a HTTPS URI
+// ---------------------------------------------------------------------------
+//
+TBool IsHttpsUri( const TDesC& aUri )
+ {
+ _LIT(KHttps, "https");
+ return aUri.Left( KHttps().Length() ) == KHttps();
+ }
+
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+TInt FileSystemAllocationL( RFs& aFs, const TDesC& aDir )
+ {
+ TInt allocation = 0;
+
+ CDirScan* dirScan = CDirScan::NewLC( aFs );
+
+ dirScan->SetScanDataL( aDir,
+ KEntryAttNormal,
+ ESortByName,
+ CDirScan::EScanDownTree );
+ CDir* dir = 0;
+ dirScan->NextL( dir );
+ while ( dir )
+ {
+ CleanupStack::PushL( dir );
+ TInt count = dir->Count();
+
+ for ( TInt i = 0; i < count; i++ )
+ {
+ const TEntry& entry = ( *dir )[i];
+ allocation += entry.iSize;
+ }
+ CleanupStack::PopAndDestroy( dir );
+ dirScan->NextL( dir );
+ }
+
+ CleanupStack::PopAndDestroy( dirScan );
+ return allocation;
+ }
+
+
+// ---------------------------------------------------------------------------
+// Read file
+// ---------------------------------------------------------------------------
+//
+HBufC8* ReadFileL( RFs& aFs, const TDesC& aFileName )
+ {
+ DLTRACEIN(( _L("File: %S"), &aFileName ));
+ RFile file;
+ User::LeaveIfError( file.Open( aFs,
+ aFileName,
+ EFileRead ) );
+ CleanupClosePushL( file );
+ HBufC8* buffer = ReadFileL( file );
+ CleanupStack::PopAndDestroy(); // file
+
+ return buffer;
+ }
+
+// ---------------------------------------------------------------------------
+// Read file
+// ---------------------------------------------------------------------------
+//
+HBufC8* ReadFileL( RFile& aFile )
+ {
+ DLTRACEIN(( "" ));
+ TInt size;
+ User::LeaveIfError( aFile.Size( size ) );
+ HBufC8* buffer = HBufC8::NewLC( size );
+ TPtr8 ptr( buffer->Des() );
+ User::LeaveIfError( aFile.Read( ptr, size ) );
+ CleanupStack::Pop( buffer );
+
+ return buffer;
+ }
+
+
+// ---------------------------------------------------------------------------
+// Checks if there's enough space on the drive
+// ---------------------------------------------------------------------------
+//
+void WouldDiskSpaceGoBelowCriticalLevelL( const TDesC& aPath,
+ RFs& aFs,
+ TInt aSpaceNeeded )
+ {
+ DLTRACEIN(( ""));
+ if ( aPath.Length() <= 0 )
+ {
+ DLERROR(("Invalid path"));
+ User::Leave( KErrArgument );
+ }
+
+ TInt driveNumber = 0;
+ User::LeaveIfError( RFs::CharToDrive( aPath[0], driveNumber ) );
+ if ( SysUtil::DiskSpaceBelowCriticalLevelL( &aFs,
+ aSpaceNeeded,
+ driveNumber ) )
+ {
+ DLERROR(( _L( "Disk space would go below critical level, path: %S, space requested: %d " ),
+ &aPath, aSpaceNeeded ));
+ User::Leave( KErrDiskFull );
+ }
+ }
+
+
+// Accepts "x", "x.y" or "x.y.z" format version strings.
+void DesToVersionL( const TDesC& aVersion,
+ TUint16& aMajor, TUint16& aMinor, TUint32& aBuild )
+ {
+ DLTRACEIN(( _L("Version: %S"), &aVersion ));
+ // Initial values. -1 indicates that the value has not been yet parsed.
+ // using double sizes to ensure that TUints fit without sign conversion
+ TInt32 major = -1;
+ TInt32 minor = -1;
+ TInt64 build = -1;
+
+ TLex lex( aVersion );
+ lex.Mark();
+ for( ;; )
+ {
+ if( lex.Eos() || lex.Peek() == '.' )
+ {
+ TPtrC data = lex.MarkedToken();
+ TLex num;
+ num.Assign( data );
+ TInt64 value = 0;
+ User::LeaveIfError( num.Val( value ) );
+
+ if( major < 0 )
+ {
+ major = value;
+ }
+ else if( minor < 0 )
+ {
+ minor = value;
+ }
+ else if( build < 0 )
+ {
+ build = value;
+ // all values received now, exit loop.
+ break;
+ }
+
+ if( lex.Eos() )
+ {
+ break;
+ }
+ else
+ {
+ lex.SkipAndMark( 1 );
+ }
+ }
+ else
+ {
+ lex.Inc();
+ }
+ }
+
+ if( major < 0 )
+ {
+ DLERROR(("No major value, leaving"));
+ // Major required.
+ User::Leave( KErrArgument );
+ }
+
+ if( minor < 0 )
+ {
+ // Assume zero for this one if not given.
+ minor = 0;
+ }
+
+ if( build < 0 )
+ {
+ // Assume zero for this one if not given.
+ build = 0;
+ }
+
+ aMajor = major;
+ aMinor = minor;
+ aBuild = build;
+ DLTRACEOUT(("Interpreted version: %d.%d.%d", aMajor, aMinor, aBuild ));
+ }
+
+// ---------------------------------------------------------------------------
+// Appends to paths
+// ---------------------------------------------------------------------------
+//
+void AppendPathsLC(
+ RBuf& aPath,
+ const TDesC& aRoot,
+ const TDesC& aAppendPath )
+ {
+ DLTRACEIN((""));
+ CleanupClosePushL( aPath );
+ aPath.CreateL( aRoot.Length() +
+ aAppendPath.Length() );
+ aPath.Append( aRoot );
+ aPath.Append( aAppendPath );
+ DLTRACEOUT(( _L("Path: %S"), &aPath ));
+ }
+
+
+
+// ---------------------------------------------------------------------------
+// Leave helpers
+// ---------------------------------------------------------------------------
+//
+void LeaveIfNotErrorL( TInt aError, TInt aAcceptErr )
+ {
+ if ( aError != KErrNone &&
+ aError != aAcceptErr )
+ {
+ DLERROR(("Error: %d, leaving", aError));
+ User::Leave( aError );
+ }
+ }
+
+
+void LeaveIfNotErrorL( TInt aError, TInt aAcceptErr, TInt aAcceptErr2 )
+ {
+ if ( aError != KErrNone &&
+ aError != aAcceptErr &&
+ aError != aAcceptErr2 )
+ {
+ DLERROR(("Error: %d, leaving", aError));
+ User::Leave( aError );
+ }
+ }
+
+
+void LeaveIfNotErrorL( TInt aError, TInt aAcceptErr,
+ TInt aAcceptErr2, TInt aAcceptErr3 )
+ {
+ if ( aError != KErrNone &&
+ aError != aAcceptErr &&
+ aError != aAcceptErr2 &&
+ aError != aAcceptErr3 )
+ {
+ DLERROR(("Error: %d, leaving", aError));
+ User::Leave( aError );
+ }
+ }
+
+
+void OpenOrCreateFileL(
+ RFs& aFs, RFile& aFile, const TDesC& aFilePath, TUint aFileMode )
+ {
+ DLTRACEIN((""));
+ TInt err = aFile.Open( aFs, aFilePath, aFileMode );
+ if ( err == KErrNotFound )
+ {
+ DLTRACE(("file not found, creating"));
+ User::LeaveIfError( aFile.Create( aFs, aFilePath, aFileMode ) );
+ }
+ else if ( err != KErrNone )
+ {
+ DLERROR(("Error when opening: %d", err));
+ User::Leave( err );
+ }
+ }