--- a/webengine/widgetengine/src/Preferences.cpp Thu Dec 17 09:20:16 2009 +0200
+++ b/webengine/widgetengine/src/Preferences.cpp Thu Jan 07 13:31:38 2010 +0200
@@ -34,6 +34,8 @@
_LIT( KKeyFormat, "%d.%S" );
_LIT( KPrefsFile,"prefs.dat" );
+_LIT( KPrefsTmpFile,"prefs.dat.tmp" );
+_LIT( KPrefsBakFile, "prefs.dat.bak" );
// ----------------------------------------------------------------------------
@@ -264,7 +266,11 @@
CleanupStack::Pop(); // k
// Save update to persistent storage
- saveL();
+ TRAPD(err, saveL());
+ if(err!= KErrNone)
+ {
+ deleteAllPrefFiles();
+ }
}
}
@@ -306,7 +312,10 @@
CleanupStack::PopAndDestroy(); // k
// Save update to persistent storage
- saveL();
+ TRAPD(err, saveL());
+ if(err!= KErrNone) {
+ deleteAllPrefFiles();
+ }
}
}
@@ -323,46 +332,180 @@
RFs fs;
- if ( fs.Connect() == KErrNone ) {
+
+ // Connect to file server
+ User::LeaveIfError(fs.Connect());
+ CleanupClosePushL( fs );
- CleanupClosePushL( fs );
- HBufC* filePath = HBufC::NewLC( m_basepath->Length() + KPrefsFile().Length() );
+ // Form filenames
+ HBufC* tmpFilePath = HBufC::NewLC( m_basepath->Length() + KPrefsTmpFile().Length() );
+ HBufC* bakFilePath = HBufC::NewLC( m_basepath->Length() + KPrefsBakFile().Length() );
+ HBufC* filePath = HBufC::NewLC( m_basepath->Length() + KPrefsFile().Length() );
+
+ TPtr fName( tmpFilePath->Des() );
+ fName.Append( *m_basepath );
+ fName.Append( KPrefsTmpFile );
+
+ fName.Set( bakFilePath->Des() );
+ fName.Append( *m_basepath );
+ fName.Append( KPrefsBakFile );
+
+ fName.Set( filePath->Des() );
+ fName.Append( *m_basepath );
+ fName.Append( KPrefsFile );
+
+ RFileWriteStream writeStream;
+ writeStream.PushL();
+
+ // Try to create the temp file
+ if(writeStream.Replace(fs, *tmpFilePath, EFileWrite|EFileShareExclusive) != KErrNone) {
+ // Make sure the private path exists
+ fs.CreatePrivatePath( EDriveC );
+
+ // Try again to create the file
+ User::LeaveIfError(writeStream.Create(fs, *tmpFilePath, EFileWrite|EFileShareExclusive));
+ }
- TPtr fName( filePath->Des() );
- fName.Append( *m_basepath );
- fName.Append( KPrefsFile );
+ // Try to externalize the data to the stream
+ TRAPD(err, externalizeL(writeStream));
+
+ // Close the stream
+ CleanupStack::PopAndDestroy(); // writeStream
+
+ // If no error at this point then we're guaranteed to have a valid file
+ if(err!=KErrNone)
+ {
+ // Delete the temp file
+ fs.Delete(*tmpFilePath);
+
+ // And leave with the error code
+ User::Leave(err);
+ }
+
+ // Backup any old valid file just in case
+ fs.Delete(*bakFilePath);
+ fs.Rename(*filePath, *bakFilePath);
+
+ // Rename the temp file to be the actual settings file
+ err = fs.Rename(*tmpFilePath, *filePath);
+ if(err!=KErrNone)
+ {
+ // If we had a backup settings file, try to return it
+ fs.Rename(*bakFilePath, *filePath);
+ User::Leave(err);
+ }
- RFileWriteStream writeStream;
- TInt fileerror = writeStream.Replace( fs, *filePath, EFileWrite );
+ // Cleanup
+ CleanupStack::PopAndDestroy(4); // filePath, bakFilePath, tmpFilePath, fs
+
+}
- if ( fileerror != KErrNone ) {
- fs.CreatePrivatePath( EDriveC );
- fileerror = writeStream.Create( fs, *filePath, EFileWrite|EFileShareExclusive );
- }
+// ----------------------------------------------------------------------------
+// WidgetPreferences::externalizeL
+//
+//
+// ----------------------------------------------------------------------------
+
+void WidgetPreferences::externalizeL(RWriteStream& aStream) const
+{
+ aStream.WriteInt32L( m_preferences->Count() );
+
+ TPtrHashMapIter<TDesC,PrefElement> it( *m_preferences );
+ const TDesC* key;
+ const PrefElement* pref;
- if ( fileerror == KErrNone ) {
- CleanupClosePushL( writeStream );
- writeStream.WriteInt32L( m_preferences->Count() );
-
- TPtrHashMapIter<TDesC,PrefElement> it( *m_preferences );
- const TDesC* key;
- const PrefElement* pref;
+ while ( ( key = it.NextKey() ) != 0 ) {
+ pref = it.CurrentValue();
+ aStream.WriteInt32L( key->Length() );
+ aStream.WriteL( *key );
+ aStream.WriteInt32L( pref->value().Length() );
+ aStream.WriteL( pref->value() );
+ aStream.WriteInt32L( pref->valueSize() );
+ }
+ aStream.CommitL();
+
+}
+
+// ----------------------------------------------------------------------------
+// WidgetPreferences::internalizeL
+//
+//
+// ----------------------------------------------------------------------------
+void WidgetPreferences::internalizeL(RReadStream& aStream)
+{
+ TInt count( aStream.ReadInt32L() );
+ for( TInt i = 0; i < count; i++ ) {
+
+ TInt len = aStream.ReadInt32L();
+
+ if ( len > 0 ) {
+ HBufC* key = HBufC::NewLC( len );
+ TPtr ptrkey = key->Des();
+ aStream.ReadL( ptrkey, len );
+ len = aStream.ReadInt32L();
- while ( ( key = it.NextKey() ) != 0 ) {
- pref = it.CurrentValue();
- writeStream.WriteInt32L( key->Length() );
- writeStream.WriteL( *key );
- writeStream.WriteInt32L( pref->value().Length() );
- writeStream.WriteL( pref->value() );
- writeStream.WriteInt32L( pref->valueSize() );
+ if ( len <= KMaxKeyValueSize ) {
+ HBufC* value = HBufC::NewLC( len );
+ TPtr ptrvalue = value->Des();
+ aStream.ReadL( ptrvalue, len );
+ PrefElement* pref = new ( ELeave ) PrefElement;
+ CleanupStack::PushL( pref );
+ pref->setValueL( ptrvalue );
+ TInt size = aStream.ReadInt32L();
+ pref->setValueSize( size );
+ m_preferences->InsertL( key, pref );
+ CleanupStack::Pop(); //pref
+ CleanupStack::PopAndDestroy(); //value
+ CleanupStack::Pop(); //key
}
+ else {
+ CleanupStack::PopAndDestroy( key );
+ }
- writeStream.CommitL();
- CleanupStack::PopAndDestroy(); //writeStream
+ }
+
+ else {
+ break;
}
+ }
- CleanupStack::PopAndDestroy( 2 ); //fs,filePath
- }
+ }
+
+// ----------------------------------------------------------------------------
+// WidgetPreferences::deleteAllPrefFiles
+//
+//
+// ----------------------------------------------------------------------------
+void WidgetPreferences::deleteAllPrefFiles(){
+
+ if ( !m_basepath || (m_basepath->Length() <= 0) )
+ return;
+
+
+ RFs fs;
+ // Deleting bkUp and main prefs file.
+ User::LeaveIfError(fs.Connect());
+ CleanupClosePushL( fs );
+
+ HBufC* bkFilePath = HBufC::NewLC( m_basepath->Length() + KPrefsBakFile().Length() );
+
+ TPtr fName( bkFilePath->Des() );
+ fName.Append( *m_basepath );
+ fName.Append( KPrefsBakFile );
+
+ fs.Delete( *bkFilePath );
+
+ CleanupStack::PopAndDestroy();
+
+ HBufC* prefFilePath = HBufC::NewLC( m_basepath->Length() + KPrefsFile().Length() );
+
+ TPtr fNamePr( prefFilePath->Des() );
+ fNamePr.Append( *m_basepath );
+ fNamePr.Append( KPrefsFile);
+
+ fs.Delete( *prefFilePath );
+
+ CleanupStack::PopAndDestroy(2);
}
@@ -374,61 +517,32 @@
// ----------------------------------------------------------------------------
void WidgetPreferences::loadL()
{
+ if ( !m_basepath || (m_basepath->Length() <= 0) )
+ return;
+
+ // Try to connect to file server
RFs fs;
- if ( !m_basepath || (m_basepath->Length() <= 0) )
- return;
-
- if ( fs.Connect() == KErrNone ) {
- CleanupClosePushL( fs );
- HBufC* filePath = HBufC::NewLC( m_basepath->Length() + KPrefsFile().Length() );
-
- TPtr fName( filePath->Des() );
- fName.Append( *m_basepath );
- fName.Append( KPrefsFile );
-
- RFileReadStream readStream;
-
- if ( readStream.Open( fs, *filePath, EFileRead ) == KErrNone ) {
- CleanupClosePushL( readStream );
- TInt count( readStream.ReadInt32L() );
-
- for( TInt i = 0; i < count; i++ ) {
- TInt len = readStream.ReadInt32L();
-
- if ( len > 0 ) {
- HBufC* key = HBufC::NewLC( len );
- TPtr ptrkey = key->Des();
- readStream.ReadL( ptrkey, len );
- len = readStream.ReadInt32L();
+ User::LeaveIfError(fs.Connect());
+ CleanupClosePushL( fs );
+
+ // Form settings file name
+ HBufC* filePath = HBufC::NewLC( m_basepath->Length() + KPrefsFile().Length() );
+ TPtr fName( filePath->Des() );
+ fName.Append( *m_basepath );
+ fName.Append( KPrefsFile );
- if ( len <= KMaxKeyValueSize ) {
- HBufC* value = HBufC::NewLC( len );
- TPtr ptrvalue = value->Des();
- readStream.ReadL( ptrvalue, len );
- PrefElement* pref = new ( ELeave ) PrefElement;
- CleanupStack::PushL( pref );
- pref->setValueL( ptrvalue );
- TInt size = readStream.ReadInt32L();
- pref->setValueSize( size );
- m_preferences->InsertL( key, pref );
- CleanupStack::Pop(); //pref
- CleanupStack::PopAndDestroy(); //value
- CleanupStack::Pop(); //key
- }
- else {
- CleanupStack::PopAndDestroy( key );
- }
- }
- else {
- break;
- }
- }
+ // Open stream
+ RFileReadStream readStream;
+ readStream.PushL();
+ TInt err = readStream.Open( fs, *filePath, EFileRead );
+ if(err!=KErrNone) {
+ User::Leave(err);
+ }
+
+ // Read the data from the stream
+ internalizeL(readStream);
- CleanupStack::PopAndDestroy(); //readStream
- }
-
- CleanupStack::PopAndDestroy( 2 ); //fs,filePath
- }
+ CleanupStack::PopAndDestroy(3); // readStream, filePath, fs
}
// ----------------------------------------------------------------------------
@@ -488,3 +602,4 @@
}
+