Index: io/qsettings.cpp
===================================================================
--- io/qsettings.cpp	(revision 43806)
+++ io/qsettings.cpp	(working copy)
@@ -74,6 +74,7 @@
 #endif // Q_OS_WIN
 #endif // QT_NO_QOBJECT
 
+#include <stdio.h>
 #include <stdlib.h>
 
 #ifndef CSIDL_COMMON_APPDATA
@@ -1584,31 +1585,52 @@
             } else
 #endif
             {
-                file.seek(0);
-                file.resize(0);
+                QFile swapFile(QString("%1/.%2.swp").arg(fileInfo.absolutePath(), fileInfo.fileName()));
 
-                if (format <= QSettings::IniFormat) {
-                    ok = writeIniFile(file, mergedKeys);
-                    if (!ok) {
-                        // try to restore old data; might work if the disk was full and the new data
-                        // was larger than the old data
-                        file.seek(0);
-                        file.resize(0);
-                        writeIniFile(file, confFile->originalKeys);
+                if (swapFile.exists()) {
+                    if (!swapFile.remove()) {
+                        for (quint32 i = 0; i < 100; i++) {
+                            swapFile.setFileName(QString("%1/.%2.%3.swp").arg(fileInfo.absolutePath()).arg(fileInfo.fileName()).arg(i));
+
+                            if (!swapFile.exists())
+                                break;
+
+                            if (swapFile.remove())
+                                break;
+                        }
                     }
-                } else {
-                    if (writeFunc) {
-                        QSettings::SettingsMap tempOriginalKeys;
+                }
 
-                        ParsedSettingsMap::const_iterator i = mergedKeys.constBegin();
-                        while (i != mergedKeys.constEnd()) {
-                            tempOriginalKeys.insert(i.key(), i.value());
-                            ++i;
+                if (swapFile.open(QFile::WriteOnly | QFile::Truncate)) {
+                    if (format <= QSettings::IniFormat) {
+                        ok = writeIniFile(swapFile, mergedKeys);
+                    } else {
+                        if (writeFunc) {
+                            QSettings::SettingsMap tempOriginalKeys;
+
+                            ParsedSettingsMap::const_iterator i = mergedKeys.constBegin();
+                            while (i != mergedKeys.constEnd()) {
+                                tempOriginalKeys.insert(i.key(), i.value());
+                                ++i;
+                            }
+                            ok = writeFunc(swapFile, tempOriginalKeys);
+                        } else {
+                            ok = false;
                         }
-                        ok = writeFunc(file, tempOriginalKeys);
-                    } else {
-                        ok = false;
                     }
+
+                    file.close();
+                    swapFile.close();
+
+                    if (ok) {
+#ifdef Q_OS_WIN
+                        ok = ::_wrename(QFileInfo(swapFile).absoluteFilePath().toStdWString().c_str(), QFileInfo(file).absoluteFilePath().toStdWString().c_str()) == 0; // Atomic move.
+#else
+                        ok = ::rename(qPrintable(QFileInfo(swapFile).absoluteFilePath()), qPrintable(QFileInfo(file).absoluteFilePath())) == 0; // Atomic move.
+#endif
+                    }
+                } else {
+                    ok = false;
                 }
             }
         } else {
