]> git.pld-linux.org Git - packages/keepassxc.git/commitdiff
- restore git.patch and qt5 support (the freezez with qt4 are still there)
authorJan Rękorajski <baggins@pld-linux.org>
Wed, 20 Apr 2016 18:06:38 +0000 (20:06 +0200)
committerJan Rękorajski <baggins@pld-linux.org>
Wed, 20 Apr 2016 18:06:38 +0000 (20:06 +0200)
- rel 2

git.patch [new file with mode: 0644]
keepassx.spec

diff --git a/git.patch b/git.patch
new file mode 100644 (file)
index 0000000..6be8810
--- /dev/null
+++ b/git.patch
@@ -0,0 +1,12915 @@
+diff --git a/.travis.yml b/.travis.yml
+index fa33cf0..550518a 100644
+--- a/.travis.yml
++++ b/.travis.yml
+@@ -5,16 +5,20 @@ compiler:
+   - gcc
+   - clang
+ language: cpp
++sudo: required
++dist: trusty
+ install:
+   - if [ "$TRAVIS_OS_NAME" = "linux" ]; then sudo apt-get -qq update; fi
+-  - if [ "$TRAVIS_OS_NAME" = "linux" ]; then sudo apt-get -qq install cmake libqt4-dev libgcrypt11-dev zlib1g-dev libxtst-dev; fi
++  - if [ "$TRAVIS_OS_NAME" = "linux" ]; then sudo apt-get -qq install cmake qtbase5-dev libqt5x11extras5-dev qttools5-dev qttools5-dev-tools libgcrypt20-dev zlib1g-dev libxtst-dev xvfb; fi
+   - if [ "$TRAVIS_OS_NAME" = "osx" ]; then brew update; fi
+   - if [ "$TRAVIS_OS_NAME" = "osx" ]; then brew ls | grep -wq cmake || brew install cmake; fi
+-  - if [ "$TRAVIS_OS_NAME" = "osx" ]; then brew ls | grep -wq qt || brew install qt; fi
++  - if [ "$TRAVIS_OS_NAME" = "osx" ]; then brew ls | grep -wq qt5 || brew install qt5; fi
+   - if [ "$TRAVIS_OS_NAME" = "osx" ]; then brew ls | grep -wq libgcrypt || brew install libgcrypt; fi
+-before_script: mkdir build && pushd build
++before_script:
++  - if [ "$TRAVIS_OS_NAME" = "osx" ]; then CMAKE_ARGS="-DCMAKE_PREFIX_PATH=/usr/local/opt/qt5"; fi
++  - mkdir build && pushd build
+ script:
+-  - cmake -DCMAKE_BUILD_TYPE=Debug -DWITH_GUI_TESTS=ON ..
++  - cmake -DCMAKE_BUILD_TYPE=Debug -DWITH_GUI_TESTS=ON $CMAKE_ARGS ..
+   - make
+   - if [ "$TRAVIS_OS_NAME" = "linux" ]; then make test ARGS+="-E testgui --output-on-failure"; fi
+   - if [ "$TRAVIS_OS_NAME" = "linux" ]; then xvfb-run -a --server-args="-screen 0 800x600x24" make test ARGS+="-R testgui --output-on-failure"; fi
+diff --git a/CMakeLists.txt b/CMakeLists.txt
+index 6df5503..21c46fa 100644
+--- a/CMakeLists.txt
++++ b/CMakeLists.txt
+@@ -21,7 +21,7 @@ endif()
+ project(KeePassX)
+-cmake_minimum_required(VERSION 2.6.4)
++cmake_minimum_required(VERSION 2.8.12)
+ set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/cmake)
+@@ -31,7 +31,7 @@ include(CheckCXXSourceCompiles)
+ option(WITH_TESTS "Enable building of unit tests" ON)
+ option(WITH_GUI_TESTS "Enable building of GUI tests" OFF)
+-option(WITH_CXX11 "Build with the C++ 11 standard" ON)
++option(WITH_DEV_BUILD "Use only for development. Disables/warns about deprecated methods." OFF)
+ set(KEEPASSX_VERSION "2.0.2")
+ set(KEEPASSX_VERSION_NUM "2.0.2")
+@@ -61,7 +61,7 @@ macro(add_gcc_compiler_flags FLAGS)
+   add_gcc_compiler_cflags("${FLAGS}")
+ endmacro(add_gcc_compiler_flags)
+-add_definitions(-DQT_NO_KEYWORDS -DQT_NO_EXCEPTIONS -DQT_NO_STL -DQT_STRICT_ITERATORS -DQT_NO_CAST_TO_ASCII)
++add_definitions(-DQT_NO_KEYWORDS -DQT_NO_EXCEPTIONS -DQT_STRICT_ITERATORS -DQT_NO_CAST_TO_ASCII)
+ add_gcc_compiler_flags("-fno-common -fstack-protector --param=ssp-buffer-size=4")
+ add_gcc_compiler_flags("-Wall -Wextra -Wundef -Wpointer-arith -Wno-long-long")
+@@ -100,14 +100,16 @@ if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
+   set(CMAKE_MODULE_LINKER_FLAGS "${CMAKE_MODULE_LINKER_FLAGS} -Wl,-z,relro")
+ endif()
+-if (WITH_CXX11)
+-  add_gcc_compiler_cxxflags("-std=c++0x")
+-  add_gcc_compiler_cflags("-ansi")
+-  if(APPLE)
+-    add_gcc_compiler_cxxflags("-stdlib=libc++")
+-  endif()
+-else()
+-  add_gcc_compiler_flags("-ansi")
++add_gcc_compiler_cxxflags("-std=c++11")
++
++if(APPLE)
++  add_gcc_compiler_cxxflags("-stdlib=libc++")
++endif()
++
++add_gcc_compiler_cflags("-ansi")
++
++if(WITH_DEV_BUILD)
++  add_definitions(-DQT_DEPRECATED_WARNINGS -DGCRYPT_NO_DEPRECATED)
+ endif()
+ if(MINGW)
+@@ -146,19 +148,18 @@ if(WITH_TESTS)
+   enable_testing()
+ endif(WITH_TESTS)
+-set(QT_REQUIRED_MODULES QtCore QtGui QtTest)
++find_package(Qt5Core          5.2 REQUIRED)
++find_package(Qt5Concurrent    5.2 REQUIRED)
++find_package(Qt5Widgets       5.2 REQUIRED)
++find_package(Qt5Test          5.2 REQUIRED)
++find_package(Qt5LinguistTools 5.2 REQUIRED)
++set(CMAKE_AUTOMOC ON)
+-find_package(Qt4 4.6.0 REQUIRED ${QT_REQUIRED_MODULES})
+-include(${QT_USE_FILE})
+ # Debian sets the the build type to None for package builds.
+ # Make sure we don't enable asserts there.
+ set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS_NONE QT_NO_DEBUG)
+-find_package(Gcrypt REQUIRED)
+-if(NOT (${GCRYPT_VERSION_STRING} VERSION_LESS "1.6.0"))
+-  message(STATUS "Gcrypt ${GCRYPT_VERSION_STRING} supports the SALSA20 cipher")
+-  set(GCRYPT_HAS_SALSA20 1)
+-endif()
++find_package(Gcrypt 1.6.0 REQUIRED)
+ find_package(ZLIB REQUIRED)
+@@ -199,10 +200,7 @@ endif()
+ include_directories(SYSTEM ${GCRYPT_INCLUDE_DIR} ${ZLIB_INCLUDE_DIR})
+-if(NOT (${CMAKE_VERSION} VERSION_LESS 2.8.3))
+-  set(PRINT_SUMMARY ON)
+-  include(FeatureSummary)
+-endif()
++include(FeatureSummary)
+ add_subdirectory(src)
+ add_subdirectory(share)
+diff --git a/README.md b/README.md
+index 326bd4a..0c18ff3 100644
+--- a/README.md
++++ b/README.md
+@@ -49,20 +49,20 @@ Once downloaded, double click on the file to execute the installer.
+ The following tools must exist within your PATH:
+ * make
+-* cmake (>= 2.6.4)
+-* g++ or clang++
++* cmake (>= 2.8.12)
++* g++ (>= 4.7) or clang++ (>= 3.0)
+ The following libraries are required:
+-* Qt 4 (>= 4.6)
+-* libgcrypt
++* Qt 5 (>= 5.2): qtbase and qttools5
++* libgcrypt (>= 1.6)
+ * zlib
+-* libxtst (optional for auto-type on X11)
++* libxtst, qtx11extras (optional for auto-type on X11)
+ On Debian you can install them with:
+ ```bash
+-sudo apt-get install build-essential cmake libqt4-dev libgcrypt11-dev zlib1g-dev
++sudo apt-get install build-essential cmake qtbase5-dev libqt5x11extras5-dev qttools5-dev qttools5-dev-tools libgcrypt20-dev zlib1g-dev
+ ```
+ #### Build Steps
+diff --git a/share/translations/CMakeLists.txt b/share/translations/CMakeLists.txt
+index b1aa878..7380750 100644
+--- a/share/translations/CMakeLists.txt
++++ b/share/translations/CMakeLists.txt
+@@ -17,9 +17,9 @@ file(GLOB TRANSLATION_FILES *.ts)
+ get_filename_component(TRANSLATION_EN_ABS keepassx_en.ts ABSOLUTE)
+ list(REMOVE_ITEM TRANSLATION_FILES keepassx_en.ts)
+ list(REMOVE_ITEM TRANSLATION_FILES ${TRANSLATION_EN_ABS})
+-message(STATUS ${TRANSLATION_FILES})
++message(STATUS "${TRANSLATION_FILES}")
+-qt4_add_translation(QM_FILES ${TRANSLATION_FILES})
++qt5_add_translation(QM_FILES ${TRANSLATION_FILES})
+ install(FILES ${QM_FILES} DESTINATION ${DATA_INSTALL_DIR}/translations)
+ add_custom_target(translations DEPENDS ${QM_FILES})
+diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
+index da8b9ec..da35651 100644
+--- a/src/CMakeLists.txt
++++ b/src/CMakeLists.txt
+@@ -54,9 +54,6 @@ set(keepassx_SOURCES
+     core/ListDeleter.h
+     core/Metadata.cpp
+     core/PasswordGenerator.cpp
+-    core/qlockfile.cpp
+-    core/qsavefile.cpp
+-    core/qsavefile_p.h
+     core/SignalMultiplexer.cpp
+     core/TimeDelta.cpp
+     core/TimeInfo.cpp
+@@ -64,8 +61,6 @@ set(keepassx_SOURCES
+     core/Tools.cpp
+     core/Translator.cpp
+     core/Uuid.cpp
+-    core/qcommandlineoption.cpp
+-    core/qcommandlineparser.cpp
+     crypto/Crypto.cpp
+     crypto/CryptoHash.cpp
+     crypto/Random.cpp
+@@ -133,94 +128,10 @@ set(keepassx_SOURCES
+     streams/SymmetricCipherStream.cpp
+ )
+-if(NOT GCRYPT_HAS_SALSA20)
+-  set(keepassx_SOURCES
+-      ${keepassx_SOURCES}
+-      crypto/salsa20/ecrypt-config.h
+-      crypto/salsa20/ecrypt-machine.h
+-      crypto/salsa20/ecrypt-portable.h
+-      crypto/salsa20/ecrypt-sync.h
+-      crypto/salsa20/salsa20.c
+-      crypto/SymmetricCipherSalsa20.cpp
+-  )
+-endif()
+-
+-if(UNIX)
+-  set(keepassx_SOURCES
+-      ${keepassx_SOURCES}
+-      core/qlockfile_unix.cpp
+-  )
+-elseif(MINGW)
+-  set(keepassx_SOURCES
+-      ${keepassx_SOURCES}
+-      core/qlockfile_win.cpp
+-  )
+-endif()
+-
+ set(keepassx_SOURCES_MAINEXE
+     main.cpp
+ )
+-set(keepassx_MOC
+-    autotype/AutoType.h
+-    autotype/AutoTypeSelectDialog.h
+-    autotype/AutoTypeSelectView.h
+-    autotype/ShortcutWidget.h
+-    autotype/WindowSelectComboBox.h
+-    core/AutoTypeAssociations.h
+-    core/Config.h
+-    core/Database.h
+-    core/Entry.h
+-    core/EntryAttachments.h
+-    core/EntryAttributes.h
+-    core/Group.h
+-    core/InactivityTimer.h
+-    core/Metadata.h
+-    core/qsavefile.h
+-    gui/AboutDialog.h
+-    gui/Application.h
+-    gui/ChangeMasterKeyWidget.h
+-    gui/Clipboard.h
+-    gui/DatabaseOpenWidget.h
+-    gui/DatabaseRepairWidget.h
+-    gui/DatabaseSettingsWidget.h
+-    gui/DatabaseTabWidget.h
+-    gui/DatabaseWidget.h
+-    gui/DatabaseWidgetStateSync.h
+-    gui/DialogyWidget.h
+-    gui/DragTabBar.h
+-    gui/EditWidget.h
+-    gui/EditWidgetIcons.h
+-    gui/EditWidgetProperties.h
+-    gui/IconModels.h
+-    gui/KeePass1OpenWidget.h
+-    gui/LineEdit.h
+-    gui/MainWindow.h
+-    gui/PasswordEdit.h
+-    gui/PasswordGeneratorWidget.h
+-    gui/PasswordComboBox.h
+-    gui/SettingsWidget.h
+-    gui/SortFilterHideProxyModel.h
+-    gui/UnlockDatabaseWidget.h
+-    gui/WelcomeWidget.h
+-    gui/entry/AutoTypeAssociationsModel.h
+-    gui/entry/EditEntryWidget.h
+-    gui/entry/EntryAttachmentsModel.h
+-    gui/entry/EntryAttributesModel.h
+-    gui/entry/EntryHistoryModel.h
+-    gui/entry/EntryModel.h
+-    gui/entry/EntryView.h
+-    gui/group/EditGroupWidget.h
+-    gui/group/GroupModel.h
+-    gui/group/GroupView.h
+-    keys/CompositeKey_p.h
+-    streams/HashedBlockStream.h
+-    streams/LayeredStream.h
+-    streams/qtiocompressor.h
+-    streams/StoreDataStream.h
+-    streams/SymmetricCipherStream.h
+-)
+-
+ set(keepassx_FORMS
+     gui/AboutDialog.ui
+     gui/ChangeMasterKeyWidget.ui
+@@ -248,17 +159,18 @@ if(MINGW)
+       ${CMAKE_SOURCE_DIR}/share/windows/icon.rc)
+ endif()
+-qt4_wrap_ui(keepassx_SOURCES ${keepassx_FORMS})
+-qt4_wrap_cpp(keepassx_SOURCES ${keepassx_MOC})
++qt5_wrap_ui(keepassx_SOURCES ${keepassx_FORMS})
+ add_library(keepassx_core STATIC ${keepassx_SOURCES})
+ set_target_properties(keepassx_core PROPERTIES COMPILE_DEFINITIONS KEEPASSX_BUILDING_CORE)
++target_link_libraries(keepassx_core Qt5::Core Qt5::Concurrent Qt5::Widgets)
+ add_executable(${PROGNAME} WIN32 MACOSX_BUNDLE ${keepassx_SOURCES_MAINEXE})
+ target_link_libraries(${PROGNAME}
+                       keepassx_core
+-                      ${QT_QTCORE_LIBRARY}
+-                      ${QT_QTGUI_LIBRARY}
++                      Qt5::Core
++                      Qt5::Concurrent
++                      Qt5::Widgets
+                       ${GCRYPT_LIBRARIES}
+                       ${ZLIB_LIBRARIES})
+@@ -276,7 +188,7 @@ install(TARGETS ${PROGNAME}
+ add_subdirectory(autotype)
+-if(APPLE AND NOT (${CMAKE_VERSION} VERSION_LESS 2.8.8))
++if(APPLE)
+   if(QT_MAC_USE_COCOA AND EXISTS "${QT_LIBRARY_DIR}/Resources/qt_menu.nib")
+     install(DIRECTORY "${QT_LIBRARY_DIR}/Resources/qt_menu.nib"
+             DESTINATION "${DATA_INSTALL_DIR}")
+@@ -294,7 +206,7 @@ if(APPLE AND NOT (${CMAKE_VERSION} VERSION_LESS 2.8.8))
+   install_qt4_executable(${PROGNAME}.app "qjpeg;qgif;qico;qtaccessiblewidgets")
+ endif()
+-if(MINGW AND NOT (${CMAKE_VERSION} VERSION_LESS 2.8.8))
++if(MINGW )
+   set(CPACK_GENERATOR "ZIP")
+   set(CPACK_STRIP_FILES ON)
+   set(CPACK_PACKAGE_FILE_NAME "${PROGNAME}-${KEEPASSX_VERSION_NUM}")
+diff --git a/src/autotype/AutoType.cpp b/src/autotype/AutoType.cpp
+index f1b7e3e..15185b2 100644
+--- a/src/autotype/AutoType.cpp
++++ b/src/autotype/AutoType.cpp
+@@ -32,7 +32,7 @@
+ #include "core/Tools.h"
+ #include "gui/MessageBox.h"
+-AutoType* AutoType::m_instance = Q_NULLPTR;
++AutoType* AutoType::m_instance = nullptr;
+ AutoType::AutoType(QObject* parent, bool test)
+     : QObject(parent)
+@@ -40,8 +40,8 @@ AutoType::AutoType(QObject* parent, bool test)
+     , m_currentGlobalKey(static_cast<Qt::Key>(0))
+     , m_currentGlobalModifiers(0)
+     , m_pluginLoader(new QPluginLoader(this))
+-    , m_plugin(Q_NULLPTR)
+-    , m_executor(Q_NULLPTR)
++    , m_plugin(nullptr)
++    , m_executor(nullptr)
+     , m_windowFromGlobal(0)
+ {
+     // prevent crash when the plugin has unresolved symbols
+@@ -49,7 +49,7 @@ AutoType::AutoType(QObject* parent, bool test)
+     QString pluginName = "keepassx-autotype-";
+     if (!test) {
+-        pluginName += Tools::platform();
++        pluginName += QApplication::platformName();
+     }
+     else {
+         pluginName += "test";
+@@ -68,7 +68,7 @@ AutoType::~AutoType()
+ {
+     if (m_executor) {
+         delete m_executor;
+-        m_executor = Q_NULLPTR;
++        m_executor = nullptr;
+     }
+ }
+@@ -79,7 +79,7 @@ void AutoType::loadPlugin(const QString& pluginPath)
+     QObject* pluginInstance = m_pluginLoader->instance();
+     if (pluginInstance) {
+         m_plugin = qobject_cast<AutoTypePlatformInterface*>(pluginInstance);
+-        m_executor = Q_NULLPTR;
++        m_executor = nullptr;
+         if (m_plugin) {
+             if (m_plugin->isAvailable()) {
+@@ -202,11 +202,11 @@ void AutoType::performGlobalAutoType(const QList<Database*>& dbList)
+         QString message = tr("Couldn't find an entry that matches the window title:");
+         message.append("\n\n");
+         message.append(windowTitle);
+-        MessageBox::information(Q_NULLPTR, tr("Auto-Type - KeePassX"), message);
++        MessageBox::information(nullptr, tr("Auto-Type - KeePassX"), message);
+     }
+     else if ((entryList.size() == 1) && !config()->get("security/autotypeask").toBool()) {
+         m_inAutoType = false;
+-        performAutoType(entryList.first(), Q_NULLPTR, sequenceHash[entryList.first()]);
++        performAutoType(entryList.first(), nullptr, sequenceHash[entryList.first()]);
+     }
+     else {
+         m_windowFromGlobal = m_plugin->activeWindow();
+@@ -228,7 +228,7 @@ void AutoType::performAutoTypeFromGlobal(Entry* entry, const QString& sequence)
+     m_plugin->raiseWindow(m_windowFromGlobal);
+     m_inAutoType = false;
+-    performAutoType(entry, Q_NULLPTR, sequence, m_windowFromGlobal);
++    performAutoType(entry, nullptr, sequence, m_windowFromGlobal);
+ }
+ void AutoType::resetInAutoType()
+@@ -242,12 +242,12 @@ void AutoType::unloadPlugin()
+ {
+     if (m_executor) {
+         delete m_executor;
+-        m_executor = Q_NULLPTR;
++        m_executor = nullptr;
+     }
+     if (m_plugin) {
+         m_plugin->unload();
+-        m_plugin = Q_NULLPTR;
++        m_plugin = nullptr;
+     }
+ }
+diff --git a/src/autotype/AutoType.h b/src/autotype/AutoType.h
+index f3d626c..d1c8817 100644
+--- a/src/autotype/AutoType.h
++++ b/src/autotype/AutoType.h
+@@ -22,8 +22,6 @@
+ #include <QStringList>
+ #include <QWidget>
+-#include "core/Global.h"
+-
+ class AutoTypeAction;
+ class AutoTypeExecutor;
+ class AutoTypePlatformInterface;
+@@ -37,7 +35,7 @@ class AutoType : public QObject
+ public:
+     QStringList windowTitles();
+-    void performAutoType(const Entry* entry, QWidget* hideWindow = Q_NULLPTR,
++    void performAutoType(const Entry* entry, QWidget* hideWindow = nullptr,
+                          const QString& customSequence = QString(), WId window = 0);
+     bool registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers);
+     void unregisterGlobalShortcut();
+@@ -62,7 +60,7 @@ private Q_SLOTS:
+     void unloadPlugin();
+ private:
+-    explicit AutoType(QObject* parent = Q_NULLPTR, bool test = false);
++    explicit AutoType(QObject* parent = nullptr, bool test = false);
+     ~AutoType();
+     void loadPlugin(const QString& pluginPath);
+     bool parseActions(const QString& sequence, const Entry* entry, QList<AutoTypeAction*>& actions);
+diff --git a/src/autotype/AutoTypeAction.h b/src/autotype/AutoTypeAction.h
+index 07e050b..490f0d8 100644
+--- a/src/autotype/AutoTypeAction.h
++++ b/src/autotype/AutoTypeAction.h
+@@ -66,7 +66,7 @@ public:
+ class KEEPASSX_EXPORT AutoTypeClearField : public AutoTypeAction
+ {
+ public:
+-    explicit AutoTypeClearField();
++    AutoTypeClearField();
+     AutoTypeAction* clone();
+     void accept(AutoTypeExecutor* executor);
+ };
+diff --git a/src/autotype/AutoTypeSelectDialog.h b/src/autotype/AutoTypeSelectDialog.h
+index 4f455c7..c0dbfe4 100644
+--- a/src/autotype/AutoTypeSelectDialog.h
++++ b/src/autotype/AutoTypeSelectDialog.h
+@@ -22,8 +22,6 @@
+ #include <QDialog>
+ #include <QHash>
+-#include "core/Global.h"
+-
+ class AutoTypeSelectView;
+ class Entry;
+@@ -32,7 +30,7 @@ class AutoTypeSelectDialog : public QDialog
+     Q_OBJECT
+ public:
+-    explicit AutoTypeSelectDialog(QWidget* parent = Q_NULLPTR);
++    explicit AutoTypeSelectDialog(QWidget* parent = nullptr);
+     void setEntries(const QList<Entry*>& entries, const QHash<Entry*, QString>& sequences);
+ Q_SIGNALS:
+diff --git a/src/autotype/AutoTypeSelectView.h b/src/autotype/AutoTypeSelectView.h
+index bcbb262..749f6a9 100644
+--- a/src/autotype/AutoTypeSelectView.h
++++ b/src/autotype/AutoTypeSelectView.h
+@@ -18,7 +18,6 @@
+ #ifndef KEEPASSX_AUTOTYPESELECTVIEW_H
+ #define KEEPASSX_AUTOTYPESELECTVIEW_H
+-#include "core/Global.h"
+ #include "gui/entry/EntryView.h"
+ class Entry;
+@@ -28,10 +27,10 @@ class AutoTypeSelectView : public EntryView
+     Q_OBJECT
+ public:
+-    explicit AutoTypeSelectView(QWidget* parent = Q_NULLPTR);
++    explicit AutoTypeSelectView(QWidget* parent = nullptr);
+ protected:
+-    void mouseMoveEvent(QMouseEvent* event) Q_DECL_OVERRIDE;
++    void mouseMoveEvent(QMouseEvent* event) override;
+ private Q_SLOTS:
+     void selectFirstEntry();
+diff --git a/src/autotype/CMakeLists.txt b/src/autotype/CMakeLists.txt
+index a0f7877..707edf9 100644
+--- a/src/autotype/CMakeLists.txt
++++ b/src/autotype/CMakeLists.txt
+@@ -1,12 +1,12 @@
+-if(Q_WS_X11)
++if(UNIX AND NOT APPLE)
+   find_package(X11)
+-  if(PRINT_SUMMARY)
+-    add_feature_info(libXi X11_Xi_FOUND "The X11 Xi Protocol library is required for auto-type")
+-    add_feature_info(libXtest X11_XTest_FOUND "The X11 XTEST Protocol library is required for auto-type")
+-  endif()
++  find_package(Qt5X11Extras 5.2)
++  add_feature_info(libXi X11_Xi_FOUND "The X11 Xi Protocol library is required for auto-type")
++  add_feature_info(libXtest X11_XTest_FOUND "The X11 XTEST Protocol library is required for auto-type")
++  add_feature_info(Qt5X11Extras Qt5X11Extras_FOUND "The Qt5X11Extras library is required for auto-type")
+-  if(X11_FOUND AND X11_Xi_FOUND AND X11_XTest_FOUND)
+-    add_subdirectory(x11)
++  if(X11_FOUND AND X11_Xi_FOUND AND X11_XTest_FOUND AND Qt5X11Extras_FOUND)
++    add_subdirectory(xcb)
+   endif()
+ endif()
+diff --git a/src/autotype/ShortcutWidget.h b/src/autotype/ShortcutWidget.h
+index 5ff306c..60898ab 100644
+--- a/src/autotype/ShortcutWidget.h
++++ b/src/autotype/ShortcutWidget.h
+@@ -20,21 +20,19 @@
+ #include <QLineEdit>
+-#include "core/Global.h"
+-
+ class ShortcutWidget : public QLineEdit
+ {
+     Q_OBJECT
+ public:
+-    explicit ShortcutWidget(QWidget* parent = Q_NULLPTR);
++    explicit ShortcutWidget(QWidget* parent = nullptr);
+     Qt::Key key() const;
+     Qt::KeyboardModifiers modifiers() const;
+     void setShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers);
+ protected:
+-    void keyPressEvent(QKeyEvent* event) Q_DECL_OVERRIDE;
+-    void keyReleaseEvent(QKeyEvent* event) Q_DECL_OVERRIDE;
++    void keyPressEvent(QKeyEvent* event) override;
++    void keyReleaseEvent(QKeyEvent* event) override;
+ private:
+     void keyEvent(QKeyEvent* event);
+diff --git a/src/autotype/WindowSelectComboBox.h b/src/autotype/WindowSelectComboBox.h
+index 661bc84..244119a 100644
+--- a/src/autotype/WindowSelectComboBox.h
++++ b/src/autotype/WindowSelectComboBox.h
+@@ -20,19 +20,17 @@
+ #include <QComboBox>
+-#include "core/Global.h"
+-
+ class WindowSelectComboBox : public QComboBox
+ {
+     Q_OBJECT
+ public:
+-    explicit WindowSelectComboBox(QWidget* parent = Q_NULLPTR);
++    explicit WindowSelectComboBox(QWidget* parent = nullptr);
+     void refreshWindowList();
+-    void showPopup() Q_DECL_OVERRIDE;
+-    QSize sizeHint() const Q_DECL_OVERRIDE;
+-    QSize minimumSizeHint() const Q_DECL_OVERRIDE;
++    void showPopup() override;
++    QSize sizeHint() const override;
++    QSize minimumSizeHint() const override;
+ };
+ #endif // KEEPASSX_WINDOWSELECTCOMBOBOX_H
+diff --git a/src/autotype/test/AutoTypeTest.cpp b/src/autotype/test/AutoTypeTest.cpp
+index a8bcc71..979af8b 100644
+--- a/src/autotype/test/AutoTypeTest.cpp
++++ b/src/autotype/test/AutoTypeTest.cpp
+@@ -129,5 +129,3 @@ void AutoTypeExecturorTest::execKey(AutoTypeKey* action)
+ {
+     m_platform->addActionKey(action);
+ }
+-
+-Q_EXPORT_PLUGIN2(keepassx-autotype-test, AutoTypePlatformTest)
+diff --git a/src/autotype/test/AutoTypeTest.h b/src/autotype/test/AutoTypeTest.h
+index c791c15..8c6e524 100644
+--- a/src/autotype/test/AutoTypeTest.h
++++ b/src/autotype/test/AutoTypeTest.h
+@@ -23,34 +23,34 @@
+ #include "autotype/AutoTypePlatformPlugin.h"
+ #include "autotype/AutoTypeAction.h"
+ #include "autotype/test/AutoTypeTestInterface.h"
+-#include "core/Global.h"
+ class AutoTypePlatformTest : public QObject,
+                              public AutoTypePlatformInterface,
+                              public AutoTypeTestInterface
+ {
+     Q_OBJECT
++    Q_PLUGIN_METADATA(IID "org.keepassx.AutoTypePlatformInterface")
+     Q_INTERFACES(AutoTypePlatformInterface AutoTypeTestInterface)
+ public:
+-    QString keyToString(Qt::Key key) Q_DECL_OVERRIDE;
++    QString keyToString(Qt::Key key) override;
+-    bool isAvailable() Q_DECL_OVERRIDE;
+-    QStringList windowTitles() Q_DECL_OVERRIDE;
+-    WId activeWindow() Q_DECL_OVERRIDE;
+-    QString activeWindowTitle() Q_DECL_OVERRIDE;
+-    bool registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) Q_DECL_OVERRIDE;
+-    void unregisterGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) Q_DECL_OVERRIDE;
+-    int platformEventFilter(void* event) Q_DECL_OVERRIDE;
+-    int initialTimeout() Q_DECL_OVERRIDE;
+-    bool raiseWindow(WId window) Q_DECL_OVERRIDE;
+-    AutoTypeExecutor* createExecutor() Q_DECL_OVERRIDE;
++    bool isAvailable() override;
++    QStringList windowTitles() override;
++    WId activeWindow() override;
++    QString activeWindowTitle() override;
++    bool registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) override;
++    void unregisterGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) override;
++    int platformEventFilter(void* event) override;
++    int initialTimeout() override;
++    bool raiseWindow(WId window) override;
++    AutoTypeExecutor* createExecutor() override;
+-    void setActiveWindowTitle(const QString& title) Q_DECL_OVERRIDE;
++    void setActiveWindowTitle(const QString& title) override;
+-    QString actionChars() Q_DECL_OVERRIDE;
+-    int actionCount() Q_DECL_OVERRIDE;
+-    void clearActions() Q_DECL_OVERRIDE;
++    QString actionChars() override;
++    int actionCount() override;
++    void clearActions() override;
+     void addActionChar(AutoTypeChar* action);
+     void addActionKey(AutoTypeKey* action);
+@@ -69,8 +69,8 @@ class AutoTypeExecturorTest : public AutoTypeExecutor
+ public:
+     explicit AutoTypeExecturorTest(AutoTypePlatformTest* platform);
+-    void execChar(AutoTypeChar* action) Q_DECL_OVERRIDE;
+-    void execKey(AutoTypeKey* action) Q_DECL_OVERRIDE;
++    void execChar(AutoTypeChar* action) override;
++    void execKey(AutoTypeKey* action) override;
+ private:
+     AutoTypePlatformTest* const m_platform;
+diff --git a/src/autotype/test/CMakeLists.txt b/src/autotype/test/CMakeLists.txt
+index 749f7d5..9b3dbd4 100644
+--- a/src/autotype/test/CMakeLists.txt
++++ b/src/autotype/test/CMakeLists.txt
+@@ -2,11 +2,5 @@ set(autotype_test_SOURCES
+     AutoTypeTest.cpp
+ )
+-set(autotype_test_MOC
+-    AutoTypeTest.h
+-)
+-
+-qt4_wrap_cpp(autotype_test_SOURCES ${autotype_test_MOC})
+-
+ add_library(keepassx-autotype-test MODULE ${autotype_test_SOURCES})
+-target_link_libraries(keepassx-autotype-test testautotype ${QT_QTCORE_LIBRARY} ${QT_QTGUI_LIBRARY})
++target_link_libraries(keepassx-autotype-test testautotype Qt5::Core Qt5::Widgets)
+diff --git a/src/autotype/x11/AutoTypeX11.cpp b/src/autotype/x11/AutoTypeX11.cpp
+deleted file mode 100644
+index 6a20a88..0000000
+--- a/src/autotype/x11/AutoTypeX11.cpp
++++ /dev/null
+@@ -1,850 +0,0 @@
+-/*
+- *  Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
+- *  Copyright (C) 2000-2008 Tom Sato <VEF00200@nifty.ne.jp>
+- *
+- *  This program is free software: you can redistribute it and/or modify
+- *  it under the terms of the GNU General Public License as published by
+- *  the Free Software Foundation, either version 2 or (at your option)
+- *  version 3 of the License.
+- *
+- *  This program is distributed in the hope that it will be useful,
+- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+- *  GNU General Public License for more details.
+- *
+- *  You should have received a copy of the GNU General Public License
+- *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+- */
+-
+-#include "AutoTypeX11.h"
+-#include "KeySymMap.h"
+-
+-#include <time.h>
+-
+-bool AutoTypePlatformX11::m_catchXErrors = false;
+-bool AutoTypePlatformX11::m_xErrorOccured = false;
+-int (*AutoTypePlatformX11::m_oldXErrorHandler)(Display*, XErrorEvent*) = Q_NULLPTR;
+-
+-AutoTypePlatformX11::AutoTypePlatformX11()
+-{
+-    m_dpy = QX11Info::display();
+-    m_rootWindow = QX11Info::appRootWindow();
+-
+-    m_atomWmState = XInternAtom(m_dpy, "WM_STATE", True);
+-    m_atomWmName = XInternAtom(m_dpy, "WM_NAME", True);
+-    m_atomNetWmName = XInternAtom(m_dpy, "_NET_WM_NAME", True);
+-    m_atomString = XInternAtom(m_dpy, "STRING", True);
+-    m_atomUtf8String = XInternAtom(m_dpy, "UTF8_STRING", True);
+-    m_atomNetActiveWindow = XInternAtom(m_dpy, "_NET_ACTIVE_WINDOW", True);
+-
+-    m_classBlacklist << "desktop_window" << "gnome-panel"; // Gnome
+-    m_classBlacklist << "kdesktop" << "kicker"; // KDE 3
+-    m_classBlacklist << "Plasma"; // KDE 4
+-    m_classBlacklist << "plasmashell"; // KDE 5
+-    m_classBlacklist << "xfdesktop" << "xfce4-panel"; // Xfce 4
+-
+-    m_currentGlobalKey = static_cast<Qt::Key>(0);
+-    m_currentGlobalModifiers = 0;
+-
+-    m_keysymTable = Q_NULLPTR;
+-    m_xkb = Q_NULLPTR;
+-    m_remapKeycode = 0;
+-    m_currentRemapKeysym = NoSymbol;
+-    m_modifierMask = ControlMask | ShiftMask | Mod1Mask | Mod4Mask;
+-
+-    m_loaded = true;
+-
+-    updateKeymap();
+-}
+-
+-bool AutoTypePlatformX11::isAvailable()
+-{
+-    int ignore;
+-
+-    if (!XQueryExtension(m_dpy, "XInputExtension", &ignore, &ignore, &ignore)) {
+-        return false;
+-    }
+-
+-    if (!XQueryExtension(m_dpy, "XTEST", &ignore, &ignore, &ignore)) {
+-        return false;
+-    }
+-
+-    if (!m_xkb) {
+-        XkbDescPtr kbd = getKeyboard();
+-
+-        if (!kbd) {
+-            return false;
+-        }
+-
+-        XkbFreeKeyboard(kbd, XkbAllComponentsMask, True);
+-    }
+-
+-    return true;
+-}
+-
+-void AutoTypePlatformX11::unload()
+-{
+-    // Restore the KeyboardMapping to its original state.
+-    if (m_currentRemapKeysym != NoSymbol) {
+-        AddKeysym(NoSymbol);
+-    }
+-
+-    if (m_keysymTable) {
+-        XFree(m_keysymTable);
+-    }
+-
+-    if (m_xkb) {
+-        XkbFreeKeyboard(m_xkb, XkbAllComponentsMask, True);
+-    }
+-
+-    m_loaded = false;
+-}
+-
+-QStringList AutoTypePlatformX11::windowTitles()
+-{
+-    return windowTitlesRecursive(m_rootWindow);
+-}
+-
+-WId AutoTypePlatformX11::activeWindow()
+-{
+-    Window window;
+-    int revert_to_return;
+-    XGetInputFocus(m_dpy, &window, &revert_to_return);
+-
+-    int tree;
+-    do {
+-        if (isTopLevelWindow(window)) {
+-            break;
+-        }
+-
+-        Window root;
+-        Window parent;
+-        Window* children = Q_NULLPTR;
+-        unsigned int numChildren;
+-        tree = XQueryTree(m_dpy, window, &root, &parent, &children, &numChildren);
+-        window = parent;
+-        if (children) {
+-            XFree(children);
+-        }
+-    } while (tree && window);
+-
+-    return window;
+-}
+-
+-QString AutoTypePlatformX11::activeWindowTitle()
+-{
+-    return windowTitle(activeWindow(), true);
+-}
+-
+-bool AutoTypePlatformX11::registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers)
+-{
+-    int keycode = XKeysymToKeycode(m_dpy, charToKeySym(key));
+-    uint nativeModifiers = qtToNativeModifiers(modifiers);
+-
+-    startCatchXErrors();
+-    XGrabKey(m_dpy, keycode, nativeModifiers, m_rootWindow, True, GrabModeAsync, GrabModeAsync);
+-    XGrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask, m_rootWindow, True, GrabModeAsync,
+-             GrabModeAsync);
+-    XGrabKey(m_dpy, keycode, nativeModifiers | LockMask, m_rootWindow, True, GrabModeAsync,
+-             GrabModeAsync);
+-    XGrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask | LockMask, m_rootWindow, True,
+-             GrabModeAsync, GrabModeAsync);
+-    stopCatchXErrors();
+-
+-    if (!m_xErrorOccured) {
+-        m_currentGlobalKey = key;
+-        m_currentGlobalModifiers = modifiers;
+-        m_currentGlobalKeycode = keycode;
+-        m_currentGlobalNativeModifiers = nativeModifiers;
+-        return true;
+-    }
+-    else {
+-        unregisterGlobalShortcut(key, modifiers);
+-        return false;
+-    }
+-}
+-
+-uint AutoTypePlatformX11::qtToNativeModifiers(Qt::KeyboardModifiers modifiers)
+-{
+-    uint nativeModifiers = 0;
+-
+-    if (modifiers & Qt::ShiftModifier) {
+-        nativeModifiers |= ShiftMask;
+-    }
+-    if (modifiers & Qt::ControlModifier) {
+-        nativeModifiers |= ControlMask;
+-    }
+-    if (modifiers & Qt::AltModifier) {
+-        nativeModifiers |= Mod1Mask;
+-    }
+-    if (modifiers & Qt::MetaModifier) {
+-        nativeModifiers |= Mod4Mask;
+-    }
+-
+-    return nativeModifiers;
+-}
+-
+-void AutoTypePlatformX11::unregisterGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers)
+-{
+-    KeyCode keycode = XKeysymToKeycode(m_dpy, charToKeySym(key));
+-    uint nativeModifiers = qtToNativeModifiers(modifiers);
+-
+-    XUngrabKey(m_dpy, keycode, nativeModifiers, m_rootWindow);
+-    XUngrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask, m_rootWindow);
+-    XUngrabKey(m_dpy, keycode, nativeModifiers | LockMask, m_rootWindow);
+-    XUngrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask | LockMask, m_rootWindow);
+-
+-    m_currentGlobalKey = static_cast<Qt::Key>(0);
+-    m_currentGlobalModifiers = 0;
+-    m_currentGlobalKeycode = 0;
+-    m_currentGlobalNativeModifiers = 0;
+-}
+-
+-int AutoTypePlatformX11::platformEventFilter(void* event)
+-{
+-    XEvent* xevent = static_cast<XEvent*>(event);
+-
+-    if ((xevent->type == KeyPress || xevent->type == KeyRelease)
+-            && m_currentGlobalKey
+-            && xevent->xkey.keycode == m_currentGlobalKeycode
+-            && (xevent->xkey.state & m_modifierMask) == m_currentGlobalNativeModifiers
+-            && (!QApplication::activeWindow() || QApplication::activeWindow()->isMinimized())
+-            && m_loaded) {
+-        if (xevent->type == KeyPress) {
+-            Q_EMIT globalShortcutTriggered();
+-        }
+-        return 1;
+-    }
+-    if (xevent->type == MappingNotify && m_loaded) {
+-        XRefreshKeyboardMapping(reinterpret_cast<XMappingEvent*>(xevent));
+-        updateKeymap();
+-    }
+-
+-    return -1;
+-}
+-
+-AutoTypeExecutor* AutoTypePlatformX11::createExecutor()
+-{
+-    return new AutoTypeExecturorX11(this);
+-}
+-
+-QString AutoTypePlatformX11::windowTitle(Window window, bool useBlacklist)
+-{
+-    QString title;
+-
+-    Atom type;
+-    int format;
+-    unsigned long nitems;
+-    unsigned long after;
+-    unsigned char* data = Q_NULLPTR;
+-
+-    // the window manager spec says we should read _NET_WM_NAME first, then fall back to WM_NAME
+-
+-    int retVal = XGetWindowProperty(m_dpy, window, m_atomNetWmName, 0, 1000, False, m_atomUtf8String,
+-                                    &type, &format, &nitems, &after, &data);
+-
+-    if ((retVal == 0) && data) {
+-        title = QString::fromUtf8(reinterpret_cast<char*>(data));
+-    }
+-    else {
+-        XTextProperty textProp;
+-        retVal = XGetTextProperty(m_dpy, window, &textProp, m_atomWmName);
+-        if ((retVal != 0) && textProp.value) {
+-            char** textList = Q_NULLPTR;
+-            int count;
+-
+-            if (textProp.encoding == m_atomUtf8String) {
+-                title = QString::fromUtf8(reinterpret_cast<char*>(textProp.value));
+-            }
+-            else if ((XmbTextPropertyToTextList(m_dpy, &textProp, &textList, &count) == 0)
+-                     && textList && (count > 0)) {
+-                title = QString::fromLocal8Bit(textList[0]);
+-            }
+-            else if (textProp.encoding == m_atomString) {
+-                title = QString::fromLocal8Bit(reinterpret_cast<char*>(textProp.value));
+-            }
+-
+-            if (textList) {
+-                XFreeStringList(textList);
+-            }
+-        }
+-
+-        if (textProp.value) {
+-            XFree(textProp.value);
+-        }
+-    }
+-
+-    if (data) {
+-        XFree(data);
+-    }
+-
+-    if (useBlacklist && !title.isEmpty()) {
+-        if (window == m_rootWindow) {
+-            return QString();
+-        }
+-
+-        QString className = windowClassName(window);
+-        if (m_classBlacklist.contains(className)) {
+-            return QString();
+-        }
+-
+-        QList<Window> keepassxWindows = widgetsToX11Windows(QApplication::topLevelWidgets());
+-        if (keepassxWindows.contains(window)) {
+-            return QString();
+-        }
+-    }
+-
+-    return title;
+-}
+-
+-QString AutoTypePlatformX11::windowClassName(Window window)
+-{
+-    QString className;
+-
+-    XClassHint wmClass;
+-    wmClass.res_name = Q_NULLPTR;
+-    wmClass.res_class = Q_NULLPTR;
+-
+-    if (XGetClassHint(m_dpy, window, &wmClass) && wmClass.res_name) {
+-        className = QString::fromLocal8Bit(wmClass.res_name);
+-    }
+-    if (wmClass.res_name) {
+-        XFree(wmClass.res_name);
+-    }
+-    if (wmClass.res_class) {
+-        XFree(wmClass.res_class);
+-    }
+-
+-    return className;
+-}
+-
+-QList<Window> AutoTypePlatformX11::widgetsToX11Windows(const QWidgetList& widgetList)
+-{
+-    QList<Window> windows;
+-
+-    Q_FOREACH (const QWidget* widget, widgetList) {
+-        windows.append(widget->effectiveWinId());
+-    }
+-
+-    return windows;
+-}
+-
+-QStringList AutoTypePlatformX11::windowTitlesRecursive(Window window)
+-{
+-    QStringList titles;
+-
+-    if (isTopLevelWindow(window)) {
+-        QString title = windowTitle(window, true);
+-        if (!title.isEmpty()) {
+-            titles.append(title);
+-        }
+-    }
+-
+-    Window root;
+-    Window parent;
+-    Window* children = Q_NULLPTR;
+-    unsigned int numChildren;
+-    if (XQueryTree(m_dpy, window, &root, &parent, &children, &numChildren) && children) {
+-        for (uint i = 0; i < numChildren; i++) {
+-            titles.append(windowTitlesRecursive(children[i]));
+-        }
+-    }
+-    if (children) {
+-        XFree(children);
+-    }
+-
+-    return titles;
+-}
+-
+-bool AutoTypePlatformX11::isTopLevelWindow(Window window)
+-{
+-    Atom type = None;
+-    int format;
+-    unsigned long nitems;
+-    unsigned long after;
+-    unsigned char* data = Q_NULLPTR;
+-    int retVal = XGetWindowProperty(m_dpy, window, m_atomWmState, 0, 0, False, AnyPropertyType, &type, &format,
+-                                    &nitems, &after, &data);
+-    if (data) {
+-        XFree(data);
+-    }
+-
+-    return (retVal == 0) && type;
+-}
+-
+-KeySym AutoTypePlatformX11::charToKeySym(const QChar& ch)
+-{
+-    ushort unicode = ch.unicode();
+-
+-    /* first check for Latin-1 characters (1:1 mapping) */
+-    if ((unicode >= 0x0020 && unicode <= 0x007e)
+-            || (unicode >= 0x00a0 && unicode <= 0x00ff)) {
+-        return unicode;
+-    }
+-
+-    /* mapping table generated from keysymdef.h */
+-    const uint* match = qBinaryFind(m_unicodeToKeysymKeys,
+-                                    m_unicodeToKeysymKeys + m_unicodeToKeysymLen,
+-                                    unicode);
+-    int index = match - m_unicodeToKeysymKeys;
+-    if (index != m_unicodeToKeysymLen) {
+-        return m_unicodeToKeysymValues[index];
+-    }
+-
+-    if (unicode >= 0x0100) {
+-        return unicode | 0x01000000;
+-    }
+-
+-    return NoSymbol;
+-}
+-
+-KeySym AutoTypePlatformX11::keyToKeySym(Qt::Key key)
+-{
+-    switch (key) {
+-    case Qt::Key_Tab:
+-        return XK_Tab;
+-    case Qt::Key_Enter:
+-        return XK_Return;
+-    case Qt::Key_Up:
+-        return XK_Up;
+-    case Qt::Key_Down:
+-        return XK_Down;
+-    case Qt::Key_Left:
+-        return XK_Left;
+-    case Qt::Key_Right:
+-        return XK_Right;
+-    case Qt::Key_Insert:
+-        return XK_Insert;
+-    case Qt::Key_Delete:
+-        return XK_Delete;
+-    case Qt::Key_Home:
+-        return XK_Home;
+-    case Qt::Key_End:
+-        return XK_End;
+-    case Qt::Key_PageUp:
+-        return XK_Page_Up;
+-    case Qt::Key_PageDown:
+-        return XK_Page_Down;
+-    case Qt::Key_Backspace:
+-        return XK_BackSpace;
+-    case Qt::Key_Pause:
+-        return XK_Break;
+-    case Qt::Key_CapsLock:
+-        return XK_Caps_Lock;
+-    case Qt::Key_Escape:
+-        return XK_Escape;
+-    case Qt::Key_Help:
+-        return XK_Help;
+-    case Qt::Key_NumLock:
+-        return XK_Num_Lock;
+-    case Qt::Key_Print:
+-        return XK_Print;
+-    case Qt::Key_ScrollLock:
+-        return XK_Scroll_Lock;
+-    default:
+-        if (key >= Qt::Key_F1 && key <= Qt::Key_F16) {
+-            return XK_F1 + (key - Qt::Key_F1);
+-        }
+-        else {
+-            return NoSymbol;
+-        }
+-    }
+-}
+-
+-/*
+- * Update the keyboard and modifier mapping.
+- * We need the KeyboardMapping for AddKeysym.
+- * Modifier mapping is required for clearing the modifiers. 
+- */
+-void AutoTypePlatformX11::updateKeymap()
+-{
+-    int keycode, inx;
+-    int mod_index, mod_key;
+-    XModifierKeymap *modifiers;
+-
+-    if (m_xkb) {
+-        XkbFreeKeyboard(m_xkb, XkbAllComponentsMask, True);
+-    }
+-    m_xkb = getKeyboard();
+-
+-    XDisplayKeycodes(m_dpy, &m_minKeycode, &m_maxKeycode);
+-    if (m_keysymTable != NULL) XFree(m_keysymTable);
+-    m_keysymTable = XGetKeyboardMapping(m_dpy,
+-            m_minKeycode, m_maxKeycode - m_minKeycode + 1,
+-            &m_keysymPerKeycode);
+-
+-    /* determine the keycode to use for remapped keys */
+-    inx = (m_remapKeycode - m_minKeycode) * m_keysymPerKeycode;
+-    if (m_remapKeycode == 0 || !isRemapKeycodeValid()) {
+-        for (keycode = m_minKeycode; keycode <= m_maxKeycode; keycode++) {
+-            inx = (keycode - m_minKeycode) * m_keysymPerKeycode;
+-            if (m_keysymTable[inx] == NoSymbol) {
+-               m_remapKeycode = keycode;
+-               m_currentRemapKeysym = NoSymbol;
+-               break;
+-            }
+-        }
+-    }
+-
+-    /* determine the keycode to use for modifiers */
+-    modifiers = XGetModifierMapping(m_dpy);
+-    for (mod_index = ShiftMapIndex; mod_index <= Mod5MapIndex; mod_index ++) {
+-        m_modifier_keycode[mod_index] = 0;
+-        for (mod_key = 0; mod_key < modifiers->max_keypermod; mod_key++) {
+-            keycode = modifiers->modifiermap[mod_index * modifiers->max_keypermod + mod_key];
+-            if (keycode) {
+-                m_modifier_keycode[mod_index] = keycode;
+-                break;
+-            }
+-        }
+-    }
+-    XFreeModifiermap(modifiers);
+-
+-    /* Xlib needs some time until the mapping is distributed to
+-       all clients */
+-    // TODO: we should probably only sleep while in the middle of typing something
+-    timespec ts;
+-    ts.tv_sec = 0;
+-    ts.tv_nsec = 30 * 1000 * 1000;
+-    nanosleep(&ts, Q_NULLPTR);
+-}
+-
+-bool AutoTypePlatformX11::isRemapKeycodeValid()
+-{
+-    int baseKeycode = (m_remapKeycode - m_minKeycode) * m_keysymPerKeycode;
+-    for (int i = 0; i < m_keysymPerKeycode; i++) {
+-        if (m_keysymTable[baseKeycode + i] == m_currentRemapKeysym) {
+-            return true;
+-        }
+-    }
+-
+-    return false;
+-}
+-
+-void AutoTypePlatformX11::startCatchXErrors()
+-{
+-    Q_ASSERT(!m_catchXErrors);
+-
+-    m_catchXErrors = true;
+-    m_xErrorOccured = false;
+-    m_oldXErrorHandler = XSetErrorHandler(x11ErrorHandler);
+-}
+-
+-void AutoTypePlatformX11::stopCatchXErrors()
+-{
+-    Q_ASSERT(m_catchXErrors);
+-
+-    XSync(m_dpy, False);
+-    XSetErrorHandler(m_oldXErrorHandler);
+-    m_catchXErrors = false;
+-}
+-
+-int AutoTypePlatformX11::x11ErrorHandler(Display* display, XErrorEvent* error)
+-{
+-    Q_UNUSED(display)
+-    Q_UNUSED(error)
+-
+-    if (m_catchXErrors) {
+-        m_xErrorOccured = true;
+-    }
+-
+-    return 1;
+-}
+-
+-XkbDescPtr AutoTypePlatformX11::getKeyboard()
+-{
+-    int num_devices;
+-    XID keyboard_id = XkbUseCoreKbd;
+-    XDeviceInfo* devices = XListInputDevices(m_dpy, &num_devices);
+-    if (!devices) {
+-        return Q_NULLPTR;
+-    }
+-
+-    for (int i = 0; i < num_devices; i++) {
+-        if (QString(devices[i].name) == "Virtual core XTEST keyboard") {
+-            keyboard_id = devices[i].id;
+-            break;
+-        }
+-    }
+-
+-    XFreeDeviceList(devices);
+-
+-    return XkbGetKeyboard(m_dpy, XkbCompatMapMask | XkbGeometryMask, keyboard_id);
+-}
+-
+-// --------------------------------------------------------------------------
+-// The following code is taken from xvkbd 3.0 and has been slightly modified.
+-// --------------------------------------------------------------------------
+-
+-/*
+- * Insert a specified keysym on the dedicated position in the keymap
+- * table.
+- */
+-int AutoTypePlatformX11::AddKeysym(KeySym keysym)
+-{
+-    if (m_remapKeycode == 0) {
+-        return 0;
+-    }
+-
+-    int inx = (m_remapKeycode- m_minKeycode) * m_keysymPerKeycode;
+-    m_keysymTable[inx] = keysym;
+-    m_currentRemapKeysym = keysym;
+-
+-    XChangeKeyboardMapping(m_dpy, m_remapKeycode, m_keysymPerKeycode, &m_keysymTable[inx], 1);
+-    XFlush(m_dpy);
+-    updateKeymap();
+-
+-    return m_remapKeycode;
+-}
+-
+-/*
+- * Send event to the focused window.
+- * If input focus is specified explicitly, select the window
+- * before send event to the window.
+- */
+-void AutoTypePlatformX11::SendEvent(XKeyEvent* event, int event_type)
+-{
+-    XSync(event->display, False);
+-    int (*oldHandler) (Display*, XErrorEvent*) = XSetErrorHandler(MyErrorHandler);
+-
+-    event->type = event_type;
+-    Bool press;
+-    if (event->type == KeyPress) {
+-        press = True;
+-    }
+-    else {
+-        press = False;
+-    }
+-    XTestFakeKeyEvent(event->display, event->keycode, press, 0);
+-    XFlush(event->display);
+-
+-    XSetErrorHandler(oldHandler);
+-}
+-
+-/*
+- * Send a modifier press/release event for all modifiers
+- * which are set in the mask variable.
+- */
+-void AutoTypePlatformX11::SendModifier(XKeyEvent *event, unsigned int mask, int event_type) 
+-{
+-    int mod_index;
+-    for (mod_index = ShiftMapIndex; mod_index <= Mod5MapIndex; mod_index ++) {
+-        if (mask & (1 << mod_index)) {
+-            event->keycode = m_modifier_keycode[mod_index];
+-            SendEvent(event, event_type);
+-            if (event_type == KeyPress) 
+-                event->state |= (1 << mod_index);
+-            else
+-                event->state &= (1 << mod_index);
+-        }
+-    }
+-}
+-
+-/*
+- * Determines the keycode and modifier mask for the given
+- * keysym.
+- */
+-int AutoTypePlatformX11::GetKeycode(KeySym keysym, unsigned int *mask)
+-{
+-    int keycode = XKeysymToKeycode(m_dpy, keysym);
+-
+-    if (keycode && keysymModifiers(keysym, keycode, mask)) {
+-        return keycode;
+-    }
+-
+-    /* no modifier matches => resort to remapping */
+-    keycode = AddKeysym(keysym);
+-    if (keycode && keysymModifiers(keysym, keycode, mask)) {
+-        return keycode;
+-    }
+-
+-    *mask = 0;
+-    return 0;
+-}
+-
+-bool AutoTypePlatformX11::keysymModifiers(KeySym keysym, int keycode, unsigned int *mask)
+-{
+-    int shift, mod;
+-    unsigned int mods_rtrn;
+-
+-    /* determine whether there is a combination of the modifiers
+-       (Mod1-Mod5) with or without shift which returns keysym */
+-    for (shift = 0; shift < 2; shift ++) {
+-        for (mod = ControlMapIndex; mod <= Mod5MapIndex; mod ++) {
+-            KeySym keysym_rtrn;
+-            *mask = (mod == ControlMapIndex) ? shift : shift | (1 << mod);
+-            XkbTranslateKeyCode(m_xkb, keycode, *mask, &mods_rtrn, &keysym_rtrn);
+-            if (keysym_rtrn == keysym) {
+-                return true;
+-            }
+-        }
+-    }
+-
+-    return false;
+-}
+-
+-
+-
+-/*
+- * Send sequence of KeyPressed/KeyReleased events to the focused
+- * window to simulate keyboard.  If modifiers (shift, control, etc)
+- * are set ON, many events will be sent.
+- */
+-void AutoTypePlatformX11::SendKeyPressedEvent(KeySym keysym)
+-{
+-    Window cur_focus;
+-    int revert_to;
+-    XKeyEvent event;
+-    int keycode;
+-
+-    if (keysym == NoSymbol) {
+-        qWarning("No such key: keysym=0x%lX", keysym);
+-        return;
+-    }
+-
+-    XGetInputFocus(m_dpy, &cur_focus, &revert_to);
+-
+-    event.display = m_dpy;
+-    event.window = cur_focus;
+-    event.root = m_rootWindow;
+-    event.subwindow = None;
+-    event.time = CurrentTime;
+-    event.x = 1;
+-    event.y = 1;
+-    event.x_root = 1;
+-    event.y_root = 1;
+-    event.same_screen = TRUE;
+-
+-    Window root, child;
+-    int root_x, root_y, x, y;
+-    unsigned int wanted_mask = 0;
+-    unsigned int original_mask;
+-
+-    XQueryPointer(m_dpy, event.root, &root, &child, &root_x, &root_y, &x, &y, &original_mask);
+-
+-    /* determine keycode and mask for the given keysym */
+-    keycode = GetKeycode(keysym, &wanted_mask);
+-    if (keycode < 8 || keycode > 255) {
+-        qWarning("Unable to get valid keycode for key: keysym=0x%lX", keysym);
+-        return;
+-    }
+-
+-    event.state = original_mask;
+-
+-    // modifiers that need to be pressed but aren't
+-    unsigned int press_mask = wanted_mask & ~original_mask;
+-
+-    // modifiers that are pressed but maybe shouldn't
+-    unsigned int release_check_mask = original_mask & ~wanted_mask;
+-
+-    // modifiers we need to release before sending the keycode
+-    unsigned int release_mask = 0;
+-
+-    // check every release_check_mask individually if it affects the keysym we would generate
+-    // if it doesn't we probably don't need to release it
+-    for (int mod_index = ShiftMapIndex; mod_index <= Mod5MapIndex; mod_index ++) {
+-        if (release_check_mask & (1 << mod_index)) {
+-            unsigned int mods_rtrn;
+-            KeySym keysym_rtrn;
+-            XkbTranslateKeyCode(m_xkb, keycode, wanted_mask | (1 << mod_index), &mods_rtrn, &keysym_rtrn);
+-
+-            if (keysym_rtrn != keysym) {
+-                release_mask |= (1 << mod_index);
+-            }
+-        }
+-    }
+-
+-    // finally check if the combination of pressed modifiers that we chose to ignore affects the keysym
+-    unsigned int mods_rtrn;
+-    KeySym keysym_rtrn;
+-    XkbTranslateKeyCode(m_xkb, keycode, wanted_mask | (release_check_mask & ~release_mask), &mods_rtrn, &keysym_rtrn);
+-    if (keysym_rtrn != keysym) {
+-        // oh well, release all the modifiers we don't want
+-        release_mask = release_check_mask;
+-    }
+-
+-    /* release all modifiers */
+-    SendModifier(&event, release_mask, KeyRelease);
+-
+-    SendModifier(&event, press_mask, KeyPress);
+-
+-    /* press and release key */
+-    event.keycode = keycode;
+-    SendEvent(&event, KeyPress);
+-    SendEvent(&event, KeyRelease);
+-
+-    /* release the modifiers */
+-    SendModifier(&event, press_mask, KeyRelease);
+-
+-    /* restore the old keyboard mask */
+-    SendModifier(&event, release_mask, KeyPress);
+-}
+-
+-int AutoTypePlatformX11::MyErrorHandler(Display* my_dpy, XErrorEvent* event)
+-{
+-    char msg[200];
+-
+-    if (event->error_code == BadWindow) {
+-        return 0;
+-    }
+-    XGetErrorText(my_dpy, event->error_code, msg, sizeof(msg) - 1);
+-    qWarning("X error trapped: %s, request-code=%d\n", msg, event->request_code);
+-    return 0;
+-}
+-
+-
+-AutoTypeExecturorX11::AutoTypeExecturorX11(AutoTypePlatformX11* platform)
+-    : m_platform(platform)
+-{
+-}
+-
+-void AutoTypeExecturorX11::execChar(AutoTypeChar* action)
+-{
+-    m_platform->SendKeyPressedEvent(m_platform->charToKeySym(action->character));
+-}
+-
+-void AutoTypeExecturorX11::execKey(AutoTypeKey* action)
+-{
+-    m_platform->SendKeyPressedEvent(m_platform->keyToKeySym(action->key));
+-}
+-
+-int AutoTypePlatformX11::initialTimeout()
+-{
+-    return 500;
+-}
+-
+-bool AutoTypePlatformX11::raiseWindow(WId window)
+-{
+-    if (m_atomNetActiveWindow == None) {
+-        return false;
+-    }
+-
+-    XRaiseWindow(m_dpy, window);
+-
+-    XEvent event;
+-    event.xclient.type = ClientMessage;
+-    event.xclient.serial = 0;
+-    event.xclient.send_event = True;
+-    event.xclient.window = window;
+-    event.xclient.message_type = m_atomNetActiveWindow;
+-    event.xclient.format = 32;
+-    event.xclient.data.l[0] = 1; // FromApplication
+-    event.xclient.data.l[1] = QX11Info::appUserTime();
+-    QWidget* activeWindow = QApplication::activeWindow();
+-    if (activeWindow) {
+-        event.xclient.data.l[2] = activeWindow->internalWinId();
+-    }
+-    else {
+-        event.xclient.data.l[2] = 0;
+-    }
+-    event.xclient.data.l[3] = 0;
+-    event.xclient.data.l[4] = 0;
+-    XSendEvent(m_dpy, m_rootWindow, False,
+-               SubstructureRedirectMask | SubstructureNotifyMask,
+-               &event);
+-    XFlush(m_dpy);
+-
+-    return true;
+-}
+-
+-Q_EXPORT_PLUGIN2(keepassx-autotype-x11, AutoTypePlatformX11)
+diff --git a/src/autotype/x11/AutoTypeX11.h b/src/autotype/x11/AutoTypeX11.h
+deleted file mode 100644
+index 99abb23..0000000
+--- a/src/autotype/x11/AutoTypeX11.h
++++ /dev/null
+@@ -1,134 +0,0 @@
+-/*
+- *  Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
+- *  Copyright (C) 2000-2008 Tom Sato <VEF00200@nifty.ne.jp>
+- *
+- *  This program is free software: you can redistribute it and/or modify
+- *  it under the terms of the GNU General Public License as published by
+- *  the Free Software Foundation, either version 2 or (at your option)
+- *  version 3 of the License.
+- *
+- *  This program is distributed in the hope that it will be useful,
+- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+- *  GNU General Public License for more details.
+- *
+- *  You should have received a copy of the GNU General Public License
+- *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+- */
+-
+-#ifndef KEEPASSX_AUTOTYPEX11_H
+-#define KEEPASSX_AUTOTYPEX11_H
+-
+-#include <QApplication>
+-#include <QSet>
+-#include <QtPlugin>
+-#include <QWidget>
+-#include <QX11Info>
+-
+-#include <X11/Xutil.h>
+-#include <X11/extensions/XTest.h>
+-#include <X11/XKBlib.h>
+-
+-#include "autotype/AutoTypePlatformPlugin.h"
+-#include "autotype/AutoTypeAction.h"
+-#include "core/Global.h"
+-
+-#define N_MOD_INDICES (Mod5MapIndex + 1)
+-
+-class AutoTypePlatformX11 : public QObject, public AutoTypePlatformInterface
+-{
+-    Q_OBJECT
+-    Q_INTERFACES(AutoTypePlatformInterface)
+-
+-public:
+-    AutoTypePlatformX11();
+-    bool isAvailable() Q_DECL_OVERRIDE;
+-    void unload() Q_DECL_OVERRIDE;
+-    QStringList windowTitles() Q_DECL_OVERRIDE;
+-    WId activeWindow() Q_DECL_OVERRIDE;
+-    QString activeWindowTitle() Q_DECL_OVERRIDE;
+-    bool registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) Q_DECL_OVERRIDE;
+-    void unregisterGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) Q_DECL_OVERRIDE;
+-    int platformEventFilter(void* event) Q_DECL_OVERRIDE;
+-    int initialTimeout() Q_DECL_OVERRIDE;
+-    bool raiseWindow(WId window) Q_DECL_OVERRIDE;
+-    AutoTypeExecutor* createExecutor() Q_DECL_OVERRIDE;
+-
+-    KeySym charToKeySym(const QChar& ch);
+-    KeySym keyToKeySym(Qt::Key key);
+-
+-    void SendKeyPressedEvent(KeySym keysym);
+-
+-Q_SIGNALS:
+-    void globalShortcutTriggered();
+-
+-private:
+-    QString windowTitle(Window window, bool useBlacklist);
+-    QStringList windowTitlesRecursive(Window window);
+-    QString windowClassName(Window window);
+-    QList<Window> widgetsToX11Windows(const QWidgetList& widgetList);
+-    bool isTopLevelWindow(Window window);
+-    uint qtToNativeModifiers(Qt::KeyboardModifiers modifiers);
+-    void startCatchXErrors();
+-    void stopCatchXErrors();
+-    static int x11ErrorHandler(Display* display, XErrorEvent* error);
+-
+-    XkbDescPtr getKeyboard();
+-    void updateKeymap();
+-    bool isRemapKeycodeValid();
+-    int AddKeysym(KeySym keysym);
+-    void AddModifier(KeySym keysym);
+-    void SendEvent(XKeyEvent* event, int event_type);
+-    void SendModifier(XKeyEvent *event, unsigned int mask, int event_type);
+-    int GetKeycode(KeySym keysym, unsigned int *mask);
+-    bool keysymModifiers(KeySym keysym, int keycode, unsigned int *mask);
+-
+-    static int MyErrorHandler(Display* my_dpy, XErrorEvent* event);
+-
+-    Display* m_dpy;
+-    Window m_rootWindow;
+-    Atom m_atomWmState;
+-    Atom m_atomWmName;
+-    Atom m_atomNetWmName;
+-    Atom m_atomString;
+-    Atom m_atomUtf8String;
+-    Atom m_atomNetActiveWindow;
+-    QSet<QString> m_classBlacklist;
+-    Qt::Key m_currentGlobalKey;
+-    Qt::KeyboardModifiers m_currentGlobalModifiers;
+-    uint m_currentGlobalKeycode;
+-    uint m_currentGlobalNativeModifiers;
+-    int m_modifierMask;
+-    static bool m_catchXErrors;
+-    static bool m_xErrorOccured;
+-    static int (*m_oldXErrorHandler)(Display*, XErrorEvent*);
+-
+-    static const int m_unicodeToKeysymLen;
+-    static const uint m_unicodeToKeysymKeys[];
+-    static const uint m_unicodeToKeysymValues[];
+-
+-    XkbDescPtr m_xkb;
+-    KeySym* m_keysymTable;
+-    int m_minKeycode;
+-    int m_maxKeycode;
+-    int m_keysymPerKeycode;
+-    /* dedicated keycode for remapped keys */
+-    unsigned int m_remapKeycode;
+-    KeySym m_currentRemapKeysym;
+-    KeyCode m_modifier_keycode[N_MOD_INDICES];
+-    bool m_loaded;
+-};
+-
+-class AutoTypeExecturorX11 : public AutoTypeExecutor
+-{
+-public:
+-    explicit AutoTypeExecturorX11(AutoTypePlatformX11* platform);
+-
+-    void execChar(AutoTypeChar* action) Q_DECL_OVERRIDE;
+-    void execKey(AutoTypeKey* action) Q_DECL_OVERRIDE;
+-
+-private:
+-    AutoTypePlatformX11* const m_platform;
+-};
+-
+-#endif // KEEPASSX_AUTOTYPEX11_H
+diff --git a/src/autotype/x11/CMakeLists.txt b/src/autotype/x11/CMakeLists.txt
+deleted file mode 100644
+index cc401f7..0000000
+--- a/src/autotype/x11/CMakeLists.txt
++++ /dev/null
+@@ -1,17 +0,0 @@
+-include_directories(SYSTEM ${X11_X11_INCLUDE_PATH})
+-
+-set(autotype_X11_SOURCES
+-    AutoTypeX11.cpp
+-)
+-
+-set(autotype_X11_MOC
+-    AutoTypeX11.h
+-)
+-
+-qt4_wrap_cpp(autotype_X11_SOURCES ${autotype_X11_MOC})
+-
+-add_library(keepassx-autotype-x11 MODULE ${autotype_X11_SOURCES})
+-target_link_libraries(keepassx-autotype-x11 ${QT_QTCORE_LIBRARY} ${QT_QTGUI_LIBRARY} ${X11_X11_LIB} ${X11_Xi_LIB} ${X11_XTest_LIB})
+-install(TARGETS keepassx-autotype-x11
+-        BUNDLE DESTINATION . COMPONENT Runtime
+-        LIBRARY DESTINATION ${PLUGIN_INSTALL_DIR} COMPONENT Runtime)
+diff --git a/src/autotype/x11/KeySymMap.h b/src/autotype/x11/KeySymMap.h
+deleted file mode 100644
+index 55022fe..0000000
+--- a/src/autotype/x11/KeySymMap.h
++++ /dev/null
+@@ -1,169 +0,0 @@
+-/*
+- *  Automatically generated by keysymmap.py from parsing keysymdef.h.
+- */
+-
+-const int AutoTypePlatformX11::m_unicodeToKeysymLen = 632;
+-
+-const uint AutoTypePlatformX11::m_unicodeToKeysymKeys[] = {
+-    0x0100, 0x0101, 0x0102, 0x0103, 0x0104, 0x0105, 0x0106, 0x0107,
+-    0x0108, 0x0109, 0x010a, 0x010b, 0x010c, 0x010d, 0x010e, 0x010f,
+-    0x0110, 0x0111, 0x0112, 0x0113, 0x0116, 0x0117, 0x0118, 0x0119,
+-    0x011a, 0x011b, 0x011c, 0x011d, 0x011e, 0x011f, 0x0120, 0x0121,
+-    0x0122, 0x0123, 0x0124, 0x0125, 0x0126, 0x0127, 0x0128, 0x0129,
+-    0x012a, 0x012b, 0x012e, 0x012f, 0x0130, 0x0131, 0x0134, 0x0135,
+-    0x0136, 0x0137, 0x0138, 0x0139, 0x013a, 0x013b, 0x013c, 0x013d,
+-    0x013e, 0x0141, 0x0142, 0x0143, 0x0144, 0x0145, 0x0146, 0x0147,
+-    0x0148, 0x014a, 0x014b, 0x014c, 0x014d, 0x0150, 0x0151, 0x0152,
+-    0x0153, 0x0154, 0x0155, 0x0156, 0x0157, 0x0158, 0x0159, 0x015a,
+-    0x015b, 0x015c, 0x015d, 0x015e, 0x015f, 0x0160, 0x0161, 0x0162,
+-    0x0163, 0x0164, 0x0165, 0x0166, 0x0167, 0x0168, 0x0169, 0x016a,
+-    0x016b, 0x016c, 0x016d, 0x016e, 0x016f, 0x0170, 0x0171, 0x0172,
+-    0x0173, 0x0178, 0x0179, 0x017a, 0x017b, 0x017c, 0x017d, 0x017e,
+-    0x0192, 0x02c7, 0x02d8, 0x02d9, 0x02db, 0x02dd, 0x0385, 0x0386,
+-    0x0388, 0x0389, 0x038a, 0x038c, 0x038e, 0x038f, 0x0390, 0x0391,
+-    0x0392, 0x0393, 0x0394, 0x0395, 0x0396, 0x0397, 0x0398, 0x0399,
+-    0x039a, 0x039b, 0x039c, 0x039d, 0x039e, 0x039f, 0x03a0, 0x03a1,
+-    0x03a3, 0x03a4, 0x03a5, 0x03a6, 0x03a7, 0x03a8, 0x03a9, 0x03aa,
+-    0x03ab, 0x03ac, 0x03ad, 0x03ae, 0x03af, 0x03b0, 0x03b1, 0x03b2,
+-    0x03b3, 0x03b4, 0x03b5, 0x03b6, 0x03b7, 0x03b8, 0x03b9, 0x03ba,
+-    0x03bb, 0x03bc, 0x03bd, 0x03be, 0x03bf, 0x03c0, 0x03c1, 0x03c2,
+-    0x03c3, 0x03c4, 0x03c5, 0x03c6, 0x03c7, 0x03c8, 0x03c9, 0x03ca,
+-    0x03cb, 0x03cc, 0x03cd, 0x03ce, 0x0401, 0x0402, 0x0403, 0x0404,
+-    0x0405, 0x0406, 0x0407, 0x0408, 0x0409, 0x040a, 0x040b, 0x040c,
+-    0x040e, 0x040f, 0x0410, 0x0411, 0x0412, 0x0413, 0x0414, 0x0415,
+-    0x0416, 0x0417, 0x0418, 0x0419, 0x041a, 0x041b, 0x041c, 0x041d,
+-    0x041e, 0x041f, 0x0420, 0x0421, 0x0422, 0x0423, 0x0424, 0x0425,
+-    0x0426, 0x0427, 0x0428, 0x0429, 0x042a, 0x042b, 0x042c, 0x042d,
+-    0x042e, 0x042f, 0x0430, 0x0431, 0x0432, 0x0433, 0x0434, 0x0435,
+-    0x0436, 0x0437, 0x0438, 0x0439, 0x043a, 0x043b, 0x043c, 0x043d,
+-    0x043e, 0x043f, 0x0440, 0x0441, 0x0442, 0x0443, 0x0444, 0x0445,
+-    0x0446, 0x0447, 0x0448, 0x0449, 0x044a, 0x044b, 0x044c, 0x044d,
+-    0x044e, 0x044f, 0x0451, 0x0452, 0x0453, 0x0454, 0x0455, 0x0456,
+-    0x0457, 0x0458, 0x0459, 0x045a, 0x045b, 0x045c, 0x045e, 0x045f,
+-    0x0490, 0x0491, 0x05d0, 0x05d1, 0x05d2, 0x05d3, 0x05d4, 0x05d5,
+-    0x05d6, 0x05d7, 0x05d8, 0x05d9, 0x05da, 0x05db, 0x05dc, 0x05dd,
+-    0x05de, 0x05df, 0x05e0, 0x05e1, 0x05e2, 0x05e3, 0x05e4, 0x05e5,
+-    0x05e6, 0x05e7, 0x05e8, 0x05e9, 0x05ea, 0x060c, 0x061b, 0x061f,
+-    0x0621, 0x0622, 0x0623, 0x0624, 0x0625, 0x0626, 0x0627, 0x0628,
+-    0x0629, 0x062a, 0x062b, 0x062c, 0x062d, 0x062e, 0x062f, 0x0630,
+-    0x0631, 0x0632, 0x0633, 0x0634, 0x0635, 0x0636, 0x0637, 0x0638,
+-    0x0639, 0x063a, 0x0640, 0x0641, 0x0642, 0x0643, 0x0644, 0x0645,
+-    0x0646, 0x0647, 0x0648, 0x0649, 0x064a, 0x064b, 0x064c, 0x064d,
+-    0x064e, 0x064f, 0x0650, 0x0651, 0x0652, 0x0e01, 0x0e02, 0x0e03,
+-    0x0e04, 0x0e05, 0x0e06, 0x0e07, 0x0e08, 0x0e09, 0x0e0a, 0x0e0b,
+-    0x0e0c, 0x0e0d, 0x0e0e, 0x0e0f, 0x0e10, 0x0e11, 0x0e12, 0x0e13,
+-    0x0e14, 0x0e15, 0x0e16, 0x0e17, 0x0e18, 0x0e19, 0x0e1a, 0x0e1b,
+-    0x0e1c, 0x0e1d, 0x0e1e, 0x0e1f, 0x0e20, 0x0e21, 0x0e22, 0x0e23,
+-    0x0e24, 0x0e25, 0x0e26, 0x0e27, 0x0e28, 0x0e29, 0x0e2a, 0x0e2b,
+-    0x0e2c, 0x0e2d, 0x0e2e, 0x0e2f, 0x0e30, 0x0e31, 0x0e32, 0x0e33,
+-    0x0e34, 0x0e35, 0x0e36, 0x0e37, 0x0e38, 0x0e39, 0x0e3a, 0x0e3f,
+-    0x0e40, 0x0e41, 0x0e42, 0x0e43, 0x0e44, 0x0e45, 0x0e46, 0x0e47,
+-    0x0e48, 0x0e49, 0x0e4a, 0x0e4b, 0x0e4c, 0x0e4d, 0x0e50, 0x0e51,
+-    0x0e52, 0x0e53, 0x0e54, 0x0e55, 0x0e56, 0x0e57, 0x0e58, 0x0e59,
+-    0x2002, 0x2003, 0x2004, 0x2005, 0x2007, 0x2008, 0x2009, 0x200a,
+-    0x2012, 0x2013, 0x2014, 0x2015, 0x2017, 0x2018, 0x2019, 0x201a,
+-    0x201c, 0x201d, 0x201e, 0x2020, 0x2021, 0x2025, 0x2026, 0x2030,
+-    0x2032, 0x2033, 0x2038, 0x203e, 0x20ac, 0x2105, 0x2116, 0x2117,
+-    0x211e, 0x2122, 0x2153, 0x2154, 0x2155, 0x2156, 0x2157, 0x2158,
+-    0x2159, 0x215a, 0x215b, 0x215c, 0x215d, 0x215e, 0x2190, 0x2191,
+-    0x2192, 0x2193, 0x21d2, 0x21d4, 0x2202, 0x2207, 0x2218, 0x221a,
+-    0x221d, 0x221e, 0x2227, 0x2228, 0x2229, 0x222a, 0x222b, 0x2234,
+-    0x223c, 0x2243, 0x2260, 0x2261, 0x2264, 0x2265, 0x2282, 0x2283,
+-    0x22a2, 0x22a3, 0x22a4, 0x22a5, 0x2308, 0x230a, 0x2315, 0x2320,
+-    0x2321, 0x2395, 0x239b, 0x239d, 0x239e, 0x23a0, 0x23a1, 0x23a3,
+-    0x23a4, 0x23a6, 0x23a8, 0x23ac, 0x23b7, 0x23ba, 0x23bb, 0x23bc,
+-    0x23bd, 0x2409, 0x240a, 0x240b, 0x240c, 0x240d, 0x2424, 0x2500,
+-    0x2502, 0x250c, 0x2510, 0x2514, 0x2518, 0x251c, 0x2524, 0x252c,
+-    0x2534, 0x253c, 0x2592, 0x25c6, 0x25cb, 0x260e, 0x2640, 0x2642,
+-    0x2663, 0x2665, 0x2666, 0x266d, 0x266f, 0x2713, 0x2717, 0x271d,
+-    0x2720, 0x3001, 0x3002, 0x300c, 0x300d, 0x309b, 0x309c, 0x30a1,
+-    0x30a2, 0x30a3, 0x30a4, 0x30a5, 0x30a6, 0x30a7, 0x30a8, 0x30a9,
+-    0x30aa, 0x30ab, 0x30ad, 0x30af, 0x30b1, 0x30b3, 0x30b5, 0x30b7,
+-    0x30b9, 0x30bb, 0x30bd, 0x30bf, 0x30c1, 0x30c3, 0x30c4, 0x30c6,
+-    0x30c8, 0x30ca, 0x30cb, 0x30cc, 0x30cd, 0x30ce, 0x30cf, 0x30d2,
+-    0x30d5, 0x30d8, 0x30db, 0x30de, 0x30df, 0x30e0, 0x30e1, 0x30e2,
+-    0x30e3, 0x30e4, 0x30e5, 0x30e6, 0x30e7, 0x30e8, 0x30e9, 0x30ea,
+-    0x30eb, 0x30ec, 0x30ed, 0x30ef, 0x30f2, 0x30f3, 0x30fb, 0x30fc
+-};
+-
+-const uint AutoTypePlatformX11::m_unicodeToKeysymValues[] = {
+-    0x03c0, 0x03e0, 0x01c3, 0x01e3, 0x01a1, 0x01b1, 0x01c6, 0x01e6,
+-    0x02c6, 0x02e6, 0x02c5, 0x02e5, 0x01c8, 0x01e8, 0x01cf, 0x01ef,
+-    0x01d0, 0x01f0, 0x03aa, 0x03ba, 0x03cc, 0x03ec, 0x01ca, 0x01ea,
+-    0x01cc, 0x01ec, 0x02d8, 0x02f8, 0x02ab, 0x02bb, 0x02d5, 0x02f5,
+-    0x03ab, 0x03bb, 0x02a6, 0x02b6, 0x02a1, 0x02b1, 0x03a5, 0x03b5,
+-    0x03cf, 0x03ef, 0x03c7, 0x03e7, 0x02a9, 0x02b9, 0x02ac, 0x02bc,
+-    0x03d3, 0x03f3, 0x03a2, 0x01c5, 0x01e5, 0x03a6, 0x03b6, 0x01a5,
+-    0x01b5, 0x01a3, 0x01b3, 0x01d1, 0x01f1, 0x03d1, 0x03f1, 0x01d2,
+-    0x01f2, 0x03bd, 0x03bf, 0x03d2, 0x03f2, 0x01d5, 0x01f5, 0x13bc,
+-    0x13bd, 0x01c0, 0x01e0, 0x03a3, 0x03b3, 0x01d8, 0x01f8, 0x01a6,
+-    0x01b6, 0x02de, 0x02fe, 0x01aa, 0x01ba, 0x01a9, 0x01b9, 0x01de,
+-    0x01fe, 0x01ab, 0x01bb, 0x03ac, 0x03bc, 0x03dd, 0x03fd, 0x03de,
+-    0x03fe, 0x02dd, 0x02fd, 0x01d9, 0x01f9, 0x01db, 0x01fb, 0x03d9,
+-    0x03f9, 0x13be, 0x01ac, 0x01bc, 0x01af, 0x01bf, 0x01ae, 0x01be,
+-    0x08f6, 0x01b7, 0x01a2, 0x01ff, 0x01b2, 0x01bd, 0x07ae, 0x07a1,
+-    0x07a2, 0x07a3, 0x07a4, 0x07a7, 0x07a8, 0x07ab, 0x07b6, 0x07c1,
+-    0x07c2, 0x07c3, 0x07c4, 0x07c5, 0x07c6, 0x07c7, 0x07c8, 0x07c9,
+-    0x07ca, 0x07cb, 0x07cc, 0x07cd, 0x07ce, 0x07cf, 0x07d0, 0x07d1,
+-    0x07d2, 0x07d4, 0x07d5, 0x07d6, 0x07d7, 0x07d8, 0x07d9, 0x07a5,
+-    0x07a9, 0x07b1, 0x07b2, 0x07b3, 0x07b4, 0x07ba, 0x07e1, 0x07e2,
+-    0x07e3, 0x07e4, 0x07e5, 0x07e6, 0x07e7, 0x07e8, 0x07e9, 0x07ea,
+-    0x07eb, 0x07ec, 0x07ed, 0x07ee, 0x07ef, 0x07f0, 0x07f1, 0x07f3,
+-    0x07f2, 0x07f4, 0x07f5, 0x07f6, 0x07f7, 0x07f8, 0x07f9, 0x07b5,
+-    0x07b9, 0x07b7, 0x07b8, 0x07bb, 0x06b3, 0x06b1, 0x06b2, 0x06b4,
+-    0x06b5, 0x06b6, 0x06b7, 0x06b8, 0x06b9, 0x06ba, 0x06bb, 0x06bc,
+-    0x06be, 0x06bf, 0x06e1, 0x06e2, 0x06f7, 0x06e7, 0x06e4, 0x06e5,
+-    0x06f6, 0x06fa, 0x06e9, 0x06ea, 0x06eb, 0x06ec, 0x06ed, 0x06ee,
+-    0x06ef, 0x06f0, 0x06f2, 0x06f3, 0x06f4, 0x06f5, 0x06e6, 0x06e8,
+-    0x06e3, 0x06fe, 0x06fb, 0x06fd, 0x06ff, 0x06f9, 0x06f8, 0x06fc,
+-    0x06e0, 0x06f1, 0x06c1, 0x06c2, 0x06d7, 0x06c7, 0x06c4, 0x06c5,
+-    0x06d6, 0x06da, 0x06c9, 0x06ca, 0x06cb, 0x06cc, 0x06cd, 0x06ce,
+-    0x06cf, 0x06d0, 0x06d2, 0x06d3, 0x06d4, 0x06d5, 0x06c6, 0x06c8,
+-    0x06c3, 0x06de, 0x06db, 0x06dd, 0x06df, 0x06d9, 0x06d8, 0x06dc,
+-    0x06c0, 0x06d1, 0x06a3, 0x06a1, 0x06a2, 0x06a4, 0x06a5, 0x06a6,
+-    0x06a7, 0x06a8, 0x06a9, 0x06aa, 0x06ab, 0x06ac, 0x06ae, 0x06af,
+-    0x06bd, 0x06ad, 0x0ce0, 0x0ce1, 0x0ce2, 0x0ce3, 0x0ce4, 0x0ce5,
+-    0x0ce6, 0x0ce7, 0x0ce8, 0x0ce9, 0x0cea, 0x0ceb, 0x0cec, 0x0ced,
+-    0x0cee, 0x0cef, 0x0cf0, 0x0cf1, 0x0cf2, 0x0cf3, 0x0cf4, 0x0cf5,
+-    0x0cf6, 0x0cf7, 0x0cf8, 0x0cf9, 0x0cfa, 0x05ac, 0x05bb, 0x05bf,
+-    0x05c1, 0x05c2, 0x05c3, 0x05c4, 0x05c5, 0x05c6, 0x05c7, 0x05c8,
+-    0x05c9, 0x05ca, 0x05cb, 0x05cc, 0x05cd, 0x05ce, 0x05cf, 0x05d0,
+-    0x05d1, 0x05d2, 0x05d3, 0x05d4, 0x05d5, 0x05d6, 0x05d7, 0x05d8,
+-    0x05d9, 0x05da, 0x05e0, 0x05e1, 0x05e2, 0x05e3, 0x05e4, 0x05e5,
+-    0x05e6, 0x05e7, 0x05e8, 0x05e9, 0x05ea, 0x05eb, 0x05ec, 0x05ed,
+-    0x05ee, 0x05ef, 0x05f0, 0x05f1, 0x05f2, 0x0da1, 0x0da2, 0x0da3,
+-    0x0da4, 0x0da5, 0x0da6, 0x0da7, 0x0da8, 0x0da9, 0x0daa, 0x0dab,
+-    0x0dac, 0x0dad, 0x0dae, 0x0daf, 0x0db0, 0x0db1, 0x0db2, 0x0db3,
+-    0x0db4, 0x0db5, 0x0db6, 0x0db7, 0x0db8, 0x0db9, 0x0dba, 0x0dbb,
+-    0x0dbc, 0x0dbd, 0x0dbe, 0x0dbf, 0x0dc0, 0x0dc1, 0x0dc2, 0x0dc3,
+-    0x0dc4, 0x0dc5, 0x0dc6, 0x0dc7, 0x0dc8, 0x0dc9, 0x0dca, 0x0dcb,
+-    0x0dcc, 0x0dcd, 0x0dce, 0x0dcf, 0x0dd0, 0x0dd1, 0x0dd2, 0x0dd3,
+-    0x0dd4, 0x0dd5, 0x0dd6, 0x0dd7, 0x0dd8, 0x0dd9, 0x0dda, 0x0ddf,
+-    0x0de0, 0x0de1, 0x0de2, 0x0de3, 0x0de4, 0x0de5, 0x0de6, 0x0de7,
+-    0x0de8, 0x0de9, 0x0dea, 0x0deb, 0x0dec, 0x0ded, 0x0df0, 0x0df1,
+-    0x0df2, 0x0df3, 0x0df4, 0x0df5, 0x0df6, 0x0df7, 0x0df8, 0x0df9,
+-    0x0aa2, 0x0aa1, 0x0aa3, 0x0aa4, 0x0aa5, 0x0aa6, 0x0aa7, 0x0aa8,
+-    0x0abb, 0x0aaa, 0x0aa9, 0x07af, 0x0cdf, 0x0ad0, 0x0ad1, 0x0afd,
+-    0x0ad2, 0x0ad3, 0x0afe, 0x0af1, 0x0af2, 0x0aaf, 0x0aae, 0x0ad5,
+-    0x0ad6, 0x0ad7, 0x0afc, 0x047e, 0x20ac, 0x0ab8, 0x06b0, 0x0afb,
+-    0x0ad4, 0x0ac9, 0x0ab0, 0x0ab1, 0x0ab2, 0x0ab3, 0x0ab4, 0x0ab5,
+-    0x0ab6, 0x0ab7, 0x0ac3, 0x0ac4, 0x0ac5, 0x0ac6, 0x08fb, 0x08fc,
+-    0x08fd, 0x08fe, 0x08ce, 0x08cd, 0x08ef, 0x08c5, 0x0bca, 0x08d6,
+-    0x08c1, 0x08c2, 0x08de, 0x08df, 0x08dc, 0x08dd, 0x08bf, 0x08c0,
+-    0x08c8, 0x08c9, 0x08bd, 0x08cf, 0x08bc, 0x08be, 0x08da, 0x08db,
+-    0x0bfc, 0x0bdc, 0x0bc2, 0x0bce, 0x0bd3, 0x0bc4, 0x0afa, 0x08a4,
+-    0x08a5, 0x0bcc, 0x08ab, 0x08ac, 0x08ad, 0x08ae, 0x08a7, 0x08a8,
+-    0x08a9, 0x08aa, 0x08af, 0x08b0, 0x08a1, 0x09ef, 0x09f0, 0x09f2,
+-    0x09f3, 0x09e2, 0x09e5, 0x09e9, 0x09e3, 0x09e4, 0x09e8, 0x09f1,
+-    0x09f8, 0x09ec, 0x09eb, 0x09ed, 0x09ea, 0x09f4, 0x09f5, 0x09f7,
+-    0x09f6, 0x09ee, 0x09e1, 0x09e0, 0x0bcf, 0x0af9, 0x0af8, 0x0af7,
+-    0x0aec, 0x0aee, 0x0aed, 0x0af6, 0x0af5, 0x0af3, 0x0af4, 0x0ad9,
+-    0x0af0, 0x04a4, 0x04a1, 0x04a2, 0x04a3, 0x04de, 0x04df, 0x04a7,
+-    0x04b1, 0x04a8, 0x04b2, 0x04a9, 0x04b3, 0x04aa, 0x04b4, 0x04ab,
+-    0x04b5, 0x04b6, 0x04b7, 0x04b8, 0x04b9, 0x04ba, 0x04bb, 0x04bc,
+-    0x04bd, 0x04be, 0x04bf, 0x04c0, 0x04c1, 0x04af, 0x04c2, 0x04c3,
+-    0x04c4, 0x04c5, 0x04c6, 0x04c7, 0x04c8, 0x04c9, 0x04ca, 0x04cb,
+-    0x04cc, 0x04cd, 0x04ce, 0x04cf, 0x04d0, 0x04d1, 0x04d2, 0x04d3,
+-    0x04ac, 0x04d4, 0x04ad, 0x04d5, 0x04ae, 0x04d6, 0x04d7, 0x04d8,
+-    0x04d9, 0x04da, 0x04db, 0x04dc, 0x04a6, 0x04dd, 0x04a5, 0x04b0
+-};
+diff --git a/src/autotype/x11/keysymmap.py b/src/autotype/x11/keysymmap.py
+deleted file mode 100755
+index a359710..0000000
+--- a/src/autotype/x11/keysymmap.py
++++ /dev/null
+@@ -1,107 +0,0 @@
+-#!/usr/bin/python3
+-
+-#
+-# Copyright (C) 2013 Felix Geyer <debfx@fobos.de>
+-#
+-# This program is free software: you can redistribute it and/or modify
+-# it under the terms of the GNU General Public License as published by
+-# the Free Software Foundation, either version 2 or (at your option)
+-# version 3 of the License.
+-#
+-# This program is distributed in the hope that it will be useful,
+-# but WITHOUT ANY WARRANTY; without even the implied warranty of
+-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+-# GNU General Public License for more details.
+-#
+-# You should have received a copy of the GNU General Public License
+-# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+-#
+-
+-#
+-# Parses keysymdef.h to construct a unicode symbol -> keysym mapping table.
+-#
+-# The lines that are parsed look like this:
+-# #define XK_Aogonek 0x01a1  /* U+0104 LATIN CAPITAL LETTER A WITH OGONEK */
+-#
+-# This would create a 0x0104 -> 0x01a1 mapping.
+-#
+-
+-import sys
+-import re
+-import collections
+-
+-cols = 8
+-
+-if len(sys.argv) >= 2:
+-    keysymdef = sys.argv[1]
+-else:
+-    keysymdef = "/usr/include/X11/keysymdef.h"
+-
+-keysymMap = {}
+-
+-f = open(keysymdef, "r")
+-for line in f:
+-    match = re.search(r'0x([0-9a-fA-F]+)\s+/\* U\+([0-9a-fA-F]+)', line)
+-    if match:
+-        keysym = int(match.group(1), 16)
+-        unicodeVal = int(match.group(2), 16)
+-
+-        # ignore 1:1 mappings
+-        if keysym >= 0x0020 and keysym <= 0x007e:
+-            continue
+-        if keysym >= 0x00a0 and keysym <= 0x00ff:
+-            continue
+-        # ignore unicode | 0x01000000 mappings
+-        if keysym >= 0x1000000:
+-            continue
+-
+-        keysymMap[unicodeVal] = keysym
+-
+-keysymMap = collections.OrderedDict(sorted(keysymMap.items(), key=lambda t: t[0]))
+-
+-print("""/*
+- *  Automatically generated by keysymmap.py from parsing keysymdef.h.
+- */
+-""")
+-
+-print("const int AutoTypePlatformX11::m_unicodeToKeysymLen = " + str(len(keysymMap)) + ";")
+-
+-print()
+-
+-print("const uint AutoTypePlatformX11::m_unicodeToKeysymKeys[] = {")
+-keys = keysymMap.keys()
+-keyLen = len(keys)
+-i = 1
+-for val in keys:
+-    hexVal = "{0:#0{1}x}".format(val, 6)
+-
+-    if i == keyLen:
+-        print(hexVal)
+-    elif (i % cols) == 0:
+-        print(hexVal + ",")
+-    elif ((i - 1) % cols) == 0:
+-        print("    " + hexVal + ", ", end="")
+-    else:
+-        print(hexVal + ", ", end="")
+-    i += 1
+-print("};")
+-
+-print()
+-
+-print("const uint AutoTypePlatformX11::m_unicodeToKeysymValues[] = {")
+-values = keysymMap.values()
+-valuesLen = len(values)
+-i = 1
+-for val in values:
+-    hexVal = "{0:#0{1}x}".format(val, 6)
+-
+-    if i == valuesLen:
+-        print(hexVal)
+-    elif (i % cols) == 0:
+-        print(hexVal + ",")
+-    elif ((i - 1) % cols) == 0:
+-        print("    " + hexVal + ", ", end="")
+-    else:
+-        print(hexVal + ", ", end="")
+-    i += 1
+-print("};")
+diff --git a/src/autotype/xcb/AutoTypeXCB.cpp b/src/autotype/xcb/AutoTypeXCB.cpp
+new file mode 100644
+index 0000000..40acaf6
+--- /dev/null
++++ b/src/autotype/xcb/AutoTypeXCB.cpp
+@@ -0,0 +1,870 @@
++/*
++ *  Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
++ *  Copyright (C) 2000-2008 Tom Sato <VEF00200@nifty.ne.jp>
++ *
++ *  This program is free software: you can redistribute it and/or modify
++ *  it under the terms of the GNU General Public License as published by
++ *  the Free Software Foundation, either version 2 or (at your option)
++ *  version 3 of the License.
++ *
++ *  This program is distributed in the hope that it will be useful,
++ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
++ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++ *  GNU General Public License for more details.
++ *
++ *  You should have received a copy of the GNU General Public License
++ *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
++ */
++
++#include "AutoTypeXCB.h"
++#include "KeySymMap.h"
++#include "core/Tools.h"
++
++#include <time.h>
++#include <xcb/xcb.h>
++
++bool AutoTypePlatformX11::m_catchXErrors = false;
++bool AutoTypePlatformX11::m_xErrorOccured = false;
++int (*AutoTypePlatformX11::m_oldXErrorHandler)(Display*, XErrorEvent*) = nullptr;
++
++AutoTypePlatformX11::AutoTypePlatformX11()
++{
++    m_dpy = QX11Info::display();
++    m_rootWindow = QX11Info::appRootWindow();
++
++    m_atomWmState = XInternAtom(m_dpy, "WM_STATE", True);
++    m_atomWmName = XInternAtom(m_dpy, "WM_NAME", True);
++    m_atomNetWmName = XInternAtom(m_dpy, "_NET_WM_NAME", True);
++    m_atomString = XInternAtom(m_dpy, "STRING", True);
++    m_atomUtf8String = XInternAtom(m_dpy, "UTF8_STRING", True);
++    m_atomNetActiveWindow = XInternAtom(m_dpy, "_NET_ACTIVE_WINDOW", True);
++
++    m_classBlacklist << "desktop_window" << "gnome-panel"; // Gnome
++    m_classBlacklist << "kdesktop" << "kicker"; // KDE 3
++    m_classBlacklist << "Plasma"; // KDE 4
++    m_classBlacklist << "plasmashell"; // KDE 5
++    m_classBlacklist << "xfdesktop" << "xfce4-panel"; // Xfce 4
++
++    m_currentGlobalKey = static_cast<Qt::Key>(0);
++    m_currentGlobalModifiers = 0;
++
++    m_keysymTable = nullptr;
++    m_xkb = nullptr;
++    m_remapKeycode = 0;
++    m_currentRemapKeysym = NoSymbol;
++    m_modifierMask = ControlMask | ShiftMask | Mod1Mask | Mod4Mask;
++
++    m_loaded = true;
++
++    updateKeymap();
++}
++
++bool AutoTypePlatformX11::isAvailable()
++{
++    int ignore;
++
++    if (!XQueryExtension(m_dpy, "XInputExtension", &ignore, &ignore, &ignore)) {
++        return false;
++    }
++
++    if (!XQueryExtension(m_dpy, "XTEST", &ignore, &ignore, &ignore)) {
++        return false;
++    }
++
++    if (!m_xkb) {
++        XkbDescPtr kbd = getKeyboard();
++
++        if (!kbd) {
++            return false;
++        }
++
++        XkbFreeKeyboard(kbd, XkbAllComponentsMask, True);
++    }
++
++    return true;
++}
++
++void AutoTypePlatformX11::unload()
++{
++    // Restore the KeyboardMapping to its original state.
++    if (m_currentRemapKeysym != NoSymbol) {
++        AddKeysym(NoSymbol);
++    }
++
++    if (m_keysymTable) {
++        XFree(m_keysymTable);
++    }
++
++    if (m_xkb) {
++        XkbFreeKeyboard(m_xkb, XkbAllComponentsMask, True);
++    }
++
++    m_loaded = false;
++}
++
++QStringList AutoTypePlatformX11::windowTitles()
++{
++    return windowTitlesRecursive(m_rootWindow);
++}
++
++WId AutoTypePlatformX11::activeWindow()
++{
++    Window window;
++    int revert_to_return;
++    XGetInputFocus(m_dpy, &window, &revert_to_return);
++
++    int tree;
++    do {
++        if (isTopLevelWindow(window)) {
++            break;
++        }
++
++        Window root;
++        Window parent;
++        Window* children = nullptr;
++        unsigned int numChildren;
++        tree = XQueryTree(m_dpy, window, &root, &parent, &children, &numChildren);
++        window = parent;
++        if (children) {
++            XFree(children);
++        }
++    } while (tree && window);
++
++    return window;
++}
++
++QString AutoTypePlatformX11::activeWindowTitle()
++{
++    return windowTitle(activeWindow(), true);
++}
++
++bool AutoTypePlatformX11::registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers)
++{
++    int keycode = XKeysymToKeycode(m_dpy, charToKeySym(key));
++    uint nativeModifiers = qtToNativeModifiers(modifiers);
++
++    startCatchXErrors();
++    XGrabKey(m_dpy, keycode, nativeModifiers, m_rootWindow, True, GrabModeAsync, GrabModeAsync);
++    XGrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask, m_rootWindow, True, GrabModeAsync,
++             GrabModeAsync);
++    XGrabKey(m_dpy, keycode, nativeModifiers | LockMask, m_rootWindow, True, GrabModeAsync,
++             GrabModeAsync);
++    XGrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask | LockMask, m_rootWindow, True,
++             GrabModeAsync, GrabModeAsync);
++    stopCatchXErrors();
++
++    if (!m_xErrorOccured) {
++        m_currentGlobalKey = key;
++        m_currentGlobalModifiers = modifiers;
++        m_currentGlobalKeycode = keycode;
++        m_currentGlobalNativeModifiers = nativeModifiers;
++        return true;
++    }
++    else {
++        unregisterGlobalShortcut(key, modifiers);
++        return false;
++    }
++}
++
++uint AutoTypePlatformX11::qtToNativeModifiers(Qt::KeyboardModifiers modifiers)
++{
++    uint nativeModifiers = 0;
++
++    if (modifiers & Qt::ShiftModifier) {
++        nativeModifiers |= ShiftMask;
++    }
++    if (modifiers & Qt::ControlModifier) {
++        nativeModifiers |= ControlMask;
++    }
++    if (modifiers & Qt::AltModifier) {
++        nativeModifiers |= Mod1Mask;
++    }
++    if (modifiers & Qt::MetaModifier) {
++        nativeModifiers |= Mod4Mask;
++    }
++
++    return nativeModifiers;
++}
++
++void AutoTypePlatformX11::unregisterGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers)
++{
++    KeyCode keycode = XKeysymToKeycode(m_dpy, charToKeySym(key));
++    uint nativeModifiers = qtToNativeModifiers(modifiers);
++
++    XUngrabKey(m_dpy, keycode, nativeModifiers, m_rootWindow);
++    XUngrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask, m_rootWindow);
++    XUngrabKey(m_dpy, keycode, nativeModifiers | LockMask, m_rootWindow);
++    XUngrabKey(m_dpy, keycode, nativeModifiers | Mod2Mask | LockMask, m_rootWindow);
++
++    m_currentGlobalKey = static_cast<Qt::Key>(0);
++    m_currentGlobalModifiers = 0;
++    m_currentGlobalKeycode = 0;
++    m_currentGlobalNativeModifiers = 0;
++}
++
++int AutoTypePlatformX11::platformEventFilter(void* event)
++{
++    xcb_generic_event_t* genericEvent = static_cast<xcb_generic_event_t*>(event);
++    quint8 type = genericEvent->response_type & 0x7f;
++
++    if (type == XCB_KEY_PRESS || type == XCB_KEY_RELEASE) {
++        xcb_key_press_event_t* keyPressEvent = static_cast<xcb_key_press_event_t*>(event);
++        if (keyPressEvent->detail == m_currentGlobalKeycode
++                && (keyPressEvent->state & m_modifierMask) == m_currentGlobalNativeModifiers
++                && (!QApplication::activeWindow() || QApplication::activeWindow()->isMinimized())
++                && m_loaded) {
++            if (type == XCB_KEY_PRESS) {
++                Q_EMIT globalShortcutTriggered();
++            }
++
++            return 1;
++        }
++    }
++    else if (type == XCB_MAPPING_NOTIFY) {
++        xcb_mapping_notify_event_t* mappingNotifyEvent = static_cast<xcb_mapping_notify_event_t*>(event);
++        if (mappingNotifyEvent->request == XCB_MAPPING_KEYBOARD
++                || mappingNotifyEvent->request == XCB_MAPPING_MODIFIER)
++        {
++            XMappingEvent xMappingEvent;
++            memset(&xMappingEvent, 0, sizeof(xMappingEvent));
++            xMappingEvent.type = MappingNotify;
++            xMappingEvent.display = m_dpy;
++            if (mappingNotifyEvent->request == XCB_MAPPING_KEYBOARD) {
++                xMappingEvent.request = MappingKeyboard;
++            }
++            else {
++                xMappingEvent.request = MappingModifier;
++            }
++            xMappingEvent.first_keycode = mappingNotifyEvent->first_keycode;
++            xMappingEvent.count = mappingNotifyEvent->count;
++            XRefreshKeyboardMapping(&xMappingEvent);
++            updateKeymap();
++        }
++    }
++
++    return -1;
++}
++
++AutoTypeExecutor* AutoTypePlatformX11::createExecutor()
++{
++    return new AutoTypeExecturorX11(this);
++}
++
++QString AutoTypePlatformX11::windowTitle(Window window, bool useBlacklist)
++{
++    QString title;
++
++    Atom type;
++    int format;
++    unsigned long nitems;
++    unsigned long after;
++    unsigned char* data = nullptr;
++
++    // the window manager spec says we should read _NET_WM_NAME first, then fall back to WM_NAME
++
++    int retVal = XGetWindowProperty(m_dpy, window, m_atomNetWmName, 0, 1000, False, m_atomUtf8String,
++                                    &type, &format, &nitems, &after, &data);
++
++    if ((retVal == 0) && data) {
++        title = QString::fromUtf8(reinterpret_cast<char*>(data));
++    }
++    else {
++        XTextProperty textProp;
++        retVal = XGetTextProperty(m_dpy, window, &textProp, m_atomWmName);
++        if ((retVal != 0) && textProp.value) {
++            char** textList = nullptr;
++            int count;
++
++            if (textProp.encoding == m_atomUtf8String) {
++                title = QString::fromUtf8(reinterpret_cast<char*>(textProp.value));
++            }
++            else if ((XmbTextPropertyToTextList(m_dpy, &textProp, &textList, &count) == 0)
++                     && textList && (count > 0)) {
++                title = QString::fromLocal8Bit(textList[0]);
++            }
++            else if (textProp.encoding == m_atomString) {
++                title = QString::fromLocal8Bit(reinterpret_cast<char*>(textProp.value));
++            }
++
++            if (textList) {
++                XFreeStringList(textList);
++            }
++        }
++
++        if (textProp.value) {
++            XFree(textProp.value);
++        }
++    }
++
++    if (data) {
++        XFree(data);
++    }
++
++    if (useBlacklist && !title.isEmpty()) {
++        if (window == m_rootWindow) {
++            return QString();
++        }
++
++        QString className = windowClassName(window);
++        if (m_classBlacklist.contains(className)) {
++            return QString();
++        }
++
++        QList<Window> keepassxWindows = widgetsToX11Windows(QApplication::topLevelWidgets());
++        if (keepassxWindows.contains(window)) {
++            return QString();
++        }
++    }
++
++    return title;
++}
++
++QString AutoTypePlatformX11::windowClassName(Window window)
++{
++    QString className;
++
++    XClassHint wmClass;
++    wmClass.res_name = nullptr;
++    wmClass.res_class = nullptr;
++
++    if (XGetClassHint(m_dpy, window, &wmClass) && wmClass.res_name) {
++        className = QString::fromLocal8Bit(wmClass.res_name);
++    }
++    if (wmClass.res_name) {
++        XFree(wmClass.res_name);
++    }
++    if (wmClass.res_class) {
++        XFree(wmClass.res_class);
++    }
++
++    return className;
++}
++
++QList<Window> AutoTypePlatformX11::widgetsToX11Windows(const QWidgetList& widgetList)
++{
++    QList<Window> windows;
++
++    Q_FOREACH (const QWidget* widget, widgetList) {
++        windows.append(widget->effectiveWinId());
++    }
++
++    return windows;
++}
++
++QStringList AutoTypePlatformX11::windowTitlesRecursive(Window window)
++{
++    QStringList titles;
++
++    if (isTopLevelWindow(window)) {
++        QString title = windowTitle(window, true);
++        if (!title.isEmpty()) {
++            titles.append(title);
++        }
++    }
++
++    Window root;
++    Window parent;
++    Window* children = nullptr;
++    unsigned int numChildren;
++    if (XQueryTree(m_dpy, window, &root, &parent, &children, &numChildren) && children) {
++        for (uint i = 0; i < numChildren; i++) {
++            titles.append(windowTitlesRecursive(children[i]));
++        }
++    }
++    if (children) {
++        XFree(children);
++    }
++
++    return titles;
++}
++
++bool AutoTypePlatformX11::isTopLevelWindow(Window window)
++{
++    Atom type = None;
++    int format;
++    unsigned long nitems;
++    unsigned long after;
++    unsigned char* data = nullptr;
++    int retVal = XGetWindowProperty(m_dpy, window, m_atomWmState, 0, 0, False, AnyPropertyType, &type, &format,
++                                    &nitems, &after, &data);
++    if (data) {
++        XFree(data);
++    }
++
++    return (retVal == 0) && type;
++}
++
++KeySym AutoTypePlatformX11::charToKeySym(const QChar& ch)
++{
++    ushort unicode = ch.unicode();
++
++    /* first check for Latin-1 characters (1:1 mapping) */
++    if ((unicode >= 0x0020 && unicode <= 0x007e)
++            || (unicode >= 0x00a0 && unicode <= 0x00ff)) {
++        return unicode;
++    }
++
++    /* mapping table generated from keysymdef.h */
++    const uint* match = Tools::binaryFind(m_unicodeToKeysymKeys,
++                                          m_unicodeToKeysymKeys + m_unicodeToKeysymLen,
++                                          unicode);
++    int index = match - m_unicodeToKeysymKeys;
++    if (index != m_unicodeToKeysymLen) {
++        return m_unicodeToKeysymValues[index];
++    }
++
++    if (unicode >= 0x0100) {
++        return unicode | 0x01000000;
++    }
++
++    return NoSymbol;
++}
++
++KeySym AutoTypePlatformX11::keyToKeySym(Qt::Key key)
++{
++    switch (key) {
++    case Qt::Key_Tab:
++        return XK_Tab;
++    case Qt::Key_Enter:
++        return XK_Return;
++    case Qt::Key_Up:
++        return XK_Up;
++    case Qt::Key_Down:
++        return XK_Down;
++    case Qt::Key_Left:
++        return XK_Left;
++    case Qt::Key_Right:
++        return XK_Right;
++    case Qt::Key_Insert:
++        return XK_Insert;
++    case Qt::Key_Delete:
++        return XK_Delete;
++    case Qt::Key_Home:
++        return XK_Home;
++    case Qt::Key_End:
++        return XK_End;
++    case Qt::Key_PageUp:
++        return XK_Page_Up;
++    case Qt::Key_PageDown:
++        return XK_Page_Down;
++    case Qt::Key_Backspace:
++        return XK_BackSpace;
++    case Qt::Key_Pause:
++        return XK_Break;
++    case Qt::Key_CapsLock:
++        return XK_Caps_Lock;
++    case Qt::Key_Escape:
++        return XK_Escape;
++    case Qt::Key_Help:
++        return XK_Help;
++    case Qt::Key_NumLock:
++        return XK_Num_Lock;
++    case Qt::Key_Print:
++        return XK_Print;
++    case Qt::Key_ScrollLock:
++        return XK_Scroll_Lock;
++    default:
++        if (key >= Qt::Key_F1 && key <= Qt::Key_F16) {
++            return XK_F1 + (key - Qt::Key_F1);
++        }
++        else {
++            return NoSymbol;
++        }
++    }
++}
++
++/*
++ * Update the keyboard and modifier mapping.
++ * We need the KeyboardMapping for AddKeysym.
++ * Modifier mapping is required for clearing the modifiers. 
++ */
++void AutoTypePlatformX11::updateKeymap()
++{
++    int keycode, inx;
++    int mod_index, mod_key;
++    XModifierKeymap *modifiers;
++
++    if (m_xkb) {
++        XkbFreeKeyboard(m_xkb, XkbAllComponentsMask, True);
++    }
++    m_xkb = getKeyboard();
++
++    XDisplayKeycodes(m_dpy, &m_minKeycode, &m_maxKeycode);
++    if (m_keysymTable != NULL) XFree(m_keysymTable);
++    m_keysymTable = XGetKeyboardMapping(m_dpy,
++            m_minKeycode, m_maxKeycode - m_minKeycode + 1,
++            &m_keysymPerKeycode);
++
++    /* determine the keycode to use for remapped keys */
++    inx = (m_remapKeycode - m_minKeycode) * m_keysymPerKeycode;
++    if (m_remapKeycode == 0 || !isRemapKeycodeValid()) {
++        for (keycode = m_minKeycode; keycode <= m_maxKeycode; keycode++) {
++            inx = (keycode - m_minKeycode) * m_keysymPerKeycode;
++            if (m_keysymTable[inx] == NoSymbol) {
++               m_remapKeycode = keycode;
++               m_currentRemapKeysym = NoSymbol;
++               break;
++            }
++        }
++    }
++
++    /* determine the keycode to use for modifiers */
++    modifiers = XGetModifierMapping(m_dpy);
++    for (mod_index = ShiftMapIndex; mod_index <= Mod5MapIndex; mod_index ++) {
++        m_modifier_keycode[mod_index] = 0;
++        for (mod_key = 0; mod_key < modifiers->max_keypermod; mod_key++) {
++            keycode = modifiers->modifiermap[mod_index * modifiers->max_keypermod + mod_key];
++            if (keycode) {
++                m_modifier_keycode[mod_index] = keycode;
++                break;
++            }
++        }
++    }
++    XFreeModifiermap(modifiers);
++
++    /* Xlib needs some time until the mapping is distributed to
++       all clients */
++    // TODO: we should probably only sleep while in the middle of typing something
++    timespec ts;
++    ts.tv_sec = 0;
++    ts.tv_nsec = 30 * 1000 * 1000;
++    nanosleep(&ts, nullptr);
++}
++
++bool AutoTypePlatformX11::isRemapKeycodeValid()
++{
++    int baseKeycode = (m_remapKeycode - m_minKeycode) * m_keysymPerKeycode;
++    for (int i = 0; i < m_keysymPerKeycode; i++) {
++        if (m_keysymTable[baseKeycode + i] == m_currentRemapKeysym) {
++            return true;
++        }
++    }
++
++    return false;
++}
++
++void AutoTypePlatformX11::startCatchXErrors()
++{
++    Q_ASSERT(!m_catchXErrors);
++
++    m_catchXErrors = true;
++    m_xErrorOccured = false;
++    m_oldXErrorHandler = XSetErrorHandler(x11ErrorHandler);
++}
++
++void AutoTypePlatformX11::stopCatchXErrors()
++{
++    Q_ASSERT(m_catchXErrors);
++
++    XSync(m_dpy, False);
++    XSetErrorHandler(m_oldXErrorHandler);
++    m_catchXErrors = false;
++}
++
++int AutoTypePlatformX11::x11ErrorHandler(Display* display, XErrorEvent* error)
++{
++    Q_UNUSED(display)
++    Q_UNUSED(error)
++
++    if (m_catchXErrors) {
++        m_xErrorOccured = true;
++    }
++
++    return 1;
++}
++
++XkbDescPtr AutoTypePlatformX11::getKeyboard()
++{
++    int num_devices;
++    XID keyboard_id = XkbUseCoreKbd;
++    XDeviceInfo* devices = XListInputDevices(m_dpy, &num_devices);
++    if (!devices) {
++        return nullptr;
++    }
++
++    for (int i = 0; i < num_devices; i++) {
++        if (QString(devices[i].name) == "Virtual core XTEST keyboard") {
++            keyboard_id = devices[i].id;
++            break;
++        }
++    }
++
++    XFreeDeviceList(devices);
++
++    return XkbGetKeyboard(m_dpy, XkbCompatMapMask | XkbGeometryMask, keyboard_id);
++}
++
++// --------------------------------------------------------------------------
++// The following code is taken from xvkbd 3.0 and has been slightly modified.
++// --------------------------------------------------------------------------
++
++/*
++ * Insert a specified keysym on the dedicated position in the keymap
++ * table.
++ */
++int AutoTypePlatformX11::AddKeysym(KeySym keysym)
++{
++    if (m_remapKeycode == 0) {
++        return 0;
++    }
++
++    int inx = (m_remapKeycode- m_minKeycode) * m_keysymPerKeycode;
++    m_keysymTable[inx] = keysym;
++    m_currentRemapKeysym = keysym;
++
++    XChangeKeyboardMapping(m_dpy, m_remapKeycode, m_keysymPerKeycode, &m_keysymTable[inx], 1);
++    XFlush(m_dpy);
++    updateKeymap();
++
++    return m_remapKeycode;
++}
++
++/*
++ * Send event to the focused window.
++ * If input focus is specified explicitly, select the window
++ * before send event to the window.
++ */
++void AutoTypePlatformX11::SendEvent(XKeyEvent* event, int event_type)
++{
++    XSync(event->display, False);
++    int (*oldHandler) (Display*, XErrorEvent*) = XSetErrorHandler(MyErrorHandler);
++
++    event->type = event_type;
++    Bool press;
++    if (event->type == KeyPress) {
++        press = True;
++    }
++    else {
++        press = False;
++    }
++    XTestFakeKeyEvent(event->display, event->keycode, press, 0);
++    XFlush(event->display);
++
++    XSetErrorHandler(oldHandler);
++}
++
++/*
++ * Send a modifier press/release event for all modifiers
++ * which are set in the mask variable.
++ */
++void AutoTypePlatformX11::SendModifier(XKeyEvent *event, unsigned int mask, int event_type) 
++{
++    int mod_index;
++    for (mod_index = ShiftMapIndex; mod_index <= Mod5MapIndex; mod_index ++) {
++        if (mask & (1 << mod_index)) {
++            event->keycode = m_modifier_keycode[mod_index];
++            SendEvent(event, event_type);
++            if (event_type == KeyPress) 
++                event->state |= (1 << mod_index);
++            else
++                event->state &= (1 << mod_index);
++        }
++    }
++}
++
++/*
++ * Determines the keycode and modifier mask for the given
++ * keysym.
++ */
++int AutoTypePlatformX11::GetKeycode(KeySym keysym, unsigned int *mask)
++{
++    int keycode = XKeysymToKeycode(m_dpy, keysym);
++
++    if (keycode && keysymModifiers(keysym, keycode, mask)) {
++        return keycode;
++    }
++
++    /* no modifier matches => resort to remapping */
++    keycode = AddKeysym(keysym);
++    if (keycode && keysymModifiers(keysym, keycode, mask)) {
++        return keycode;
++    }
++
++    *mask = 0;
++    return 0;
++}
++
++bool AutoTypePlatformX11::keysymModifiers(KeySym keysym, int keycode, unsigned int *mask)
++{
++    int shift, mod;
++    unsigned int mods_rtrn;
++
++    /* determine whether there is a combination of the modifiers
++       (Mod1-Mod5) with or without shift which returns keysym */
++    for (shift = 0; shift < 2; shift ++) {
++        for (mod = ControlMapIndex; mod <= Mod5MapIndex; mod ++) {
++            KeySym keysym_rtrn;
++            *mask = (mod == ControlMapIndex) ? shift : shift | (1 << mod);
++            XkbTranslateKeyCode(m_xkb, keycode, *mask, &mods_rtrn, &keysym_rtrn);
++            if (keysym_rtrn == keysym) {
++                return true;
++            }
++        }
++    }
++
++    return false;
++}
++
++
++
++/*
++ * Send sequence of KeyPressed/KeyReleased events to the focused
++ * window to simulate keyboard.  If modifiers (shift, control, etc)
++ * are set ON, many events will be sent.
++ */
++void AutoTypePlatformX11::SendKeyPressedEvent(KeySym keysym)
++{
++    Window cur_focus;
++    int revert_to;
++    XKeyEvent event;
++    int keycode;
++
++    if (keysym == NoSymbol) {
++        qWarning("No such key: keysym=0x%lX", keysym);
++        return;
++    }
++
++    XGetInputFocus(m_dpy, &cur_focus, &revert_to);
++
++    event.display = m_dpy;
++    event.window = cur_focus;
++    event.root = m_rootWindow;
++    event.subwindow = None;
++    event.time = CurrentTime;
++    event.x = 1;
++    event.y = 1;
++    event.x_root = 1;
++    event.y_root = 1;
++    event.same_screen = True;
++
++    Window root, child;
++    int root_x, root_y, x, y;
++    unsigned int wanted_mask = 0;
++    unsigned int original_mask;
++
++    XQueryPointer(m_dpy, event.root, &root, &child, &root_x, &root_y, &x, &y, &original_mask);
++
++    /* determine keycode and mask for the given keysym */
++    keycode = GetKeycode(keysym, &wanted_mask);
++    if (keycode < 8 || keycode > 255) {
++        qWarning("Unable to get valid keycode for key: keysym=0x%lX", keysym);
++        return;
++    }
++
++    event.state = original_mask;
++
++    // modifiers that need to be pressed but aren't
++    unsigned int press_mask = wanted_mask & ~original_mask;
++
++    // modifiers that are pressed but maybe shouldn't
++    unsigned int release_check_mask = original_mask & ~wanted_mask;
++
++    // modifiers we need to release before sending the keycode
++    unsigned int release_mask = 0;
++
++    // check every release_check_mask individually if it affects the keysym we would generate
++    // if it doesn't we probably don't need to release it
++    for (int mod_index = ShiftMapIndex; mod_index <= Mod5MapIndex; mod_index ++) {
++        if (release_check_mask & (1 << mod_index)) {
++            unsigned int mods_rtrn;
++            KeySym keysym_rtrn;
++            XkbTranslateKeyCode(m_xkb, keycode, wanted_mask | (1 << mod_index), &mods_rtrn, &keysym_rtrn);
++
++            if (keysym_rtrn != keysym) {
++                release_mask |= (1 << mod_index);
++            }
++        }
++    }
++
++    // finally check if the combination of pressed modifiers that we chose to ignore affects the keysym
++    unsigned int mods_rtrn;
++    KeySym keysym_rtrn;
++    XkbTranslateKeyCode(m_xkb, keycode, wanted_mask | (release_check_mask & ~release_mask), &mods_rtrn, &keysym_rtrn);
++    if (keysym_rtrn != keysym) {
++        // oh well, release all the modifiers we don't want
++        release_mask = release_check_mask;
++    }
++
++    /* release all modifiers */
++    SendModifier(&event, release_mask, KeyRelease);
++
++    SendModifier(&event, press_mask, KeyPress);
++
++    /* press and release key */
++    event.keycode = keycode;
++    SendEvent(&event, KeyPress);
++    SendEvent(&event, KeyRelease);
++
++    /* release the modifiers */
++    SendModifier(&event, press_mask, KeyRelease);
++
++    /* restore the old keyboard mask */
++    SendModifier(&event, release_mask, KeyPress);
++}
++
++int AutoTypePlatformX11::MyErrorHandler(Display* my_dpy, XErrorEvent* event)
++{
++    char msg[200];
++
++    if (event->error_code == BadWindow) {
++        return 0;
++    }
++    XGetErrorText(my_dpy, event->error_code, msg, sizeof(msg) - 1);
++    qWarning("X error trapped: %s, request-code=%d\n", msg, event->request_code);
++    return 0;
++}
++
++
++AutoTypeExecturorX11::AutoTypeExecturorX11(AutoTypePlatformX11* platform)
++    : m_platform(platform)
++{
++}
++
++void AutoTypeExecturorX11::execChar(AutoTypeChar* action)
++{
++    m_platform->SendKeyPressedEvent(m_platform->charToKeySym(action->character));
++}
++
++void AutoTypeExecturorX11::execKey(AutoTypeKey* action)
++{
++    m_platform->SendKeyPressedEvent(m_platform->keyToKeySym(action->key));
++}
++
++int AutoTypePlatformX11::initialTimeout()
++{
++    return 500;
++}
++
++bool AutoTypePlatformX11::raiseWindow(WId window)
++{
++    if (m_atomNetActiveWindow == None) {
++        return false;
++    }
++
++    XRaiseWindow(m_dpy, window);
++
++    XEvent event;
++    event.xclient.type = ClientMessage;
++    event.xclient.serial = 0;
++    event.xclient.send_event = True;
++    event.xclient.window = window;
++    event.xclient.message_type = m_atomNetActiveWindow;
++    event.xclient.format = 32;
++    event.xclient.data.l[0] = 1; // FromApplication
++    event.xclient.data.l[1] = QX11Info::appUserTime();
++    QWidget* activeWindow = QApplication::activeWindow();
++    if (activeWindow) {
++        event.xclient.data.l[2] = activeWindow->internalWinId();
++    }
++    else {
++        event.xclient.data.l[2] = 0;
++    }
++    event.xclient.data.l[3] = 0;
++    event.xclient.data.l[4] = 0;
++    XSendEvent(m_dpy, m_rootWindow, False,
++               SubstructureRedirectMask | SubstructureNotifyMask,
++               &event);
++    XFlush(m_dpy);
++
++    return true;
++}
+diff --git a/src/autotype/xcb/AutoTypeXCB.h b/src/autotype/xcb/AutoTypeXCB.h
+new file mode 100644
+index 0000000..8adee77
+--- /dev/null
++++ b/src/autotype/xcb/AutoTypeXCB.h
+@@ -0,0 +1,134 @@
++/*
++ *  Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
++ *  Copyright (C) 2000-2008 Tom Sato <VEF00200@nifty.ne.jp>
++ *
++ *  This program is free software: you can redistribute it and/or modify
++ *  it under the terms of the GNU General Public License as published by
++ *  the Free Software Foundation, either version 2 or (at your option)
++ *  version 3 of the License.
++ *
++ *  This program is distributed in the hope that it will be useful,
++ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
++ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++ *  GNU General Public License for more details.
++ *
++ *  You should have received a copy of the GNU General Public License
++ *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
++ */
++
++#ifndef KEEPASSX_AUTOTYPEXCB_H
++#define KEEPASSX_AUTOTYPEXCB_H
++
++#include <QApplication>
++#include <QSet>
++#include <QtPlugin>
++#include <QWidget>
++#include <QX11Info>
++
++#include <X11/Xutil.h>
++#include <X11/extensions/XTest.h>
++#include <X11/XKBlib.h>
++
++#include "autotype/AutoTypePlatformPlugin.h"
++#include "autotype/AutoTypeAction.h"
++
++#define N_MOD_INDICES (Mod5MapIndex + 1)
++
++class AutoTypePlatformX11 : public QObject, public AutoTypePlatformInterface
++{
++    Q_OBJECT
++    Q_PLUGIN_METADATA(IID "org.keepassx.AutoTypePlatformX11")
++    Q_INTERFACES(AutoTypePlatformInterface)
++
++public:
++    AutoTypePlatformX11();
++    bool isAvailable() override;
++    void unload() override;
++    QStringList windowTitles() override;
++    WId activeWindow() override;
++    QString activeWindowTitle() override;
++    bool registerGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) override;
++    void unregisterGlobalShortcut(Qt::Key key, Qt::KeyboardModifiers modifiers) override;
++    int platformEventFilter(void* event) override;
++    int initialTimeout() override;
++    bool raiseWindow(WId window) override;
++    AutoTypeExecutor* createExecutor() override;
++
++    KeySym charToKeySym(const QChar& ch);
++    KeySym keyToKeySym(Qt::Key key);
++
++    void SendKeyPressedEvent(KeySym keysym);
++
++Q_SIGNALS:
++    void globalShortcutTriggered();
++
++private:
++    QString windowTitle(Window window, bool useBlacklist);
++    QStringList windowTitlesRecursive(Window window);
++    QString windowClassName(Window window);
++    QList<Window> widgetsToX11Windows(const QWidgetList& widgetList);
++    bool isTopLevelWindow(Window window);
++    uint qtToNativeModifiers(Qt::KeyboardModifiers modifiers);
++    void startCatchXErrors();
++    void stopCatchXErrors();
++    static int x11ErrorHandler(Display* display, XErrorEvent* error);
++
++    XkbDescPtr getKeyboard();
++    void updateKeymap();
++    bool isRemapKeycodeValid();
++    int AddKeysym(KeySym keysym);
++    void AddModifier(KeySym keysym);
++    void SendEvent(XKeyEvent* event, int event_type);
++    void SendModifier(XKeyEvent *event, unsigned int mask, int event_type);
++    int GetKeycode(KeySym keysym, unsigned int *mask);
++    bool keysymModifiers(KeySym keysym, int keycode, unsigned int *mask);
++
++    static int MyErrorHandler(Display* my_dpy, XErrorEvent* event);
++
++    Display* m_dpy;
++    Window m_rootWindow;
++    Atom m_atomWmState;
++    Atom m_atomWmName;
++    Atom m_atomNetWmName;
++    Atom m_atomString;
++    Atom m_atomUtf8String;
++    Atom m_atomNetActiveWindow;
++    QSet<QString> m_classBlacklist;
++    Qt::Key m_currentGlobalKey;
++    Qt::KeyboardModifiers m_currentGlobalModifiers;
++    uint m_currentGlobalKeycode;
++    uint m_currentGlobalNativeModifiers;
++    int m_modifierMask;
++    static bool m_catchXErrors;
++    static bool m_xErrorOccured;
++    static int (*m_oldXErrorHandler)(Display*, XErrorEvent*);
++
++    static const int m_unicodeToKeysymLen;
++    static const uint m_unicodeToKeysymKeys[];
++    static const uint m_unicodeToKeysymValues[];
++
++    XkbDescPtr m_xkb;
++    KeySym* m_keysymTable;
++    int m_minKeycode;
++    int m_maxKeycode;
++    int m_keysymPerKeycode;
++    /* dedicated keycode for remapped keys */
++    unsigned int m_remapKeycode;
++    KeySym m_currentRemapKeysym;
++    KeyCode m_modifier_keycode[N_MOD_INDICES];
++    bool m_loaded;
++};
++
++class AutoTypeExecturorX11 : public AutoTypeExecutor
++{
++public:
++    explicit AutoTypeExecturorX11(AutoTypePlatformX11* platform);
++
++    void execChar(AutoTypeChar* action) override;
++    void execKey(AutoTypeKey* action) override;
++
++private:
++    AutoTypePlatformX11* const m_platform;
++};
++
++#endif // KEEPASSX_AUTOTYPEXCB_H
+diff --git a/src/autotype/xcb/CMakeLists.txt b/src/autotype/xcb/CMakeLists.txt
+new file mode 100644
+index 0000000..3b56b31
+--- /dev/null
++++ b/src/autotype/xcb/CMakeLists.txt
+@@ -0,0 +1,11 @@
++include_directories(SYSTEM ${X11_X11_INCLUDE_PATH})
++
++set(autotype_XCB_SOURCES
++    AutoTypeXCB.cpp
++)
++
++add_library(keepassx-autotype-xcb MODULE ${autotype_XCB_SOURCES})
++target_link_libraries(keepassx-autotype-xcb Qt5::Core Qt5::Widgets Qt5::X11Extras ${X11_X11_LIB} ${X11_Xi_LIB} ${X11_XTest_LIB})
++install(TARGETS keepassx-autotype-xcb
++        BUNDLE DESTINATION . COMPONENT Runtime
++        LIBRARY DESTINATION ${PLUGIN_INSTALL_DIR} COMPONENT Runtime)
+diff --git a/src/autotype/xcb/KeySymMap.h b/src/autotype/xcb/KeySymMap.h
+new file mode 100644
+index 0000000..55022fe
+--- /dev/null
++++ b/src/autotype/xcb/KeySymMap.h
+@@ -0,0 +1,169 @@
++/*
++ *  Automatically generated by keysymmap.py from parsing keysymdef.h.
++ */
++
++const int AutoTypePlatformX11::m_unicodeToKeysymLen = 632;
++
++const uint AutoTypePlatformX11::m_unicodeToKeysymKeys[] = {
++    0x0100, 0x0101, 0x0102, 0x0103, 0x0104, 0x0105, 0x0106, 0x0107,
++    0x0108, 0x0109, 0x010a, 0x010b, 0x010c, 0x010d, 0x010e, 0x010f,
++    0x0110, 0x0111, 0x0112, 0x0113, 0x0116, 0x0117, 0x0118, 0x0119,
++    0x011a, 0x011b, 0x011c, 0x011d, 0x011e, 0x011f, 0x0120, 0x0121,
++    0x0122, 0x0123, 0x0124, 0x0125, 0x0126, 0x0127, 0x0128, 0x0129,
++    0x012a, 0x012b, 0x012e, 0x012f, 0x0130, 0x0131, 0x0134, 0x0135,
++    0x0136, 0x0137, 0x0138, 0x0139, 0x013a, 0x013b, 0x013c, 0x013d,
++    0x013e, 0x0141, 0x0142, 0x0143, 0x0144, 0x0145, 0x0146, 0x0147,
++    0x0148, 0x014a, 0x014b, 0x014c, 0x014d, 0x0150, 0x0151, 0x0152,
++    0x0153, 0x0154, 0x0155, 0x0156, 0x0157, 0x0158, 0x0159, 0x015a,
++    0x015b, 0x015c, 0x015d, 0x015e, 0x015f, 0x0160, 0x0161, 0x0162,
++    0x0163, 0x0164, 0x0165, 0x0166, 0x0167, 0x0168, 0x0169, 0x016a,
++    0x016b, 0x016c, 0x016d, 0x016e, 0x016f, 0x0170, 0x0171, 0x0172,
++    0x0173, 0x0178, 0x0179, 0x017a, 0x017b, 0x017c, 0x017d, 0x017e,
++    0x0192, 0x02c7, 0x02d8, 0x02d9, 0x02db, 0x02dd, 0x0385, 0x0386,
++    0x0388, 0x0389, 0x038a, 0x038c, 0x038e, 0x038f, 0x0390, 0x0391,
++    0x0392, 0x0393, 0x0394, 0x0395, 0x0396, 0x0397, 0x0398, 0x0399,
++    0x039a, 0x039b, 0x039c, 0x039d, 0x039e, 0x039f, 0x03a0, 0x03a1,
++    0x03a3, 0x03a4, 0x03a5, 0x03a6, 0x03a7, 0x03a8, 0x03a9, 0x03aa,
++    0x03ab, 0x03ac, 0x03ad, 0x03ae, 0x03af, 0x03b0, 0x03b1, 0x03b2,
++    0x03b3, 0x03b4, 0x03b5, 0x03b6, 0x03b7, 0x03b8, 0x03b9, 0x03ba,
++    0x03bb, 0x03bc, 0x03bd, 0x03be, 0x03bf, 0x03c0, 0x03c1, 0x03c2,
++    0x03c3, 0x03c4, 0x03c5, 0x03c6, 0x03c7, 0x03c8, 0x03c9, 0x03ca,
++    0x03cb, 0x03cc, 0x03cd, 0x03ce, 0x0401, 0x0402, 0x0403, 0x0404,
++    0x0405, 0x0406, 0x0407, 0x0408, 0x0409, 0x040a, 0x040b, 0x040c,
++    0x040e, 0x040f, 0x0410, 0x0411, 0x0412, 0x0413, 0x0414, 0x0415,
++    0x0416, 0x0417, 0x0418, 0x0419, 0x041a, 0x041b, 0x041c, 0x041d,
++    0x041e, 0x041f, 0x0420, 0x0421, 0x0422, 0x0423, 0x0424, 0x0425,
++    0x0426, 0x0427, 0x0428, 0x0429, 0x042a, 0x042b, 0x042c, 0x042d,
++    0x042e, 0x042f, 0x0430, 0x0431, 0x0432, 0x0433, 0x0434, 0x0435,
++    0x0436, 0x0437, 0x0438, 0x0439, 0x043a, 0x043b, 0x043c, 0x043d,
++    0x043e, 0x043f, 0x0440, 0x0441, 0x0442, 0x0443, 0x0444, 0x0445,
++    0x0446, 0x0447, 0x0448, 0x0449, 0x044a, 0x044b, 0x044c, 0x044d,
++    0x044e, 0x044f, 0x0451, 0x0452, 0x0453, 0x0454, 0x0455, 0x0456,
++    0x0457, 0x0458, 0x0459, 0x045a, 0x045b, 0x045c, 0x045e, 0x045f,
++    0x0490, 0x0491, 0x05d0, 0x05d1, 0x05d2, 0x05d3, 0x05d4, 0x05d5,
++    0x05d6, 0x05d7, 0x05d8, 0x05d9, 0x05da, 0x05db, 0x05dc, 0x05dd,
++    0x05de, 0x05df, 0x05e0, 0x05e1, 0x05e2, 0x05e3, 0x05e4, 0x05e5,
++    0x05e6, 0x05e7, 0x05e8, 0x05e9, 0x05ea, 0x060c, 0x061b, 0x061f,
++    0x0621, 0x0622, 0x0623, 0x0624, 0x0625, 0x0626, 0x0627, 0x0628,
++    0x0629, 0x062a, 0x062b, 0x062c, 0x062d, 0x062e, 0x062f, 0x0630,
++    0x0631, 0x0632, 0x0633, 0x0634, 0x0635, 0x0636, 0x0637, 0x0638,
++    0x0639, 0x063a, 0x0640, 0x0641, 0x0642, 0x0643, 0x0644, 0x0645,
++    0x0646, 0x0647, 0x0648, 0x0649, 0x064a, 0x064b, 0x064c, 0x064d,
++    0x064e, 0x064f, 0x0650, 0x0651, 0x0652, 0x0e01, 0x0e02, 0x0e03,
++    0x0e04, 0x0e05, 0x0e06, 0x0e07, 0x0e08, 0x0e09, 0x0e0a, 0x0e0b,
++    0x0e0c, 0x0e0d, 0x0e0e, 0x0e0f, 0x0e10, 0x0e11, 0x0e12, 0x0e13,
++    0x0e14, 0x0e15, 0x0e16, 0x0e17, 0x0e18, 0x0e19, 0x0e1a, 0x0e1b,
++    0x0e1c, 0x0e1d, 0x0e1e, 0x0e1f, 0x0e20, 0x0e21, 0x0e22, 0x0e23,
++    0x0e24, 0x0e25, 0x0e26, 0x0e27, 0x0e28, 0x0e29, 0x0e2a, 0x0e2b,
++    0x0e2c, 0x0e2d, 0x0e2e, 0x0e2f, 0x0e30, 0x0e31, 0x0e32, 0x0e33,
++    0x0e34, 0x0e35, 0x0e36, 0x0e37, 0x0e38, 0x0e39, 0x0e3a, 0x0e3f,
++    0x0e40, 0x0e41, 0x0e42, 0x0e43, 0x0e44, 0x0e45, 0x0e46, 0x0e47,
++    0x0e48, 0x0e49, 0x0e4a, 0x0e4b, 0x0e4c, 0x0e4d, 0x0e50, 0x0e51,
++    0x0e52, 0x0e53, 0x0e54, 0x0e55, 0x0e56, 0x0e57, 0x0e58, 0x0e59,
++    0x2002, 0x2003, 0x2004, 0x2005, 0x2007, 0x2008, 0x2009, 0x200a,
++    0x2012, 0x2013, 0x2014, 0x2015, 0x2017, 0x2018, 0x2019, 0x201a,
++    0x201c, 0x201d, 0x201e, 0x2020, 0x2021, 0x2025, 0x2026, 0x2030,
++    0x2032, 0x2033, 0x2038, 0x203e, 0x20ac, 0x2105, 0x2116, 0x2117,
++    0x211e, 0x2122, 0x2153, 0x2154, 0x2155, 0x2156, 0x2157, 0x2158,
++    0x2159, 0x215a, 0x215b, 0x215c, 0x215d, 0x215e, 0x2190, 0x2191,
++    0x2192, 0x2193, 0x21d2, 0x21d4, 0x2202, 0x2207, 0x2218, 0x221a,
++    0x221d, 0x221e, 0x2227, 0x2228, 0x2229, 0x222a, 0x222b, 0x2234,
++    0x223c, 0x2243, 0x2260, 0x2261, 0x2264, 0x2265, 0x2282, 0x2283,
++    0x22a2, 0x22a3, 0x22a4, 0x22a5, 0x2308, 0x230a, 0x2315, 0x2320,
++    0x2321, 0x2395, 0x239b, 0x239d, 0x239e, 0x23a0, 0x23a1, 0x23a3,
++    0x23a4, 0x23a6, 0x23a8, 0x23ac, 0x23b7, 0x23ba, 0x23bb, 0x23bc,
++    0x23bd, 0x2409, 0x240a, 0x240b, 0x240c, 0x240d, 0x2424, 0x2500,
++    0x2502, 0x250c, 0x2510, 0x2514, 0x2518, 0x251c, 0x2524, 0x252c,
++    0x2534, 0x253c, 0x2592, 0x25c6, 0x25cb, 0x260e, 0x2640, 0x2642,
++    0x2663, 0x2665, 0x2666, 0x266d, 0x266f, 0x2713, 0x2717, 0x271d,
++    0x2720, 0x3001, 0x3002, 0x300c, 0x300d, 0x309b, 0x309c, 0x30a1,
++    0x30a2, 0x30a3, 0x30a4, 0x30a5, 0x30a6, 0x30a7, 0x30a8, 0x30a9,
++    0x30aa, 0x30ab, 0x30ad, 0x30af, 0x30b1, 0x30b3, 0x30b5, 0x30b7,
++    0x30b9, 0x30bb, 0x30bd, 0x30bf, 0x30c1, 0x30c3, 0x30c4, 0x30c6,
++    0x30c8, 0x30ca, 0x30cb, 0x30cc, 0x30cd, 0x30ce, 0x30cf, 0x30d2,
++    0x30d5, 0x30d8, 0x30db, 0x30de, 0x30df, 0x30e0, 0x30e1, 0x30e2,
++    0x30e3, 0x30e4, 0x30e5, 0x30e6, 0x30e7, 0x30e8, 0x30e9, 0x30ea,
++    0x30eb, 0x30ec, 0x30ed, 0x30ef, 0x30f2, 0x30f3, 0x30fb, 0x30fc
++};
++
++const uint AutoTypePlatformX11::m_unicodeToKeysymValues[] = {
++    0x03c0, 0x03e0, 0x01c3, 0x01e3, 0x01a1, 0x01b1, 0x01c6, 0x01e6,
++    0x02c6, 0x02e6, 0x02c5, 0x02e5, 0x01c8, 0x01e8, 0x01cf, 0x01ef,
++    0x01d0, 0x01f0, 0x03aa, 0x03ba, 0x03cc, 0x03ec, 0x01ca, 0x01ea,
++    0x01cc, 0x01ec, 0x02d8, 0x02f8, 0x02ab, 0x02bb, 0x02d5, 0x02f5,
++    0x03ab, 0x03bb, 0x02a6, 0x02b6, 0x02a1, 0x02b1, 0x03a5, 0x03b5,
++    0x03cf, 0x03ef, 0x03c7, 0x03e7, 0x02a9, 0x02b9, 0x02ac, 0x02bc,
++    0x03d3, 0x03f3, 0x03a2, 0x01c5, 0x01e5, 0x03a6, 0x03b6, 0x01a5,
++    0x01b5, 0x01a3, 0x01b3, 0x01d1, 0x01f1, 0x03d1, 0x03f1, 0x01d2,
++    0x01f2, 0x03bd, 0x03bf, 0x03d2, 0x03f2, 0x01d5, 0x01f5, 0x13bc,
++    0x13bd, 0x01c0, 0x01e0, 0x03a3, 0x03b3, 0x01d8, 0x01f8, 0x01a6,
++    0x01b6, 0x02de, 0x02fe, 0x01aa, 0x01ba, 0x01a9, 0x01b9, 0x01de,
++    0x01fe, 0x01ab, 0x01bb, 0x03ac, 0x03bc, 0x03dd, 0x03fd, 0x03de,
++    0x03fe, 0x02dd, 0x02fd, 0x01d9, 0x01f9, 0x01db, 0x01fb, 0x03d9,
++    0x03f9, 0x13be, 0x01ac, 0x01bc, 0x01af, 0x01bf, 0x01ae, 0x01be,
++    0x08f6, 0x01b7, 0x01a2, 0x01ff, 0x01b2, 0x01bd, 0x07ae, 0x07a1,
++    0x07a2, 0x07a3, 0x07a4, 0x07a7, 0x07a8, 0x07ab, 0x07b6, 0x07c1,
++    0x07c2, 0x07c3, 0x07c4, 0x07c5, 0x07c6, 0x07c7, 0x07c8, 0x07c9,
++    0x07ca, 0x07cb, 0x07cc, 0x07cd, 0x07ce, 0x07cf, 0x07d0, 0x07d1,
++    0x07d2, 0x07d4, 0x07d5, 0x07d6, 0x07d7, 0x07d8, 0x07d9, 0x07a5,
++    0x07a9, 0x07b1, 0x07b2, 0x07b3, 0x07b4, 0x07ba, 0x07e1, 0x07e2,
++    0x07e3, 0x07e4, 0x07e5, 0x07e6, 0x07e7, 0x07e8, 0x07e9, 0x07ea,
++    0x07eb, 0x07ec, 0x07ed, 0x07ee, 0x07ef, 0x07f0, 0x07f1, 0x07f3,
++    0x07f2, 0x07f4, 0x07f5, 0x07f6, 0x07f7, 0x07f8, 0x07f9, 0x07b5,
++    0x07b9, 0x07b7, 0x07b8, 0x07bb, 0x06b3, 0x06b1, 0x06b2, 0x06b4,
++    0x06b5, 0x06b6, 0x06b7, 0x06b8, 0x06b9, 0x06ba, 0x06bb, 0x06bc,
++    0x06be, 0x06bf, 0x06e1, 0x06e2, 0x06f7, 0x06e7, 0x06e4, 0x06e5,
++    0x06f6, 0x06fa, 0x06e9, 0x06ea, 0x06eb, 0x06ec, 0x06ed, 0x06ee,
++    0x06ef, 0x06f0, 0x06f2, 0x06f3, 0x06f4, 0x06f5, 0x06e6, 0x06e8,
++    0x06e3, 0x06fe, 0x06fb, 0x06fd, 0x06ff, 0x06f9, 0x06f8, 0x06fc,
++    0x06e0, 0x06f1, 0x06c1, 0x06c2, 0x06d7, 0x06c7, 0x06c4, 0x06c5,
++    0x06d6, 0x06da, 0x06c9, 0x06ca, 0x06cb, 0x06cc, 0x06cd, 0x06ce,
++    0x06cf, 0x06d0, 0x06d2, 0x06d3, 0x06d4, 0x06d5, 0x06c6, 0x06c8,
++    0x06c3, 0x06de, 0x06db, 0x06dd, 0x06df, 0x06d9, 0x06d8, 0x06dc,
++    0x06c0, 0x06d1, 0x06a3, 0x06a1, 0x06a2, 0x06a4, 0x06a5, 0x06a6,
++    0x06a7, 0x06a8, 0x06a9, 0x06aa, 0x06ab, 0x06ac, 0x06ae, 0x06af,
++    0x06bd, 0x06ad, 0x0ce0, 0x0ce1, 0x0ce2, 0x0ce3, 0x0ce4, 0x0ce5,
++    0x0ce6, 0x0ce7, 0x0ce8, 0x0ce9, 0x0cea, 0x0ceb, 0x0cec, 0x0ced,
++    0x0cee, 0x0cef, 0x0cf0, 0x0cf1, 0x0cf2, 0x0cf3, 0x0cf4, 0x0cf5,
++    0x0cf6, 0x0cf7, 0x0cf8, 0x0cf9, 0x0cfa, 0x05ac, 0x05bb, 0x05bf,
++    0x05c1, 0x05c2, 0x05c3, 0x05c4, 0x05c5, 0x05c6, 0x05c7, 0x05c8,
++    0x05c9, 0x05ca, 0x05cb, 0x05cc, 0x05cd, 0x05ce, 0x05cf, 0x05d0,
++    0x05d1, 0x05d2, 0x05d3, 0x05d4, 0x05d5, 0x05d6, 0x05d7, 0x05d8,
++    0x05d9, 0x05da, 0x05e0, 0x05e1, 0x05e2, 0x05e3, 0x05e4, 0x05e5,
++    0x05e6, 0x05e7, 0x05e8, 0x05e9, 0x05ea, 0x05eb, 0x05ec, 0x05ed,
++    0x05ee, 0x05ef, 0x05f0, 0x05f1, 0x05f2, 0x0da1, 0x0da2, 0x0da3,
++    0x0da4, 0x0da5, 0x0da6, 0x0da7, 0x0da8, 0x0da9, 0x0daa, 0x0dab,
++    0x0dac, 0x0dad, 0x0dae, 0x0daf, 0x0db0, 0x0db1, 0x0db2, 0x0db3,
++    0x0db4, 0x0db5, 0x0db6, 0x0db7, 0x0db8, 0x0db9, 0x0dba, 0x0dbb,
++    0x0dbc, 0x0dbd, 0x0dbe, 0x0dbf, 0x0dc0, 0x0dc1, 0x0dc2, 0x0dc3,
++    0x0dc4, 0x0dc5, 0x0dc6, 0x0dc7, 0x0dc8, 0x0dc9, 0x0dca, 0x0dcb,
++    0x0dcc, 0x0dcd, 0x0dce, 0x0dcf, 0x0dd0, 0x0dd1, 0x0dd2, 0x0dd3,
++    0x0dd4, 0x0dd5, 0x0dd6, 0x0dd7, 0x0dd8, 0x0dd9, 0x0dda, 0x0ddf,
++    0x0de0, 0x0de1, 0x0de2, 0x0de3, 0x0de4, 0x0de5, 0x0de6, 0x0de7,
++    0x0de8, 0x0de9, 0x0dea, 0x0deb, 0x0dec, 0x0ded, 0x0df0, 0x0df1,
++    0x0df2, 0x0df3, 0x0df4, 0x0df5, 0x0df6, 0x0df7, 0x0df8, 0x0df9,
++    0x0aa2, 0x0aa1, 0x0aa3, 0x0aa4, 0x0aa5, 0x0aa6, 0x0aa7, 0x0aa8,
++    0x0abb, 0x0aaa, 0x0aa9, 0x07af, 0x0cdf, 0x0ad0, 0x0ad1, 0x0afd,
++    0x0ad2, 0x0ad3, 0x0afe, 0x0af1, 0x0af2, 0x0aaf, 0x0aae, 0x0ad5,
++    0x0ad6, 0x0ad7, 0x0afc, 0x047e, 0x20ac, 0x0ab8, 0x06b0, 0x0afb,
++    0x0ad4, 0x0ac9, 0x0ab0, 0x0ab1, 0x0ab2, 0x0ab3, 0x0ab4, 0x0ab5,
++    0x0ab6, 0x0ab7, 0x0ac3, 0x0ac4, 0x0ac5, 0x0ac6, 0x08fb, 0x08fc,
++    0x08fd, 0x08fe, 0x08ce, 0x08cd, 0x08ef, 0x08c5, 0x0bca, 0x08d6,
++    0x08c1, 0x08c2, 0x08de, 0x08df, 0x08dc, 0x08dd, 0x08bf, 0x08c0,
++    0x08c8, 0x08c9, 0x08bd, 0x08cf, 0x08bc, 0x08be, 0x08da, 0x08db,
++    0x0bfc, 0x0bdc, 0x0bc2, 0x0bce, 0x0bd3, 0x0bc4, 0x0afa, 0x08a4,
++    0x08a5, 0x0bcc, 0x08ab, 0x08ac, 0x08ad, 0x08ae, 0x08a7, 0x08a8,
++    0x08a9, 0x08aa, 0x08af, 0x08b0, 0x08a1, 0x09ef, 0x09f0, 0x09f2,
++    0x09f3, 0x09e2, 0x09e5, 0x09e9, 0x09e3, 0x09e4, 0x09e8, 0x09f1,
++    0x09f8, 0x09ec, 0x09eb, 0x09ed, 0x09ea, 0x09f4, 0x09f5, 0x09f7,
++    0x09f6, 0x09ee, 0x09e1, 0x09e0, 0x0bcf, 0x0af9, 0x0af8, 0x0af7,
++    0x0aec, 0x0aee, 0x0aed, 0x0af6, 0x0af5, 0x0af3, 0x0af4, 0x0ad9,
++    0x0af0, 0x04a4, 0x04a1, 0x04a2, 0x04a3, 0x04de, 0x04df, 0x04a7,
++    0x04b1, 0x04a8, 0x04b2, 0x04a9, 0x04b3, 0x04aa, 0x04b4, 0x04ab,
++    0x04b5, 0x04b6, 0x04b7, 0x04b8, 0x04b9, 0x04ba, 0x04bb, 0x04bc,
++    0x04bd, 0x04be, 0x04bf, 0x04c0, 0x04c1, 0x04af, 0x04c2, 0x04c3,
++    0x04c4, 0x04c5, 0x04c6, 0x04c7, 0x04c8, 0x04c9, 0x04ca, 0x04cb,
++    0x04cc, 0x04cd, 0x04ce, 0x04cf, 0x04d0, 0x04d1, 0x04d2, 0x04d3,
++    0x04ac, 0x04d4, 0x04ad, 0x04d5, 0x04ae, 0x04d6, 0x04d7, 0x04d8,
++    0x04d9, 0x04da, 0x04db, 0x04dc, 0x04a6, 0x04dd, 0x04a5, 0x04b0
++};
+diff --git a/src/autotype/xcb/keysymmap.py b/src/autotype/xcb/keysymmap.py
+new file mode 100755
+index 0000000..a359710
+--- /dev/null
++++ b/src/autotype/xcb/keysymmap.py
+@@ -0,0 +1,107 @@
++#!/usr/bin/python3
++
++#
++# Copyright (C) 2013 Felix Geyer <debfx@fobos.de>
++#
++# This program is free software: you can redistribute it and/or modify
++# it under the terms of the GNU General Public License as published by
++# the Free Software Foundation, either version 2 or (at your option)
++# version 3 of the License.
++#
++# This program is distributed in the hope that it will be useful,
++# but WITHOUT ANY WARRANTY; without even the implied warranty of
++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++# GNU General Public License for more details.
++#
++# You should have received a copy of the GNU General Public License
++# along with this program.  If not, see <http://www.gnu.org/licenses/>.
++#
++
++#
++# Parses keysymdef.h to construct a unicode symbol -> keysym mapping table.
++#
++# The lines that are parsed look like this:
++# #define XK_Aogonek 0x01a1  /* U+0104 LATIN CAPITAL LETTER A WITH OGONEK */
++#
++# This would create a 0x0104 -> 0x01a1 mapping.
++#
++
++import sys
++import re
++import collections
++
++cols = 8
++
++if len(sys.argv) >= 2:
++    keysymdef = sys.argv[1]
++else:
++    keysymdef = "/usr/include/X11/keysymdef.h"
++
++keysymMap = {}
++
++f = open(keysymdef, "r")
++for line in f:
++    match = re.search(r'0x([0-9a-fA-F]+)\s+/\* U\+([0-9a-fA-F]+)', line)
++    if match:
++        keysym = int(match.group(1), 16)
++        unicodeVal = int(match.group(2), 16)
++
++        # ignore 1:1 mappings
++        if keysym >= 0x0020 and keysym <= 0x007e:
++            continue
++        if keysym >= 0x00a0 and keysym <= 0x00ff:
++            continue
++        # ignore unicode | 0x01000000 mappings
++        if keysym >= 0x1000000:
++            continue
++
++        keysymMap[unicodeVal] = keysym
++
++keysymMap = collections.OrderedDict(sorted(keysymMap.items(), key=lambda t: t[0]))
++
++print("""/*
++ *  Automatically generated by keysymmap.py from parsing keysymdef.h.
++ */
++""")
++
++print("const int AutoTypePlatformX11::m_unicodeToKeysymLen = " + str(len(keysymMap)) + ";")
++
++print()
++
++print("const uint AutoTypePlatformX11::m_unicodeToKeysymKeys[] = {")
++keys = keysymMap.keys()
++keyLen = len(keys)
++i = 1
++for val in keys:
++    hexVal = "{0:#0{1}x}".format(val, 6)
++
++    if i == keyLen:
++        print(hexVal)
++    elif (i % cols) == 0:
++        print(hexVal + ",")
++    elif ((i - 1) % cols) == 0:
++        print("    " + hexVal + ", ", end="")
++    else:
++        print(hexVal + ", ", end="")
++    i += 1
++print("};")
++
++print()
++
++print("const uint AutoTypePlatformX11::m_unicodeToKeysymValues[] = {")
++values = keysymMap.values()
++valuesLen = len(values)
++i = 1
++for val in values:
++    hexVal = "{0:#0{1}x}".format(val, 6)
++
++    if i == valuesLen:
++        print(hexVal)
++    elif (i % cols) == 0:
++        print(hexVal + ",")
++    elif ((i - 1) % cols) == 0:
++        print("    " + hexVal + ", ", end="")
++    else:
++        print(hexVal + ", ", end="")
++    i += 1
++print("};")
+diff --git a/src/config-keepassx.h.cmake b/src/config-keepassx.h.cmake
+index 197c0d3..dc418b6 100644
+--- a/src/config-keepassx.h.cmake
++++ b/src/config-keepassx.h.cmake
+@@ -16,6 +16,4 @@
+ #cmakedefine HAVE_RLIMIT_CORE 1
+ #cmakedefine HAVE_PT_DENY_ATTACH 1
+-#cmakedefine GCRYPT_HAS_SALSA20
+-
+ #endif // KEEPASSX_CONFIG_KEEPASSX_H
+diff --git a/src/core/AutoTypeAssociations.h b/src/core/AutoTypeAssociations.h
+index 1b5871b..491a5db 100644
+--- a/src/core/AutoTypeAssociations.h
++++ b/src/core/AutoTypeAssociations.h
+@@ -20,8 +20,6 @@
+ #include <QObject>
+-#include "core/Global.h"
+-
+ class AutoTypeAssociations : public QObject
+ {
+     Q_OBJECT
+@@ -36,7 +34,7 @@ public:
+         bool operator!=(const AutoTypeAssociations::Association& other) const;
+     };
+-    explicit AutoTypeAssociations(QObject* parent = Q_NULLPTR);
++    explicit AutoTypeAssociations(QObject* parent = nullptr);
+     void copyDataFrom(const AutoTypeAssociations* other);
+     void add(const AutoTypeAssociations::Association& association);
+     void remove(int index);
+diff --git a/src/core/Config.cpp b/src/core/Config.cpp
+index 046a0fe..5b06c22 100644
+--- a/src/core/Config.cpp
++++ b/src/core/Config.cpp
+@@ -18,12 +18,12 @@
+ #include "Config.h"
+ #include <QCoreApplication>
+-#include <QDesktopServices>
+ #include <QDir>
+ #include <QSettings>
++#include <QStandardPaths>
+ #include <QTemporaryFile>
+-Config* Config::m_instance(Q_NULLPTR);
++Config* Config::m_instance(nullptr);
+ QVariant Config::get(const QString& key)
+ {
+@@ -53,7 +53,7 @@ Config::Config(QObject* parent)
+     QString homePath = QDir::homePath();
+ #if defined(Q_OS_UNIX) && !defined(Q_OS_MAC)
+-    // we can't use QDesktopServices on X11 as it uses XDG_DATA_HOME instead of XDG_CONFIG_HOME
++    // we can't use QStandardPaths on X11 as it uses XDG_DATA_HOME instead of XDG_CONFIG_HOME
+     QByteArray env = qgetenv("XDG_CONFIG_HOME");
+     if (env.isEmpty()) {
+         userPath = homePath;
+@@ -70,7 +70,7 @@ Config::Config(QObject* parent)
+     userPath += "/keepassx/";
+ #else
+-    userPath = QDir::fromNativeSeparators(QDesktopServices::storageLocation(QDesktopServices::DataLocation));
++    userPath = QDir::fromNativeSeparators(QStandardPaths::writableLocation(QStandardPaths::DataLocation));
+     // storageLocation() appends the application name ("/keepassx") to the end
+     userPath += "/";
+ #endif
+diff --git a/src/core/Config.h b/src/core/Config.h
+index ca0f74c..09aa02f 100644
+--- a/src/core/Config.h
++++ b/src/core/Config.h
+@@ -21,8 +21,6 @@
+ #include <QScopedPointer>
+ #include <QVariant>
+-#include "core/Global.h"
+-
+ class QSettings;
+ class Config : public QObject
+diff --git a/src/core/Database.cpp b/src/core/Database.cpp
+index 098cc06..6f94235 100644
+--- a/src/core/Database.cpp
++++ b/src/core/Database.cpp
+@@ -23,7 +23,6 @@
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+-#include "core/Tools.h"
+ #include "crypto/Random.h"
+ #include "format/KeePass2.h"
+@@ -105,7 +104,7 @@ Entry* Database::recFindEntry(const Uuid& uuid, Group* group)
+         }
+     }
+-    return Q_NULLPTR;
++    return nullptr;
+ }
+ Group* Database::resolveGroup(const Uuid& uuid)
+@@ -126,7 +125,7 @@ Group* Database::recFindGroup(const Uuid& uuid, Group* group)
+         }
+     }
+-    return Q_NULLPTR;
++    return nullptr;
+ }
+ QList<DeletedObject> Database::deletedObjects()
+@@ -143,7 +142,7 @@ void Database::addDeletedObject(const DeletedObject& delObj)
+ void Database::addDeletedObject(const Uuid& uuid)
+ {
+     DeletedObject delObj;
+-    delObj.deletionTime = Tools::currentDateTimeUtc();
++    delObj.deletionTime = QDateTime::currentDateTimeUtc();
+     delObj.uuid = uuid;
+     addDeletedObject(delObj);
+@@ -223,7 +222,7 @@ bool Database::setKey(const CompositeKey& key, const QByteArray& transformSeed,
+     m_data.transformedMasterKey = transformedMasterKey;
+     m_data.hasKey = true;
+     if (updateChangedTime) {
+-        m_metadata->setMasterKeyChanged(Tools::currentDateTimeUtc());
++        m_metadata->setMasterKeyChanged(QDateTime::currentDateTimeUtc());
+     }
+     Q_EMIT modifiedImmediate();
+diff --git a/src/core/Database.h b/src/core/Database.h
+index 97ccad2..6fde3c6 100644
+--- a/src/core/Database.h
++++ b/src/core/Database.h
+@@ -20,6 +20,7 @@
+ #include <QDateTime>
+ #include <QHash>
++#include <QObject>
+ #include "core/Uuid.h"
+ #include "keys/CompositeKey.h"
+diff --git a/src/core/DatabaseIcons.cpp b/src/core/DatabaseIcons.cpp
+index d6e816f..4e62f79 100644
+--- a/src/core/DatabaseIcons.cpp
++++ b/src/core/DatabaseIcons.cpp
+@@ -19,7 +19,7 @@
+ #include "core/FilePath.h"
+-DatabaseIcons* DatabaseIcons::m_instance(Q_NULLPTR);
++DatabaseIcons* DatabaseIcons::m_instance(nullptr);
+ const int DatabaseIcons::IconCount(69);
+ const int DatabaseIcons::ExpiredIconIndex(45);
+ const char* const DatabaseIcons::m_indexToName[] = {
+diff --git a/src/core/DatabaseIcons.h b/src/core/DatabaseIcons.h
+index 68d1e0c..a1d9480 100644
+--- a/src/core/DatabaseIcons.h
++++ b/src/core/DatabaseIcons.h
+@@ -23,8 +23,6 @@
+ #include <QPixmapCache>
+ #include <QVector>
+-#include "core/Global.h"
+-
+ class DatabaseIcons
+ {
+ public:
+diff --git a/src/core/Entry.cpp b/src/core/Entry.cpp
+index 784b489..2fd52d0 100644
+--- a/src/core/Entry.cpp
++++ b/src/core/Entry.cpp
+@@ -21,7 +21,6 @@
+ #include "core/DatabaseIcons.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+-#include "core/Tools.h"
+ const int Entry::DefaultIconNumber = 0;
+@@ -29,7 +28,7 @@ Entry::Entry()
+     : m_attributes(new EntryAttributes(this))
+     , m_attachments(new EntryAttachments(this))
+     , m_autoTypeAssociations(new AutoTypeAssociations(this))
+-    , m_tmpHistoryItem(Q_NULLPTR)
++    , m_tmpHistoryItem(nullptr)
+     , m_modifiedSinceBegin(false)
+     , m_updateTimeinfo(true)
+ {
+@@ -74,8 +73,8 @@ template <class T> inline bool Entry::set(T& property, const T& value)
+ void Entry::updateTimeinfo()
+ {
+     if (m_updateTimeinfo) {
+-        m_data.timeInfo.setLastModificationTime(Tools::currentDateTimeUtc());
+-        m_data.timeInfo.setLastAccessTime(Tools::currentDateTimeUtc());
++        m_data.timeInfo.setLastModificationTime(QDateTime::currentDateTimeUtc());
++        m_data.timeInfo.setLastAccessTime(QDateTime::currentDateTimeUtc());
+     }
+ }
+@@ -223,7 +222,7 @@ QString Entry::notes() const
+ bool Entry::isExpired() const
+ {
+-    return m_data.timeInfo.expires() && m_data.timeInfo.expiryTime() < Tools::currentDateTimeUtc();
++    return m_data.timeInfo.expires() && m_data.timeInfo.expiryTime() < QDateTime::currentDateTimeUtc();
+ }
+ EntryAttributes* Entry::attributes()
+@@ -474,7 +473,7 @@ Entry* Entry::clone(CloneFlags flags) const
+     entry->setUpdateTimeinfo(true);
+     if (flags & CloneResetTimeInfo) {
+-        QDateTime now = Tools::currentDateTimeUtc();
++        QDateTime now = QDateTime::currentDateTimeUtc();
+         entry->m_data.timeInfo.setCreationTime(now);
+         entry->m_data.timeInfo.setLastModificationTime(now);
+         entry->m_data.timeInfo.setLastAccessTime(now);
+@@ -522,7 +521,7 @@ void Entry::endUpdate()
+         delete m_tmpHistoryItem;
+     }
+-    m_tmpHistoryItem = Q_NULLPTR;
++    m_tmpHistoryItem = nullptr;
+ }
+ void Entry::updateModifiedSinceBegin()
+@@ -568,7 +567,7 @@ void Entry::setGroup(Group* group)
+     QObject::setParent(group);
+     if (m_updateTimeinfo) {
+-        m_data.timeInfo.setLocationChanged(Tools::currentDateTimeUtc());
++        m_data.timeInfo.setLocationChanged(QDateTime::currentDateTimeUtc());
+     }
+ }
+@@ -583,7 +582,7 @@ const Database* Entry::database() const
+         return m_group->database();
+     }
+     else {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+ }
+diff --git a/src/core/Entry.h b/src/core/Entry.h
+index 3044dc8..cd7c7b7 100644
+--- a/src/core/Entry.h
++++ b/src/core/Entry.h
+@@ -29,7 +29,6 @@
+ #include "core/AutoTypeAssociations.h"
+ #include "core/EntryAttachments.h"
+ #include "core/EntryAttributes.h"
+-#include "core/Global.h"
+ #include "core/TimeInfo.h"
+ #include "core/Uuid.h"
+diff --git a/src/core/EntryAttachments.h b/src/core/EntryAttachments.h
+index 3446b31..903ca10 100644
+--- a/src/core/EntryAttachments.h
++++ b/src/core/EntryAttachments.h
+@@ -21,14 +21,12 @@
+ #include <QMap>
+ #include <QObject>
+-#include "core/Global.h"
+-
+ class EntryAttachments : public QObject
+ {
+     Q_OBJECT
+ public:
+-    explicit EntryAttachments(QObject* parent = Q_NULLPTR);
++    explicit EntryAttachments(QObject* parent = nullptr);
+     QList<QString> keys() const;
+     bool hasKey(const QString& key) const;
+     QList<QByteArray> values() const;
+diff --git a/src/core/EntryAttributes.h b/src/core/EntryAttributes.h
+index 334eb0a..c6bbf29 100644
+--- a/src/core/EntryAttributes.h
++++ b/src/core/EntryAttributes.h
+@@ -23,14 +23,12 @@
+ #include <QSet>
+ #include <QStringList>
+-#include "core/Global.h"
+-
+ class EntryAttributes : public QObject
+ {
+     Q_OBJECT
+ public:
+-    explicit EntryAttributes(QObject* parent = Q_NULLPTR);
++    explicit EntryAttributes(QObject* parent = nullptr);
+     QList<QString> keys() const;
+     bool hasKey(const QString& key) const;
+     QList<QString> customKeys();
+diff --git a/src/core/EntrySearcher.cpp b/src/core/EntrySearcher.cpp
+index 82a553e..05c4c58 100644
+--- a/src/core/EntrySearcher.cpp
++++ b/src/core/EntrySearcher.cpp
+@@ -19,7 +19,8 @@
+ #include "core/Group.h"
+-QList<Entry*> EntrySearcher::search(const QString &searchTerm, const Group* group, Qt::CaseSensitivity caseSensitivity)
++QList<Entry*> EntrySearcher::search(const QString& searchTerm, const Group* group,
++                                    Qt::CaseSensitivity caseSensitivity)
+ {
+     if (!group->resolveSearchingEnabled()) {
+         return QList<Entry*>();
+@@ -28,7 +29,8 @@ QList<Entry*> EntrySearcher::search(const QString &searchTerm, const Group* grou
+     return searchEntries(searchTerm, group, caseSensitivity);
+ }
+-QList<Entry*> EntrySearcher::searchEntries(const QString& searchTerm, const Group* group, Qt::CaseSensitivity caseSensitivity)
++QList<Entry*> EntrySearcher::searchEntries(const QString& searchTerm, const Group* group,
++                                           Qt::CaseSensitivity caseSensitivity)
+ {
+     QList<Entry*> searchResult;
+@@ -44,7 +46,8 @@ QList<Entry*> EntrySearcher::searchEntries(const QString& searchTerm, const Grou
+     return searchResult;
+ }
+-QList<Entry*> EntrySearcher::matchEntry(const QString& searchTerm, Entry* entry, Qt::CaseSensitivity caseSensitivity)
++QList<Entry*> EntrySearcher::matchEntry(const QString& searchTerm, Entry* entry,
++                                        Qt::CaseSensitivity caseSensitivity)
+ {
+     QStringList wordList = searchTerm.split(QRegExp("\\s"), QString::SkipEmptyParts);
+     Q_FOREACH (const QString& word, wordList) {
+diff --git a/src/core/EntrySearcher.h b/src/core/EntrySearcher.h
+index 246538c..c7075dc 100644
+--- a/src/core/EntrySearcher.h
++++ b/src/core/EntrySearcher.h
+@@ -28,10 +28,11 @@ class EntrySearcher
+ {
+ public:
+     QList<Entry*> search(const QString& searchTerm, const Group* group, Qt::CaseSensitivity caseSensitivity);
++
+ private:
+     QList<Entry*> searchEntries(const QString& searchTerm, const Group* group, Qt::CaseSensitivity caseSensitivity);
+     QList<Entry*> matchEntry(const QString& searchTerm, Entry* entry, Qt::CaseSensitivity caseSensitivity);
+-    bool wordMatch(const QString &word, Entry *entry, Qt::CaseSensitivity caseSensitivity);
++    bool wordMatch(const QString& word, Entry* entry, Qt::CaseSensitivity caseSensitivity);
+ };
+ #endif // KEEPASSX_ENTRYSEARCHER_H
+diff --git a/src/core/FilePath.cpp b/src/core/FilePath.cpp
+index f7c4075..497568a 100644
+--- a/src/core/FilePath.cpp
++++ b/src/core/FilePath.cpp
+@@ -23,7 +23,7 @@
+ #include "config-keepassx.h"
+-FilePath* FilePath::m_instance(Q_NULLPTR);
++FilePath* FilePath::m_instance(nullptr);
+ QString FilePath::dataPath(const QString& name)
+ {
+diff --git a/src/core/FilePath.h b/src/core/FilePath.h
+index 9e98d3e..c37a908 100644
+--- a/src/core/FilePath.h
++++ b/src/core/FilePath.h
+@@ -22,8 +22,6 @@
+ #include <QIcon>
+ #include <QString>
+-#include "core/Global.h"
+-
+ class FilePath
+ {
+ public:
+diff --git a/src/core/Global.h b/src/core/Global.h
+index 914c7b4..14281ee 100644
+--- a/src/core/Global.h
++++ b/src/core/Global.h
+@@ -20,104 +20,8 @@
+ #ifndef KEEPASSX_GLOBAL_H
+ #define KEEPASSX_GLOBAL_H
+-// mostly copied from qcompilerdetection.h which is part of Qt 5
+-
+ #include <QtGlobal>
+-#ifdef Q_CC_CLANG
+-#  if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__)
+-#    if __has_feature(cxx_strong_enums)
+-#      define COMPILER_CLASS_ENUM
+-#    endif
+-#    if __has_feature(cxx_constexpr)
+-#      define COMPILER_CONSTEXPR
+-#    endif
+-#    if __has_feature(cxx_decltype) /* && __has_feature(cxx_decltype_incomplete_return_types) */
+-#      define COMPILER_DECLTYPE
+-#    endif
+-#    if __has_feature(cxx_override_control)
+-#      define COMPILER_EXPLICIT_OVERRIDES
+-#    endif
+-#    if __has_feature(cxx_nullptr)
+-#      define COMPILER_NULLPTR
+-#    endif
+-#    if __has_feature(cxx_static_assert)
+-#      define COMPILER_STATIC_ASSERT
+-#    endif
+-#  endif
+-#endif // Q_CC_CLANG
+-
+-#if defined(Q_CC_GNU) && !defined(Q_CC_INTEL) && !defined(Q_CC_CLANG)
+-#  if defined(__GXX_EXPERIMENTAL_CXX0X__) || __cplusplus >= 201103L
+-#    if (__GNUC__ * 100 + __GNUC_MINOR__) >= 403
+-#      define COMPILER_DECLTYPE
+-#      define COMPILER_STATIC_ASSERT
+-#    endif
+-#    if (__GNUC__ * 100 + __GNUC_MINOR__) >= 404
+-#      define COMPILER_CLASS_ENUM
+-#    endif
+-#    if (__GNUC__ * 100 + __GNUC_MINOR__) >= 406
+-#      define COMPILER_CONSTEXPR
+-#      define COMPILER_NULLPTR
+-#    endif
+-#    if (__GNUC__ * 100 + __GNUC_MINOR__) >= 407
+-#      define COMPILER_EXPLICIT_OVERRIDES
+-#    endif
+-#  endif
+-#endif
+-
+-/*
+- * C++11 keywords and expressions
+- */
+-#if !defined(Q_NULLPTR)
+-#  ifdef COMPILER_NULLPTR
+-#    define Q_NULLPTR nullptr
+-#  else
+-#    define Q_NULLPTR 0
+-#  endif
+-#endif
+-
+-#if !defined(Q_DECL_CONSTEXPR)
+-#  ifdef COMPILER_CONSTEXPR
+-#    define Q_DECL_CONSTEXPR constexpr
+-#  else
+-#    define Q_DECL_CONSTEXPR
+-#  endif
+-#endif
+-
+-#if !defined(Q_DECL_OVERRIDE) && !defined(Q_DECL_FINAL) && !defined(Q_DECL_FINAL_CLASS)
+-#  ifdef COMPILER_EXPLICIT_OVERRIDES
+-#    define Q_DECL_OVERRIDE override
+-#    define Q_DECL_FINAL final
+-#    ifdef  COMPILER_DECLTYPE
+-#      define Q_DECL_FINAL_CLASS final
+-#    else
+-#      define Q_DECL_FINAL_CLASS
+-#    endif
+-#  else
+-#    define Q_DECL_OVERRIDE
+-#    define Q_DECL_FINAL
+-#    define Q_DECL_FINAL_CLASS
+-#  endif
+-#endif
+-
+-#if !defined(Q_STATIC_ASSERT) && !defined(Q_STATIC_ASSERT_X)
+-#ifdef COMPILER_STATIC_ASSERT
+-#define Q_STATIC_ASSERT(Condition) static_assert(static_cast<bool>(Condition), #Condition)
+-#define Q_STATIC_ASSERT_X(Condition, Message) static_assert(static_cast<bool>(Condition), Message)
+-#else
+-// Intentionally undefined
+-template <bool Test> class QStaticAssertFailure;
+-template <> class QStaticAssertFailure<true> {};
+-
+-#define Q_STATIC_ASSERT_PRIVATE_JOIN(A, B) Q_STATIC_ASSERT_PRIVATE_JOIN_IMPL(A, B)
+-#define Q_STATIC_ASSERT_PRIVATE_JOIN_IMPL(A, B) A ## B
+-#define Q_STATIC_ASSERT(Condition) \
+-    enum {Q_STATIC_ASSERT_PRIVATE_JOIN(q_static_assert_result, __LINE__) = sizeof(QStaticAssertFailure<!!(Condition)>)}
+-#define Q_STATIC_ASSERT_X(Condition, Message) Q_STATIC_ASSERT(Condition)
+-#endif // COMPILER_STATIC_ASSERT
+-#endif // !defined(Q_STATIC_ASSERT) && !defined(Q_STATIC_ASSERT_X)
+-
+ #if defined(Q_OS_WIN)
+ #  if defined(KEEPASSX_BUILDING_CORE)
+ #    define KEEPASSX_EXPORT Q_DECL_EXPORT
+diff --git a/src/core/Group.cpp b/src/core/Group.cpp
+index 371f3e4..2b9e9bc 100644
+--- a/src/core/Group.cpp
++++ b/src/core/Group.cpp
+@@ -20,7 +20,6 @@
+ #include "core/Config.h"
+ #include "core/DatabaseIcons.h"
+ #include "core/Metadata.h"
+-#include "core/Tools.h"
+ const int Group::DefaultIconNumber = 48;
+ const int Group::RecycleBinIconNumber = 43;
+@@ -50,7 +49,7 @@ Group::~Group()
+     if (m_db && m_parent) {
+         DeletedObject delGroup;
+-        delGroup.deletionTime = Tools::currentDateTimeUtc();
++        delGroup.deletionTime = QDateTime::currentDateTimeUtc();
+         delGroup.uuid = m_uuid;
+         m_db->addDeletedObject(delGroup);
+     }
+@@ -84,8 +83,8 @@ template <class P, class V> inline bool Group::set(P& property, const V& value)
+ void Group::updateTimeinfo()
+ {
+     if (m_updateTimeinfo) {
+-        m_data.timeInfo.setLastModificationTime(Tools::currentDateTimeUtc());
+-        m_data.timeInfo.setLastAccessTime(Tools::currentDateTimeUtc());
++        m_data.timeInfo.setLastModificationTime(QDateTime::currentDateTimeUtc());
++        m_data.timeInfo.setLastAccessTime(QDateTime::currentDateTimeUtc());
+     }
+ }
+@@ -203,7 +202,7 @@ Entry* Group::lastTopVisibleEntry() const
+ bool Group::isExpired() const
+ {
+-    return m_data.timeInfo.expires() && m_data.timeInfo.expiryTime() < Tools::currentDateTimeUtc();
++    return m_data.timeInfo.expires() && m_data.timeInfo.expiryTime() < QDateTime::currentDateTimeUtc();
+ }
+ void Group::setUuid(const Uuid& uuid)
+@@ -365,7 +364,7 @@ void Group::setParent(Group* parent, int index)
+     }
+     if (m_updateTimeinfo) {
+-        m_data.timeInfo.setLocationChanged(Tools::currentDateTimeUtc());
++        m_data.timeInfo.setLocationChanged(QDateTime::currentDateTimeUtc());
+     }
+     Q_EMIT modified();
+@@ -385,7 +384,7 @@ void Group::setParent(Database* db)
+     cleanupParent();
+-    m_parent = Q_NULLPTR;
++    m_parent = nullptr;
+     recSetDatabase(db);
+     QObject::setParent(db);
+@@ -510,7 +509,7 @@ Group* Group::clone(Entry::CloneFlags entryFlags) const
+     clonedGroup->setUpdateTimeinfo(true);
+-    QDateTime now = Tools::currentDateTimeUtc();
++    QDateTime now = QDateTime::currentDateTimeUtc();
+     clonedGroup->m_data.timeInfo.setCreationTime(now);
+     clonedGroup->m_data.timeInfo.setLastModificationTime(now);
+     clonedGroup->m_data.timeInfo.setLastAccessTime(now);
+diff --git a/src/core/InactivityTimer.h b/src/core/InactivityTimer.h
+index e0a21e0..ba571a5 100644
+--- a/src/core/InactivityTimer.h
++++ b/src/core/InactivityTimer.h
+@@ -21,8 +21,6 @@
+ #include <QMutex>
+ #include <QObject>
+-#include "core/Global.h"
+-
+ class QTimer;
+ class InactivityTimer : public QObject
+@@ -30,7 +28,7 @@ class InactivityTimer : public QObject
+     Q_OBJECT
+ public:
+-    explicit InactivityTimer(QObject* parent = Q_NULLPTR);
++    explicit InactivityTimer(QObject* parent = nullptr);
+     void setInactivityTimeout(int inactivityTimeout);
+     void activate();
+     void deactivate();
+diff --git a/src/core/Metadata.cpp b/src/core/Metadata.cpp
+index 0c67bba..a50c6ef 100644
+--- a/src/core/Metadata.cpp
++++ b/src/core/Metadata.cpp
+@@ -42,7 +42,7 @@ Metadata::Metadata(QObject* parent)
+     m_data.protectNotes = false;
+     // m_data.autoEnableVisualHiding = false;
+-    QDateTime now = Tools::currentDateTimeUtc();
++    QDateTime now = QDateTime::currentDateTimeUtc();
+     m_data.nameChanged = now;
+     m_data.descriptionChanged = now;
+     m_data.defaultUserNameChanged = now;
+@@ -67,7 +67,7 @@ template <class P, class V> bool Metadata::set(P& property, const V& value, QDat
+     if (property != value) {
+         property = value;
+         if (m_updateDatetime) {
+-            dateTime = Tools::currentDateTimeUtc();
++            dateTime = QDateTime::currentDateTimeUtc();
+         }
+         Q_EMIT modified();
+         return true;
+diff --git a/src/core/Metadata.h b/src/core/Metadata.h
+index 062e552..c35aed3 100644
+--- a/src/core/Metadata.h
++++ b/src/core/Metadata.h
+@@ -26,7 +26,6 @@
+ #include <QPixmapCache>
+ #include <QPointer>
+-#include "core/Global.h"
+ #include "core/Uuid.h"
+ class Database;
+@@ -37,7 +36,7 @@ class Metadata : public QObject
+     Q_OBJECT
+ public:
+-    explicit Metadata(QObject* parent = Q_NULLPTR);
++    explicit Metadata(QObject* parent = nullptr);
+     struct MetadataData
+     {
+diff --git a/src/core/PasswordGenerator.h b/src/core/PasswordGenerator.h
+index 6a9d212..cc8196f 100644
+--- a/src/core/PasswordGenerator.h
++++ b/src/core/PasswordGenerator.h
+@@ -22,8 +22,6 @@
+ #include <QString>
+ #include <QVector>
+-#include "core/Global.h"
+-
+ typedef QVector<QChar> PasswordGroup;
+ class PasswordGenerator
+diff --git a/src/core/SignalMultiplexer.cpp b/src/core/SignalMultiplexer.cpp
+index a70e9ef..ebf38bf 100644
+--- a/src/core/SignalMultiplexer.cpp
++++ b/src/core/SignalMultiplexer.cpp
+@@ -24,7 +24,7 @@ SignalMultiplexer::SignalMultiplexer()
+ SignalMultiplexer::~SignalMultiplexer()
+ {
+     // disconnect all connections
+-    setCurrentObject(Q_NULLPTR);
++    setCurrentObject(nullptr);
+ }
+ QObject* SignalMultiplexer::currentObject() const
+diff --git a/src/core/SignalMultiplexer.h b/src/core/SignalMultiplexer.h
+index 6d39cd5..b27e1f3 100644
+--- a/src/core/SignalMultiplexer.h
++++ b/src/core/SignalMultiplexer.h
+@@ -21,8 +21,6 @@
+ #include <QObject>
+ #include <QPointer>
+-#include "core/Global.h"
+-
+ class SignalMultiplexer
+ {
+ public:
+diff --git a/src/core/TimeInfo.cpp b/src/core/TimeInfo.cpp
+index 2613325..ec6ebde 100644
+--- a/src/core/TimeInfo.cpp
++++ b/src/core/TimeInfo.cpp
+@@ -23,7 +23,7 @@ TimeInfo::TimeInfo()
+     : m_expires(false)
+     , m_usageCount(0)
+ {
+-    QDateTime now = Tools::currentDateTimeUtc();
++    QDateTime now = QDateTime::currentDateTimeUtc();
+     m_lastModificationTime = now;
+     m_creationTime = now;
+     m_lastAccessTime = now;
+diff --git a/src/core/Tools.cpp b/src/core/Tools.cpp
+index db3baa8..06eb73d 100644
+--- a/src/core/Tools.cpp
++++ b/src/core/Tools.cpp
+@@ -23,11 +23,7 @@
+ #include <QLocale>
+ #include <QStringList>
+-#if QT_VERSION >= QT_VERSION_CHECK(4, 7, 0)
+ #include <QElapsedTimer>
+-#else
+-#include <QTime>
+-#endif
+ #ifdef Q_OS_WIN
+ #include <windows.h> // for Sleep(), SetDllDirectoryA() and SetSearchPathMode()
+@@ -122,15 +118,6 @@ bool readAllFromDevice(QIODevice* device, QByteArray& data)
+     }
+ }
+-QDateTime currentDateTimeUtc()
+-{
+-#if QT_VERSION >= QT_VERSION_CHECK(4, 7, 0)
+-     return QDateTime::currentDateTimeUtc();
+-#else
+-     return QDateTime::currentDateTime().toUTC();
+-#endif
+-}
+-
+ QString imageReaderFilter()
+ {
+     QList<QByteArray> formats = QImageReader::supportedImageFormats();
+@@ -184,7 +171,7 @@ void sleep(int ms)
+     timespec ts;
+     ts.tv_sec = ms / 1000;
+     ts.tv_nsec = (ms % 1000) * 1000 * 1000;
+-    nanosleep(&ts, Q_NULLPTR);
++    nanosleep(&ts, nullptr);
+ #endif
+ }
+@@ -196,11 +183,7 @@ void wait(int ms)
+         return;
+     }
+-#if QT_VERSION >= QT_VERSION_CHECK(4, 7, 0)
+     QElapsedTimer timer;
+-#else
+-    QTime timer;
+-#endif
+     timer.start();
+     if (ms <= 50) {
+@@ -215,23 +198,10 @@ void wait(int ms)
+                 QCoreApplication::processEvents(QEventLoop::AllEvents, timeLeft);
+                 sleep(10);
+             }
+-        } while (timer.elapsed() < ms);
++        } while (!timer.hasExpired(ms));
+     }
+ }
+-QString platform()
+-{
+-#if defined(Q_WS_X11)
+-    return "x11";
+-#elif defined(Q_WS_MAC)
+-    return "mac";
+-#elif defined(Q_WS_WIN)
+-    return "win";
+-#else
+-    return QString();
+-#endif
+-}
+-
+ void disableCoreDumps()
+ {
+     // default to true
+diff --git a/src/core/Tools.h b/src/core/Tools.h
+index 68e9dcd..65df1ea 100644
+--- a/src/core/Tools.h
++++ b/src/core/Tools.h
+@@ -18,11 +18,13 @@
+ #ifndef KEEPASSX_TOOLS_H
+ #define KEEPASSX_TOOLS_H
++#include "core/Global.h"
++
+ #include <QDateTime>
+ #include <QObject>
+ #include <QString>
+-#include "core/Global.h"
++#include <algorithm>
+ class QIODevice;
+@@ -32,16 +34,27 @@ QString humanReadableFileSize(qint64 bytes);
+ bool hasChild(const QObject* parent, const QObject* child);
+ bool readFromDevice(QIODevice* device, QByteArray& data, int size = 16384);
+ bool readAllFromDevice(QIODevice* device, QByteArray& data);
+-QDateTime currentDateTimeUtc();
+ QString imageReaderFilter();
+ bool isHex(const QByteArray& ba);
+ bool isBase64(const QByteArray& ba);
+ void sleep(int ms);
+ void wait(int ms);
+-QString platform();
+ void disableCoreDumps();
+ void setupSearchPaths();
++template <typename RandomAccessIterator, typename T>
++RandomAccessIterator binaryFind(RandomAccessIterator begin, RandomAccessIterator end, const T& value)
++{
++    RandomAccessIterator it = std::lower_bound(begin, end, value);
++
++    if ((it == end) || (value < *it)) {
++        return end;
++    }
++    else {
++        return it;
++    }
++}
++
+ } // namespace Tools
+ #endif // KEEPASSX_TOOLS_H
+diff --git a/src/core/qcommandlineoption.cpp b/src/core/qcommandlineoption.cpp
+deleted file mode 100644
+index c908807..0000000
+--- a/src/core/qcommandlineoption.cpp
++++ /dev/null
+@@ -1,305 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 Laszlo Papp <lpapp@kde.org>
+-** Copyright (C) 2013 David Faure <faure@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia.  For licensing terms and
+-** conditions see http://qt.digia.com/licensing.  For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.LGPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU Lesser General Public License version 2.1 requirements
+-** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights.  These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU
+-** General Public License version 3.0 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.GPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU General Public License version 3.0 requirements will be
+-** met: http://www.gnu.org/copyleft/gpl.html.
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#include "qcommandlineoption.h"
+-
+-#include <QSet>
+-
+-class QCommandLineOptionPrivate : public QSharedData
+-{
+-public:
+-    inline QCommandLineOptionPrivate()
+-    { }
+-
+-    void setNames(const QStringList &nameList);
+-
+-    //! The list of names used for this option.
+-    QStringList names;
+-
+-    //! The documentation name for the value, if one is expected
+-    //! Example: "-o <file>" means valueName == "file"
+-    QString valueName;
+-
+-    //! The description used for this option.
+-    QString description;
+-
+-    //! The list of default values used for this option.
+-    QStringList defaultValues;
+-};
+-
+-/*!
+-    \since 5.2
+-    \class QCommandLineOption
+-    \brief The QCommandLineOption class defines a possible command-line option.
+-    \inmodule QtCore
+-    \ingroup shared
+-    \ingroup tools
+-
+-    This class is used to describe an option on the command line. It allows
+-    different ways of defining the same option with multiple aliases possible.
+-    It is also used to describe how the option is used - it may be a flag (e.g. \c{-v})
+-    or take an argument (e.g. \c{-o file}).
+-
+-    Examples:
+-    \snippet code/src_corelib_tools_qcommandlineoption.cpp 0
+-
+-    \sa QCommandLineParser
+-*/
+-
+-/*!
+-    Constructs a command line option object with the given arguments.
+-
+-    The name of the option is set to \a name.
+-    The name can be either short or long. If the name is one character in
+-    length, it is considered a short name. Option names must not be empty,
+-    must not start with a dash or a slash character, must not contain a \c{=}
+-    and cannot be repeated.
+-
+-    The description is set to \a description. It is customary to add a "."
+-    at the end of the description.
+-
+-    In addition, the \a valueName can be set if the option expects a value.
+-    The default value for the option is set to \a defaultValue.
+-
+-    \sa setDescription(), setValueName(), setDefaultValues()
+-*/
+-QCommandLineOption::QCommandLineOption(const QString &name, const QString &description,
+-                                       const QString &valueName,
+-                                       const QString &defaultValue)
+-    : d(new QCommandLineOptionPrivate)
+-{
+-    d->setNames(QStringList(name));
+-    setValueName(valueName);
+-    setDescription(description);
+-    setDefaultValue(defaultValue);
+-}
+-
+-/*!
+-    Constructs a command line option object with the given arguments.
+-
+-    This overload allows to set multiple names for the option, for instance
+-    \c{o} and \c{output}.
+-
+-    The names of the option are set to \a names.
+-    The names can be either short or long. Any name in the list that is one
+-    character in length is a short name. Option names must not be empty,
+-    must not start with a dash or a slash character, must not contain a \c{=}
+-    and cannot be repeated.
+-
+-    The description is set to \a description. It is customary to add a "."
+-    at the end of the description.
+-
+-    In addition, the \a valueName can be set if the option expects a value.
+-    The default value for the option is set to \a defaultValue.
+-
+-    \sa setDescription(), setValueName(), setDefaultValues()
+-*/
+-QCommandLineOption::QCommandLineOption(const QStringList &names, const QString &description,
+-                                       const QString &valueName,
+-                                       const QString &defaultValue)
+-    : d(new QCommandLineOptionPrivate)
+-{
+-    d->setNames(names);
+-    setValueName(valueName);
+-    setDescription(description);
+-    setDefaultValue(defaultValue);
+-}
+-
+-/*!
+-    Constructs a QCommandLineOption object that is a copy of the QCommandLineOption
+-    object \a other.
+-
+-    \sa operator=()
+-*/
+-QCommandLineOption::QCommandLineOption(const QCommandLineOption &other)
+-    : d(other.d)
+-{
+-}
+-
+-/*!
+-    Destroys the command line option object.
+-*/
+-QCommandLineOption::~QCommandLineOption()
+-{
+-}
+-
+-/*!
+-    Makes a copy of the \a other object and assigns it to this QCommandLineOption
+-    object.
+-*/
+-QCommandLineOption &QCommandLineOption::operator=(const QCommandLineOption &other)
+-{
+-    d = other.d;
+-    return *this;
+-}
+-
+-/*!
+-    Returns the names set for this option.
+- */
+-QStringList QCommandLineOption::names() const
+-{
+-    return d->names;
+-}
+-
+-void QCommandLineOptionPrivate::setNames(const QStringList &nameList)
+-{
+-    QStringList newNames;
+-    if (nameList.isEmpty())
+-        qWarning("QCommandLineOption: Options must have at least one name");
+-    Q_FOREACH (const QString &name, nameList) {
+-        if (name.isEmpty()) {
+-            qWarning("QCommandLineOption: Option names cannot be empty");
+-        } else {
+-            const QChar c = name.at(0);
+-            if (c == QLatin1Char('-'))
+-                qWarning("QCommandLineOption: Option names cannot start with a '-'");
+-            else if (c == QLatin1Char('/'))
+-                qWarning("QCommandLineOption: Option names cannot start with a '/'");
+-            else if (name.contains(QLatin1Char('=')))
+-                qWarning("QCommandLineOption: Option names cannot contain a '='");
+-            else
+-                newNames.append(name);
+-        }
+-    }
+-    // commit
+-    names = newNames;
+-}
+-
+-/*!
+-    Sets the name of the expected value, for the documentation, to \a valueName.
+-
+-    Options without a value assigned have a boolean-like behavior:
+-    either the user specifies --option or they don't.
+-
+-    Options with a value assigned need to set a name for the expected value,
+-    for the documentation of the option in the help output. An option with names \c{o} and \c{output},
+-    and a value name of \c{file} will appear as \c{-o, --output <file>}.
+-
+-    Call QCommandLineParser::argument() if you expect the option to be present
+-    only once, and QCommandLineParser::arguments() if you expect that option
+-    to be present multiple times.
+-
+-    \sa valueName()
+- */
+-void QCommandLineOption::setValueName(const QString &valueName)
+-{
+-    d->valueName = valueName;
+-}
+-
+-/*!
+-    Returns the name of the expected value.
+-
+-    If empty, the option doesn't take a value.
+-
+-    \sa setValueName()
+- */
+-QString QCommandLineOption::valueName() const
+-{
+-    return d->valueName;
+-}
+-
+-/*!
+-    Sets the description used for this option to \a description.
+-
+-    It is customary to add a "." at the end of the description.
+-
+-    The description is used by QCommandLineParser::showHelp().
+-
+-    \sa description()
+- */
+-void QCommandLineOption::setDescription(const QString &description)
+-{
+-    d->description = description;
+-}
+-
+-/*!
+-    Returns the description set for this option.
+-
+-    \sa setDescription()
+- */
+-QString QCommandLineOption::description() const
+-{
+-    return d->description;
+-}
+-
+-/*!
+-    Sets the default value used for this option to \a defaultValue.
+-
+-    The default value is used if the user of the application does not specify
+-    the option on the command line.
+-
+-    If \a defaultValue is empty, the option has no default values.
+-
+-    \sa defaultValues() setDefaultValues()
+- */
+-void QCommandLineOption::setDefaultValue(const QString &defaultValue)
+-{
+-    QStringList newDefaultValues;
+-    if (!defaultValue.isEmpty()) {
+-        newDefaultValues << defaultValue;
+-    }
+-    // commit:
+-    d->defaultValues = newDefaultValues;
+-}
+-
+-/*!
+-    Sets the list of default values used for this option to \a defaultValues.
+-
+-    The default values are used if the user of the application does not specify
+-    the option on the command line.
+-
+-    \sa defaultValues() setDefaultValue()
+- */
+-void QCommandLineOption::setDefaultValues(const QStringList &defaultValues)
+-{
+-    d->defaultValues = defaultValues;
+-}
+-
+-/*!
+-    Returns the default values set for this option.
+-
+-    \sa setDefaultValues()
+- */
+-QStringList QCommandLineOption::defaultValues() const
+-{
+-    return d->defaultValues;
+-}
+diff --git a/src/core/qcommandlineoption.h b/src/core/qcommandlineoption.h
+deleted file mode 100644
+index b97d44c..0000000
+--- a/src/core/qcommandlineoption.h
++++ /dev/null
+@@ -1,81 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 Laszlo Papp <lpapp@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia.  For licensing terms and
+-** conditions see http://qt.digia.com/licensing.  For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.LGPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU Lesser General Public License version 2.1 requirements
+-** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights.  These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU
+-** General Public License version 3.0 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.GPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU General Public License version 3.0 requirements will be
+-** met: http://www.gnu.org/copyleft/gpl.html.
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef QCOMMANDLINEOPTION_H
+-#define QCOMMANDLINEOPTION_H
+-
+-#include <QStringList>
+-#include <QSharedData>
+-
+-class QCommandLineOptionPrivate;
+-
+-class QCommandLineOption
+-{
+-public:
+-    explicit QCommandLineOption(const QString &name, const QString &description = QString(),
+-                                const QString &valueName = QString(),
+-                                const QString &defaultValue = QString());
+-    explicit QCommandLineOption(const QStringList &names, const QString &description = QString(),
+-                                const QString &valueName = QString(),
+-                                const QString &defaultValue = QString());
+-    QCommandLineOption(const QCommandLineOption &other);
+-
+-    ~QCommandLineOption();
+-
+-    QCommandLineOption &operator=(const QCommandLineOption &other);
+-
+-    QStringList names() const;
+-
+-    void setValueName(const QString &name);
+-    QString valueName() const;
+-
+-    void setDescription(const QString &description);
+-    QString description() const;
+-
+-    void setDefaultValue(const QString &defaultValue);
+-    void setDefaultValues(const QStringList &defaultValues);
+-    QStringList defaultValues() const;
+-
+-private:
+-    QSharedDataPointer<QCommandLineOptionPrivate> d;
+-};
+-
+-#endif // QCOMMANDLINEOPTION_H
+diff --git a/src/core/qcommandlineparser.cpp b/src/core/qcommandlineparser.cpp
+deleted file mode 100644
+index f97d78a..0000000
+--- a/src/core/qcommandlineparser.cpp
++++ /dev/null
+@@ -1,944 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 Laszlo Papp <lpapp@kde.org>
+-** Copyright (C) 2013 David Faure <faure@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia.  For licensing terms and
+-** conditions see http://qt.digia.com/licensing.  For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.LGPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU Lesser General Public License version 2.1 requirements
+-** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights.  These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU
+-** General Public License version 3.0 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.GPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU General Public License version 3.0 requirements will be
+-** met: http://www.gnu.org/copyleft/gpl.html.
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#include "qcommandlineparser.h"
+-
+-#include <QCoreApplication>
+-#include <QHash>
+-#include <QVector>
+-#include <stdio.h>
+-#include <stdlib.h>
+-
+-typedef QHash<QString, int> NameHash_t;
+-
+-class QCommandLineParserPrivate
+-{
+-public:
+-    inline QCommandLineParserPrivate()
+-        : singleDashWordOptionMode(QCommandLineParser::ParseAsCompactedShortOptions),
+-          builtinVersionOption(false),
+-          builtinHelpOption(false),
+-          needsParsing(true)
+-    { }
+-
+-    bool parse(const QStringList &args);
+-    void checkParsed(const char *method);
+-    QStringList aliases(const QString &name) const;
+-    QString helpText() const;
+-    bool registerFoundOption(const QString &optionName);
+-    bool parseOptionValue(const QString &optionName, const QString &argument,
+-                          QStringList::const_iterator *argumentIterator,
+-                          QStringList::const_iterator argsEnd);
+-
+-    //! Error text set when parse() returns false
+-    QString errorText;
+-
+-    //! The command line options used for parsing
+-    QList<QCommandLineOption> commandLineOptionList;
+-
+-    //! Hash mapping option names to their offsets in commandLineOptionList and optionArgumentList.
+-    NameHash_t nameHash;
+-
+-    //! Option values found (only for options with a value)
+-    QHash<int, QStringList> optionValuesHash;
+-
+-    //! Names of options found on the command line.
+-    QStringList optionNames;
+-
+-    //! Arguments which did not belong to any option.
+-    QStringList positionalArgumentList;
+-
+-    //! Names of options which were unknown.
+-    QStringList unknownOptionNames;
+-
+-    //! Application description
+-    QString description;
+-
+-    //! Documentation for positional arguments
+-    struct PositionalArgumentDefinition
+-    {
+-        QString name;
+-        QString description;
+-        QString syntax;
+-    };
+-    QVector<PositionalArgumentDefinition> positionalArgumentDefinitions;
+-
+-    //! The parsing mode for "-abc"
+-    QCommandLineParser::SingleDashWordOptionMode singleDashWordOptionMode;
+-
+-    //! Whether addVersionOption was called
+-    bool builtinVersionOption;
+-
+-    //! Whether addHelpOption was called
+-    bool builtinHelpOption;
+-
+-    //! True if parse() needs to be called
+-    bool needsParsing;
+-};
+-
+-QStringList QCommandLineParserPrivate::aliases(const QString &optionName) const
+-{
+-    const NameHash_t::const_iterator it = nameHash.find(optionName);
+-    if (it == nameHash.end()) {
+-        qWarning("QCommandLineParser: option not defined: \"%s\"", qPrintable(optionName));
+-        return QStringList();
+-    }
+-    return commandLineOptionList.at(*it).names();
+-}
+-
+-/*!
+-    \since 5.2
+-    \class QCommandLineParser
+-    \inmodule QtCore
+-    \ingroup tools
+-
+-    \brief The QCommandLineParser class provides a means for handling the
+-    command line options.
+-
+-    QCoreApplication provides the command-line arguments as a simple list of strings.
+-    QCommandLineParser provides the ability to define a set of options, parse the
+-    command-line arguments, and store which options have actually been used, as
+-    well as option values.
+-
+-    Any argument that isn't an option (i.e. doesn't start with a \c{-}) is stored
+-    as a "positional argument".
+-
+-    The parser handles short names, long names, more than one name for the same
+-    option, and option values.
+-
+-    Options on the command line are recognized as starting with a single or
+-    double \c{-} character(s).
+-    The option \c{-} (single dash alone) is a special case, often meaning standard
+-    input, and not treated as an option. The parser will treat everything after the
+-    option \c{--} (double dash) as positional arguments.
+-
+-    Short options are single letters. The option \c{v} would be specified by
+-    passing \c{-v} on the command line. In the default parsing mode, short options
+-    can be written in a compact form, for instance \c{-abc} is equivalent to \c{-a -b -c}.
+-    The parsing mode for can be set to ParseAsLongOptions, in which case \c{-abc}
+-    will be parsed as the long option \c{abc}.
+-
+-    Long options are more than one letter long and cannot be compacted together.
+-    The long option \c{verbose} would be passed as \c{--verbose} or \c{-verbose}.
+-
+-    Passing values to options can be done using the assignment operator: \c{-v=value}
+-    \c{--verbose=value}, or a space: \c{-v value} \c{--verbose value}, i.e. the next
+-    argument is used as value (even if it starts with a \c{-}).
+-
+-    The parser does not support optional values - if an option is set to
+-    require a value, one must be present. If such an option is placed last
+-    and has no value, the option will be treated as if it had not been
+-    specified.
+-
+-    The parser does not automatically support negating or disabling long options
+-    by using the format \c{--disable-option} or \c{--no-option}. However, it is
+-    possible to handle this case explicitly by making an option with \c{no-option}
+-    as one of its names, and handling the option explicitly.
+-
+-    Example:
+-    \snippet code/src_corelib_tools_qcommandlineparser_main.cpp 0
+-
+-    Known limitation: the parsing of Qt options inside QCoreApplication and subclasses
+-    happens before QCommandLineParser exists, so it can't take it into account. This
+-    means any option value that looks like a builtin Qt option, will be treated by
+-    QCoreApplication as a builtin Qt option. Example: \c{--profile -reverse} will
+-    lead to QGuiApplication seeing the -reverse option set, and removing it from
+-    QCoreApplication::arguments() before QCommandLineParser defines the \c{profile}
+-    option and parses the command line.
+-
+-    \sa QCommandLineOption, QCoreApplication
+-*/
+-
+-/*!
+-    Constructs a command line parser object.
+-*/
+-QCommandLineParser::QCommandLineParser()
+-    : d(new QCommandLineParserPrivate)
+-{
+-}
+-
+-/*!
+-    Destroys the command line parser object.
+-*/
+-QCommandLineParser::~QCommandLineParser()
+-{
+-    delete d;
+-}
+-
+-/*!
+-    \enum QCommandLineParser::SingleDashWordOptionMode
+-
+-    This enum describes the way the parser interprets command-line
+-    options that use a single dash followed by multiple letters, as as \c{-abc}.
+-
+-    \value ParseAsCompactedShortOptions \c{-abc} is interpreted as \c{-a -b -c},
+-    i.e. as three short options that have been compacted on the command-line,
+-    if none of the options take a value. If \c{a} takes a value, then it
+-    is interpreted as \c{-a bc}, i.e. the short option \c{a} followed by the value \c{bc}.
+-    This is typically used in tools that behave like compilers, in order
+-    to handle options such as \c{-DDEFINE=VALUE} or \c{-I/include/path}.
+-    This is the default parsing mode. New applications are recommended to
+-    use this mode.
+-
+-    \value ParseAsLongOptions \c{-abc} is interpreted as \c{--abc},
+-    i.e. as the long option named \c{abc}. This is how Qt's own tools
+-    (uic, rcc...) have always been parsing arguments. This mode should be
+-    used for preserving compatibility in applications that were parsing
+-    arguments in such a way.
+-
+-    \sa setSingleDashWordOptionMode()
+-*/
+-
+-/*!
+-    Sets the parsing mode to \a singleDashWordOptionMode.
+-    This must be called before process() or parse().
+-*/
+-void QCommandLineParser::setSingleDashWordOptionMode(QCommandLineParser::SingleDashWordOptionMode singleDashWordOptionMode)
+-{
+-    d->singleDashWordOptionMode = singleDashWordOptionMode;
+-}
+-
+-/*!
+-    Adds the option \a option to look for while parsing.
+-
+-    Returns \c true if adding the option was successful; otherwise returns \c false.
+-
+-    Adding the option fails if there is no name attached to the option, or
+-    the option has a name that clashes with an option name added before.
+- */
+-bool QCommandLineParser::addOption(const QCommandLineOption &option)
+-{
+-    QStringList optionNames = option.names();
+-
+-    if (!optionNames.isEmpty()) {
+-        Q_FOREACH (const QString &name, optionNames) {
+-            if (d->nameHash.contains(name))
+-                return false;
+-        }
+-
+-        d->commandLineOptionList.append(option);
+-
+-        const int offset = d->commandLineOptionList.size() - 1;
+-        Q_FOREACH (const QString &name, optionNames)
+-            d->nameHash.insert(name, offset);
+-
+-        return true;
+-    }
+-
+-    return false;
+-}
+-
+-/*!
+-    Adds the \c{-v} / \c{--version} option, which displays the version string of the application.
+-
+-    This option is handled automatically by QCommandLineParser.
+-
+-    You can set the actual version string by using QCoreApplication::setApplicationVersion().
+-
+-    Returns the option instance, which can be used to call isSet().
+-*/
+-QCommandLineOption QCommandLineParser::addVersionOption()
+-{
+-    QCommandLineOption opt(QStringList() << "v" << "version", tr("Displays version information."));
+-    addOption(opt);
+-    d->builtinVersionOption = true;
+-    return opt;
+-}
+-
+-/*!
+-    Adds the help option (\c{-h}, \c{--help} and \c{-?} on Windows)
+-    This option is handled automatically by QCommandLineParser.
+-
+-    Remember to use setApplicationDescription to set the application description,
+-    which will be displayed when this option is used.
+-
+-    Example:
+-    \snippet code/src_corelib_tools_qcommandlineparser_main.cpp 0
+-
+-    Returns the option instance, which can be used to call isSet().
+-*/
+-QCommandLineOption QCommandLineParser::addHelpOption()
+-{
+-    QCommandLineOption opt(QStringList()
+-#ifdef Q_OS_WIN
+-                << "?"
+-#endif
+-                << "h"
+-                << "help", tr("Displays this help."));
+-    addOption(opt);
+-    d->builtinHelpOption = true;
+-    return opt;
+-}
+-
+-/*!
+-    Sets the application \a description shown by helpText().
+-*/
+-void QCommandLineParser::setApplicationDescription(const QString &description)
+-{
+-    d->description = description;
+-}
+-
+-/*!
+-    Returns the application description set in setApplicationDescription().
+-*/
+-QString QCommandLineParser::applicationDescription() const
+-{
+-    return d->description;
+-}
+-
+-/*!
+-    Defines an additional argument to the application, for the benefit of the help text.
+-
+-    The argument \a name and \a description will appear under the \c{Arguments:} section
+-    of the help. If \a syntax is specified, it will be appended to the Usage line, otherwise
+-    the \a name will be appended.
+-
+-    Example:
+-    \snippet code/src_corelib_tools_qcommandlineparser.cpp 2
+-
+-    \sa addHelpOption(), helpText()
+-*/
+-void QCommandLineParser::addPositionalArgument(const QString &name, const QString &description, const QString &syntax)
+-{
+-    QCommandLineParserPrivate::PositionalArgumentDefinition arg;
+-    arg.name = name;
+-    arg.description = description;
+-    arg.syntax = syntax.isEmpty() ? name : syntax;
+-    d->positionalArgumentDefinitions.append(arg);
+-}
+-
+-/*!
+-    Clears the definitions of additional arguments from the help text.
+-
+-    This is only needed for the special case of tools which support multiple commands
+-    with different options. Once the actual command has been identified, the options
+-    for this command can be defined, and the help text for the command can be adjusted
+-    accordingly.
+-
+-    Example:
+-    \snippet code/src_corelib_tools_qcommandlineparser.cpp 3
+-*/
+-void QCommandLineParser::clearPositionalArguments()
+-{
+-    d->positionalArgumentDefinitions.clear();
+-}
+-
+-/*!
+-    Parses the command line \a arguments.
+-
+-    Most programs don't need to call this, a simple call to process() is enough.
+-
+-    parse() is more low-level, and only does the parsing. The application will have to
+-    take care of the error handling, using errorText() if parse() returns \c false.
+-    This can be useful for instance to show a graphical error message in graphical programs.
+-
+-    Calling parse() instead of process() can also be useful in order to ignore unknown
+-    options temporarily, because more option definitions will be provided later on
+-    (depending on one of the arguments), before calling process().
+-
+-    Don't forget that \a arguments must start with the name of the executable (ignored, though).
+-
+-    Returns \c false in case of a parse error (unknown option or missing value); returns \c true otherwise.
+-
+-    \sa process()
+-*/
+-bool QCommandLineParser::parse(const QStringList &arguments)
+-{
+-    return d->parse(arguments);
+-}
+-
+-/*!
+-    Returns a translated error text for the user.
+-    This should only be called when parse() returns \c false.
+-*/
+-QString QCommandLineParser::errorText() const
+-{
+-    if (!d->errorText.isEmpty())
+-        return d->errorText;
+-    if (d->unknownOptionNames.count() == 1)
+-        return tr("Unknown option '%1'.").arg(d->unknownOptionNames.first());
+-    if (d->unknownOptionNames.count() > 1)
+-        return tr("Unknown options: %1.").arg(d->unknownOptionNames.join(", "));
+-    return QString();
+-}
+-
+-/*!
+-    Processes the command line \a arguments.
+-
+-    In addition to parsing the options (like parse()), this function also handles the builtin
+-    options and handles errors.
+-
+-    The builtin options are \c{--version} if addVersionOption was called and \c{--help} if addHelpOption was called.
+-
+-    When invoking one of these options, or when an error happens (for instance an unknown option was
+-    passed), the current process will then stop, using the exit() function.
+-
+-    \sa QCoreApplication::arguments(), parse()
+- */
+-void QCommandLineParser::process(const QStringList &arguments)
+-{
+-    if (!d->parse(arguments)) {
+-        fprintf(stderr, "%s\n", qPrintable(errorText()));
+-        ::exit(EXIT_FAILURE);
+-    }
+-
+-    if (d->builtinVersionOption && isSet("version")) {
+-        printf("%s %s\n", qPrintable(QCoreApplication::applicationName()), qPrintable(QCoreApplication::applicationVersion()));
+-        ::exit(EXIT_SUCCESS);
+-    }
+-
+-    if (d->builtinHelpOption && isSet("help"))
+-        showHelp(EXIT_SUCCESS);
+-}
+-
+-/*!
+-    \overload
+-
+-    The command line is obtained from the QCoreApplication instance \a app.
+- */
+-void QCommandLineParser::process(const QCoreApplication &app)
+-{
+-    // QCoreApplication::arguments() is static, but the app instance must exist so we require it as parameter
+-    Q_UNUSED(app);
+-    process(QCoreApplication::arguments());
+-}
+-
+-void QCommandLineParserPrivate::checkParsed(const char *method)
+-{
+-    if (needsParsing)
+-        qWarning("QCommandLineParser: call process() or parse() before %s", method);
+-}
+-
+-/*!
+-    \internal
+-    Looks up the option \a optionName (found on the command line) and register it as found.
+-    Returns \c true on success.
+- */
+-bool QCommandLineParserPrivate::registerFoundOption(const QString &optionName)
+-{
+-    if (nameHash.contains(optionName)) {
+-        optionNames.append(optionName);
+-        return true;
+-    } else {
+-        unknownOptionNames.append(optionName);
+-        return false;
+-    }
+-}
+-
+-/*!
+-    \internal
+-    \brief Parse the value for a given option, if it was defined to expect one.
+-
+-    The value is taken from the next argument, or after the equal sign in \a argument.
+-
+-    \param optionName the short option name
+-    \param argument the argument from the command line currently parsed. Only used for -k=value parsing.
+-    \param argumentIterator iterator to the currently parsed argument. Incremented if the next argument contains the value.
+-    \param argsEnd args.end(), to check if ++argumentIterator goes out of bounds
+-    Returns \c true on success.
+- */
+-bool QCommandLineParserPrivate::parseOptionValue(const QString &optionName, const QString &argument,
+-                                                 QStringList::const_iterator *argumentIterator, QStringList::const_iterator argsEnd)
+-{
+-    const QLatin1Char assignChar('=');
+-    const NameHash_t::const_iterator nameHashIt = nameHash.constFind(optionName);
+-    if (nameHashIt != nameHash.constEnd()) {
+-        const int assignPos = argument.indexOf(assignChar);
+-        const NameHash_t::mapped_type optionOffset = *nameHashIt;
+-        const bool withValue = !commandLineOptionList.at(optionOffset).valueName().isEmpty();
+-        if (withValue) {
+-            if (assignPos == -1) {
+-                ++(*argumentIterator);
+-                if (*argumentIterator == argsEnd) {
+-                    errorText = QCommandLineParser::tr("Missing value after '%1'.").arg(argument);
+-                    return false;
+-                }
+-                optionValuesHash[optionOffset].append(*(*argumentIterator));
+-            } else {
+-                optionValuesHash[optionOffset].append(argument.mid(assignPos + 1));
+-            }
+-        } else {
+-            if (assignPos != -1) {
+-                errorText = QCommandLineParser::tr("Unexpected value after '%1'.").arg(argument.left(assignPos));
+-                return false;
+-            }
+-        }
+-    }
+-    return true;
+-}
+-
+-/*!
+-    \internal
+-
+-    Parse the list of arguments \a args, and fills in
+-    optionNames, optionValuesHash, unknownOptionNames, positionalArguments, and errorText.
+-
+-    Any results from a previous parse operation are removed.
+-
+-    The parser will not look for further options once it encounters the option
+-    \c{--}; this does not include when \c{--} follows an option that requires a value.
+- */
+-bool QCommandLineParserPrivate::parse(const QStringList &args)
+-{
+-    needsParsing = false;
+-    bool error = false;
+-
+-    const QString     doubleDashString("--");
+-    const QLatin1Char dashChar('-');
+-    const QLatin1Char assignChar('=');
+-
+-    bool doubleDashFound = false;
+-    errorText.clear();
+-    positionalArgumentList.clear();
+-    optionNames.clear();
+-    unknownOptionNames.clear();
+-    optionValuesHash.clear();
+-
+-    if (args.isEmpty()) {
+-        qWarning("QCommandLineParser: argument list cannot be empty, it should contain at least the executable name");
+-        return false;
+-    }
+-
+-    QStringList::const_iterator argumentIterator = args.begin();
+-    ++argumentIterator; // skip executable name
+-
+-    for (; argumentIterator != args.end() ; ++argumentIterator) {
+-        QString argument = *argumentIterator;
+-
+-        if (doubleDashFound) {
+-            positionalArgumentList.append(argument);
+-        } else if (argument.startsWith(doubleDashString)) {
+-            if (argument.length() > 2) {
+-                QString optionName = argument.mid(2).section(assignChar, 0, 0);
+-                if (registerFoundOption(optionName)) {
+-                    if (!parseOptionValue(optionName, argument, &argumentIterator, args.end()))
+-                        error = true;
+-                } else {
+-                    error = true;
+-                }
+-            } else {
+-                doubleDashFound = true;
+-            }
+-        } else if (argument.startsWith(dashChar)) {
+-            if (argument.size() == 1) { // single dash ("stdin")
+-                positionalArgumentList.append(argument);
+-                continue;
+-            }
+-            switch (singleDashWordOptionMode) {
+-            case QCommandLineParser::ParseAsCompactedShortOptions:
+-            {
+-                QString optionName;
+-                bool valueFound = false;
+-                for (int pos = 1 ; pos < argument.size(); ++pos) {
+-                    optionName = argument.mid(pos, 1);
+-                    if (!registerFoundOption(optionName)) {
+-                        error = true;
+-                    } else {
+-                        const NameHash_t::const_iterator nameHashIt = nameHash.constFind(optionName);
+-                        Q_ASSERT(nameHashIt != nameHash.constEnd()); // checked by registerFoundOption
+-                        const NameHash_t::mapped_type optionOffset = *nameHashIt;
+-                        const bool withValue = !commandLineOptionList.at(optionOffset).valueName().isEmpty();
+-                        if (withValue) {
+-                            if (pos + 1 < argument.size()) {
+-                                if (argument.at(pos + 1) == assignChar)
+-                                    ++pos;
+-                                optionValuesHash[optionOffset].append(argument.mid(pos + 1));
+-                                valueFound = true;
+-                            }
+-                            break;
+-                        }
+-                        if (pos + 1 < argument.size() && argument.at(pos + 1) == assignChar)
+-                            break;
+-                    }
+-                }
+-                if (!valueFound && !parseOptionValue(optionName, argument, &argumentIterator, args.end()))
+-                    error = true;
+-                break;
+-            }
+-            case QCommandLineParser::ParseAsLongOptions:
+-            {
+-                const QString optionName = argument.mid(1).section(assignChar, 0, 0);
+-                if (registerFoundOption(optionName)) {
+-                    if (!parseOptionValue(optionName, argument, &argumentIterator, args.end()))
+-                        error = true;
+-                } else {
+-                    error = true;
+-                }
+-                break;
+-            }
+-            }
+-        } else {
+-            positionalArgumentList.append(argument);
+-        }
+-        if (argumentIterator == args.end())
+-            break;
+-    }
+-    return !error;
+-}
+-
+-/*!
+-    Checks whether the option \a name was passed to the application.
+-
+-    Returns \c true if the option \a name was set, false otherwise.
+-
+-    The name provided can be any long or short name of any option that was
+-    added with \c addOption(). All the options names are treated as being
+-    equivalent. If the name is not recognized or that option was not present,
+-    false is returned.
+-
+-    Example:
+-    \snippet code/src_corelib_tools_qcommandlineparser.cpp 0
+- */
+-
+-bool QCommandLineParser::isSet(const QString &name) const
+-{
+-    d->checkParsed("isSet");
+-    if (d->optionNames.contains(name))
+-        return true;
+-    const QStringList aliases = d->aliases(name);
+-    Q_FOREACH (const QString &optionName, d->optionNames) {
+-        if (aliases.contains(optionName))
+-            return true;
+-    }
+-    return false;
+-}
+-
+-/*!
+-    Returns the option value found for the given option name \a optionName, or
+-    an empty string if not found.
+-
+-    The name provided can be any long or short name of any option that was
+-    added with \c addOption(). All the option names are treated as being
+-    equivalent. If the name is not recognized or that option was not present, an
+-    empty string is returned.
+-
+-    For options found by the parser, the last value found for
+-    that option is returned. If the option wasn't specified on the command line,
+-    the default value is returned.
+-
+-    An empty string is returned if the option does not take a value.
+-
+-    \sa values(), QCommandLineOption::setDefaultValue(), QCommandLineOption::setDefaultValues()
+- */
+-
+-QString QCommandLineParser::value(const QString &optionName) const
+-{
+-    d->checkParsed("value");
+-    const QStringList valueList = values(optionName);
+-
+-    if (!valueList.isEmpty())
+-        return valueList.last();
+-
+-    return QString();
+-}
+-
+-/*!
+-    Returns a list of option values found for the given option name \a
+-    optionName, or an empty list if not found.
+-
+-    The name provided can be any long or short name of any option that was
+-    added with \c addOption(). All the options names are treated as being
+-    equivalent. If the name is not recognized or that option was not present, an
+-    empty list is returned.
+-
+-    For options found by the parser, the list will contain an entry for
+-    each time the option was encountered by the parser. If the option wasn't
+-    specified on the command line, the default values are returned.
+-
+-    An empty list is returned if the option does not take a value.
+-
+-    \sa value(), QCommandLineOption::setDefaultValue(), QCommandLineOption::setDefaultValues()
+- */
+-
+-QStringList QCommandLineParser::values(const QString &optionName) const
+-{
+-    d->checkParsed("values");
+-    const NameHash_t::const_iterator it = d->nameHash.constFind(optionName);
+-    if (it != d->nameHash.constEnd()) {
+-        const int optionOffset = *it;
+-        QStringList values = d->optionValuesHash.value(optionOffset);
+-        if (values.isEmpty())
+-            values = d->commandLineOptionList.at(optionOffset).defaultValues();
+-        return values;
+-    }
+-
+-    qWarning("QCommandLineParser: option not defined: \"%s\"", qPrintable(optionName));
+-    return QStringList();
+-}
+-
+-/*!
+-    \overload
+-    Checks whether the \a option was passed to the application.
+-
+-    Returns \c true if the \a option was set, false otherwise.
+-
+-    This is the recommended way to check for options with no values.
+-
+-    Example:
+-    \snippet code/src_corelib_tools_qcommandlineparser.cpp 1
+-*/
+-bool QCommandLineParser::isSet(const QCommandLineOption &option) const
+-{
+-    // option.names() might be empty if the constructor failed
+-    return !option.names().isEmpty() && isSet(option.names().first());
+-}
+-
+-/*!
+-    \overload
+-    Returns the option value found for the given \a option, or
+-    an empty string if not found.
+-
+-    For options found by the parser, the last value found for
+-    that option is returned. If the option wasn't specified on the command line,
+-    the default value is returned.
+-
+-    An empty string is returned if the option does not take a value.
+-
+-    \sa values(), QCommandLineOption::setDefaultValue(), QCommandLineOption::setDefaultValues()
+-*/
+-QString QCommandLineParser::value(const QCommandLineOption &option) const
+-{
+-    return value(option.names().first());
+-}
+-
+-/*!
+-    \overload
+-    Returns a list of option values found for the given \a option,
+-    or an empty list if not found.
+-
+-    For options found by the parser, the list will contain an entry for
+-    each time the option was encountered by the parser. If the option wasn't
+-    specified on the command line, the default values are returned.
+-
+-    An empty list is returned if the option does not take a value.
+-
+-    \sa value(), QCommandLineOption::setDefaultValue(), QCommandLineOption::setDefaultValues()
+-*/
+-QStringList QCommandLineParser::values(const QCommandLineOption &option) const
+-{
+-    return values(option.names().first());
+-}
+-
+-/*!
+-    Returns a list of positional arguments.
+-
+-    These are all of the arguments that were not recognized as part of an
+-    option.
+- */
+-
+-QStringList QCommandLineParser::positionalArguments() const
+-{
+-    d->checkParsed("positionalArguments");
+-    return d->positionalArgumentList;
+-}
+-
+-/*!
+-    Returns a list of option names that were found.
+-
+-    This returns a list of all the recognized option names found by the
+-    parser, in the order in which they were found. For any long options
+-    that were in the form {--option=value}, the value part will have been
+-    dropped.
+-
+-    The names in this list do not include the preceding dash characters.
+-    Names may appear more than once in this list if they were encountered
+-    more than once by the parser.
+-
+-    Any entry in the list can be used with \c value() or with
+-    \c values() to get any relevant option values.
+- */
+-
+-QStringList QCommandLineParser::optionNames() const
+-{
+-    d->checkParsed("optionNames");
+-    return d->optionNames;
+-}
+-
+-/*!
+-    Returns a list of unknown option names.
+-
+-    This list will include both long an short name options that were not
+-    recognized. For any long options that were in the form {--option=value},
+-    the value part will have been dropped and only the long name is added.
+-
+-    The names in this list do not include the preceding dash characters.
+-    Names may appear more than once in this list if they were encountered
+-    more than once by the parser.
+-
+-    \sa optionNames()
+- */
+-
+-QStringList QCommandLineParser::unknownOptionNames() const
+-{
+-    d->checkParsed("unknownOptionNames");
+-    return d->unknownOptionNames;
+-}
+-
+-/*!
+-    Displays the help information, and exits the application.
+-    This is automatically triggered by the --help option, but can also
+-    be used to display the help when the user is not invoking the
+-    application correctly.
+-    The exit code is set to \a exitCode. It should be set to 0 if the
+-    user requested to see the help, and to any other value in case of
+-    an error.
+-
+-    \sa helpText()
+-*/
+-void QCommandLineParser::showHelp(int exitCode)
+-{
+-    fprintf(stdout, "%s", qPrintable(d->helpText()));
+-    ::exit(exitCode);
+-}
+-
+-/*!
+-    Returns a string containing the complete help information.
+-
+-    \sa showHelp()
+-*/
+-QString QCommandLineParser::helpText() const
+-{
+-    return d->helpText();
+-}
+-
+-static QString wrapText(const QString &names, int longestOptionNameString, const QString &description)
+-{
+-    const QLatin1Char nl('\n');
+-    QString text = QString("  ") + names.leftJustified(longestOptionNameString) + QLatin1Char(' ');
+-    const int indent = text.length();
+-    int lineStart = 0;
+-    int lastBreakable = -1;
+-    const int max = 79 - indent;
+-    int x = 0;
+-    const int len = description.length();
+-
+-    for (int i = 0; i < len; ++i) {
+-        ++x;
+-        const QChar c = description.at(i);
+-        if (c.isSpace())
+-            lastBreakable = i;
+-
+-        int breakAt = -1;
+-        int nextLineStart = -1;
+-        if (x > max && lastBreakable != -1) {
+-            // time to break and we know where
+-            breakAt = lastBreakable;
+-            nextLineStart = lastBreakable + 1;
+-        } else if ((x > max - 1 && lastBreakable == -1) || i == len - 1) {
+-            // time to break but found nowhere [-> break here], or end of last line
+-            breakAt = i + 1;
+-            nextLineStart = breakAt;
+-        } else if (c == nl) {
+-            // forced break
+-            breakAt = i;
+-            nextLineStart = i + 1;
+-        }
+-
+-        if (breakAt != -1) {
+-            const int numChars = breakAt - lineStart;
+-            //qDebug() << "breakAt=" << description.at(breakAt) << "breakAtSpace=" << breakAtSpace << lineStart << "to" << breakAt << description.mid(lineStart, numChars);
+-            if (lineStart > 0)
+-                text += QString(indent, QLatin1Char(' '));
+-            text += description.mid(lineStart, numChars) + nl;
+-            x = 0;
+-            lastBreakable = -1;
+-            lineStart = nextLineStart;
+-            if (lineStart < len && description.at(lineStart).isSpace())
+-                ++lineStart; // don't start a line with a space
+-            i = lineStart;
+-        }
+-    }
+-
+-    return text;
+-}
+-
+-QString QCommandLineParserPrivate::helpText() const
+-{
+-    const QLatin1Char nl('\n');
+-    QString text;
+-    const QString exeName = QCoreApplication::instance()->arguments().first();
+-    QString usage = exeName;
+-    if (!commandLineOptionList.isEmpty()) {
+-        usage += QLatin1Char(' ');
+-        usage += QCommandLineParser::tr("[options]");
+-    }
+-    Q_FOREACH (const PositionalArgumentDefinition &arg, positionalArgumentDefinitions) {
+-        usage += QLatin1Char(' ');
+-        usage += arg.syntax;
+-    }
+-    text += QCommandLineParser::tr("Usage: %1").arg(usage) + nl;
+-    if (!description.isEmpty())
+-       text += description + nl;
+-    text += nl;
+-    if (!commandLineOptionList.isEmpty())
+-        text += QCommandLineParser::tr("Options:") + nl;
+-    QStringList optionNameList;
+-    int longestOptionNameString = 0;
+-    Q_FOREACH (const QCommandLineOption &option, commandLineOptionList) {
+-        QStringList optionNames;
+-        Q_FOREACH (const QString &optionName, option.names()) {
+-            if (optionName.length() == 1)
+-                optionNames.append(QLatin1Char('-') + optionName);
+-            else
+-                optionNames.append(QString("--") + optionName);
+-        }
+-        QString optionNamesString = optionNames.join(", ");
+-        if (!option.valueName().isEmpty())
+-            optionNamesString += QString(" <") + option.valueName() + QLatin1Char('>');
+-        optionNameList.append(optionNamesString);
+-        longestOptionNameString = qMax(longestOptionNameString, optionNamesString.length());
+-    }
+-    ++longestOptionNameString;
+-    for (int i = 0; i < commandLineOptionList.count(); ++i) {
+-        const QCommandLineOption &option = commandLineOptionList.at(i);
+-        text += wrapText(optionNameList.at(i), longestOptionNameString, option.description());
+-    }
+-    if (!positionalArgumentDefinitions.isEmpty()) {
+-        if (!commandLineOptionList.isEmpty())
+-            text += nl;
+-        text += QCommandLineParser::tr("Arguments:") + nl;
+-        Q_FOREACH (const PositionalArgumentDefinition &arg, positionalArgumentDefinitions) {
+-            text += wrapText(arg.name, longestOptionNameString, arg.description);
+-        }
+-    }
+-    return text;
+-}
+diff --git a/src/core/qcommandlineparser.h b/src/core/qcommandlineparser.h
+deleted file mode 100644
+index eeecf2d..0000000
+--- a/src/core/qcommandlineparser.h
++++ /dev/null
+@@ -1,102 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 Laszlo Papp <lpapp@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia.  For licensing terms and
+-** conditions see http://qt.digia.com/licensing.  For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.LGPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU Lesser General Public License version 2.1 requirements
+-** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights.  These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU
+-** General Public License version 3.0 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.GPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU General Public License version 3.0 requirements will be
+-** met: http://www.gnu.org/copyleft/gpl.html.
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef QCOMMANDLINEPARSER_H
+-#define QCOMMANDLINEPARSER_H
+-
+-#include <QStringList>
+-#include <QCoreApplication>
+-
+-#include "qcommandlineoption.h"
+-
+-class QCommandLineParserPrivate;
+-class QCoreApplication;
+-
+-class QCommandLineParser
+-{
+-    Q_DECLARE_TR_FUNCTIONS(QCommandLineParser)
+-public:
+-    QCommandLineParser();
+-    ~QCommandLineParser();
+-
+-    enum SingleDashWordOptionMode {
+-        ParseAsCompactedShortOptions,
+-        ParseAsLongOptions
+-    };
+-    void setSingleDashWordOptionMode(SingleDashWordOptionMode parsingMode);
+-
+-    bool addOption(const QCommandLineOption &commandLineOption);
+-
+-    QCommandLineOption addVersionOption();
+-    QCommandLineOption addHelpOption();
+-    void setApplicationDescription(const QString &description);
+-    QString applicationDescription() const;
+-    void addPositionalArgument(const QString &name, const QString &description, const QString &syntax = QString());
+-    void clearPositionalArguments();
+-
+-    void process(const QStringList &arguments);
+-    void process(const QCoreApplication &app);
+-
+-    bool parse(const QStringList &arguments);
+-    QString errorText() const;
+-
+-    bool isSet(const QString &name) const;
+-    QString value(const QString &name) const;
+-    QStringList values(const QString &name) const;
+-
+-    bool isSet(const QCommandLineOption &option) const;
+-    QString value(const QCommandLineOption &option) const;
+-    QStringList values(const QCommandLineOption &option) const;
+-
+-    QStringList positionalArguments() const;
+-    QStringList optionNames() const;
+-    QStringList unknownOptionNames() const;
+-
+-    void showHelp(int exitCode = 0);
+-    QString helpText() const;
+-
+-private:
+-    Q_DISABLE_COPY(QCommandLineParser)
+-
+-    QCommandLineParserPrivate * const d;
+-};
+-
+-#endif // QCOMMANDLINEPARSER_H
+diff --git a/src/core/qlockfile.cpp b/src/core/qlockfile.cpp
+deleted file mode 100644
+index 567440c..0000000
+--- a/src/core/qlockfile.cpp
++++ /dev/null
+@@ -1,344 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure+bluesystems@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL21$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia. For licensing terms and
+-** conditions see http://qt.digia.com/licensing. For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 or version 3 as published by the Free
+-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+-** following information to ensure the GNU Lesser General Public License
+-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights. These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#include "qlockfile.h"
+-#include "qlockfile_p.h"
+-#if QT_VERSION >= QT_VERSION_CHECK(4, 7, 0)
+-#    include <QElapsedTimer>
+-#else
+-#    include <QTime>
+-#endif
+-#include <QDateTime>
+-
+-QT_BEGIN_NAMESPACE
+-
+-/*!
+-    \class QLockFile
+-    \inmodule QtCore
+-    \brief The QLockFile class provides locking between processes using a file.
+-    \since 5.1
+-
+-    A lock file can be used to prevent multiple processes from accessing concurrently
+-    the same resource. For instance, a configuration file on disk, or a socket, a port,
+-    a region of shared memory...
+-
+-    Serialization is only guaranteed if all processes that access the shared resource
+-    use QLockFile, with the same file path.
+-
+-    QLockFile supports two use cases:
+-    to protect a resource for a short-term operation (e.g. verifying if a configuration
+-    file has changed before saving new settings), and for long-lived protection of a
+-    resource (e.g. a document opened by a user in an editor) for an indefinite amount of time.
+-
+-    When protecting for a short-term operation, it is acceptable to call lock() and wait
+-    until any running operation finishes.
+-    When protecting a resource over a long time, however, the application should always
+-    call setStaleLockTime(0) and then tryLock() with a short timeout, in order to
+-    warn the user that the resource is locked.
+-
+-    If the process holding the lock crashes, the lock file stays on disk and can prevent
+-    any other process from accessing the shared resource, ever. For this reason, QLockFile
+-    tries to detect such a "stale" lock file, based on the process ID written into the file,
+-    and (in case that process ID got reused meanwhile), on the last modification time of
+-    the lock file (30s by default, for the use case of a short-lived operation).
+-    If the lock file is found to be stale, it will be deleted.
+-
+-    For the use case of protecting a resource over a long time, you should therefore call
+-    setStaleLockTime(0), and when tryLock() returns LockFailedError, inform the user
+-    that the document is locked, possibly using getLockInfo() for more details.
+-*/
+-
+-/*!
+-    \enum QLockFile::LockError
+-
+-    This enum describes the result of the last call to lock() or tryLock().
+-
+-    \value NoError The lock was acquired successfully.
+-    \value LockFailedError The lock could not be acquired because another process holds it.
+-    \value PermissionError The lock file could not be created, for lack of permissions
+-                           in the parent directory.
+-    \value UnknownError Another error happened, for instance a full partition
+-                        prevented writing out the lock file.
+-*/
+-
+-/*!
+-    Constructs a new lock file object.
+-    The object is created in an unlocked state.
+-    When calling lock() or tryLock(), a lock file named \a fileName will be created,
+-    if it doesn't already exist.
+-
+-    \sa lock(), unlock()
+-*/
+-QLockFile::QLockFile(const QString &fileName)
+-    : d_ptr(new QLockFilePrivate(fileName))
+-{
+-}
+-
+-/*!
+-    Destroys the lock file object.
+-    If the lock was acquired, this will release the lock, by deleting the lock file.
+-*/
+-QLockFile::~QLockFile()
+-{
+-    unlock();
+-}
+-
+-/*!
+-    Sets \a staleLockTime to be the time in milliseconds after which
+-    a lock file is considered stale.
+-    The default value is 30000, i.e. 30 seconds.
+-    If your application typically keeps the file locked for more than 30 seconds
+-    (for instance while saving megabytes of data for 2 minutes), you should set
+-    a bigger value using setStaleLockTime().
+-
+-    The value of \a staleLockTime is used by lock() and tryLock() in order
+-    to determine when an existing lock file is considered stale, i.e. left over
+-    by a crashed process. This is useful for the case where the PID got reused
+-    meanwhile, so the only way to detect a stale lock file is by the fact that
+-    it has been around for a long time.
+-
+-    \sa staleLockTime()
+-*/
+-void QLockFile::setStaleLockTime(int staleLockTime)
+-{
+-    Q_D(QLockFile);
+-    d->staleLockTime = staleLockTime;
+-}
+-
+-/*!
+-    Returns the time in milliseconds after which
+-    a lock file is considered stale.
+-
+-    \sa setStaleLockTime()
+-*/
+-int QLockFile::staleLockTime() const
+-{
+-    Q_D(const QLockFile);
+-    return d->staleLockTime;
+-}
+-
+-/*!
+-    Returns \c true if the lock was acquired by this QLockFile instance,
+-    otherwise returns \c false.
+-
+-    \sa lock(), unlock(), tryLock()
+-*/
+-bool QLockFile::isLocked() const
+-{
+-    Q_D(const QLockFile);
+-    return d->isLocked;
+-}
+-
+-/*!
+-    Creates the lock file.
+-
+-    If another process (or another thread) has created the lock file already,
+-    this function will block until that process (or thread) releases it.
+-
+-    Calling this function multiple times on the same lock from the same
+-    thread without unlocking first is not allowed. This function will
+-    \e dead-lock when the file is locked recursively.
+-
+-    Returns \c true if the lock was acquired, false if it could not be acquired
+-    due to an unrecoverable error, such as no permissions in the parent directory.
+-
+-    \sa unlock(), tryLock()
+-*/
+-bool QLockFile::lock()
+-{
+-    return tryLock(-1);
+-}
+-
+-/*!
+-    Attempts to create the lock file. This function returns \c true if the
+-    lock was obtained; otherwise it returns \c false. If another process (or
+-    another thread) has created the lock file already, this function will
+-    wait for at most \a timeout milliseconds for the lock file to become
+-    available.
+-
+-    Note: Passing a negative number as the \a timeout is equivalent to
+-    calling lock(), i.e. this function will wait forever until the lock
+-    file can be locked if \a timeout is negative.
+-
+-    If the lock was obtained, it must be released with unlock()
+-    before another process (or thread) can successfully lock it.
+-
+-    Calling this function multiple times on the same lock from the same
+-    thread without unlocking first is not allowed, this function will
+-    \e always return false when attempting to lock the file recursively.
+-
+-    \sa lock(), unlock()
+-*/
+-bool QLockFile::tryLock(int timeout)
+-{
+-    Q_D(QLockFile);
+-#if QT_VERSION >= QT_VERSION_CHECK(4, 7, 0)
+-    QElapsedTimer timer;
+-#else
+-    QTime timer;
+-#endif
+-    if (timeout > 0)
+-        timer.start();
+-    int sleepTime = 100;
+-    Q_FOREVER {
+-        d->lockError = d->tryLock_sys();
+-        switch (d->lockError) {
+-        case NoError:
+-            d->isLocked = true;
+-            return true;
+-        case PermissionError:
+-        case UnknownError:
+-            return false;
+-        case LockFailedError:
+-            if (!d->isLocked && d->isApparentlyStale()) {
+-                // Stale lock from another thread/process
+-                // Ensure two processes don't remove it at the same time
+-                QLockFile rmlock(d->fileName + QLatin1String(".rmlock"));
+-                if (rmlock.tryLock()) {
+-                    if (d->isApparentlyStale() && d->removeStaleLock())
+-                        continue;
+-                }
+-            }
+-            break;
+-        }
+-        if (timeout == 0 || (timeout > 0 && (timer.elapsed() > timeout)))
+-            return false;
+-        QLockFileThread::msleep(sleepTime);
+-        if (sleepTime < 5 * 1000)
+-            sleepTime *= 2;
+-    }
+-    // not reached
+-    return false;
+-}
+-
+-/*!
+-    \fn void QLockFile::unlock()
+-    Releases the lock, by deleting the lock file.
+-
+-    Calling unlock() without locking the file first, does nothing.
+-
+-    \sa lock(), tryLock()
+-*/
+-
+-/*!
+-    Retrieves information about the current owner of the lock file.
+-
+-    If tryLock() returns \c false, and error() returns LockFailedError,
+-    this function can be called to find out more information about the existing
+-    lock file:
+-    \list
+-    \li the PID of the application (returned in \a pid)
+-    \li the \a hostname it's running on (useful in case of networked filesystems),
+-    \li the name of the application which created it (returned in \a appname),
+-    \endlist
+-
+-    Note that tryLock() automatically deleted the file if there is no
+-    running application with this PID, so LockFailedError can only happen if there is
+-    an application with this PID (it could be unrelated though).
+-
+-    This can be used to inform users about the existing lock file and give them
+-    the choice to delete it. After removing the file using removeStaleLockFile(),
+-    the application can call tryLock() again.
+-
+-    This function returns \c true if the information could be successfully retrieved, false
+-    if the lock file doesn't exist or doesn't contain the expected data.
+-    This can happen if the lock file was deleted between the time where tryLock() failed
+-    and the call to this function. Simply call tryLock() again if this happens.
+-*/
+-bool QLockFile::getLockInfo(qint64 *pid, QString *hostname, QString *appname) const
+-{
+-    Q_D(const QLockFile);
+-    return d->getLockInfo(pid, hostname, appname);
+-}
+-
+-bool QLockFilePrivate::getLockInfo(qint64 *pid, QString *hostname, QString *appname) const
+-{
+-    QFile reader(fileName);
+-    if (!reader.open(QIODevice::ReadOnly))
+-        return false;
+-
+-    QByteArray pidLine = reader.readLine();
+-    pidLine.chop(1);
+-    QByteArray appNameLine = reader.readLine();
+-    appNameLine.chop(1);
+-    QByteArray hostNameLine = reader.readLine();
+-    hostNameLine.chop(1);
+-    if (pidLine.isEmpty())
+-        return false;
+-
+-    qint64 thePid = pidLine.toLongLong();
+-    if (pid)
+-        *pid = thePid;
+-    if (appname)
+-        *appname = QString::fromUtf8(appNameLine);
+-    if (hostname)
+-        *hostname = QString::fromUtf8(hostNameLine);
+-    return thePid > 0;
+-}
+-
+-/*!
+-    Attempts to forcefully remove an existing lock file.
+-
+-    Calling this is not recommended when protecting a short-lived operation: QLockFile
+-    already takes care of removing lock files after they are older than staleLockTime().
+-
+-    This method should only be called when protecting a resource for a long time, i.e.
+-    with staleLockTime(0), and after tryLock() returned LockFailedError, and the user
+-    agreed on removing the lock file.
+-
+-    Returns \c true on success, false if the lock file couldn't be removed. This happens
+-    on Windows, when the application owning the lock is still running.
+-*/
+-bool QLockFile::removeStaleLockFile()
+-{
+-    Q_D(QLockFile);
+-    if (d->isLocked) {
+-        qWarning("removeStaleLockFile can only be called when not holding the lock");
+-        return false;
+-    }
+-    return d->removeStaleLock();
+-}
+-
+-/*!
+-    Returns the lock file error status.
+-
+-    If tryLock() returns \c false, this function can be called to find out
+-    the reason why the locking failed.
+-*/
+-QLockFile::LockError QLockFile::error() const
+-{
+-    Q_D(const QLockFile);
+-    return d->lockError;
+-}
+-
+-QT_END_NAMESPACE
+diff --git a/src/core/qlockfile.h b/src/core/qlockfile.h
+deleted file mode 100644
+index 673026f..0000000
+--- a/src/core/qlockfile.h
++++ /dev/null
+@@ -1,79 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure+bluesystems@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL21$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia. For licensing terms and
+-** conditions see http://qt.digia.com/licensing. For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 or version 3 as published by the Free
+-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+-** following information to ensure the GNU Lesser General Public License
+-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights. These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef QLOCKFILE_H
+-#define QLOCKFILE_H
+-
+-#include <QString>
+-#include <QScopedPointer>
+-
+-QT_BEGIN_NAMESPACE
+-
+-class QLockFilePrivate;
+-
+-class QLockFile
+-{
+-public:
+-    QLockFile(const QString &fileName);
+-    ~QLockFile();
+-
+-    bool lock();
+-    bool tryLock(int timeout = 0);
+-    void unlock();
+-
+-    void setStaleLockTime(int);
+-    int staleLockTime() const;
+-
+-    bool isLocked() const;
+-    bool getLockInfo(qint64 *pid, QString *hostname, QString *appname) const;
+-    bool removeStaleLockFile();
+-
+-    enum LockError {
+-        NoError = 0,
+-        LockFailedError = 1,
+-        PermissionError = 2,
+-        UnknownError = 3
+-    };
+-    LockError error() const;
+-
+-protected:
+-    QScopedPointer<QLockFilePrivate> d_ptr;
+-
+-private:
+-    Q_DECLARE_PRIVATE(QLockFile)
+-    Q_DISABLE_COPY(QLockFile)
+-};
+-
+-QT_END_NAMESPACE
+-
+-#endif // QLOCKFILE_H
+diff --git a/src/core/qlockfile_p.h b/src/core/qlockfile_p.h
+deleted file mode 100644
+index 15fa37b..0000000
+--- a/src/core/qlockfile_p.h
++++ /dev/null
+@@ -1,101 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure+bluesystems@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL21$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia. For licensing terms and
+-** conditions see http://qt.digia.com/licensing. For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 or version 3 as published by the Free
+-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+-** following information to ensure the GNU Lesser General Public License
+-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights. These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef QLOCKFILE_P_H
+-#define QLOCKFILE_P_H
+-
+-//
+-//  W A R N I N G
+-//  -------------
+-//
+-// This file is not part of the Qt API.  It exists purely as an
+-// implementation detail.  This header file may change from version to
+-// version without notice, or even be removed.
+-//
+-// We mean it.
+-//
+-
+-#include "qlockfile.h"
+-
+-#include <QFile>
+-#include <QThread>
+-
+-#ifdef Q_OS_WIN
+-#include <qt_windows.h>
+-#endif
+-
+-QT_BEGIN_NAMESPACE
+-
+-class QLockFileThread : public QThread
+-{
+-public:
+-    static void msleep(unsigned long msecs) { QThread::msleep(msecs); }
+-};
+-
+-class QLockFilePrivate
+-{
+-public:
+-    QLockFilePrivate(const QString &fn)
+-        : fileName(fn),
+-#ifdef Q_OS_WIN
+-          fileHandle(INVALID_HANDLE_VALUE),
+-#else
+-          fileHandle(-1),
+-#endif
+-          staleLockTime(30 * 1000), // 30 seconds
+-          lockError(QLockFile::NoError),
+-          isLocked(false)
+-    {
+-    }
+-    QLockFile::LockError tryLock_sys();
+-    bool removeStaleLock();
+-    bool getLockInfo(qint64 *pid, QString *hostname, QString *appname) const;
+-    // Returns \c true if the lock belongs to dead PID, or is old.
+-    // The attempt to delete it will tell us if it was really stale or not, though.
+-    bool isApparentlyStale() const;
+-    static QString processNameByPid(qint64 pid);
+-
+-    QString fileName;
+-#ifdef Q_OS_WIN
+-    Qt::HANDLE fileHandle;
+-#else
+-    int fileHandle;
+-#endif
+-    int staleLockTime; // "int milliseconds" is big enough for 24 days
+-    QLockFile::LockError lockError;
+-    bool isLocked;
+-};
+-
+-QT_END_NAMESPACE
+-
+-#endif /* QLOCKFILE_P_H */
+diff --git a/src/core/qlockfile_unix.cpp b/src/core/qlockfile_unix.cpp
+deleted file mode 100644
+index 5b3add3..0000000
+--- a/src/core/qlockfile_unix.cpp
++++ /dev/null
+@@ -1,244 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure+bluesystems@kde.org>
+-** Copyright (C) 2015 The Qt Company Ltd.
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL21$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia. For licensing terms and
+-** conditions see http://qt.digia.com/licensing. For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 or version 3 as published by the Free
+-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+-** following information to ensure the GNU Lesser General Public License
+-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights. These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#include "qlockfile_p.h"
+-
+-#include <QTemporaryFile>
+-#include <QCoreApplication>
+-#include <QFileInfo>
+-#include <QDebug>
+-#include <QDateTime>
+-
+-#include <sys/file.h>  // flock
+-#include <sys/types.h> // kill
+-#include <signal.h>    // kill
+-#include <unistd.h>    // gethostname
+-
+-#include <errno.h>
+-
+-#if defined(Q_OS_MAC)
+-#   include <libproc.h>
+-#elif defined(Q_OS_LINUX)
+-#   include <unistd.h>
+-#   include <cstdio>
+-#endif
+-
+-QT_BEGIN_NAMESPACE
+-
+-#define EINTR_LOOP(var, cmd)                    \
+-    do {                                        \
+-        var = cmd;                              \
+-    } while (var == -1 && errno == EINTR)
+-
+-// don't call QT_OPEN or ::open
+-// call qt_safe_open
+-static inline int qt_safe_open(const char *pathname, int flags, mode_t mode = 0777)
+-{
+-#ifdef O_CLOEXEC
+-    flags |= O_CLOEXEC;
+-#endif
+-    int fd;
+-    EINTR_LOOP(fd, ::open(pathname, flags, mode));
+-
+-    // unknown flags are ignored, so we have no way of verifying if
+-    // O_CLOEXEC was accepted
+-    if (fd != -1)
+-        ::fcntl(fd, F_SETFD, FD_CLOEXEC);
+-    return fd;
+-}
+-
+-static inline qint64 qt_safe_write(int fd, const void *data, qint64 len)
+-{
+-    qint64 ret = 0;
+-    EINTR_LOOP(ret, ::write(fd, data, len));
+-    return ret;
+-}
+-
+-static QByteArray localHostName() // from QHostInfo::localHostName(), modified to return a QByteArray
+-{
+-    QByteArray hostName(512, Qt::Uninitialized);
+-    if (gethostname(hostName.data(), hostName.size()) == -1)
+-        return QByteArray();
+-    hostName.truncate(strlen(hostName.data()));
+-    return hostName;
+-}
+-
+-// ### merge into qt_safe_write?
+-static qint64 qt_write_loop(int fd, const char *data, qint64 len)
+-{
+-    qint64 pos = 0;
+-    while (pos < len) {
+-        const qint64 ret = qt_safe_write(fd, data + pos, len - pos);
+-        if (ret == -1) // e.g. partition full
+-            return pos;
+-        pos += ret;
+-    }
+-    return pos;
+-}
+-
+-static bool setNativeLocks(int fd)
+-{
+-#if defined(LOCK_EX) && defined(LOCK_NB)
+-    if (flock(fd, LOCK_EX | LOCK_NB) == -1) // other threads, and other processes on a local fs
+-        return false;
+-#endif
+-    struct flock flockData;
+-    flockData.l_type = F_WRLCK;
+-    flockData.l_whence = SEEK_SET;
+-    flockData.l_start = 0;
+-    flockData.l_len = 0; // 0 = entire file
+-    flockData.l_pid = getpid();
+-    if (fcntl(fd, F_SETLK, &flockData) == -1) // for networked filesystems
+-        return false;
+-    return true;
+-}
+-
+-QLockFile::LockError QLockFilePrivate::tryLock_sys()
+-{
+-    // Assemble data, to write in a single call to write
+-    // (otherwise we'd have to check every write call)
+-    // Use operator% from the fast builder to avoid multiple memory allocations.
+-    QByteArray fileData = QByteArray::number(QCoreApplication::applicationPid()) + '\n'
+-                          + QCoreApplication::applicationName().toUtf8() + '\n'
+-                          + localHostName() + '\n';
+-
+-    const QByteArray lockFileName = QFile::encodeName(fileName);
+-    const int fd = qt_safe_open(lockFileName.constData(), O_WRONLY | O_CREAT | O_EXCL, 0644);
+-    if (fd < 0) {
+-        switch (errno) {
+-        case EEXIST:
+-            return QLockFile::LockFailedError;
+-        case EACCES:
+-        case EROFS:
+-            return QLockFile::PermissionError;
+-        default:
+-            return QLockFile::UnknownError;
+-        }
+-    }
+-    // Ensure nobody else can delete the file while we have it
+-    if (!setNativeLocks(fd))
+-        qWarning() << "setNativeLocks failed:" << strerror(errno);
+-
+-    if (qt_write_loop(fd, fileData.constData(), fileData.size()) < fileData.size()) {
+-        close(fd);
+-        if (!QFile::remove(fileName))
+-            qWarning("QLockFile: Could not remove our own lock file %s.", qPrintable(fileName));
+-        return QLockFile::UnknownError; // partition full
+-    }
+-
+-    // We hold the lock, continue.
+-    fileHandle = fd;
+-
+-    return QLockFile::NoError;
+-}
+-
+-bool QLockFilePrivate::removeStaleLock()
+-{
+-    const QByteArray lockFileName = QFile::encodeName(fileName);
+-    const int fd = qt_safe_open(lockFileName.constData(), O_WRONLY, 0644);
+-    if (fd < 0) // gone already?
+-        return false;
+-#ifdef Q_OS_MAC
+-    // ugly workaround: ignore setNativeLocks() result on Mac since it's broken there
+-    setNativeLocks(fd);
+-    bool success = (::unlink(lockFileName) == 0);
+-#else
+-    bool success = setNativeLocks(fd) && (::unlink(lockFileName) == 0);
+-#endif
+-    close(fd);
+-    return success;
+-}
+-
+-bool QLockFilePrivate::isApparentlyStale() const
+-{
+-    qint64 pid;
+-    QString hostname, appname;
+-    if (getLockInfo(&pid, &hostname, &appname)) {
+-        if (hostname.isEmpty() || hostname == QString::fromLocal8Bit(localHostName())) {
+-            if (::kill(pid, 0) == -1 && errno == ESRCH)
+-                return true; // PID doesn't exist anymore
+-            const QString processName = processNameByPid(pid);
+-            if (!processName.isEmpty()) {
+-                QFileInfo fi(appname);
+-                if (fi.isSymLink())
+-                    fi.setFile(fi.symLinkTarget());
+-                if (processName.toLower() != fi.fileName().toLower())
+-                    return true; // PID got reused by a different application.
+-            }
+-        }
+-    }
+-    const qint64 age = QFileInfo(fileName).lastModified().secsTo(QDateTime::currentDateTime()) * 1000;
+-    return staleLockTime > 0 && age > staleLockTime;
+-}
+-
+-QString QLockFilePrivate::processNameByPid(qint64 pid)
+-{
+-#if defined(Q_OS_MAC)
+-    char name[1024];
+-    proc_name(pid, name, sizeof(name) / sizeof(char));
+-    return QFile::decodeName(name);
+-#elif defined(Q_OS_LINUX)
+-    if (!QFile::exists(QString("/proc/version")))
+-        return QString();
+-    char exePath[64];
+-    char buf[PATH_MAX + 1];
+-    sprintf(exePath, "/proc/%lld/exe", pid);
+-    size_t len = static_cast<size_t>(readlink(exePath, buf, sizeof(buf)));
+-    if (len >= sizeof(buf)) {
+-        // The pid is gone. Return some invalid process name to fail the test.
+-        return QString("/ERROR/");
+-    }
+-    buf[len] = 0;
+-    return QFileInfo(QFile::decodeName(buf)).fileName();
+-#else
+-    return QString();
+-#endif
+-}
+-
+-void QLockFile::unlock()
+-{
+-    Q_D(QLockFile);
+-    if (!d->isLocked)
+-        return;
+-    close(d->fileHandle);
+-    d->fileHandle = -1;
+-    if (!QFile::remove(d->fileName)) {
+-        qWarning() << "Could not remove our own lock file" << d->fileName << "maybe permissions changed meanwhile?";
+-        // This is bad because other users of this lock file will now have to wait for the stale-lock-timeout...
+-    }
+-    d->lockError = QLockFile::NoError;
+-    d->isLocked = false;
+-}
+-
+-QT_END_NAMESPACE
+diff --git a/src/core/qlockfile_win.cpp b/src/core/qlockfile_win.cpp
+deleted file mode 100644
+index 5fc3327..0000000
+--- a/src/core/qlockfile_win.cpp
++++ /dev/null
+@@ -1,227 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure+bluesystems@kde.org>
+-** Copyright (C) 2015 The Qt Company Ltd.
+-** Contact: http://www.qt.io/licensing/
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL21$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and The Qt Company. For licensing terms
+-** and conditions see http://www.qt.io/terms-conditions. For further
+-** information use the contact form at http://www.qt.io/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 or version 3 as published by the Free
+-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+-** following information to ensure the GNU Lesser General Public License
+-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** As a special exception, The Qt Company gives you certain additional
+-** rights. These rights are described in The Qt Company LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef _UNICODE
+-#define _UNICODE
+-#endif
+-
+-#ifndef UNICODE
+-#define UNICODE
+-#endif
+-
+-#include "qlockfile_p.h"
+-
+-#include <qt_windows.h>
+-
+-#include <QCoreApplication>
+-#include <QDir>
+-#include <QFileInfo>
+-#include <QDateTime>
+-#include <QDebug>
+-
+-QT_BEGIN_NAMESPACE
+-
+-static inline QByteArray localHostName()
+-{
+-    return qgetenv("COMPUTERNAME");
+-}
+-
+-static inline bool fileExists(const wchar_t *fileName)
+-{
+-    WIN32_FILE_ATTRIBUTE_DATA  data;
+-    return GetFileAttributesEx(fileName, GetFileExInfoStandard, &data);
+-}
+-
+-QLockFile::LockError QLockFilePrivate::tryLock_sys()
+-{
+-    const ushort* nativePath = QDir::toNativeSeparators(fileName).utf16();
+-    // When writing, allow others to read.
+-    // When reading, QFile will allow others to read and write, all good.
+-    // Adding FILE_SHARE_DELETE would allow forceful deletion of stale files,
+-    // but Windows doesn't allow recreating it while this handle is open anyway,
+-    // so this would only create confusion (can't lock, but no lock file to read from).
+-    const DWORD dwShareMode = FILE_SHARE_READ;
+-#ifndef Q_OS_WINRT
+-    SECURITY_ATTRIBUTES securityAtts = { sizeof(SECURITY_ATTRIBUTES), NULL, FALSE };
+-    HANDLE fh = CreateFile((const wchar_t*)nativePath,
+-                           GENERIC_WRITE,
+-                           dwShareMode,
+-                           &securityAtts,
+-                           CREATE_NEW, // error if already exists
+-                           FILE_ATTRIBUTE_NORMAL,
+-                           NULL);
+-#else // !Q_OS_WINRT
+-    HANDLE fh = CreateFile2((const wchar_t*)nativePath,
+-                            GENERIC_WRITE,
+-                            dwShareMode,
+-                            CREATE_NEW, // error if already exists
+-                            NULL);
+-#endif // Q_OS_WINRT
+-    if (fh == INVALID_HANDLE_VALUE) {
+-        const DWORD lastError = GetLastError();
+-        switch (lastError) {
+-        case ERROR_SHARING_VIOLATION:
+-        case ERROR_ALREADY_EXISTS:
+-        case ERROR_FILE_EXISTS:
+-            return QLockFile::LockFailedError;
+-        case ERROR_ACCESS_DENIED:
+-            // readonly file, or file still in use by another process.
+-            // Assume the latter if the file exists, since we don't create it readonly.
+-            return fileExists((const wchar_t*)nativePath)
+-                ? QLockFile::LockFailedError
+-                : QLockFile::PermissionError;
+-        default:
+-            qWarning() << "Got unexpected locking error" << lastError;
+-            return QLockFile::UnknownError;
+-        }
+-    }
+-
+-    // We hold the lock, continue.
+-    fileHandle = fh;
+-    // Assemble data, to write in a single call to write
+-    // (otherwise we'd have to check every write call)
+-    QByteArray fileData;
+-    fileData += QByteArray::number(QCoreApplication::applicationPid());
+-    fileData += '\n';
+-    fileData += QCoreApplication::applicationName().toUtf8();
+-    fileData += '\n';
+-    fileData += localHostName();
+-    fileData += '\n';
+-    DWORD bytesWritten = 0;
+-    QLockFile::LockError error = QLockFile::NoError;
+-    if (!WriteFile(fh, fileData.constData(), fileData.size(), &bytesWritten, NULL) || !FlushFileBuffers(fh))
+-        error = QLockFile::UnknownError; // partition full
+-    return error;
+-}
+-
+-bool QLockFilePrivate::removeStaleLock()
+-{
+-    // QFile::remove fails on Windows if the other process is still using the file, so it's not stale.
+-    return QFile::remove(fileName);
+-}
+-
+-bool QLockFilePrivate::isApparentlyStale() const
+-{
+-    qint64 pid;
+-    QString hostname, appname;
+-
+-    // On WinRT there seems to be no way of obtaining information about other
+-    // processes due to sandboxing
+-#ifndef Q_OS_WINRT
+-    if (getLockInfo(&pid, &hostname, &appname)) {
+-        if (hostname.isEmpty() || hostname == QString::fromLocal8Bit(localHostName())) {
+-            HANDLE procHandle = ::OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, pid);
+-            if (!procHandle)
+-                return true;
+-            // We got a handle but check if process is still alive
+-            DWORD dwR = ::WaitForSingleObject(procHandle, 0);
+-            ::CloseHandle(procHandle);
+-            if (dwR == WAIT_TIMEOUT)
+-                return true;
+-            const QString processName = processNameByPid(pid);
+-            if (!processName.isEmpty() && processName != appname)
+-                return true; // PID got reused by a different application.
+-        }
+-    }
+-#else // !Q_OS_WINRT
+-    Q_UNUSED(pid);
+-    Q_UNUSED(hostname);
+-    Q_UNUSED(appname);
+-#endif // Q_OS_WINRT
+-    const qint64 age = QFileInfo(fileName).lastModified().msecsTo(QDateTime::currentDateTime());
+-    return staleLockTime > 0 && age > staleLockTime;
+-}
+-
+-QString QLockFilePrivate::processNameByPid(qint64 pid)
+-{
+-#if !defined(Q_OS_WINRT) && !defined(Q_OS_WINCE)
+-    typedef DWORD (WINAPI *GetModuleFileNameExFunc)(HANDLE, HMODULE, LPTSTR, DWORD);
+-
+-    HMODULE hPsapi = LoadLibraryA("psapi");
+-    if (!hPsapi)
+-        return QString();
+-
+-    GetModuleFileNameExFunc qGetModuleFileNameEx
+-            = (GetModuleFileNameExFunc)GetProcAddress(hPsapi, "GetModuleFileNameExW");
+-    if (!qGetModuleFileNameEx) {
+-        FreeLibrary(hPsapi);
+-        return QString();
+-    }
+-
+-    HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, DWORD(pid));
+-    if (!hProcess) {
+-        FreeLibrary(hPsapi);
+-        return QString();
+-    }
+-    wchar_t buf[MAX_PATH];
+-    const DWORD length = qGetModuleFileNameEx(hProcess, NULL, buf, sizeof(buf) / sizeof(wchar_t));
+-    CloseHandle(hProcess);
+-    FreeLibrary(hPsapi);
+-    if (!length)
+-        return QString();
+-    QString name = QString::fromWCharArray(buf, length);
+-    int i = name.lastIndexOf(QLatin1Char('\\'));
+-    if (i >= 0)
+-        name.remove(0, i + 1);
+-    i = name.lastIndexOf(QLatin1Char('.'));
+-    if (i >= 0)
+-        name.truncate(i);
+-    return name;
+-#else
+-    Q_UNUSED(pid);
+-    return QString();
+-#endif
+-}
+-
+-void QLockFile::unlock()
+-{
+-    Q_D(QLockFile);
+-     if (!d->isLocked)
+-        return;
+-     CloseHandle(d->fileHandle);
+-     int attempts = 0;
+-     static const int maxAttempts = 500; // 500ms
+-     while (!QFile::remove(d->fileName) && ++attempts < maxAttempts) {
+-         // Someone is reading the lock file right now (on Windows this prevents deleting it).
+-         QLockFileThread::msleep(1);
+-     }
+-     if (attempts == maxAttempts) {
+-        qWarning() << "Could not remove our own lock file" << d->fileName << ". Either other users of the lock file are reading it constantly for 500 ms, or we (no longer) have permissions to delete the file";
+-        // This is bad because other users of this lock file will now have to wait for the stale-lock-timeout...
+-     }
+-     d->lockError = QLockFile::NoError;
+-     d->isLocked = false;
+-}
+-
+-QT_END_NAMESPACE
+diff --git a/src/core/qsavefile.cpp b/src/core/qsavefile.cpp
+deleted file mode 100644
+index 287f9e8..0000000
+--- a/src/core/qsavefile.cpp
++++ /dev/null
+@@ -1,452 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
+-** Contact: http://www.qt-project.org/
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** GNU Lesser General Public License Usage
+-** This file may be used under the terms of the GNU Lesser General Public
+-** License version 2.1 as published by the Free Software Foundation and
+-** appearing in the file LICENSE.LGPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU Lesser
+-** General Public License version 2.1 requirements will be met:
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Nokia gives you certain additional
+-** rights. These rights are described in the Nokia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU General
+-** Public License version 3.0 as published by the Free Software Foundation
+-** and appearing in the file LICENSE.GPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU General
+-** Public License version 3.0 requirements will be met:
+-** http://www.gnu.org/copyleft/gpl.html.
+-**
+-** Other Usage
+-** Alternatively, this file may be used in accordance with the terms and
+-** conditions contained in a signed written agreement between you and Nokia.
+-**
+-**
+-**
+-**
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#include "qsavefile.h"
+-#include "qsavefile_p.h"
+-
+-#include <QAbstractFileEngine>
+-#include <QFileInfo>
+-#include <QTemporaryFile>
+-
+-#ifdef Q_OS_WIN
+-#  include <windows.h>
+-#else
+-#  include <unistd.h>
+-#endif
+-
+-QSaveFilePrivate::QSaveFilePrivate()
+-    : tempFile(0), error(QFile::NoError)
+-{
+-}
+-
+-QSaveFilePrivate::~QSaveFilePrivate()
+-{
+-}
+-
+-/*!
+-    \class QSaveFile
+-    \brief The QSaveFile class provides an interface for safely writing to files.
+-
+-    \ingroup io
+-
+-    \reentrant
+-
+-    QSaveFile is an I/O device for writing text and binary files, without losing
+-    existing data if the writing operation fails.
+-
+-    While writing, the contents will be written to a temporary file, and if
+-    no error happened, commit() will move it to the final file. This ensures that
+-    no data at the final file is lost in case an error happens while writing,
+-    and no partially-written file is ever present at the final location. Always
+-    use QSaveFile when saving entire documents to disk.
+-
+-    QSaveFile automatically detects errors while writing, such as the full partition
+-    situation, where write() cannot write all the bytes. It will remember that
+-    an error happened, and will discard the temporary file in commit().
+-
+-    Much like with QFile, the file is opened with open(). Data is usually read
+-    and written using QDataStream or QTextStream, but you can also call the
+-    QIODevice-inherited functions read(), readLine(), readAll(), write().
+-
+-    Unlike QFile, calling close() is not allowed. commit() replaces it. If commit()
+-    was not called and the QSaveFile instance is destroyed, the temporary file is
+-    discarded.
+-
+-    \sa QTextStream, QDataStream, QFileInfo, QDir, QFile, QTemporaryFile
+-*/
+-
+-/*!
+-    \internal
+-*/
+-QSaveFile::QSaveFile()
+-    : QIODevice(), d_ptr(new QSaveFilePrivate)
+-{
+-}
+-/*!
+-    Constructs a new file object with the given \a parent.
+-*/
+-QSaveFile::QSaveFile(QObject *parent)
+-    : QIODevice(parent), d_ptr(new QSaveFilePrivate)
+-{
+-}
+-/*!
+-    Constructs a new file object to represent the file with the given \a name.
+-*/
+-QSaveFile::QSaveFile(const QString &name)
+-    : QIODevice(0), d_ptr(new QSaveFilePrivate)
+-{
+-    Q_D(QSaveFile);
+-    d->fileName = name;
+-}
+-/*!
+-    Constructs a new file object with the given \a parent to represent the
+-    file with the specified \a name.
+-*/
+-QSaveFile::QSaveFile(const QString &name, QObject *parent)
+-    : QIODevice(parent), d_ptr(new QSaveFilePrivate)
+-{
+-    Q_D(QSaveFile);
+-    d->fileName = name;
+-}
+-
+-/*!
+-    Destroys the file object, discarding the saved contents unless commit() was called.
+-*/
+-QSaveFile::~QSaveFile()
+-{
+-    Q_D(QSaveFile);
+-    if (d->tempFile) {
+-        d->tempFile->setAutoRemove(true);
+-        delete d->tempFile;
+-    }
+-    QIODevice::close();
+-    delete d;
+-}
+-
+-/*!
+-    Returns false since temporary files support random access.
+-
+-    \sa QIODevice::isSequential()
+-*/
+-bool QSaveFile::isSequential() const
+-{
+-    return false;
+-}
+-
+-/*!
+-    Returns the file error status.
+-
+-    The I/O device status returns an error code. For example, if open()
+-    returns false, or a read/write operation returns -1, this function can
+-    be called to find out the reason why the operation failed.
+-
+-    Unlike QFile which clears the error on the next operation, QSaveFile remembers
+-    the error until the file is closed, in order to discard the file contents in close().
+-
+-    \sa unsetError()
+-*/
+-
+-QFile::FileError QSaveFile::error() const
+-{
+-    return d_func()->error;
+-}
+-
+-/*!
+-    Sets the file's error to QFile::NoError.
+-
+-    This will make QSaveFile forget that an error happened during saving, so you
+-    probably don't want to call this, unless you're really sure that you want to
+-    save the file anyway.
+-
+-    \sa error()
+-*/
+-void QSaveFile::unsetError()
+-{
+-    d_func()->error = QFile::NoError;
+-    setErrorString(QString());
+-}
+-
+-/*!
+-    Returns the name set by setFileName() or to the QSaveFile
+-    constructor.
+-
+-    \sa setFileName()
+-*/
+-QString QSaveFile::fileName() const
+-{
+-    return d_func()->fileName;
+-}
+-
+-/*!
+-    Sets the \a name of the file. The name can have no path, a
+-    relative path, or an absolute path.
+-
+-    \sa QFile::setFileName(), fileName()
+-*/
+-void QSaveFile::setFileName(const QString &name)
+-{
+-    d_func()->fileName = name;
+-}
+-
+-/*!
+-    Opens the file using OpenMode \a mode, returning true if successful;
+-    otherwise false.
+-
+-    Important: the \a mode must be QIODevice::WriteOnly.
+-    It may also have additional flags, such as QIODevice::Text and QIODevice::Unbuffered.
+-
+-    QIODevice::ReadWrite and QIODevice::Append are not supported at the moment.
+-
+-    \sa QIODevice::OpenMode, setFileName()
+-*/
+-bool QSaveFile::open(OpenMode mode)
+-{
+-    Q_D(QSaveFile);
+-    if (isOpen()) {
+-        qWarning("QSaveFile::open: File (%s) already open", qPrintable(fileName()));
+-        return false;
+-    }
+-    unsetError();
+-    if ((mode & (ReadOnly | WriteOnly)) == 0) {
+-        qWarning("QSaveFile::open: Open mode not specified");
+-        return false;
+-    }
+-    // In the future we could implement Append and ReadWrite by copying from the existing file to the temp file...
+-    if ((mode & ReadOnly) || (mode & Append)) {
+-        qWarning("QSaveFile::open: Unsupported open mode %d", int(mode));
+-        return false;
+-    }
+-
+-    // check if existing file is writable
+-    QFileInfo existingFile(d->fileName);
+-    if (existingFile.exists() && !existingFile.isWritable()) {
+-        d->error = QFile::WriteError;
+-        setErrorString(QSaveFile::tr("Existing file %1 is not writable").arg(d->fileName));
+-        return false;
+-    }
+-    d->tempFile = new QTemporaryFile;
+-    d->tempFile->setAutoRemove(false);
+-    d->tempFile->setFileTemplate(d->fileName);
+-    if (!d->tempFile->open()) {
+-        d->error = d->tempFile->error();
+-        setErrorString(d->tempFile->errorString());
+-        delete d->tempFile;
+-        d->tempFile = 0;
+-        return false;
+-    }
+-    QIODevice::open(mode);
+-    if (existingFile.exists())
+-        d->tempFile->setPermissions(existingFile.permissions());
+-    return true;
+-}
+-
+-/*!
+-  \reimp
+-  Cannot be called.
+-  Call commit() instead.
+-*/
+-void QSaveFile::close()
+-{
+-    qFatal("QSaveFile::close called");
+-}
+-
+-/*
+-  Commits the changes to disk, if all previous writes were successful.
+-
+-  It is mandatory to call this at the end of the saving operation, otherwise the file will be
+-  discarded.
+-
+-  If an error happened during writing, deletes the temporary file and returns false.
+-  Otherwise, renames it to the final fileName and returns true on success.
+-  Finally, closes the device.
+-
+-  \sa cancelWriting()
+-*/
+-bool QSaveFile::commit()
+-{
+-    Q_D(QSaveFile);
+-    if (!d->tempFile)
+-        return false;
+-    if (!isOpen()) {
+-        qWarning("QSaveFile::commit: File (%s) is not open", qPrintable(fileName()));
+-        return false;
+-    }
+-    flush();
+-#ifdef Q_OS_WIN
+-    FlushFileBuffers(reinterpret_cast<HANDLE>(handle()));
+-#elif defined(_POSIX_SYNCHRONIZED_IO) && _POSIX_SYNCHRONIZED_IO > 0
+-    fdatasync(d->tempFile->handle());
+-#else
+-    fsync(d->tempFile->handle());
+-#endif
+-    QIODevice::close();
+-    if (d->error != QFile::NoError) {
+-        d->tempFile->remove();
+-        unsetError();
+-        delete d->tempFile;
+-        d->tempFile = 0;
+-        return false;
+-    }
+-    d->tempFile->close();
+-#ifdef Q_OS_WIN
+-    // On Windows QAbstractFileEngine::rename() fails if the the target exists,
+-    // so we have to rename the target.
+-    // Ideally the winapi ReplaceFile() method should be used.
+-    QString bakname = d->fileName + "~";
+-    QFile::remove(bakname);
+-    QFile::rename(d->fileName, bakname);
+-#endif
+-    QAbstractFileEngine* fileEngine = d->tempFile->fileEngine();
+-    Q_ASSERT(fileEngine);
+-    if (!fileEngine->rename(d->fileName)) {
+-        d->error = fileEngine->error();
+-        setErrorString(fileEngine->errorString());
+-        d->tempFile->remove();
+-        delete d->tempFile;
+-        d->tempFile = 0;
+-#ifdef Q_OS_WIN
+-        QFile::rename(bakname, d->fileName);
+-#endif
+-        return false;
+-    }
+-    delete d->tempFile;
+-    d->tempFile = 0;
+-#ifdef Q_OS_WIN
+-    QFile::remove(bakname);
+-#endif
+-    return true;
+-}
+-
+-/*!
+-  Sets an error code so that commit() discards the temporary file.
+-
+-  Further write operations are possible after calling this method, but none
+-  of it will have any effect, the written file will be discarded.
+-
+-  \sa commit()
+-*/
+-void QSaveFile::cancelWriting()
+-{
+-    if (!isOpen())
+-        return;
+-    d_func()->error = QFile::WriteError;
+-    setErrorString(QSaveFile::tr("Writing canceled by application"));
+-}
+-
+-/*!
+-  Returns the size of the file.
+-  \sa QFile::size()
+-*/
+-qint64 QSaveFile::size() const
+-{
+-    Q_D(const QSaveFile);
+-    return d->tempFile ? d->tempFile->size() : qint64(-1);
+-}
+-
+-/*!
+-  \reimp
+-*/
+-qint64 QSaveFile::pos() const
+-{
+-    Q_D(const QSaveFile);
+-    return d->tempFile ? d->tempFile->pos() : qint64(-1);
+-}
+-
+-/*!
+-  \reimp
+-*/
+-bool QSaveFile::seek(qint64 offset)
+-{
+-    Q_D(QSaveFile);
+-    return d->tempFile ? d->tempFile->seek(offset) : false;
+-}
+-
+-/*!
+-  \reimp
+-*/
+-bool QSaveFile::atEnd() const
+-{
+-    Q_D(const QSaveFile);
+-    return d->tempFile ? d->tempFile->atEnd() : true;
+-}
+-
+-/*!
+-    Flushes any buffered data to the file. Returns true if successful;
+-    otherwise returns false.
+-*/
+-bool QSaveFile::flush()
+-{
+-    Q_D(QSaveFile);
+-    if (d->tempFile) {
+-        if (!d->tempFile->flush()) {
+-            d->error = d->tempFile->error();
+-            setErrorString(d->tempFile->errorString());
+-            return false;
+-        }
+-        return true;
+-    }
+-    return false;
+-}
+-
+-/*!
+-  Returns the file handle of the temporary file.
+-
+-  \sa QFile::handle()
+-*/
+-int QSaveFile::handle() const
+-{
+-    Q_D(const QSaveFile);
+-    return d->tempFile ? d->tempFile->handle() : -1;
+-}
+-
+-/*!
+-  \reimp
+-*/
+-qint64 QSaveFile::readData(char *data, qint64 maxlen)
+-{
+-    Q_D(QSaveFile);
+-    return d->tempFile ? d->tempFile->read(data, maxlen) : -1;
+-}
+-
+-/*!
+-  \reimp
+-*/
+-qint64 QSaveFile::writeData(const char *data, qint64 len)
+-{
+-    Q_D(QSaveFile);
+-    if (!d->tempFile)
+-        return -1;
+-    const qint64 written = d->tempFile->write(data, len);
+-    if (written != len) {
+-        d->error = QFile::WriteError;
+-        setErrorString(QSaveFile::tr("Partial write. Partition full?"));
+-    }
+-    return written;
+-}
+-
+-/*!
+-  \reimp
+-*/
+-qint64 QSaveFile::readLineData(char *data, qint64 maxlen)
+-{
+-    Q_D(QSaveFile);
+-    return d->tempFile ? d->tempFile->readLine(data, maxlen) : -1;
+-}
+diff --git a/src/core/qsavefile.h b/src/core/qsavefile.h
+deleted file mode 100644
+index 84d5a24..0000000
+--- a/src/core/qsavefile.h
++++ /dev/null
+@@ -1,105 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
+-** Contact: http://www.qt-project.org/
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** GNU Lesser General Public License Usage
+-** This file may be used under the terms of the GNU Lesser General Public
+-** License version 2.1 as published by the Free Software Foundation and
+-** appearing in the file LICENSE.LGPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU Lesser
+-** General Public License version 2.1 requirements will be met:
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Nokia gives you certain additional
+-** rights. These rights are described in the Nokia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU General
+-** Public License version 3.0 as published by the Free Software Foundation
+-** and appearing in the file LICENSE.GPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU General
+-** Public License version 3.0 requirements will be met:
+-** http://www.gnu.org/copyleft/gpl.html.
+-**
+-** Other Usage
+-** Alternatively, this file may be used in accordance with the terms and
+-** conditions contained in a signed written agreement between you and Nokia.
+-**
+-**
+-**
+-**
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef QSAVEFILE_H
+-#define QSAVEFILE_H
+-
+-#include <QFile>
+-#include <QString>
+-
+-#ifdef open
+-#error qsavefile.h must be included before any header file that defines open
+-#endif
+-
+-class QAbstractFileEngine;
+-class QSaveFilePrivate;
+-
+-class QSaveFile : public QIODevice
+-{
+-    Q_OBJECT
+-    Q_DECLARE_PRIVATE(QSaveFile)
+-
+-public:
+-
+-    QSaveFile();
+-    explicit QSaveFile(const QString &name);
+-    explicit QSaveFile(QObject *parent);
+-    QSaveFile(const QString &name, QObject *parent);
+-    ~QSaveFile();
+-
+-    QFile::FileError error() const;
+-    void unsetError();
+-
+-    QString fileName() const;
+-    void setFileName(const QString &name);
+-
+-    bool isSequential() const;
+-
+-    virtual bool open(OpenMode flags);
+-    bool commit();
+-
+-    void cancelWriting();
+-
+-    qint64 size() const;
+-    qint64 pos() const;
+-    bool seek(qint64 offset);
+-    bool atEnd() const;
+-    bool flush();
+-
+-    bool resize(qint64 sz);
+-
+-    int handle() const;
+-
+-protected:
+-    qint64 readData(char *data, qint64 maxlen);
+-    qint64 writeData(const char *data, qint64 len);
+-    qint64 readLineData(char *data, qint64 maxlen);
+-
+-private:
+-    virtual void close();
+-
+-private:
+-    Q_DISABLE_COPY(QSaveFile)
+-
+-    QSaveFilePrivate* const d_ptr;
+-};
+-
+-#endif // QSAVEFILE_H
+diff --git a/src/core/qsavefile_p.h b/src/core/qsavefile_p.h
+deleted file mode 100644
+index 549ecc1..0000000
+--- a/src/core/qsavefile_p.h
++++ /dev/null
+@@ -1,71 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
+-** Contact: http://www.qt-project.org/
+-**
+-** This file is part of the QtCore module of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** GNU Lesser General Public License Usage
+-** This file may be used under the terms of the GNU Lesser General Public
+-** License version 2.1 as published by the Free Software Foundation and
+-** appearing in the file LICENSE.LGPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU Lesser
+-** General Public License version 2.1 requirements will be met:
+-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Nokia gives you certain additional
+-** rights. These rights are described in the Nokia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU General
+-** Public License version 3.0 as published by the Free Software Foundation
+-** and appearing in the file LICENSE.GPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU General
+-** Public License version 3.0 requirements will be met:
+-** http://www.gnu.org/copyleft/gpl.html.
+-**
+-** Other Usage
+-** Alternatively, this file may be used in accordance with the terms and
+-** conditions contained in a signed written agreement between you and Nokia.
+-**
+-**
+-**
+-**
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef QSAVEFILE_P_H
+-#define QSAVEFILE_P_H
+-
+-//
+-//  W A R N I N G
+-//  -------------
+-//
+-// This file is not part of the Qt API.  It exists purely as an
+-// implementation detail.  This header file may change from version to
+-// version without notice, or even be removed.
+-//
+-// We mean it.
+-//
+-
+-#include <QTemporaryFile>
+-
+-class QSaveFilePrivate
+-{
+-public:
+-    QSaveFilePrivate();
+-    ~QSaveFilePrivate();
+-
+-    QString fileName;
+-    QTemporaryFile *tempFile;
+-
+-    QFile::FileError error;
+-};
+-
+-#endif // QSAVEFILE_P_H
+-
+diff --git a/src/crypto/Crypto.cpp b/src/crypto/Crypto.cpp
+index 40ec7ea..1ff6fde 100644
+--- a/src/crypto/Crypto.cpp
++++ b/src/crypto/Crypto.cpp
+@@ -29,43 +29,6 @@ bool Crypto::m_initalized(false);
+ QString Crypto::m_errorStr;
+ QString Crypto::m_backendVersion;
+-#if !defined(GCRYPT_VERSION_NUMBER) || (GCRYPT_VERSION_NUMBER < 0x010600)
+-static int gcry_qt_mutex_init(void** p_sys)
+-{
+-    *p_sys = new QMutex();
+-    return 0;
+-}
+-
+-static int gcry_qt_mutex_destroy(void** p_sys)
+-{
+-    delete reinterpret_cast<QMutex*>(*p_sys);
+-    return 0;
+-}
+-
+-static int gcry_qt_mutex_lock(void** p_sys)
+-{
+-    reinterpret_cast<QMutex*>(*p_sys)->lock();
+-    return 0;
+-}
+-
+-static int gcry_qt_mutex_unlock(void** p_sys)
+-{
+-    reinterpret_cast<QMutex*>(*p_sys)->unlock();
+-    return 0;
+-}
+-
+-static const struct gcry_thread_cbs gcry_threads_qt =
+-{
+-    GCRY_THREAD_OPTION_USER,
+-    0,
+-    gcry_qt_mutex_init,
+-    gcry_qt_mutex_destroy,
+-    gcry_qt_mutex_lock,
+-    gcry_qt_mutex_unlock,
+-    0, 0, 0, 0, 0, 0, 0, 0
+-};
+-#endif
+-
+ Crypto::Crypto()
+ {
+ }
+@@ -77,10 +40,6 @@ bool Crypto::init()
+         return true;
+     }
+-    // libgcrypt >= 1.6 doesn't allow custom thread callbacks anymore.
+-#if !defined(GCRYPT_VERSION_NUMBER) || (GCRYPT_VERSION_NUMBER < 0x010600)
+-    gcry_control(GCRYCTL_SET_THREAD_CBS, &gcry_threads_qt);
+-#endif
+     m_backendVersion = QString::fromLocal8Bit(gcry_check_version(0));
+     gcry_control(GCRYCTL_INITIALIZATION_FINISHED, 0);
+@@ -121,18 +80,18 @@ bool Crypto::backendSelfTest()
+ bool Crypto::checkAlgorithms()
+ {
+-    if (gcry_cipher_algo_info(GCRY_CIPHER_AES256, GCRYCTL_TEST_ALGO, Q_NULLPTR, Q_NULLPTR) != 0) {
++    if (gcry_cipher_algo_info(GCRY_CIPHER_AES256, GCRYCTL_TEST_ALGO, nullptr, nullptr) != 0) {
+         m_errorStr = "GCRY_CIPHER_AES256 not found.";
+         qWarning("Crypto::checkAlgorithms: %s", qPrintable(m_errorStr));
+         return false;
+     }
+-    if (gcry_cipher_algo_info(GCRY_CIPHER_TWOFISH, GCRYCTL_TEST_ALGO, Q_NULLPTR, Q_NULLPTR) != 0) {
++    if (gcry_cipher_algo_info(GCRY_CIPHER_TWOFISH, GCRYCTL_TEST_ALGO, nullptr, nullptr) != 0) {
+         m_errorStr = "GCRY_CIPHER_TWOFISH not found.";
+         qWarning("Crypto::checkAlgorithms: %s", qPrintable(m_errorStr));
+         return false;
+     }
+ #ifdef GCRYPT_HAS_SALSA20
+-    if (gcry_cipher_algo_info(GCRY_CIPHER_SALSA20, GCRYCTL_TEST_ALGO, Q_NULLPTR, Q_NULLPTR) != 0) {
++    if (gcry_cipher_algo_info(GCRY_CIPHER_SALSA20, GCRYCTL_TEST_ALGO, nullptr, nullptr) != 0) {
+         m_errorStr = "GCRY_CIPHER_SALSA20 not found.";
+         qWarning("Crypto::checkAlgorithms: %s", qPrintable(m_errorStr));
+         return false;
+diff --git a/src/crypto/Crypto.h b/src/crypto/Crypto.h
+index 1726865..0ce2903 100644
+--- a/src/crypto/Crypto.h
++++ b/src/crypto/Crypto.h
+@@ -20,8 +20,6 @@
+ #include <QString>
+-#include "core/Global.h"
+-
+ class Crypto
+ {
+ public:
+diff --git a/src/crypto/Random.cpp b/src/crypto/Random.cpp
+index 2a375f3..dc0667f 100644
+--- a/src/crypto/Random.cpp
++++ b/src/crypto/Random.cpp
+@@ -19,15 +19,16 @@
+ #include <gcrypt.h>
++#include "core/Global.h"
+ #include "crypto/Crypto.h"
+ class RandomBackendGcrypt : public RandomBackend
+ {
+ public:
+-    void randomize(void* data, int len) Q_DECL_OVERRIDE;
++    void randomize(void* data, int len) override;
+ };
+-Random* Random::m_instance(Q_NULLPTR);
++Random* Random::m_instance(nullptr);
+ void Random::randomize(QByteArray& ba)
+ {
+diff --git a/src/crypto/SymmetricCipher.cpp b/src/crypto/SymmetricCipher.cpp
+index 454548c..12ec264 100644
+--- a/src/crypto/SymmetricCipher.cpp
++++ b/src/crypto/SymmetricCipher.cpp
+@@ -19,7 +19,6 @@
+ #include "config-keepassx.h"
+ #include "crypto/SymmetricCipherGcrypt.h"
+-#include "crypto/SymmetricCipherSalsa20.h"
+ SymmetricCipher::SymmetricCipher(SymmetricCipher::Algorithm algo, SymmetricCipher::Mode mode,
+                                  SymmetricCipher::Direction direction)
+@@ -61,19 +60,12 @@ SymmetricCipherBackend* SymmetricCipher::createBackend(SymmetricCipher::Algorith
+     switch (algo) {
+     case SymmetricCipher::Aes256:
+     case SymmetricCipher::Twofish:
+-#if defined(GCRYPT_HAS_SALSA20)
+     case SymmetricCipher::Salsa20:
+-#endif
+         return new SymmetricCipherGcrypt(algo, mode, direction);
+-#if !defined(GCRYPT_HAS_SALSA20)
+-    case SymmetricCipher::Salsa20:
+-        return new SymmetricCipherSalsa20(algo, mode, direction);
+-#endif
+-
+     default:
+         Q_ASSERT(false);
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+ }
+diff --git a/src/crypto/SymmetricCipher.h b/src/crypto/SymmetricCipher.h
+index b8b3eb1..4fc06b7 100644
+--- a/src/crypto/SymmetricCipher.h
++++ b/src/crypto/SymmetricCipher.h
+@@ -22,7 +22,6 @@
+ #include <QScopedPointer>
+ #include <QString>
+-#include "core/Global.h"
+ #include "crypto/SymmetricCipherBackend.h"
+ class SymmetricCipher
+diff --git a/src/crypto/SymmetricCipherGcrypt.cpp b/src/crypto/SymmetricCipherGcrypt.cpp
+index 5c4fe6a..cd43240 100644
+--- a/src/crypto/SymmetricCipherGcrypt.cpp
++++ b/src/crypto/SymmetricCipherGcrypt.cpp
+@@ -22,7 +22,7 @@
+ SymmetricCipherGcrypt::SymmetricCipherGcrypt(SymmetricCipher::Algorithm algo, SymmetricCipher::Mode mode,
+                                              SymmetricCipher::Direction direction)
+-    : m_ctx(Q_NULLPTR)
++    : m_ctx(nullptr)
+     , m_algo(gcryptAlgo(algo))
+     , m_mode(gcryptMode(mode))
+     , m_direction(direction)
+@@ -44,10 +44,8 @@ int SymmetricCipherGcrypt::gcryptAlgo(SymmetricCipher::Algorithm algo)
+     case SymmetricCipher::Twofish:
+         return GCRY_CIPHER_TWOFISH;
+-#ifdef GCRYPT_HAS_SALSA20
+     case SymmetricCipher::Salsa20:
+         return GCRY_CIPHER_SALSA20;
+-#endif
+     default:
+         Q_ASSERT(false);
+@@ -95,7 +93,7 @@ bool SymmetricCipherGcrypt::init()
+     }
+     size_t blockSizeT;
+-    error = gcry_cipher_algo_info(m_algo, GCRYCTL_GET_BLKLEN, Q_NULLPTR, &blockSizeT);
++    error = gcry_cipher_algo_info(m_algo, GCRYCTL_GET_BLKLEN, nullptr, &blockSizeT);
+     if (error != 0) {
+         setErrorString(error);
+         return false;
+@@ -163,10 +161,10 @@ bool SymmetricCipherGcrypt::processInPlace(QByteArray& data)
+     gcry_error_t error;
+     if (m_direction == SymmetricCipher::Decrypt) {
+-        error = gcry_cipher_decrypt(m_ctx, data.data(), data.size(), Q_NULLPTR, 0);
++        error = gcry_cipher_decrypt(m_ctx, data.data(), data.size(), nullptr, 0);
+     }
+     else {
+-        error = gcry_cipher_encrypt(m_ctx, data.data(), data.size(), Q_NULLPTR, 0);
++        error = gcry_cipher_encrypt(m_ctx, data.data(), data.size(), nullptr, 0);
+     }
+     if (error != 0) {
+@@ -188,7 +186,7 @@ bool SymmetricCipherGcrypt::processInPlace(QByteArray& data, quint64 rounds)
+     if (m_direction == SymmetricCipher::Decrypt) {
+         for (quint64 i = 0; i != rounds; ++i) {
+-            error = gcry_cipher_decrypt(m_ctx, rawData, size, Q_NULLPTR, 0);
++            error = gcry_cipher_decrypt(m_ctx, rawData, size, nullptr, 0);
+             if (error != 0) {
+                 setErrorString(error);
+@@ -198,7 +196,7 @@ bool SymmetricCipherGcrypt::processInPlace(QByteArray& data, quint64 rounds)
+     }
+     else {
+         for (quint64 i = 0; i != rounds; ++i) {
+-            error = gcry_cipher_encrypt(m_ctx, rawData, size, Q_NULLPTR, 0);
++            error = gcry_cipher_encrypt(m_ctx, rawData, size, nullptr, 0);
+             if (error != 0) {
+                 setErrorString(error);
+diff --git a/src/crypto/salsa20/ecrypt-config.h b/src/crypto/salsa20/ecrypt-config.h
+deleted file mode 100644
+index 0914fbc..0000000
+--- a/src/crypto/salsa20/ecrypt-config.h
++++ /dev/null
+@@ -1,260 +0,0 @@
+-/* ecrypt-config.h */
+-
+-/* *** Normally, it should not be necessary to edit this file. *** */
+-
+-#ifndef ECRYPT_CONFIG
+-#define ECRYPT_CONFIG
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* Guess the endianness of the target architecture. */
+-
+-#include <QtGlobal>
+-
+-#if Q_BYTE_ORDER == Q_LITTLE_ENDIAN
+-#define ECRYPT_LITTLE_ENDIAN
+-#elif Q_BYTE_ORDER == Q_BIG_ENDIAN
+-#define ECRYPT_BIG_ENDIAN
+-#else
+-#define ECRYPT_UNKNOWN
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/*
+- * Find minimal-width types to store 8-bit, 16-bit, 32-bit, and 64-bit
+- * integers.
+- *
+- * Note: to enable 64-bit types on 32-bit compilers, it might be
+- * necessary to switch from ISO C90 mode to ISO C99 mode (e.g., gcc
+- * -std=c99), or to allow compiler-specific extensions.
+- */
+-
+-#include <limits.h>
+-
+-/* --- check char --- */
+-
+-#if (UCHAR_MAX / 0xFU > 0xFU)
+-#ifndef I8T
+-#define I8T char
+-#define U8C(v) (v##U)
+-
+-#if (UCHAR_MAX == 0xFFU)
+-#define ECRYPT_I8T_IS_BYTE
+-#endif
+-
+-#endif
+-
+-#if (UCHAR_MAX / 0xFFU > 0xFFU)
+-#ifndef I16T
+-#define I16T char
+-#define U16C(v) (v##U)
+-#endif
+-
+-#if (UCHAR_MAX / 0xFFFFU > 0xFFFFU)
+-#ifndef I32T
+-#define I32T char
+-#define U32C(v) (v##U)
+-#endif
+-
+-#if (UCHAR_MAX / 0xFFFFFFFFU > 0xFFFFFFFFU)
+-#ifndef I64T
+-#define I64T char
+-#define U64C(v) (v##U)
+-#define ECRYPT_NATIVE64
+-#endif
+-
+-#endif
+-#endif
+-#endif
+-#endif
+-
+-/* --- check short --- */
+-
+-#if (USHRT_MAX / 0xFU > 0xFU)
+-#ifndef I8T
+-#define I8T short
+-#define U8C(v) (v##U)
+-
+-#if (USHRT_MAX == 0xFFU)
+-#define ECRYPT_I8T_IS_BYTE
+-#endif
+-
+-#endif
+-
+-#if (USHRT_MAX / 0xFFU > 0xFFU)
+-#ifndef I16T
+-#define I16T short
+-#define U16C(v) (v##U)
+-#endif
+-
+-#if (USHRT_MAX / 0xFFFFU > 0xFFFFU)
+-#ifndef I32T
+-#define I32T short
+-#define U32C(v) (v##U)
+-#endif
+-
+-#if (USHRT_MAX / 0xFFFFFFFFU > 0xFFFFFFFFU)
+-#ifndef I64T
+-#define I64T short
+-#define U64C(v) (v##U)
+-#define ECRYPT_NATIVE64
+-#endif
+-
+-#endif
+-#endif
+-#endif
+-#endif
+-
+-/* --- check int --- */
+-
+-#if (UINT_MAX / 0xFU > 0xFU)
+-#ifndef I8T
+-#define I8T int
+-#define U8C(v) (v##U)
+-
+-#if (ULONG_MAX == 0xFFU)
+-#define ECRYPT_I8T_IS_BYTE
+-#endif
+-
+-#endif
+-
+-#if (UINT_MAX / 0xFFU > 0xFFU)
+-#ifndef I16T
+-#define I16T int
+-#define U16C(v) (v##U)
+-#endif
+-
+-#if (UINT_MAX / 0xFFFFU > 0xFFFFU)
+-#ifndef I32T
+-#define I32T int
+-#define U32C(v) (v##U)
+-#endif
+-
+-#if (UINT_MAX / 0xFFFFFFFFU > 0xFFFFFFFFU)
+-#ifndef I64T
+-#define I64T int
+-#define U64C(v) (v##U)
+-#define ECRYPT_NATIVE64
+-#endif
+-
+-#endif
+-#endif
+-#endif
+-#endif
+-
+-/* --- check long --- */
+-
+-#if (ULONG_MAX / 0xFUL > 0xFUL)
+-#ifndef I8T
+-#define I8T long
+-#define U8C(v) (v##UL)
+-
+-#if (ULONG_MAX == 0xFFUL)
+-#define ECRYPT_I8T_IS_BYTE
+-#endif
+-
+-#endif
+-
+-#if (ULONG_MAX / 0xFFUL > 0xFFUL)
+-#ifndef I16T
+-#define I16T long
+-#define U16C(v) (v##UL)
+-#endif
+-
+-#if (ULONG_MAX / 0xFFFFUL > 0xFFFFUL)
+-#ifndef I32T
+-#define I32T long
+-#define U32C(v) (v##UL)
+-#endif
+-
+-#if (ULONG_MAX / 0xFFFFFFFFUL > 0xFFFFFFFFUL)
+-#ifndef I64T
+-#define I64T long
+-#define U64C(v) (v##UL)
+-#define ECRYPT_NATIVE64
+-#endif
+-
+-#endif
+-#endif
+-#endif
+-#endif
+-
+-/* --- check long long --- */
+-
+-#ifdef ULLONG_MAX
+-
+-#if (ULLONG_MAX / 0xFULL > 0xFULL)
+-#ifndef I8T
+-#define I8T long long
+-#define U8C(v) (v##ULL)
+-
+-#if (ULLONG_MAX == 0xFFULL)
+-#define ECRYPT_I8T_IS_BYTE
+-#endif
+-
+-#endif
+-
+-#if (ULLONG_MAX / 0xFFULL > 0xFFULL)
+-#ifndef I16T
+-#define I16T long long
+-#define U16C(v) (v##ULL)
+-#endif
+-
+-#if (ULLONG_MAX / 0xFFFFULL > 0xFFFFULL)
+-#ifndef I32T
+-#define I32T long long
+-#define U32C(v) (v##ULL)
+-#endif
+-
+-#if (ULLONG_MAX / 0xFFFFFFFFULL > 0xFFFFFFFFULL)
+-#ifndef I64T
+-#define I64T long long
+-#define U64C(v) (v##ULL)
+-#endif
+-
+-#endif
+-#endif
+-#endif
+-#endif
+-
+-#endif
+-
+-/* --- check __int64 --- */
+-
+-#if !defined(__STDC__) && defined(_UI64_MAX)
+-
+-#ifndef I64T
+-#define I64T __int64
+-#define U64C(v) (v##ui64)
+-#endif
+-
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* find the largest type on this platform (used for alignment) */
+-
+-#if defined(__SSE__) || (defined(_MSC_VER) && (_MSC_VER >= 1300))
+-
+-#include <xmmintrin.h>
+-#define MAXT __m128
+-
+-#elif defined(__MMX__)
+-
+-#include <mmintrin.h>
+-#define MAXT __m64
+-
+-#elif defined(__ALTIVEC__)
+-
+-#define MAXT __vector int
+-
+-#else
+-
+-#define MAXT long
+-
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+-
+-#endif
+diff --git a/src/crypto/salsa20/ecrypt-machine.h b/src/crypto/salsa20/ecrypt-machine.h
+deleted file mode 100644
+index d006bed..0000000
+--- a/src/crypto/salsa20/ecrypt-machine.h
++++ /dev/null
+@@ -1,49 +0,0 @@
+-/* ecrypt-machine.h */
+-
+-/*
+- * This file is included by 'ecrypt-portable.h'. It allows to override
+- * the default macros for specific platforms. Please carefully check
+- * the machine code generated by your compiler (with optimisations
+- * turned on) before deciding to edit this file.
+- */
+-
+-/* ------------------------------------------------------------------------- */
+-
+-#if (defined(ECRYPT_DEFAULT_ROT) && !defined(ECRYPT_MACHINE_ROT))
+-
+-#define ECRYPT_MACHINE_ROT
+-
+-#if (defined(WIN32) && defined(_MSC_VER))
+-
+-#undef ROTL32
+-#undef ROTR32
+-#undef ROTL64
+-#undef ROTR64
+-
+-#include <stdlib.h>
+-
+-#pragma intrinsic(_lrotl)     /* compile rotations "inline" */
+-#pragma intrinsic(_lrotr)
+-
+-#define ROTL32(v, n) _lrotl(v, n)
+-#define ROTR32(v, n) _lrotr(v, n)
+-#define ROTL64(v, n) _rotl64(v, n)
+-#define ROTR64(v, n) _rotr64(v, n)
+-
+-#endif
+-
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+-
+-#if (defined(ECRYPT_DEFAULT_SWAP) && !defined(ECRYPT_MACHINE_SWAP))
+-
+-#define ECRYPT_MACHINE_SWAP
+-
+-/*
+- * If you want to overwrite the default swap macros, put it here. And so on.
+- */
+-
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+diff --git a/src/crypto/salsa20/ecrypt-portable.h b/src/crypto/salsa20/ecrypt-portable.h
+deleted file mode 100644
+index 438a464..0000000
+--- a/src/crypto/salsa20/ecrypt-portable.h
++++ /dev/null
+@@ -1,310 +0,0 @@
+-/* ecrypt-portable.h */
+-
+-/*
+- * WARNING: the conversions defined below are implemented as macros,
+- * and should be used carefully. They should NOT be used with
+- * parameters which perform some action. E.g., the following two lines
+- * are not equivalent:
+- * 
+- *  1) ++x; y = ROTL32(x, n); 
+- *  2) y = ROTL32(++x, n);
+- */
+-
+-/*
+- * *** Please do not edit this file. ***
+- *
+- * The default macros can be overridden for specific architectures by
+- * editing 'ecrypt-machine.h'.
+- */
+-
+-#ifndef ECRYPT_PORTABLE
+-#define ECRYPT_PORTABLE
+-
+-#include "ecrypt-config.h"
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/*
+- * The following types are defined (if available):
+- *
+- * u8:  unsigned integer type, at least 8 bits
+- * u16: unsigned integer type, at least 16 bits
+- * u32: unsigned integer type, at least 32 bits
+- * u64: unsigned integer type, at least 64 bits
+- *
+- * s8, s16, s32, s64 -> signed counterparts of u8, u16, u32, u64
+- *
+- * The selection of minimum-width integer types is taken care of by
+- * 'ecrypt-config.h'. Note: to enable 64-bit types on 32-bit
+- * compilers, it might be necessary to switch from ISO C90 mode to ISO
+- * C99 mode (e.g., gcc -std=c99).
+- */
+-
+-#ifdef I8T
+-typedef signed I8T s8;
+-typedef unsigned I8T u8;
+-#endif
+-
+-#ifdef I16T
+-typedef signed I16T s16;
+-typedef unsigned I16T u16;
+-#endif
+-
+-#ifdef I32T
+-typedef signed I32T s32;
+-typedef unsigned I32T u32;
+-#endif
+-
+-#ifdef I64T
+-typedef signed I64T s64;
+-typedef unsigned I64T u64;
+-#endif
+-
+-/*
+- * The following macros are used to obtain exact-width results.
+- */
+-
+-#define U8V(v) ((u8)(v) & U8C(0xFF))
+-#define U16V(v) ((u16)(v) & U16C(0xFFFF))
+-#define U32V(v) ((u32)(v) & U32C(0xFFFFFFFF))
+-#define U64V(v) ((u64)(v) & U64C(0xFFFFFFFFFFFFFFFF))
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/*
+- * The following macros return words with their bits rotated over n
+- * positions to the left/right.
+- */
+-
+-#define ECRYPT_DEFAULT_ROT
+-
+-#define ROTL8(v, n) \
+-  (U8V((v) << (n)) | ((v) >> (8 - (n))))
+-
+-#define ROTL16(v, n) \
+-  (U16V((v) << (n)) | ((v) >> (16 - (n))))
+-
+-#define ROTL32(v, n) \
+-  (U32V((v) << (n)) | ((v) >> (32 - (n))))
+-
+-#define ROTL64(v, n) \
+-  (U64V((v) << (n)) | ((v) >> (64 - (n))))
+-
+-#define ROTR8(v, n) ROTL8(v, 8 - (n))
+-#define ROTR16(v, n) ROTL16(v, 16 - (n))
+-#define ROTR32(v, n) ROTL32(v, 32 - (n))
+-#define ROTR64(v, n) ROTL64(v, 64 - (n))
+-
+-#include "ecrypt-machine.h"
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/*
+- * The following macros return a word with bytes in reverse order.
+- */
+-
+-#define ECRYPT_DEFAULT_SWAP
+-
+-#define SWAP16(v) \
+-  ROTL16(v, 8)
+-
+-#define SWAP32(v) \
+-  ((ROTL32(v,  8) & U32C(0x00FF00FF)) | \
+-   (ROTL32(v, 24) & U32C(0xFF00FF00)))
+-
+-#ifdef ECRYPT_NATIVE64
+-#define SWAP64(v) \
+-  ((ROTL64(v,  8) & U64C(0x000000FF000000FF)) | \
+-   (ROTL64(v, 24) & U64C(0x0000FF000000FF00)) | \
+-   (ROTL64(v, 40) & U64C(0x00FF000000FF0000)) | \
+-   (ROTL64(v, 56) & U64C(0xFF000000FF000000)))
+-#else
+-#define SWAP64(v) \
+-  (((u64)SWAP32(U32V(v)) << 32) | (u64)SWAP32(U32V(v >> 32)))
+-#endif
+-
+-#include "ecrypt-machine.h"
+-
+-#define ECRYPT_DEFAULT_WTOW
+-
+-#ifdef ECRYPT_LITTLE_ENDIAN
+-#define U16TO16_LITTLE(v) (v)
+-#define U32TO32_LITTLE(v) (v)
+-#define U64TO64_LITTLE(v) (v)
+-
+-#define U16TO16_BIG(v) SWAP16(v)
+-#define U32TO32_BIG(v) SWAP32(v)
+-#define U64TO64_BIG(v) SWAP64(v)
+-#endif
+-
+-#ifdef ECRYPT_BIG_ENDIAN
+-#define U16TO16_LITTLE(v) SWAP16(v)
+-#define U32TO32_LITTLE(v) SWAP32(v)
+-#define U64TO64_LITTLE(v) SWAP64(v)
+-
+-#define U16TO16_BIG(v) (v)
+-#define U32TO32_BIG(v) (v)
+-#define U64TO64_BIG(v) (v)
+-#endif
+-
+-#include "ecrypt-machine.h"
+-
+-/*
+- * The following macros load words from an array of bytes with
+- * different types of endianness, and vice versa.
+- */
+-
+-#define ECRYPT_DEFAULT_BTOW
+-
+-#if (!defined(ECRYPT_UNKNOWN) && defined(ECRYPT_I8T_IS_BYTE))
+-
+-#define U8TO16_LITTLE(p) U16TO16_LITTLE(((u16*)(p))[0])
+-#define U8TO32_LITTLE(p) U32TO32_LITTLE(((u32*)(p))[0])
+-#define U8TO64_LITTLE(p) U64TO64_LITTLE(((u64*)(p))[0])
+-
+-#define U8TO16_BIG(p) U16TO16_BIG(((u16*)(p))[0])
+-#define U8TO32_BIG(p) U32TO32_BIG(((u32*)(p))[0])
+-#define U8TO64_BIG(p) U64TO64_BIG(((u64*)(p))[0])
+-
+-#define U16TO8_LITTLE(p, v) (((u16*)(p))[0] = U16TO16_LITTLE(v))
+-#define U32TO8_LITTLE(p, v) (((u32*)(p))[0] = U32TO32_LITTLE(v))
+-#define U64TO8_LITTLE(p, v) (((u64*)(p))[0] = U64TO64_LITTLE(v))
+-
+-#define U16TO8_BIG(p, v) (((u16*)(p))[0] = U16TO16_BIG(v))
+-#define U32TO8_BIG(p, v) (((u32*)(p))[0] = U32TO32_BIG(v))
+-#define U64TO8_BIG(p, v) (((u64*)(p))[0] = U64TO64_BIG(v))
+-
+-#else
+-
+-#define U8TO16_LITTLE(p) \
+-  (((u16)((p)[0])      ) | \
+-   ((u16)((p)[1]) <<  8))
+-
+-#define U8TO32_LITTLE(p) \
+-  (((u32)((p)[0])      ) | \
+-   ((u32)((p)[1]) <<  8) | \
+-   ((u32)((p)[2]) << 16) | \
+-   ((u32)((p)[3]) << 24))
+-
+-#ifdef ECRYPT_NATIVE64
+-#define U8TO64_LITTLE(p) \
+-  (((u64)((p)[0])      ) | \
+-   ((u64)((p)[1]) <<  8) | \
+-   ((u64)((p)[2]) << 16) | \
+-   ((u64)((p)[3]) << 24) | \
+-   ((u64)((p)[4]) << 32) | \
+-   ((u64)((p)[5]) << 40) | \
+-   ((u64)((p)[6]) << 48) | \
+-   ((u64)((p)[7]) << 56))
+-#else
+-#define U8TO64_LITTLE(p) \
+-  ((u64)U8TO32_LITTLE(p) | ((u64)U8TO32_LITTLE((p) + 4) << 32))
+-#endif
+-
+-#define U8TO16_BIG(p) \
+-  (((u16)((p)[0]) <<  8) | \
+-   ((u16)((p)[1])      ))
+-
+-#define U8TO32_BIG(p) \
+-  (((u32)((p)[0]) << 24) | \
+-   ((u32)((p)[1]) << 16) | \
+-   ((u32)((p)[2]) <<  8) | \
+-   ((u32)((p)[3])      ))
+-
+-#ifdef ECRYPT_NATIVE64
+-#define U8TO64_BIG(p) \
+-  (((u64)((p)[0]) << 56) | \
+-   ((u64)((p)[1]) << 48) | \
+-   ((u64)((p)[2]) << 40) | \
+-   ((u64)((p)[3]) << 32) | \
+-   ((u64)((p)[4]) << 24) | \
+-   ((u64)((p)[5]) << 16) | \
+-   ((u64)((p)[6]) <<  8) | \
+-   ((u64)((p)[7])      ))
+-#else
+-#define U8TO64_BIG(p) \
+-  (((u64)U8TO32_BIG(p) << 32) | (u64)U8TO32_BIG((p) + 4))
+-#endif
+-
+-#define U16TO8_LITTLE(p, v) \
+-  do { \
+-    (p)[0] = U8V((v)      ); \
+-    (p)[1] = U8V((v) >>  8); \
+-  } while (0)
+-
+-#define U32TO8_LITTLE(p, v) \
+-  do { \
+-    (p)[0] = U8V((v)      ); \
+-    (p)[1] = U8V((v) >>  8); \
+-    (p)[2] = U8V((v) >> 16); \
+-    (p)[3] = U8V((v) >> 24); \
+-  } while (0)
+-
+-#ifdef ECRYPT_NATIVE64
+-#define U64TO8_LITTLE(p, v) \
+-  do { \
+-    (p)[0] = U8V((v)      ); \
+-    (p)[1] = U8V((v) >>  8); \
+-    (p)[2] = U8V((v) >> 16); \
+-    (p)[3] = U8V((v) >> 24); \
+-    (p)[4] = U8V((v) >> 32); \
+-    (p)[5] = U8V((v) >> 40); \
+-    (p)[6] = U8V((v) >> 48); \
+-    (p)[7] = U8V((v) >> 56); \
+-  } while (0)
+-#else
+-#define U64TO8_LITTLE(p, v) \
+-  do { \
+-    U32TO8_LITTLE((p),     U32V((v)      )); \
+-    U32TO8_LITTLE((p) + 4, U32V((v) >> 32)); \
+-  } while (0)
+-#endif
+-
+-#define U16TO8_BIG(p, v) \
+-  do { \
+-    (p)[0] = U8V((v)      ); \
+-    (p)[1] = U8V((v) >>  8); \
+-  } while (0)
+-
+-#define U32TO8_BIG(p, v) \
+-  do { \
+-    (p)[0] = U8V((v) >> 24); \
+-    (p)[1] = U8V((v) >> 16); \
+-    (p)[2] = U8V((v) >>  8); \
+-    (p)[3] = U8V((v)      ); \
+-  } while (0)
+-
+-#ifdef ECRYPT_NATIVE64
+-#define U64TO8_BIG(p, v) \
+-  do { \
+-    (p)[0] = U8V((v) >> 56); \
+-    (p)[1] = U8V((v) >> 48); \
+-    (p)[2] = U8V((v) >> 40); \
+-    (p)[3] = U8V((v) >> 32); \
+-    (p)[4] = U8V((v) >> 24); \
+-    (p)[5] = U8V((v) >> 16); \
+-    (p)[6] = U8V((v) >>  8); \
+-    (p)[7] = U8V((v)      ); \
+-  } while (0)
+-#else
+-#define U64TO8_BIG(p, v) \
+-  do { \
+-    U32TO8_BIG((p),     U32V((v) >> 32)); \
+-    U32TO8_BIG((p) + 4, U32V((v)      )); \
+-  } while (0)
+-#endif
+-
+-#endif
+-
+-#include "ecrypt-machine.h"
+-
+-/* ------------------------------------------------------------------------- */
+-
+-#define AT_LEAST_ONE(n) (((n) < 1) ? 1 : (n))
+-
+-#define ALIGN(t, v, n) \
+-  union { t b[n]; MAXT l[AT_LEAST_ONE(n * sizeof(t) / sizeof(MAXT))]; } v
+-
+-/* ------------------------------------------------------------------------- */
+-
+-#endif
+diff --git a/src/crypto/salsa20/ecrypt-sync.h b/src/crypto/salsa20/ecrypt-sync.h
+deleted file mode 100644
+index 245793e..0000000
+--- a/src/crypto/salsa20/ecrypt-sync.h
++++ /dev/null
+@@ -1,287 +0,0 @@
+-/* ecrypt-sync.h */
+-
+-/*
+- * Header file for synchronous stream ciphers without authentication
+- * mechanism.
+- *
+- * *** Please only edit parts marked with "[edit]". ***
+- */
+-
+-#ifndef ECRYPT_SYNC
+-#define ECRYPT_SYNC
+-
+-#ifdef __cplusplus
+-extern "C" {
+-#endif 
+-
+-#include "ecrypt-portable.h"
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* Cipher parameters */
+-
+-/* 
+- * The name of your cipher.
+- */
+-#define ECRYPT_NAME "Salsa20"    /* [edit] */ 
+-#define ECRYPT_PROFILE "S!_H."
+-
+-/*
+- * Specify which key and IV sizes are supported by your cipher. A user
+- * should be able to enumerate the supported sizes by running the
+- * following code:
+- *
+- * for (i = 0; ECRYPT_KEYSIZE(i) <= ECRYPT_MAXKEYSIZE; ++i)
+- *   {
+- *     keysize = ECRYPT_KEYSIZE(i);
+- *
+- *     ...
+- *   }
+- *
+- * All sizes are in bits.
+- */
+-
+-#define ECRYPT_MAXKEYSIZE 256                 /* [edit] */
+-#define ECRYPT_KEYSIZE(i) (128 + (i)*128)     /* [edit] */
+-
+-#define ECRYPT_MAXIVSIZE 64                   /* [edit] */
+-#define ECRYPT_IVSIZE(i) (64 + (i)*64)        /* [edit] */
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* Data structures */
+-
+-/* 
+- * ECRYPT_ctx is the structure containing the representation of the
+- * internal state of your cipher. 
+- */
+-
+-typedef struct
+-{
+-  u32 input[16]; /* could be compressed */
+-  /* 
+-   * [edit]
+-   *
+-   * Put here all state variable needed during the encryption process.
+-   */
+-} ECRYPT_ctx;
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* Mandatory functions */
+-
+-/*
+- * Key and message independent initialization. This function will be
+- * called once when the program starts (e.g., to build expanded S-box
+- * tables).
+- */
+-void ECRYPT_init();
+-
+-/*
+- * Key setup. It is the user's responsibility to select the values of
+- * keysize and ivsize from the set of supported values specified
+- * above.
+- */
+-void ECRYPT_keysetup(
+-  ECRYPT_ctx* ctx, 
+-  const u8* key, 
+-  u32 keysize,                /* Key size in bits. */ 
+-  u32 ivsize);                /* IV size in bits. */ 
+-
+-/*
+- * IV setup. After having called ECRYPT_keysetup(), the user is
+- * allowed to call ECRYPT_ivsetup() different times in order to
+- * encrypt/decrypt different messages with the same key but different
+- * IV's.
+- */
+-void ECRYPT_ivsetup(
+-  ECRYPT_ctx* ctx, 
+-  const u8* iv);
+-
+-/*
+- * Encryption/decryption of arbitrary length messages.
+- *
+- * For efficiency reasons, the API provides two types of
+- * encrypt/decrypt functions. The ECRYPT_encrypt_bytes() function
+- * (declared here) encrypts byte strings of arbitrary length, while
+- * the ECRYPT_encrypt_blocks() function (defined later) only accepts
+- * lengths which are multiples of ECRYPT_BLOCKLENGTH.
+- * 
+- * The user is allowed to make multiple calls to
+- * ECRYPT_encrypt_blocks() to incrementally encrypt a long message,
+- * but he is NOT allowed to make additional encryption calls once he
+- * has called ECRYPT_encrypt_bytes() (unless he starts a new message
+- * of course). For example, this sequence of calls is acceptable:
+- *
+- * ECRYPT_keysetup();
+- *
+- * ECRYPT_ivsetup();
+- * ECRYPT_encrypt_blocks();
+- * ECRYPT_encrypt_blocks();
+- * ECRYPT_encrypt_bytes();
+- *
+- * ECRYPT_ivsetup();
+- * ECRYPT_encrypt_blocks();
+- * ECRYPT_encrypt_blocks();
+- *
+- * ECRYPT_ivsetup();
+- * ECRYPT_encrypt_bytes();
+- * 
+- * The following sequence is not:
+- *
+- * ECRYPT_keysetup();
+- * ECRYPT_ivsetup();
+- * ECRYPT_encrypt_blocks();
+- * ECRYPT_encrypt_bytes();
+- * ECRYPT_encrypt_blocks();
+- */
+-
+-void ECRYPT_encrypt_bytes(
+-  ECRYPT_ctx* ctx, 
+-  const u8* plaintext, 
+-  u8* ciphertext, 
+-  u32 msglen);                /* Message length in bytes. */ 
+-
+-void ECRYPT_decrypt_bytes(
+-  ECRYPT_ctx* ctx, 
+-  const u8* ciphertext, 
+-  u8* plaintext, 
+-  u32 msglen);                /* Message length in bytes. */ 
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* Optional features */
+-
+-/* 
+- * For testing purposes it can sometimes be useful to have a function
+- * which immediately generates keystream without having to provide it
+- * with a zero plaintext. If your cipher cannot provide this function
+- * (e.g., because it is not strictly a synchronous cipher), please
+- * reset the ECRYPT_GENERATES_KEYSTREAM flag.
+- */
+-
+-#define ECRYPT_GENERATES_KEYSTREAM
+-#ifdef ECRYPT_GENERATES_KEYSTREAM
+-
+-void ECRYPT_keystream_bytes(
+-  ECRYPT_ctx* ctx,
+-  u8* keystream,
+-  u32 length);                /* Length of keystream in bytes. */
+-
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+-
+-/* Optional optimizations */
+-
+-/* 
+- * By default, the functions in this section are implemented using
+- * calls to functions declared above. However, you might want to
+- * implement them differently for performance reasons.
+- */
+-
+-/*
+- * All-in-one encryption/decryption of (short) packets.
+- *
+- * The default definitions of these functions can be found in
+- * "ecrypt-sync.c". If you want to implement them differently, please
+- * undef the ECRYPT_USES_DEFAULT_ALL_IN_ONE flag.
+- */
+-#define ECRYPT_USES_DEFAULT_ALL_IN_ONE        /* [edit] */
+-
+-void ECRYPT_encrypt_packet(
+-  ECRYPT_ctx* ctx, 
+-  const u8* iv,
+-  const u8* plaintext, 
+-  u8* ciphertext, 
+-  u32 msglen);
+-
+-void ECRYPT_decrypt_packet(
+-  ECRYPT_ctx* ctx, 
+-  const u8* iv,
+-  const u8* ciphertext, 
+-  u8* plaintext, 
+-  u32 msglen);
+-
+-/*
+- * Encryption/decryption of blocks.
+- * 
+- * By default, these functions are defined as macros. If you want to
+- * provide a different implementation, please undef the
+- * ECRYPT_USES_DEFAULT_BLOCK_MACROS flag and implement the functions
+- * declared below.
+- */
+-
+-#define ECRYPT_BLOCKLENGTH 64                  /* [edit] */
+-
+-#define ECRYPT_USES_DEFAULT_BLOCK_MACROS      /* [edit] */
+-#ifdef ECRYPT_USES_DEFAULT_BLOCK_MACROS
+-
+-#define ECRYPT_encrypt_blocks(ctx, plaintext, ciphertext, blocks)  \
+-  ECRYPT_encrypt_bytes(ctx, plaintext, ciphertext,                 \
+-    (blocks) * ECRYPT_BLOCKLENGTH)
+-
+-#define ECRYPT_decrypt_blocks(ctx, ciphertext, plaintext, blocks)  \
+-  ECRYPT_decrypt_bytes(ctx, ciphertext, plaintext,                 \
+-    (blocks) * ECRYPT_BLOCKLENGTH)
+-
+-#ifdef ECRYPT_GENERATES_KEYSTREAM
+-
+-#define ECRYPT_keystream_blocks(ctx, keystream, blocks)            \
+-  ECRYPT_keystream_bytes(ctx, keystream,                        \
+-    (blocks) * ECRYPT_BLOCKLENGTH)
+-
+-#endif
+-
+-#else
+-
+-void ECRYPT_encrypt_blocks(
+-  ECRYPT_ctx* ctx, 
+-  const u8* plaintext, 
+-  u8* ciphertext, 
+-  u32 blocks);                /* Message length in blocks. */ 
+-
+-void ECRYPT_decrypt_blocks(
+-  ECRYPT_ctx* ctx, 
+-  const u8* ciphertext, 
+-  u8* plaintext, 
+-  u32 blocks);                /* Message length in blocks. */ 
+-
+-#ifdef ECRYPT_GENERATES_KEYSTREAM
+-
+-void ECRYPT_keystream_blocks(
+-  ECRYPT_ctx* ctx,
+-  const u8* keystream,
+-  u32 blocks);                /* Keystream length in blocks. */ 
+-
+-#endif
+-
+-#endif
+-
+-/*
+- * If your cipher can be implemented in different ways, you can use
+- * the ECRYPT_VARIANT parameter to allow the user to choose between
+- * them at compile time (e.g., gcc -DECRYPT_VARIANT=3 ...). Please
+- * only use this possibility if you really think it could make a
+- * significant difference and keep the number of variants
+- * (ECRYPT_MAXVARIANT) as small as possible (definitely not more than
+- * 10). Note also that all variants should have exactly the same
+- * external interface (i.e., the same ECRYPT_BLOCKLENGTH, etc.). 
+- */
+-#define ECRYPT_MAXVARIANT 1                   /* [edit] */
+-
+-#ifndef ECRYPT_VARIANT
+-#define ECRYPT_VARIANT 1
+-#endif
+-
+-#if (ECRYPT_VARIANT > ECRYPT_MAXVARIANT)
+-#error this variant does not exist
+-#endif
+-
+-/* ------------------------------------------------------------------------- */
+-
+-#ifdef __cplusplus
+-}
+-#endif
+-
+-#endif
+diff --git a/src/crypto/salsa20/salsa20.c b/src/crypto/salsa20/salsa20.c
+deleted file mode 100644
+index 74f806c..0000000
+--- a/src/crypto/salsa20/salsa20.c
++++ /dev/null
+@@ -1,133 +0,0 @@
+-/*
+-salsa20-ref.c version 20051118
+-D. J. Bernstein
+-Public domain.
+-*/
+-
+-#include "ecrypt-sync.h"
+-
+-#define ROTATE(v,c) (ROTL32(v,c))
+-#define XOR(v,w) ((v) ^ (w))
+-#define PLUS(v,w) (U32V((v) + (w)))
+-#define PLUSONE(v) (PLUS((v),1))
+-
+-static void salsa20_wordtobyte(u8 output[64],const u32 input[16])
+-{
+-  u32 x[16];
+-  int i;
+-
+-  for (i = 0;i < 16;++i) x[i] = input[i];
+-  for (i = 20;i > 0;i -= 2) {
+-    x[ 4] = XOR(x[ 4],ROTATE(PLUS(x[ 0],x[12]), 7));
+-    x[ 8] = XOR(x[ 8],ROTATE(PLUS(x[ 4],x[ 0]), 9));
+-    x[12] = XOR(x[12],ROTATE(PLUS(x[ 8],x[ 4]),13));
+-    x[ 0] = XOR(x[ 0],ROTATE(PLUS(x[12],x[ 8]),18));
+-    x[ 9] = XOR(x[ 9],ROTATE(PLUS(x[ 5],x[ 1]), 7));
+-    x[13] = XOR(x[13],ROTATE(PLUS(x[ 9],x[ 5]), 9));
+-    x[ 1] = XOR(x[ 1],ROTATE(PLUS(x[13],x[ 9]),13));
+-    x[ 5] = XOR(x[ 5],ROTATE(PLUS(x[ 1],x[13]),18));
+-    x[14] = XOR(x[14],ROTATE(PLUS(x[10],x[ 6]), 7));
+-    x[ 2] = XOR(x[ 2],ROTATE(PLUS(x[14],x[10]), 9));
+-    x[ 6] = XOR(x[ 6],ROTATE(PLUS(x[ 2],x[14]),13));
+-    x[10] = XOR(x[10],ROTATE(PLUS(x[ 6],x[ 2]),18));
+-    x[ 3] = XOR(x[ 3],ROTATE(PLUS(x[15],x[11]), 7));
+-    x[ 7] = XOR(x[ 7],ROTATE(PLUS(x[ 3],x[15]), 9));
+-    x[11] = XOR(x[11],ROTATE(PLUS(x[ 7],x[ 3]),13));
+-    x[15] = XOR(x[15],ROTATE(PLUS(x[11],x[ 7]),18));
+-    x[ 1] = XOR(x[ 1],ROTATE(PLUS(x[ 0],x[ 3]), 7));
+-    x[ 2] = XOR(x[ 2],ROTATE(PLUS(x[ 1],x[ 0]), 9));
+-    x[ 3] = XOR(x[ 3],ROTATE(PLUS(x[ 2],x[ 1]),13));
+-    x[ 0] = XOR(x[ 0],ROTATE(PLUS(x[ 3],x[ 2]),18));
+-    x[ 6] = XOR(x[ 6],ROTATE(PLUS(x[ 5],x[ 4]), 7));
+-    x[ 7] = XOR(x[ 7],ROTATE(PLUS(x[ 6],x[ 5]), 9));
+-    x[ 4] = XOR(x[ 4],ROTATE(PLUS(x[ 7],x[ 6]),13));
+-    x[ 5] = XOR(x[ 5],ROTATE(PLUS(x[ 4],x[ 7]),18));
+-    x[11] = XOR(x[11],ROTATE(PLUS(x[10],x[ 9]), 7));
+-    x[ 8] = XOR(x[ 8],ROTATE(PLUS(x[11],x[10]), 9));
+-    x[ 9] = XOR(x[ 9],ROTATE(PLUS(x[ 8],x[11]),13));
+-    x[10] = XOR(x[10],ROTATE(PLUS(x[ 9],x[ 8]),18));
+-    x[12] = XOR(x[12],ROTATE(PLUS(x[15],x[14]), 7));
+-    x[13] = XOR(x[13],ROTATE(PLUS(x[12],x[15]), 9));
+-    x[14] = XOR(x[14],ROTATE(PLUS(x[13],x[12]),13));
+-    x[15] = XOR(x[15],ROTATE(PLUS(x[14],x[13]),18));
+-  }
+-  for (i = 0;i < 16;++i) x[i] = PLUS(x[i],input[i]);
+-  for (i = 0;i < 16;++i) U32TO8_LITTLE(output + 4 * i,x[i]);
+-}
+-
+-void ECRYPT_init(void)
+-{
+-  return;
+-}
+-
+-static const char sigma[16] = "expand 32-byte k";
+-static const char tau[16] = "expand 16-byte k";
+-
+-void ECRYPT_keysetup(ECRYPT_ctx *x,const u8 *k,u32 kbits,u32 ivbits)
+-{
+-  (void)ivbits;
+-  const char *constants;
+-
+-  x->input[1] = U8TO32_LITTLE(k + 0);
+-  x->input[2] = U8TO32_LITTLE(k + 4);
+-  x->input[3] = U8TO32_LITTLE(k + 8);
+-  x->input[4] = U8TO32_LITTLE(k + 12);
+-  if (kbits == 256) { /* recommended */
+-    k += 16;
+-    constants = sigma;
+-  } else { /* kbits == 128 */
+-    constants = tau;
+-  }
+-  x->input[11] = U8TO32_LITTLE(k + 0);
+-  x->input[12] = U8TO32_LITTLE(k + 4);
+-  x->input[13] = U8TO32_LITTLE(k + 8);
+-  x->input[14] = U8TO32_LITTLE(k + 12);
+-  x->input[0] = U8TO32_LITTLE(constants + 0);
+-  x->input[5] = U8TO32_LITTLE(constants + 4);
+-  x->input[10] = U8TO32_LITTLE(constants + 8);
+-  x->input[15] = U8TO32_LITTLE(constants + 12);
+-}
+-
+-void ECRYPT_ivsetup(ECRYPT_ctx *x,const u8 *iv)
+-{
+-  x->input[6] = U8TO32_LITTLE(iv + 0);
+-  x->input[7] = U8TO32_LITTLE(iv + 4);
+-  x->input[8] = 0;
+-  x->input[9] = 0;
+-}
+-
+-void ECRYPT_encrypt_bytes(ECRYPT_ctx *x,const u8 *m,u8 *c,u32 bytes)
+-{
+-  u8 output[64];
+-  u32 i;
+-
+-  if (!bytes) return;
+-  for (;;) {
+-    salsa20_wordtobyte(output,x->input);
+-    x->input[8] = PLUSONE(x->input[8]);
+-    if (!x->input[8]) {
+-      x->input[9] = PLUSONE(x->input[9]);
+-      /* stopping at 2^70 bytes per nonce is user's responsibility */
+-    }
+-    if (bytes <= 64) {
+-      for (i = 0;i < bytes;++i) c[i] = m[i] ^ output[i];
+-      return;
+-    }
+-    for (i = 0;i < 64;++i) c[i] = m[i] ^ output[i];
+-    bytes -= 64;
+-    c += 64;
+-    m += 64;
+-  }
+-}
+-
+-void ECRYPT_decrypt_bytes(ECRYPT_ctx *x,const u8 *c,u8 *m,u32 bytes)
+-{
+-  ECRYPT_encrypt_bytes(x,c,m,bytes);
+-}
+-
+-void ECRYPT_keystream_bytes(ECRYPT_ctx *x,u8 *stream,u32 bytes)
+-{
+-  u32 i;
+-  for (i = 0;i < bytes;++i) stream[i] = 0;
+-  ECRYPT_encrypt_bytes(x,stream,stream,bytes);
+-}
+diff --git a/src/format/KeePass1Reader.cpp b/src/format/KeePass1Reader.cpp
+index 0e6b4a9..89775b5 100644
+--- a/src/format/KeePass1Reader.cpp
++++ b/src/format/KeePass1Reader.cpp
+@@ -49,9 +49,9 @@ private:
+ KeePass1Reader::KeePass1Reader()
+-    : m_db(Q_NULLPTR)
+-    , m_tmpParent(Q_NULLPTR)
+-    , m_device(Q_NULLPTR)
++    : m_db(nullptr)
++    , m_tmpParent(nullptr)
++    , m_device(nullptr)
+     , m_encryptionFlags(0)
+     , m_transformRounds(0)
+     , m_error(false)
+@@ -72,16 +72,16 @@ Database* KeePass1Reader::readDatabase(QIODevice* device, const QString& passwor
+         if (keyfileData.isEmpty()) {
+             raiseError(tr("Unable to read keyfile.").append("\n").append(keyfileDevice->errorString()));
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         if (!keyfileDevice->seek(0)) {
+             raiseError(tr("Unable to read keyfile.").append("\n").append(keyfileDevice->errorString()));
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         if (!newFileKey.load(keyfileDevice)) {
+             raiseError(tr("Unable to read keyfile.").append("\n").append(keyfileDevice->errorString()));
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+     }
+@@ -96,72 +96,72 @@ Database* KeePass1Reader::readDatabase(QIODevice* device, const QString& passwor
+     quint32 signature1 = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok || signature1 != KeePass1::SIGNATURE_1) {
+         raiseError(tr("Not a KeePass database."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     quint32 signature2 = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok || signature2 != KeePass1::SIGNATURE_2) {
+         raiseError(tr("Not a KeePass database."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     m_encryptionFlags = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok || !(m_encryptionFlags & KeePass1::Rijndael || m_encryptionFlags & KeePass1::Twofish)) {
+         raiseError(tr("Unsupported encryption algorithm."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     quint32 version = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok || (version & KeePass1::FILE_VERSION_CRITICAL_MASK)
+             != (KeePass1::FILE_VERSION & KeePass1::FILE_VERSION_CRITICAL_MASK)) {
+         raiseError(tr("Unsupported KeePass database version."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     m_masterSeed = m_device->read(16);
+     if (m_masterSeed.size() != 16) {
+         raiseError("Unable to read master seed");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     m_encryptionIV = m_device->read(16);
+     if (m_encryptionIV.size() != 16) {
+         raiseError("Unable to read encryption IV");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     quint32 numGroups = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok) {
+         raiseError("Invalid number of groups");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     quint32 numEntries = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok) {
+         raiseError("Invalid number of entries");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     m_contentHashHeader = m_device->read(32);
+     if (m_contentHashHeader.size() != 32) {
+         raiseError("Invalid content hash size");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     m_transformSeed = m_device->read(32);
+     if (m_transformSeed.size() != 32) {
+         raiseError("Invalid transform seed size");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     m_transformRounds = Endian::readUInt32(m_device, KeePass1::BYTEORDER, &ok);
+     if (!ok) {
+         raiseError("Invalid number of transform rounds");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     if (!m_db->setTransformRounds(m_transformRounds)) {
+         raiseError(tr("Unable to calculate master key"));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     qint64 contentPos = m_device->pos();
+@@ -169,14 +169,14 @@ Database* KeePass1Reader::readDatabase(QIODevice* device, const QString& passwor
+     QScopedPointer<SymmetricCipherStream> cipherStream(testKeys(password, keyfileData, contentPos));
+     if (!cipherStream) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QList<Group*> groups;
+     for (quint32 i = 0; i < numGroups; i++) {
+         Group* group = readGroup(cipherStream.data());
+         if (!group) {
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         groups.append(group);
+     }
+@@ -185,14 +185,14 @@ Database* KeePass1Reader::readDatabase(QIODevice* device, const QString& passwor
+     for (quint32 i = 0; i < numEntries; i++) {
+         Entry* entry = readEntry(cipherStream.data());
+         if (!entry) {
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         entries.append(entry);
+     }
+     if (!constructGroupTree(groups)) {
+         raiseError("Unable to construct group tree");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     Q_FOREACH (Entry* entry, entries) {
+@@ -243,7 +243,7 @@ Database* KeePass1Reader::readDatabase(QIODevice* device, const QString& passwor
+     if (!db->setKey(key)) {
+         raiseError(tr("Unable to calculate master key"));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     return db.take();
+@@ -257,7 +257,7 @@ Database* KeePass1Reader::readDatabase(QIODevice* device, const QString& passwor
+         keyFile.reset(new QFile(keyfileName));
+         if (!keyFile->open(QFile::ReadOnly)) {
+             raiseError(keyFile->errorString());
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+     }
+@@ -272,14 +272,14 @@ Database* KeePass1Reader::readDatabase(const QString& filename, const QString& p
+     QFile dbFile(filename);
+     if (!dbFile.open(QFile::ReadOnly)) {
+         raiseError(dbFile.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     Database* db = readDatabase(&dbFile, password, keyfileName);
+     if (dbFile.error() != QFile::NoError) {
+         raiseError(dbFile.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     return db;
+@@ -337,7 +337,7 @@ SymmetricCipherStream* KeePass1Reader::testKeys(const QString& password, const Q
+         QByteArray finalKey = key(passwordData, keyfileData);
+         if (finalKey.isEmpty()) {
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         if (m_encryptionFlags & KeePass1::Rijndael) {
+             cipherStream.reset(new SymmetricCipherStream(m_device, SymmetricCipher::Aes256,
+@@ -350,11 +350,11 @@ SymmetricCipherStream* KeePass1Reader::testKeys(const QString& password, const Q
+         if (!cipherStream->init(finalKey, m_encryptionIV)) {
+             raiseError(cipherStream->errorString());
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         if (!cipherStream->open(QIODevice::ReadOnly)) {
+             raiseError(cipherStream->errorString());
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         bool success = verifyKey(cipherStream.data());
+@@ -368,7 +368,7 @@ SymmetricCipherStream* KeePass1Reader::testKeys(const QString& password, const Q
+             }
+             raiseError(msg);
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         cipherStream->open(QIODevice::ReadOnly);
+@@ -442,19 +442,19 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         quint16 fieldType = Endian::readUInt16(cipherStream, KeePass1::BYTEORDER, &ok);
+         if (!ok) {
+             raiseError("Invalid group field type number");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         int fieldSize = static_cast<int>(Endian::readUInt32(cipherStream, KeePass1::BYTEORDER, &ok));
+         if (!ok) {
+             raiseError("Invalid group field size");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         QByteArray fieldData = cipherStream->read(fieldSize);
+         if (fieldData.size() != fieldSize) {
+             raiseError("Read group field data doesn't match size");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         switch (fieldType) {
+@@ -464,7 +464,7 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         case 0x0001:
+             if (fieldSize != 4) {
+                 raiseError("Incorrect group id field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             groupId = Endian::bytesToUInt32(fieldData, KeePass1::BYTEORDER);
+             groupIdSet = true;
+@@ -476,7 +476,7 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         {
+             if (fieldSize != 5) {
+                 raiseError("Incorrect group creation time field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             QDateTime dateTime = dateFromPackedStruct(fieldData);
+             if (dateTime.isValid()) {
+@@ -488,7 +488,7 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         {
+             if (fieldSize != 5) {
+                 raiseError("Incorrect group modification time field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             QDateTime dateTime = dateFromPackedStruct(fieldData);
+             if (dateTime.isValid()) {
+@@ -523,7 +523,7 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         {
+             if (fieldSize != 4) {
+                 raiseError("Incorrect group icon field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             quint32 iconNumber = Endian::bytesToUInt32(fieldData, KeePass1::BYTEORDER);
+             group->setIcon(iconNumber);
+@@ -533,7 +533,7 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         {
+             if (fieldSize != 2) {
+                 raiseError("Incorrect group level field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             groupLevel = Endian::bytesToUInt16(fieldData, KeePass1::BYTEORDER);
+             groupLevelSet = true;
+@@ -548,13 +548,13 @@ Group* KeePass1Reader::readGroup(QIODevice* cipherStream)
+         default:
+             // invalid field
+             raiseError("Invalid group field type");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+     } while (!reachedEnd);
+     if (!groupIdSet || !groupLevelSet) {
+         raiseError("Missing group id or level");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     group->setUuid(Uuid::random());
+@@ -580,19 +580,19 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         quint16 fieldType = Endian::readUInt16(cipherStream, KeePass1::BYTEORDER, &ok);
+         if (!ok) {
+             raiseError("Missing entry field type number");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         int fieldSize = static_cast<int>(Endian::readUInt32(cipherStream, KeePass1::BYTEORDER, &ok));
+         if (!ok) {
+             raiseError("Invalid entry field size");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         QByteArray fieldData = cipherStream->read(fieldSize);
+         if (fieldData.size() != fieldSize) {
+             raiseError("Read entry field data doesn't match size");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         switch (fieldType) {
+@@ -602,7 +602,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         case 0x0001:
+             if (fieldSize != 16) {
+                 raiseError("Invalid entry uuid field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             m_entryUuids.insert(fieldData, entry.data());
+             break;
+@@ -610,7 +610,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         {
+             if (fieldSize != 4) {
+                 raiseError("Invalid entry group id field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             quint32 groupId = Endian::bytesToUInt32(fieldData, KeePass1::BYTEORDER);
+             m_entryGroupIds.insert(entry.data(), groupId);
+@@ -620,7 +620,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         {
+             if (fieldSize != 4) {
+                 raiseError("Invalid entry icon field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             quint32 iconNumber = Endian::bytesToUInt32(fieldData, KeePass1::BYTEORDER);
+             entry->setIcon(iconNumber);
+@@ -645,7 +645,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         {
+             if (fieldSize != 5) {
+                 raiseError("Invalid entry creation time field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             QDateTime dateTime = dateFromPackedStruct(fieldData);
+             if (dateTime.isValid()) {
+@@ -657,7 +657,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         {
+             if (fieldSize != 5) {
+                 raiseError("Invalid entry modification time field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             QDateTime dateTime = dateFromPackedStruct(fieldData);
+             if (dateTime.isValid()) {
+@@ -669,7 +669,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         {
+             if (fieldSize != 5) {
+                 raiseError("Invalid entry creation time field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             QDateTime dateTime = dateFromPackedStruct(fieldData);
+             if (dateTime.isValid()) {
+@@ -681,7 +681,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         {
+             if (fieldSize != 5) {
+                 raiseError("Invalid entry expiry time field size");
+-                return Q_NULLPTR;
++                return nullptr;
+             }
+             QDateTime dateTime = dateFromPackedStruct(fieldData);
+             if (dateTime.isValid()) {
+@@ -704,7 +704,7 @@ Entry* KeePass1Reader::readEntry(QIODevice* cipherStream)
+         default:
+             // invalid field
+             raiseError("Invalid entry field type");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+     } while (!reachedEnd);
+diff --git a/src/format/KeePass2Reader.cpp b/src/format/KeePass2Reader.cpp
+index d1ca9ed..00ebc07 100644
+--- a/src/format/KeePass2Reader.cpp
++++ b/src/format/KeePass2Reader.cpp
+@@ -34,12 +34,12 @@
+ #include "streams/SymmetricCipherStream.h"
+ KeePass2Reader::KeePass2Reader()
+-    : m_device(Q_NULLPTR)
+-    , m_headerStream(Q_NULLPTR)
++    : m_device(nullptr)
++    , m_headerStream(nullptr)
+     , m_error(false)
+     , m_headerEnd(false)
+     , m_saveXml(false)
+-    , m_db(Q_NULLPTR)
++    , m_db(nullptr)
+ {
+ }
+@@ -67,7 +67,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+     quint32 signature1 = Endian::readUInt32(m_headerStream, KeePass2::BYTEORDER, &ok);
+     if (!ok || signature1 != KeePass2::SIGNATURE_1) {
+         raiseError(tr("Not a KeePass database."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     quint32 signature2 = Endian::readUInt32(m_headerStream, KeePass2::BYTEORDER, &ok);
+@@ -76,11 +76,11 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+                       "You can import it by clicking on Database > 'Import KeePass 1 database'.\n"
+                       "This is a one-way migration. You won't be able to open the imported "
+                       "database with the old KeePassX 0.4 version."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     else if (!ok || signature2 != KeePass2::SIGNATURE_2) {
+         raiseError(tr("Not a KeePass database."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     quint32 version = Endian::readUInt32(m_headerStream, KeePass2::BYTEORDER, &ok)
+@@ -88,7 +88,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+     quint32 maxVersion = KeePass2::FILE_VERSION & KeePass2::FILE_VERSION_CRITICAL_MASK;
+     if (!ok || (version < KeePass2::FILE_VERSION_MIN) || (version > maxVersion)) {
+         raiseError(tr("Unsupported KeePass database version."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     while (readHeaderField() && !hasError()) {
+@@ -97,7 +97,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+     headerStream.close();
+     if (hasError()) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     // check if all required headers were present
+@@ -105,12 +105,12 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+             || m_streamStartBytes.isEmpty() || m_protectedStreamKey.isEmpty()
+             || m_db->cipher().isNull()) {
+         raiseError("missing database headers");
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     if (!m_db->setKey(key, m_transformSeed, false)) {
+         raiseError(tr("Unable to calculate master key"));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     CryptoHash hash(CryptoHash::Sha256);
+@@ -122,24 +122,24 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+                                        SymmetricCipher::Cbc, SymmetricCipher::Decrypt);
+     if (!cipherStream.init(finalKey, m_encryptionIV)) {
+         raiseError(cipherStream.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     if (!cipherStream.open(QIODevice::ReadOnly)) {
+         raiseError(cipherStream.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QByteArray realStart = cipherStream.read(32);
+     if (realStart != m_streamStartBytes) {
+         raiseError(tr("Wrong key or database file is corrupt."));
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     HashedBlockStream hashedStream(&cipherStream);
+     if (!hashedStream.open(QIODevice::ReadOnly)) {
+         raiseError(hashedStream.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QIODevice* xmlDevice;
+@@ -153,7 +153,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+         ioCompressor->setStreamFormat(QtIOCompressor::GzipFormat);
+         if (!ioCompressor->open(QIODevice::ReadOnly)) {
+             raiseError(ioCompressor->errorString());
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+         xmlDevice = ioCompressor.data();
+     }
+@@ -161,7 +161,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+     KeePass2RandomStream randomStream;
+     if (!randomStream.init(m_protectedStreamKey)) {
+         raiseError(randomStream.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QScopedPointer<QBuffer> buffer;
+@@ -182,7 +182,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+             return db.take();
+         }
+         else {
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+     }
+@@ -192,7 +192,7 @@ Database* KeePass2Reader::readDatabase(QIODevice* device, const CompositeKey& ke
+         QByteArray headerHash = CryptoHash::hash(headerStream.storedData(), CryptoHash::Sha256);
+         if (headerHash != xmlReader.headerHash()) {
+             raiseError("Head doesn't match hash");
+-            return Q_NULLPTR;
++            return nullptr;
+         }
+     }
+@@ -204,14 +204,14 @@ Database* KeePass2Reader::readDatabase(const QString& filename, const CompositeK
+     QFile file(filename);
+     if (!file.open(QFile::ReadOnly)) {
+         raiseError(file.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QScopedPointer<Database> db(readDatabase(&file, key));
+     if (file.error() != QFile::NoError) {
+         raiseError(file.errorString());
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     return db.take();
+diff --git a/src/format/KeePass2Repair.cpp b/src/format/KeePass2Repair.cpp
+index f435a7d..81ada2f 100644
+--- a/src/format/KeePass2Repair.cpp
++++ b/src/format/KeePass2Repair.cpp
+@@ -25,13 +25,13 @@
+ #include "format/KeePass2XmlReader.h"
+ KeePass2Repair::KeePass2Repair()
+-    : m_db(Q_NULLPTR)
++    : m_db(nullptr)
+ {
+ }
+ KeePass2Repair::RepairResult KeePass2Repair::repairDatabase(QIODevice* device, const CompositeKey& key)
+ {
+-    m_db = Q_NULLPTR;
++    m_db = nullptr;
+     m_errorStr.clear();
+     KeePass2Reader reader;
+diff --git a/src/format/KeePass2XmlReader.cpp b/src/format/KeePass2XmlReader.cpp
+index 815cbf9..40087a6 100644
+--- a/src/format/KeePass2XmlReader.cpp
++++ b/src/format/KeePass2XmlReader.cpp
+@@ -31,10 +31,10 @@
+ typedef QPair<QString, QString> StringPair;
+ KeePass2XmlReader::KeePass2XmlReader()
+-    : m_randomStream(Q_NULLPTR)
+-    , m_db(Q_NULLPTR)
+-    , m_meta(Q_NULLPTR)
+-    , m_tmpParent(Q_NULLPTR)
++    : m_randomStream(nullptr)
++    , m_db(nullptr)
++    , m_meta(nullptr)
++    , m_tmpParent(nullptr)
+     , m_error(false)
+     , m_strictMode(false)
+ {
+@@ -1045,7 +1045,7 @@ QDateTime KeePass2XmlReader::readDateTime()
+             raiseError("Invalid date time value");
+         }
+         else {
+-            dt = Tools::currentDateTimeUtc();
++            dt = QDateTime::currentDateTimeUtc();
+         }
+     }
+@@ -1146,7 +1146,7 @@ QByteArray KeePass2XmlReader::readCompressedBinary()
+ Group* KeePass2XmlReader::getGroup(const Uuid& uuid)
+ {
+     if (uuid.isNull()) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     if (m_groups.contains(uuid)) {
+@@ -1165,7 +1165,7 @@ Group* KeePass2XmlReader::getGroup(const Uuid& uuid)
+ Entry* KeePass2XmlReader::getEntry(const Uuid& uuid)
+ {
+     if (uuid.isNull()) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     if (m_entries.contains(uuid)) {
+diff --git a/src/format/KeePass2XmlReader.h b/src/format/KeePass2XmlReader.h
+index ca311b0..d2e0e00 100644
+--- a/src/format/KeePass2XmlReader.h
++++ b/src/format/KeePass2XmlReader.h
+@@ -25,7 +25,6 @@
+ #include <QPair>
+ #include <QXmlStreamReader>
+-#include "core/Global.h"
+ #include "core/TimeInfo.h"
+ #include "core/Uuid.h"
+@@ -42,7 +41,7 @@ class KeePass2XmlReader
+ public:
+     KeePass2XmlReader();
+     Database* readDatabase(QIODevice* device);
+-    void readDatabase(QIODevice* device, Database* db, KeePass2RandomStream* randomStream = Q_NULLPTR);
++    void readDatabase(QIODevice* device, Database* db, KeePass2RandomStream* randomStream = nullptr);
+     Database* readDatabase(const QString& filename);
+     bool hasError();
+     QString errorString();
+diff --git a/src/format/KeePass2XmlWriter.cpp b/src/format/KeePass2XmlWriter.cpp
+index 1eb8dc1..7fd03cc 100644
+--- a/src/format/KeePass2XmlWriter.cpp
++++ b/src/format/KeePass2XmlWriter.cpp
+@@ -25,9 +25,9 @@
+ #include "streams/QtIOCompressor"
+ KeePass2XmlWriter::KeePass2XmlWriter()
+-    : m_db(Q_NULLPTR)
+-    , m_meta(Q_NULLPTR)
+-    , m_randomStream(Q_NULLPTR)
++    : m_db(nullptr)
++    , m_meta(nullptr)
++    , m_randomStream(nullptr)
+     , m_error(false)
+ {
+     m_xml.setAutoFormatting(true);
+@@ -58,11 +58,9 @@ void KeePass2XmlWriter::writeDatabase(QIODevice* device, Database* db, KeePass2R
+     m_xml.writeEndDocument();
+-#if QT_VERSION >= QT_VERSION_CHECK(4, 8, 0)
+     if (m_xml.hasError()) {
+         raiseError(device->errorString());
+     }
+-#endif
+ }
+ void KeePass2XmlWriter::writeDatabase(const QString& filename, Database* db)
+diff --git a/src/format/KeePass2XmlWriter.h b/src/format/KeePass2XmlWriter.h
+index 48dde6a..23e148d 100644
+--- a/src/format/KeePass2XmlWriter.h
++++ b/src/format/KeePass2XmlWriter.h
+@@ -36,7 +36,7 @@ class KeePass2XmlWriter
+ {
+ public:
+     KeePass2XmlWriter();
+-    void writeDatabase(QIODevice* device, Database* db, KeePass2RandomStream* randomStream = Q_NULLPTR,
++    void writeDatabase(QIODevice* device, Database* db, KeePass2RandomStream* randomStream = nullptr,
+                        const QByteArray& headerHash = QByteArray());
+     void writeDatabase(const QString& filename, Database* db);
+     bool hasError();
+diff --git a/src/gui/AboutDialog.h b/src/gui/AboutDialog.h
+index 1436aee..08db6c8 100644
+--- a/src/gui/AboutDialog.h
++++ b/src/gui/AboutDialog.h
+@@ -21,8 +21,6 @@
+ #include <QDialog>
+ #include <QScopedPointer>
+-#include "core/Global.h"
+-
+ namespace Ui {
+     class AboutDialog;
+ }
+@@ -32,7 +30,7 @@ class AboutDialog : public QDialog
+     Q_OBJECT
+ public:
+-    explicit AboutDialog(QWidget* parent = Q_NULLPTR);
++    explicit AboutDialog(QWidget* parent = nullptr);
+     ~AboutDialog();
+ private:
+diff --git a/src/gui/Application.cpp b/src/gui/Application.cpp
+index ae6931f..70550c5 100644
+--- a/src/gui/Application.cpp
++++ b/src/gui/Application.cpp
+@@ -18,14 +18,38 @@
+ #include "Application.h"
++#include <QAbstractNativeEventFilter>
+ #include <QFileOpenEvent>
+ #include "autotype/AutoType.h"
++#if defined(Q_OS_UNIX) && !defined(Q_OS_OSX)
++class XcbEventFilter : public QAbstractNativeEventFilter
++{
++public:
++    bool nativeEventFilter(const QByteArray& eventType, void* message, long* result) override
++    {
++        Q_UNUSED(result)
++
++        if (eventType == QByteArrayLiteral("xcb_generic_event_t")) {
++            int retCode = autoType()->callEventFilter(message);
++            if (retCode == 1) {
++                return true;
++            }
++        }
++
++        return false;
++    }
++};
++#endif
++
+ Application::Application(int& argc, char** argv)
+     : QApplication(argc, argv)
+-    , m_mainWindow(Q_NULLPTR)
++    , m_mainWindow(nullptr)
+ {
++#if defined(Q_OS_UNIX) && !defined(Q_OS_OSX)
++    installNativeEventFilter(new XcbEventFilter());
++#endif
+ }
+ void Application::setMainWindow(QWidget* mainWindow)
+@@ -53,19 +77,3 @@ bool Application::event(QEvent* event)
+     return QApplication::event(event);
+ }
+-
+-#ifdef Q_WS_X11
+-bool Application::x11EventFilter(XEvent* event)
+-{
+-    int retCode = autoType()->callEventFilter(event);
+-
+-    if (retCode == 0) {
+-        return false;
+-    }
+-    else if (retCode == 1) {
+-        return true;
+-    }
+-
+-    return QApplication::x11EventFilter(event);
+-}
+-#endif
+diff --git a/src/gui/Application.h b/src/gui/Application.h
+index 2b78998..149b61d 100644
+--- a/src/gui/Application.h
++++ b/src/gui/Application.h
+@@ -21,8 +21,6 @@
+ #include <QApplication>
+-#include "core/Global.h"
+-
+ class Application : public QApplication
+ {
+     Q_OBJECT
+@@ -31,10 +29,7 @@ public:
+     Application(int& argc, char** argv);
+     void setMainWindow(QWidget* mainWindow);
+-    bool event(QEvent* event) Q_DECL_OVERRIDE;
+-#ifdef Q_WS_X11
+-    bool x11EventFilter(XEvent* event) Q_DECL_OVERRIDE;
+-#endif
++    bool event(QEvent* event) override;
+ Q_SIGNALS:
+     void openFile(const QString& filename);
+diff --git a/src/gui/ChangeMasterKeyWidget.h b/src/gui/ChangeMasterKeyWidget.h
+index 46fc3ef..8985ff7 100644
+--- a/src/gui/ChangeMasterKeyWidget.h
++++ b/src/gui/ChangeMasterKeyWidget.h
+@@ -33,7 +33,7 @@ class ChangeMasterKeyWidget : public DialogyWidget
+     Q_OBJECT
+ public:
+-    explicit ChangeMasterKeyWidget(QWidget* parent = Q_NULLPTR);
++    explicit ChangeMasterKeyWidget(QWidget* parent = nullptr);
+     ~ChangeMasterKeyWidget();
+     void clearForms();
+     CompositeKey newMasterKey();
+diff --git a/src/gui/Clipboard.cpp b/src/gui/Clipboard.cpp
+index 698ca89..bf4db8f 100644
+--- a/src/gui/Clipboard.cpp
++++ b/src/gui/Clipboard.cpp
+@@ -23,7 +23,7 @@
+ #include "core/Config.h"
+-Clipboard* Clipboard::m_instance(Q_NULLPTR);
++Clipboard* Clipboard::m_instance(nullptr);
+ Clipboard::Clipboard(QObject* parent)
+     : QObject(parent)
+diff --git a/src/gui/Clipboard.h b/src/gui/Clipboard.h
+index 8c234a2..dafce70 100644
+--- a/src/gui/Clipboard.h
++++ b/src/gui/Clipboard.h
+@@ -20,8 +20,6 @@
+ #include <QObject>
+-#include "core/Global.h"
+-
+ class QTimer;
+ class Clipboard : public QObject
+@@ -40,7 +38,7 @@ private Q_SLOTS:
+     void clearClipboard();
+ private:
+-    explicit Clipboard(QObject* parent = Q_NULLPTR);
++    explicit Clipboard(QObject* parent = nullptr);
+     static Clipboard* m_instance;
+diff --git a/src/gui/DatabaseOpenWidget.cpp b/src/gui/DatabaseOpenWidget.cpp
+index 7e34176..00aae6b 100644
+--- a/src/gui/DatabaseOpenWidget.cpp
++++ b/src/gui/DatabaseOpenWidget.cpp
+@@ -30,7 +30,7 @@
+ DatabaseOpenWidget::DatabaseOpenWidget(QWidget* parent)
+     : DialogyWidget(parent)
+     , m_ui(new Ui::DatabaseOpenWidget())
+-    , m_db(Q_NULLPTR)
++    , m_db(nullptr)
+ {
+     m_ui->setupUi(this);
+diff --git a/src/gui/DatabaseOpenWidget.h b/src/gui/DatabaseOpenWidget.h
+index 9c9a062..ba55e4c 100644
+--- a/src/gui/DatabaseOpenWidget.h
++++ b/src/gui/DatabaseOpenWidget.h
+@@ -35,7 +35,7 @@ class DatabaseOpenWidget : public DialogyWidget
+     Q_OBJECT
+ public:
+-    explicit DatabaseOpenWidget(QWidget* parent = Q_NULLPTR);
++    explicit DatabaseOpenWidget(QWidget* parent = nullptr);
+     ~DatabaseOpenWidget();
+     void load(const QString& filename);
+     void enterKey(const QString& pw, const QString& keyFile);
+diff --git a/src/gui/DatabaseRepairWidget.h b/src/gui/DatabaseRepairWidget.h
+index 56c5c96..6775d2d 100644
+--- a/src/gui/DatabaseRepairWidget.h
++++ b/src/gui/DatabaseRepairWidget.h
+@@ -25,14 +25,14 @@ class DatabaseRepairWidget : public DatabaseOpenWidget
+     Q_OBJECT
+ public:
+-    explicit DatabaseRepairWidget(QWidget* parent = Q_NULLPTR);
++    explicit DatabaseRepairWidget(QWidget* parent = nullptr);
+ Q_SIGNALS:
+     void success();
+     void error();
+ protected:
+-    void openDatabase() Q_DECL_OVERRIDE;
++    void openDatabase() override;
+ private Q_SLOTS:
+     void processEditFinished(bool result);
+diff --git a/src/gui/DatabaseSettingsWidget.cpp b/src/gui/DatabaseSettingsWidget.cpp
+index 007c44a..d4ca8dd 100644
+--- a/src/gui/DatabaseSettingsWidget.cpp
++++ b/src/gui/DatabaseSettingsWidget.cpp
+@@ -26,7 +26,7 @@
+ DatabaseSettingsWidget::DatabaseSettingsWidget(QWidget* parent)
+     : DialogyWidget(parent)
+     , m_ui(new Ui::DatabaseSettingsWidget())
+-    , m_db(Q_NULLPTR)
++    , m_db(nullptr)
+ {
+     m_ui->setupUi(this);
+diff --git a/src/gui/DatabaseSettingsWidget.h b/src/gui/DatabaseSettingsWidget.h
+index a7d2832..040e0db 100644
+--- a/src/gui/DatabaseSettingsWidget.h
++++ b/src/gui/DatabaseSettingsWidget.h
+@@ -33,7 +33,7 @@ class DatabaseSettingsWidget : public DialogyWidget
+     Q_OBJECT
+ public:
+-    explicit DatabaseSettingsWidget(QWidget* parent = Q_NULLPTR);
++    explicit DatabaseSettingsWidget(QWidget* parent = nullptr);
+     ~DatabaseSettingsWidget();
+     void load(Database* db);
+diff --git a/src/gui/DatabaseTabWidget.cpp b/src/gui/DatabaseTabWidget.cpp
+index 3d03093..69b4f7e 100644
+--- a/src/gui/DatabaseTabWidget.cpp
++++ b/src/gui/DatabaseTabWidget.cpp
+@@ -18,6 +18,8 @@
+ #include "DatabaseTabWidget.h"
+ #include <QFileInfo>
++#include <QLockFile>
++#include <QSaveFile>
+ #include <QTabWidget>
+ #include "autotype/AutoType.h"
+@@ -25,7 +27,6 @@
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+-#include "core/qsavefile.h"
+ #include "format/CsvExporter.h"
+ #include "gui/Clipboard.h"
+ #include "gui/DatabaseWidget.h"
+@@ -37,8 +38,8 @@
+ #include "gui/group/GroupView.h"
+ DatabaseManagerStruct::DatabaseManagerStruct()
+-    : dbWidget(Q_NULLPTR)
+-    , lockFile(Q_NULLPTR)
++    : dbWidget(nullptr)
++    , lockFile(nullptr)
+     , saveToFilename(false)
+     , modified(false)
+     , readOnly(false)
+@@ -160,7 +161,7 @@ void DatabaseTabWidget::openDatabase(const QString& fileName, const QString& pw,
+             if (result == QMessageBox::No) {
+                 dbStruct.readOnly = true;
+                 delete lockFile;
+-                lockFile = Q_NULLPTR;
++                lockFile = nullptr;
+             }
+             else {
+                 // take over the lock file if possible
+@@ -332,7 +333,7 @@ bool DatabaseTabWidget::saveDatabaseAs(Database* db)
+     }
+     QString fileName = fileDialog()->getSaveFileName(this, tr("Save database as"),
+                                                      oldFileName, tr("KeePass 2 Database").append(" (*.kdbx)"),
+-                                                     Q_NULLPTR, 0, "kdbx");
++                                                     nullptr, 0, "kdbx");
+     if (!fileName.isEmpty()) {
+         QFileInfo fileInfo(fileName);
+         QString lockFilePath;
+@@ -453,7 +454,7 @@ void DatabaseTabWidget::exportToCsv()
+     QString fileName = fileDialog()->getSaveFileName(this, tr("Export database to CSV file"),
+                                                      QString(), tr("CSV file").append(" (*.csv)"),
+-                                                     Q_NULLPTR, 0, "csv");
++                                                     nullptr, 0, "csv");
+     if (fileName.isEmpty()) {
+         return;
+     }
+@@ -558,7 +559,7 @@ Database* DatabaseTabWidget::indexDatabase(int index)
+         }
+     }
+-    return Q_NULLPTR;
++    return nullptr;
+ }
+ DatabaseManagerStruct DatabaseTabWidget::indexDatabaseManagerStruct(int index)
+@@ -586,7 +587,7 @@ Database* DatabaseTabWidget::databaseFromDatabaseWidget(DatabaseWidget* dbWidget
+         }
+     }
+-    return Q_NULLPTR;
++    return nullptr;
+ }
+ void DatabaseTabWidget::insertDatabase(Database* db, const DatabaseManagerStruct& dbStruct)
+@@ -611,7 +612,7 @@ DatabaseWidget* DatabaseTabWidget::currentDatabaseWidget()
+         return m_dbList[db].dbWidget;
+     }
+     else {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+ }
+diff --git a/src/gui/DatabaseTabWidget.h b/src/gui/DatabaseTabWidget.h
+index c15408d..de4a9ca 100644
+--- a/src/gui/DatabaseTabWidget.h
++++ b/src/gui/DatabaseTabWidget.h
+@@ -21,7 +21,6 @@
+ #include <QHash>
+ #include <QTabWidget>
+-#include "core/qlockfile.h"
+ #include "format/KeePass2Writer.h"
+ #include "gui/DatabaseWidget.h"
+@@ -29,6 +28,7 @@ class DatabaseWidget;
+ class DatabaseWidgetStateSync;
+ class DatabaseOpenWidget;
+ class QFile;
++class QLockFile;
+ struct DatabaseManagerStruct
+ {
+@@ -51,7 +51,7 @@ class DatabaseTabWidget : public QTabWidget
+     Q_OBJECT
+ public:
+-    explicit DatabaseTabWidget(QWidget* parent = Q_NULLPTR);
++    explicit DatabaseTabWidget(QWidget* parent = nullptr);
+     ~DatabaseTabWidget();
+     void openDatabase(const QString& fileName, const QString& pw = QString(),
+                       const QString& keyFile = QString());
+@@ -101,7 +101,7 @@ private:
+     Database* databaseFromDatabaseWidget(DatabaseWidget* dbWidget);
+     void insertDatabase(Database* db, const DatabaseManagerStruct& dbStruct);
+     void updateLastDatabases(const QString& filename);
+-    void connectDatabase(Database* newDb, Database* oldDb = Q_NULLPTR);
++    void connectDatabase(Database* newDb, Database* oldDb = nullptr);
+     KeePass2Writer m_writer;
+     QHash<Database*, DatabaseManagerStruct> m_dbList;
+diff --git a/src/gui/DatabaseWidget.cpp b/src/gui/DatabaseWidget.cpp
+index 8de842f..3bca6fa 100644
+--- a/src/gui/DatabaseWidget.cpp
++++ b/src/gui/DatabaseWidget.cpp
+@@ -52,9 +52,9 @@ DatabaseWidget::DatabaseWidget(Database* db, QWidget* parent)
+     , m_db(db)
+     , m_searchUi(new Ui::SearchWidget())
+     , m_searchWidget(new QWidget())
+-    , m_newGroup(Q_NULLPTR)
+-    , m_newEntry(Q_NULLPTR)
+-    , m_newParent(Q_NULLPTR)
++    , m_newGroup(nullptr)
++    , m_newEntry(nullptr)
++    , m_newParent(nullptr)
+ {
+     m_searchUi->setupUi(m_searchWidget);
+@@ -175,7 +175,7 @@ DatabaseWidget::~DatabaseWidget()
+ DatabaseWidget::Mode DatabaseWidget::currentMode() const
+ {
+-    if (currentWidget() == Q_NULLPTR) {
++    if (currentWidget() == nullptr) {
+         return DatabaseWidget::None;
+     }
+     else if (currentWidget() == m_mainWidget) {
+@@ -554,8 +554,8 @@ void DatabaseWidget::switchToView(bool accepted)
+             delete m_newGroup;
+         }
+-        m_newGroup = Q_NULLPTR;
+-        m_newParent = Q_NULLPTR;
++        m_newGroup = nullptr;
++        m_newParent = nullptr;
+     }
+     else if (m_newEntry) {
+         if (accepted) {
+@@ -567,8 +567,8 @@ void DatabaseWidget::switchToView(bool accepted)
+             delete m_newEntry;
+         }
+-        m_newEntry = Q_NULLPTR;
+-        m_newParent = Q_NULLPTR;
++        m_newEntry = nullptr;
++        m_newParent = nullptr;
+     }
+     setCurrentWidget(m_mainWidget);
+@@ -638,9 +638,9 @@ void DatabaseWidget::openDatabase(bool accepted)
+         // We won't need those anymore and KeePass1OpenWidget closes
+         // the file in its dtor.
+         delete m_databaseOpenWidget;
+-        m_databaseOpenWidget = Q_NULLPTR;
++        m_databaseOpenWidget = nullptr;
+         delete m_keepass1OpenWidget;
+-        m_keepass1OpenWidget = Q_NULLPTR;
++        m_keepass1OpenWidget = nullptr;
+     }
+     else {
+         if (m_databaseOpenWidget->database()) {
+@@ -883,7 +883,7 @@ bool DatabaseWidget::isInSearchMode() const
+ void DatabaseWidget::clearLastGroup(Group* group)
+ {
+     if (group) {
+-        m_lastGroup = Q_NULLPTR;
++        m_lastGroup = nullptr;
+         m_searchWidget->hide();
+     }
+ }
+@@ -932,7 +932,7 @@ QStringList DatabaseWidget::customEntryAttributes() const
+ bool DatabaseWidget::isGroupSelected() const
+ {
+-    return m_groupView->currentGroup() != Q_NULLPTR;
++    return m_groupView->currentGroup() != nullptr;
+ }
+ bool DatabaseWidget::currentEntryHasTitle()
+diff --git a/src/gui/DatabaseWidget.h b/src/gui/DatabaseWidget.h
+index a925606..38a685c 100644
+--- a/src/gui/DatabaseWidget.h
++++ b/src/gui/DatabaseWidget.h
+@@ -21,7 +21,6 @@
+ #include <QScopedPointer>
+ #include <QStackedWidget>
+-#include "core/Global.h"
+ #include "core/Uuid.h"
+ #include "gui/entry/EntryModel.h"
+@@ -59,7 +58,7 @@ public:
+         LockedMode
+     };
+-    explicit DatabaseWidget(Database* db, QWidget* parent = Q_NULLPTR);
++    explicit DatabaseWidget(Database* db, QWidget* parent = nullptr);
+     ~DatabaseWidget();
+     Database* database();
+     bool dbHasKey() const;
+@@ -103,7 +102,7 @@ Q_SIGNALS:
+     void entryColumnSizesChanged();
+ protected:
+-    bool eventFilter(QObject* object, QEvent* event) Q_DECL_OVERRIDE;
++    bool eventFilter(QObject* object, QEvent* event) override;
+ public Q_SLOTS:
+     void createEntry();
+diff --git a/src/gui/DatabaseWidgetStateSync.cpp b/src/gui/DatabaseWidgetStateSync.cpp
+index 66b8492..430380c 100644
+--- a/src/gui/DatabaseWidgetStateSync.cpp
++++ b/src/gui/DatabaseWidgetStateSync.cpp
+@@ -22,7 +22,7 @@
+ DatabaseWidgetStateSync::DatabaseWidgetStateSync(QObject* parent)
+     : QObject(parent)
+-    , m_activeDbWidget(Q_NULLPTR)
++    , m_activeDbWidget(nullptr)
+     , m_blockUpdates(false)
+ {
+     m_splitterSizes = variantToIntList(config()->get("GUI/SplitterState"));
+diff --git a/src/gui/DatabaseWidgetStateSync.h b/src/gui/DatabaseWidgetStateSync.h
+index f6a87cd..a486117 100644
+--- a/src/gui/DatabaseWidgetStateSync.h
++++ b/src/gui/DatabaseWidgetStateSync.h
+@@ -16,8 +16,8 @@
+  *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+  */
+-#ifndef KEEPASSX_HEADERVIEWSYNC_H
+-#define KEEPASSX_HEADERVIEWSYNC_H
++#ifndef KEEPASSX_DATABASEWIDGETSTATESYNC_H
++#define KEEPASSX_DATABASEWIDGETSTATESYNC_H
+ #include "gui/DatabaseWidget.h"
+@@ -26,7 +26,7 @@ class DatabaseWidgetStateSync : public QObject
+     Q_OBJECT
+ public:
+-    explicit DatabaseWidgetStateSync(QObject* parent = Q_NULLPTR);
++    explicit DatabaseWidgetStateSync(QObject* parent = nullptr);
+     ~DatabaseWidgetStateSync();
+ public Q_SLOTS:
+@@ -51,4 +51,4 @@ private:
+     QList<int> m_columnSizesSearch;
+ };
+-#endif // KEEPASSX_HEADERVIEWSYNC_H
++#endif // KEEPASSX_DATABASEWIDGETSTATESYNC_H
+diff --git a/src/gui/DialogyWidget.h b/src/gui/DialogyWidget.h
+index 9dd0528..b0915a2 100644
+--- a/src/gui/DialogyWidget.h
++++ b/src/gui/DialogyWidget.h
+@@ -21,17 +21,15 @@
+ #include <QDialogButtonBox>
+ #include <QWidget>
+-#include "core/Global.h"
+-
+ class DialogyWidget : public QWidget
+ {
+     Q_OBJECT
+ public:
+-    explicit DialogyWidget(QWidget* parent = Q_NULLPTR);
++    explicit DialogyWidget(QWidget* parent = nullptr);
+ protected:
+-    virtual void keyPressEvent(QKeyEvent* e) Q_DECL_OVERRIDE;
++    void keyPressEvent(QKeyEvent* e) override;
+ private:
+     bool clickButton(QDialogButtonBox::StandardButton standardButton);
+diff --git a/src/gui/DragTabBar.h b/src/gui/DragTabBar.h
+index 1b6005d..a6117a0 100644
+--- a/src/gui/DragTabBar.h
++++ b/src/gui/DragTabBar.h
+@@ -20,21 +20,19 @@
+ #include <QTabBar>
+-#include "core/Global.h"
+-
+ class DragTabBar : public QTabBar
+ {
+     Q_OBJECT
+ public:
+-    explicit DragTabBar(QWidget* parent = Q_NULLPTR);
++    explicit DragTabBar(QWidget* parent = nullptr);
+ protected:
+-    void dragEnterEvent(QDragEnterEvent* event) Q_DECL_OVERRIDE;
+-    void dragMoveEvent(QDragMoveEvent* event) Q_DECL_OVERRIDE;
+-    void dragLeaveEvent(QDragLeaveEvent* event) Q_DECL_OVERRIDE;
+-    void dropEvent(QDropEvent* event) Q_DECL_OVERRIDE;
+-    void tabLayoutChange() Q_DECL_OVERRIDE;
++    void dragEnterEvent(QDragEnterEvent* event) override;
++    void dragMoveEvent(QDragMoveEvent* event) override;
++    void dragLeaveEvent(QDragLeaveEvent* event) override;
++    void dropEvent(QDropEvent* event) override;
++    void tabLayoutChange() override;
+ private Q_SLOTS:
+     void dragSwitchTab();
+diff --git a/src/gui/EditWidget.h b/src/gui/EditWidget.h
+index d27abe9..c5f507a 100644
+--- a/src/gui/EditWidget.h
++++ b/src/gui/EditWidget.h
+@@ -33,7 +33,7 @@ class EditWidget : public DialogyWidget
+     Q_OBJECT
+ public:
+-    explicit EditWidget(QWidget* parent = Q_NULLPTR);
++    explicit EditWidget(QWidget* parent = nullptr);
+     ~EditWidget();
+     void add(const QString& labelText, QWidget* widget);
+diff --git a/src/gui/EditWidgetIcons.cpp b/src/gui/EditWidgetIcons.cpp
+index c408940..3d3565c 100644
+--- a/src/gui/EditWidgetIcons.cpp
++++ b/src/gui/EditWidgetIcons.cpp
+@@ -35,7 +35,7 @@ IconStruct::IconStruct()
+ EditWidgetIcons::EditWidgetIcons(QWidget* parent)
+     : QWidget(parent)
+     , m_ui(new Ui::EditWidgetIcons())
+-    , m_database(Q_NULLPTR)
++    , m_database(nullptr)
+     , m_defaultIconModel(new DefaultIconModel(this))
+     , m_customIconModel(new CustomIconModel(this))
+ {
+@@ -85,7 +85,7 @@ IconStruct EditWidgetIcons::save()
+         }
+     }
+-    m_database = Q_NULLPTR;
++    m_database = nullptr;
+     m_currentUuid = Uuid();
+     return iconStruct;
+ }
+diff --git a/src/gui/EditWidgetIcons.h b/src/gui/EditWidgetIcons.h
+index e18f444..f3f3f11 100644
+--- a/src/gui/EditWidgetIcons.h
++++ b/src/gui/EditWidgetIcons.h
+@@ -20,7 +20,6 @@
+ #include <QWidget>
+-#include "core/Global.h"
+ #include "core/Uuid.h"
+ class Database;
+@@ -44,7 +43,7 @@ class EditWidgetIcons : public QWidget
+     Q_OBJECT
+ public:
+-    explicit EditWidgetIcons(QWidget* parent = Q_NULLPTR);
++    explicit EditWidgetIcons(QWidget* parent = nullptr);
+     ~EditWidgetIcons();
+     IconStruct save();
+diff --git a/src/gui/EditWidgetProperties.h b/src/gui/EditWidgetProperties.h
+index c5d0eb0..4a2c059 100644
+--- a/src/gui/EditWidgetProperties.h
++++ b/src/gui/EditWidgetProperties.h
+@@ -20,7 +20,6 @@
+ #include <QWidget>
+-#include "core/Global.h"
+ #include "core/TimeInfo.h"
+ #include "core/Uuid.h"
+@@ -33,7 +32,7 @@ class EditWidgetProperties : public QWidget
+     Q_OBJECT
+ public:
+-    explicit EditWidgetProperties(QWidget* parent = Q_NULLPTR);
++    explicit EditWidgetProperties(QWidget* parent = nullptr);
+     ~EditWidgetProperties();
+     void setFields(TimeInfo timeInfo, Uuid uuid);
+diff --git a/src/gui/FileDialog.cpp b/src/gui/FileDialog.cpp
+index 8448258..e293db2 100644
+--- a/src/gui/FileDialog.cpp
++++ b/src/gui/FileDialog.cpp
+@@ -19,7 +19,7 @@
+ #include "core/Config.h"
+-FileDialog* FileDialog::m_instance(Q_NULLPTR);
++FileDialog* FileDialog::m_instance(nullptr);
+ QString FileDialog::getOpenFileName(QWidget* parent, const QString& caption, QString dir,
+                                     const QString& filter, QString* selectedFilter,
+diff --git a/src/gui/FileDialog.h b/src/gui/FileDialog.h
+index 46c6353..9f8fbb5 100644
+--- a/src/gui/FileDialog.h
++++ b/src/gui/FileDialog.h
+@@ -20,17 +20,15 @@
+ #include <QFileDialog>
+-#include "core/Global.h"
+-
+ class FileDialog
+ {
+ public:
+-    QString getOpenFileName(QWidget* parent = Q_NULLPTR, const QString& caption = QString(),
++    QString getOpenFileName(QWidget* parent = nullptr, const QString& caption = QString(),
+                             QString dir = QString(), const QString& filter = QString(),
+-                            QString* selectedFilter = Q_NULLPTR, QFileDialog::Options options = 0);
+-    QString getSaveFileName(QWidget* parent = Q_NULLPTR, const QString& caption = QString(),
++                            QString* selectedFilter = nullptr, QFileDialog::Options options = 0);
++    QString getSaveFileName(QWidget* parent = nullptr, const QString& caption = QString(),
+                             QString dir = QString(), const QString& filter = QString(),
+-                            QString* selectedFilter = Q_NULLPTR, QFileDialog::Options options = 0,
++                            QString* selectedFilter = nullptr, QFileDialog::Options options = 0,
+                             const QString& defaultExtension = QString());
+     /**
+diff --git a/src/gui/IconModels.h b/src/gui/IconModels.h
+index 8a24707..868ce44 100644
+--- a/src/gui/IconModels.h
++++ b/src/gui/IconModels.h
+@@ -21,7 +21,6 @@
+ #include <QAbstractListModel>
+ #include <QPixmap>
+-#include "core/Global.h"
+ #include "core/Uuid.h"
+ class DefaultIconModel : public QAbstractListModel
+@@ -29,10 +28,10 @@ class DefaultIconModel : public QAbstractListModel
+     Q_OBJECT
+ public:
+-    explicit DefaultIconModel(QObject* parent = Q_NULLPTR);
++    explicit DefaultIconModel(QObject* parent = nullptr);
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
+ };
+ class CustomIconModel : public QAbstractListModel
+@@ -40,10 +39,10 @@ class CustomIconModel : public QAbstractListModel
+     Q_OBJECT
+ public:
+-    explicit CustomIconModel(QObject* parent = Q_NULLPTR);
++    explicit CustomIconModel(QObject* parent = nullptr);
+-    virtual int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    virtual QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
+     void setIcons(const QHash<Uuid, QPixmap>& icons, const QList<Uuid>& iconsOrder);
+     Uuid uuidFromIndex(const QModelIndex& index) const;
+     QModelIndex indexFromUuid(const Uuid& uuid) const;
+diff --git a/src/gui/KeePass1OpenWidget.h b/src/gui/KeePass1OpenWidget.h
+index a398f9a..203b786 100644
+--- a/src/gui/KeePass1OpenWidget.h
++++ b/src/gui/KeePass1OpenWidget.h
+@@ -25,10 +25,10 @@ class KeePass1OpenWidget : public DatabaseOpenWidget
+     Q_OBJECT
+ public:
+-    explicit KeePass1OpenWidget(QWidget* parent = Q_NULLPTR);
++    explicit KeePass1OpenWidget(QWidget* parent = nullptr);
+ protected:
+-    void openDatabase() Q_DECL_OVERRIDE;
++    void openDatabase() override;
+ };
+ #endif // KEEPASSX_KEEPASS1OPENWIDGET_H
+diff --git a/src/gui/LineEdit.h b/src/gui/LineEdit.h
+index 2672aae..f5f0584 100644
+--- a/src/gui/LineEdit.h
++++ b/src/gui/LineEdit.h
+@@ -22,8 +22,6 @@
+ #include <QLineEdit>
+-#include "core/Global.h"
+-
+ class QToolButton;
+ class LineEdit : public QLineEdit
+@@ -31,10 +29,10 @@ class LineEdit : public QLineEdit
+     Q_OBJECT
+ public:
+-    explicit LineEdit(QWidget* parent = Q_NULLPTR);
++    explicit LineEdit(QWidget* parent = nullptr);
+ protected:
+-    void resizeEvent(QResizeEvent* event) Q_DECL_OVERRIDE;
++    void resizeEvent(QResizeEvent* event) override;
+ private Q_SLOTS:
+     void updateCloseButton(const QString& text);
+diff --git a/src/gui/MainWindow.cpp b/src/gui/MainWindow.cpp
+index b6dc1df..6245dc7 100644
+--- a/src/gui/MainWindow.cpp
++++ b/src/gui/MainWindow.cpp
+@@ -38,7 +38,7 @@ const QString MainWindow::BaseWindowTitle = "KeePassX";
+ MainWindow::MainWindow()
+     : m_ui(new Ui::MainWindow())
+-    , m_trayIcon(Q_NULLPTR)
++    , m_trayIcon(nullptr)
+ {
+     m_ui->setupUi(this);
+@@ -227,6 +227,7 @@ void MainWindow::updateLastDatabasesMenu()
+     QStringList lastDatabases = config()->get("LastDatabases", QVariant()).toStringList();
+     Q_FOREACH (const QString& database, lastDatabases) {
+         QAction* action = m_ui->menuRecentDatabases->addAction(database);
++        action->setData(database);
+         m_lastDatabasesActions->addAction(action);
+     }
+     m_ui->menuRecentDatabases->addSeparator();
+@@ -257,7 +258,7 @@ void MainWindow::updateCopyAttributesMenu()
+ void MainWindow::openRecentDatabase(QAction* action)
+ {
+-    openDatabase(action->text());
++    openDatabase(action->data().toString());
+ }
+ void MainWindow::clearLastDatabases()
+@@ -450,7 +451,7 @@ void MainWindow::closeEvent(QCloseEvent* event)
+     }
+ }
+-void MainWindow::changeEvent(QEvent *event)
++void MainWindow::changeEvent(QEvent* event)
+ {
+     if ((event->type() == QEvent::WindowStateChange) && isMinimized()
+             && isTrayIconEnabled() && m_trayIcon && m_trayIcon->isVisible()
+@@ -521,7 +522,7 @@ void MainWindow::updateTrayIcon()
+         if (m_trayIcon) {
+             m_trayIcon->hide();
+             delete m_trayIcon;
+-            m_trayIcon = Q_NULLPTR;
++            m_trayIcon = nullptr;
+         }
+     }
+ }
+@@ -622,7 +623,7 @@ void MainWindow::repairDatabase()
+     if (dialog->exec() == QDialog::Accepted && dbRepairWidget->database()) {
+         QString saveFileName = fileDialog()->getSaveFileName(this, tr("Save repaired database"), QString(),
+                                                              tr("KeePass 2 Database").append(" (*.kdbx)"),
+-                                                             Q_NULLPTR, 0, "kdbx");
++                                                             nullptr, 0, "kdbx");
+         if (!saveFileName.isEmpty()) {
+             KeePass2Writer writer;
+diff --git a/src/gui/MainWindow.h b/src/gui/MainWindow.h
+index 5aa39ca..c52cfba 100644
+--- a/src/gui/MainWindow.h
++++ b/src/gui/MainWindow.h
+@@ -44,8 +44,8 @@ public Q_SLOTS:
+                       const QString& keyFile = QString());
+ protected:
+-     void closeEvent(QCloseEvent* event) Q_DECL_OVERRIDE;
+-     void changeEvent(QEvent* event) Q_DECL_OVERRIDE;
++     void closeEvent(QCloseEvent* event) override;
++     void changeEvent(QEvent* event) override;
+ private Q_SLOTS:
+     void setMenuActionState(DatabaseWidget::Mode mode = DatabaseWidget::None);
+diff --git a/src/gui/MessageBox.h b/src/gui/MessageBox.h
+index abb12c0..1ea4022 100644
+--- a/src/gui/MessageBox.h
++++ b/src/gui/MessageBox.h
+@@ -20,8 +20,6 @@
+ #include <QMessageBox>
+-#include "core/Global.h"
+-
+ class MessageBox
+ {
+ public:
+diff --git a/src/gui/PasswordComboBox.cpp b/src/gui/PasswordComboBox.cpp
+index f11311a..e121850 100644
+--- a/src/gui/PasswordComboBox.cpp
++++ b/src/gui/PasswordComboBox.cpp
+@@ -24,7 +24,7 @@
+ PasswordComboBox::PasswordComboBox(QWidget* parent)
+     : QComboBox(parent)
+-    , m_generator(Q_NULLPTR)
++    , m_generator(nullptr)
+     , m_alternatives(10)
+ {
+     setEditable(true);
+@@ -51,7 +51,6 @@ void PasswordComboBox::setEcho(bool echo)
+ #else
+         setStyleSheet("QComboBox { font-family: monospace,Courier; }");
+ #endif
+-
+     }
+     else {
+         // clear items so the combobox indicates that no popup menu is available
+diff --git a/src/gui/PasswordComboBox.h b/src/gui/PasswordComboBox.h
+index 69ce152..7c54e27 100644
+--- a/src/gui/PasswordComboBox.h
++++ b/src/gui/PasswordComboBox.h
+@@ -21,8 +21,6 @@
+ #include <QComboBox>
+-#include "core/Global.h"
+-
+ class PasswordGenerator;
+ class PasswordComboBox : public QComboBox
+@@ -30,7 +28,7 @@ class PasswordComboBox : public QComboBox
+     Q_OBJECT
+ public:
+-    explicit PasswordComboBox(QWidget* parent = Q_NULLPTR);
++    explicit PasswordComboBox(QWidget* parent = nullptr);
+     ~PasswordComboBox();
+     void setGenerator(PasswordGenerator* generator);
+diff --git a/src/gui/PasswordEdit.cpp b/src/gui/PasswordEdit.cpp
+index b68eef6..e5bbf6b 100644
+--- a/src/gui/PasswordEdit.cpp
++++ b/src/gui/PasswordEdit.cpp
+@@ -17,14 +17,12 @@
+ #include "PasswordEdit.h"
+-#include "core/Global.h"
+-
+ const QColor PasswordEdit::CorrectSoFarColor = QColor(255, 205, 15);
+ const QColor PasswordEdit::ErrorColor = QColor(255, 125, 125);
+ PasswordEdit::PasswordEdit(QWidget* parent)
+     : QLineEdit(parent)
+-    , m_basePasswordEdit(Q_NULLPTR)
++    , m_basePasswordEdit(nullptr)
+ {
+ }
+diff --git a/src/gui/PasswordEdit.h b/src/gui/PasswordEdit.h
+index cfb4a76..7ce4908 100644
+--- a/src/gui/PasswordEdit.h
++++ b/src/gui/PasswordEdit.h
+@@ -20,8 +20,6 @@
+ #include <QLineEdit>
+-#include "core/Global.h"
+-
+ class PasswordEdit : public QLineEdit
+ {
+     Q_OBJECT
+@@ -30,7 +28,7 @@ public:
+     static const QColor CorrectSoFarColor;
+     static const QColor ErrorColor;
+-    explicit PasswordEdit(QWidget* parent = Q_NULLPTR);
++    explicit PasswordEdit(QWidget* parent = nullptr);
+     void enableVerifyMode(PasswordEdit* baseEdit);
+ public Q_SLOTS:
+diff --git a/src/gui/PasswordGeneratorWidget.h b/src/gui/PasswordGeneratorWidget.h
+index 96f3f60..cfb21bb 100644
+--- a/src/gui/PasswordGeneratorWidget.h
++++ b/src/gui/PasswordGeneratorWidget.h
+@@ -21,7 +21,6 @@
+ #include <QWidget>
+ #include <QComboBox>
+-#include "core/Global.h"
+ #include "core/PasswordGenerator.h"
+ namespace Ui {
+@@ -35,7 +34,7 @@ class PasswordGeneratorWidget : public QWidget
+     Q_OBJECT
+ public:
+-    explicit PasswordGeneratorWidget(QWidget* parent = Q_NULLPTR);
++    explicit PasswordGeneratorWidget(QWidget* parent = nullptr);
+     ~PasswordGeneratorWidget();
+     void loadSettings();
+     void reset();
+diff --git a/src/gui/SettingsWidget.h b/src/gui/SettingsWidget.h
+index cefbf6d..3fe621d 100644
+--- a/src/gui/SettingsWidget.h
++++ b/src/gui/SettingsWidget.h
+@@ -30,7 +30,7 @@ class SettingsWidget : public EditWidget
+     Q_OBJECT
+ public:
+-    explicit SettingsWidget(QWidget* parent = Q_NULLPTR);
++    explicit SettingsWidget(QWidget* parent = nullptr);
+     ~SettingsWidget();
+     void loadSettings();
+diff --git a/src/gui/SortFilterHideProxyModel.cpp b/src/gui/SortFilterHideProxyModel.cpp
+index 0902361..0193d95 100644
+--- a/src/gui/SortFilterHideProxyModel.cpp
++++ b/src/gui/SortFilterHideProxyModel.cpp
+@@ -22,6 +22,11 @@ SortFilterHideProxyModel::SortFilterHideProxyModel(QObject* parent)
+ {
+ }
++Qt::DropActions SortFilterHideProxyModel::supportedDragActions() const
++{
++    return sourceModel()->supportedDragActions();
++}
++
+ void SortFilterHideProxyModel::hideColumn(int column, bool hide)
+ {
+     m_hiddenColumns.resize(column + 1);
+diff --git a/src/gui/SortFilterHideProxyModel.h b/src/gui/SortFilterHideProxyModel.h
+index a6f1e71..58d9ff7 100644
+--- a/src/gui/SortFilterHideProxyModel.h
++++ b/src/gui/SortFilterHideProxyModel.h
+@@ -21,18 +21,17 @@
+ #include <QBitArray>
+ #include <QSortFilterProxyModel>
+-#include "core/Global.h"
+-
+ class SortFilterHideProxyModel : public QSortFilterProxyModel
+ {
+     Q_OBJECT
+ public:
+-    explicit SortFilterHideProxyModel(QObject* parent = Q_NULLPTR);
++    explicit SortFilterHideProxyModel(QObject* parent = nullptr);
++    Qt::DropActions supportedDragActions() const override;
+     void hideColumn(int column, bool hide);
+ protected:
+-    bool filterAcceptsColumn(int sourceColumn, const QModelIndex& sourceParent) const Q_DECL_OVERRIDE;
++    bool filterAcceptsColumn(int sourceColumn, const QModelIndex& sourceParent) const override;
+ private:
+     QBitArray m_hiddenColumns;
+diff --git a/src/gui/UnlockDatabaseWidget.cpp b/src/gui/UnlockDatabaseWidget.cpp
+index 242b07a..a005d0e 100644
+--- a/src/gui/UnlockDatabaseWidget.cpp
++++ b/src/gui/UnlockDatabaseWidget.cpp
+@@ -34,5 +34,5 @@ void UnlockDatabaseWidget::clearForms()
+     m_ui->checkPassword->setChecked(false);
+     m_ui->checkKeyFile->setChecked(false);
+     m_ui->buttonTogglePassword->setChecked(false);
+-    m_db = Q_NULLPTR;
++    m_db = nullptr;
+ }
+diff --git a/src/gui/UnlockDatabaseWidget.h b/src/gui/UnlockDatabaseWidget.h
+index 052578b..adb5efb 100644
+--- a/src/gui/UnlockDatabaseWidget.h
++++ b/src/gui/UnlockDatabaseWidget.h
+@@ -25,7 +25,7 @@ class UnlockDatabaseWidget : public DatabaseOpenWidget
+     Q_OBJECT
+ public:
+-    explicit UnlockDatabaseWidget(QWidget* parent = Q_NULLPTR);
++    explicit UnlockDatabaseWidget(QWidget* parent = nullptr);
+     void clearForms();
+ };
+diff --git a/src/gui/WelcomeWidget.h b/src/gui/WelcomeWidget.h
+index 983aaa0..80a0dde 100644
+--- a/src/gui/WelcomeWidget.h
++++ b/src/gui/WelcomeWidget.h
+@@ -20,8 +20,6 @@
+ #include <QWidget>
+-#include "core/Global.h"
+-
+ namespace Ui {
+     class WelcomeWidget;
+ }
+@@ -31,7 +29,7 @@ class WelcomeWidget : public QWidget
+     Q_OBJECT
+ public:
+-    explicit WelcomeWidget(QWidget* parent = Q_NULLPTR);
++    explicit WelcomeWidget(QWidget* parent = nullptr);
+     ~WelcomeWidget();
+ private:
+diff --git a/src/gui/entry/AutoTypeAssociationsModel.cpp b/src/gui/entry/AutoTypeAssociationsModel.cpp
+index 6d6dc97..49f6786 100644
+--- a/src/gui/entry/AutoTypeAssociationsModel.cpp
++++ b/src/gui/entry/AutoTypeAssociationsModel.cpp
+@@ -19,7 +19,7 @@
+ AutoTypeAssociationsModel::AutoTypeAssociationsModel(QObject* parent)
+     : QAbstractListModel(parent)
+-    , m_autoTypeAssociations(Q_NULLPTR)
++    , m_autoTypeAssociations(nullptr)
+ {
+ }
+diff --git a/src/gui/entry/AutoTypeAssociationsModel.h b/src/gui/entry/AutoTypeAssociationsModel.h
+index ecb4247..c75168c 100644
+--- a/src/gui/entry/AutoTypeAssociationsModel.h
++++ b/src/gui/entry/AutoTypeAssociationsModel.h
+@@ -29,12 +29,12 @@ class AutoTypeAssociationsModel : public QAbstractListModel
+     Q_OBJECT
+ public:
+-    explicit AutoTypeAssociationsModel(QObject* parent = Q_NULLPTR);
++    explicit AutoTypeAssociationsModel(QObject* parent = nullptr);
+     void setAutoTypeAssociations(AutoTypeAssociations* autoTypeAssociations);
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    int columnCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    int columnCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
+ public Q_SLOTS:
+     void associationChange(int i);
+diff --git a/src/gui/entry/EditEntryWidget.cpp b/src/gui/entry/EditEntryWidget.cpp
+index 8cad924..00d510c 100644
+--- a/src/gui/entry/EditEntryWidget.cpp
++++ b/src/gui/entry/EditEntryWidget.cpp
+@@ -23,6 +23,7 @@
+ #include <QDesktopServices>
+ #include <QStackedLayout>
++#include <QStandardPaths>
+ #include <QMenu>
+ #include <QSortFilterProxyModel>
+ #include <QTemporaryFile>
+@@ -45,7 +46,7 @@
+ EditEntryWidget::EditEntryWidget(QWidget* parent)
+     : EditWidget(parent)
+-    , m_entry(Q_NULLPTR)
++    , m_entry(nullptr)
+     , m_mainUi(new Ui::EditEntryWidgetMain())
+     , m_advancedUi(new Ui::EditEntryWidgetAdvanced())
+     , m_autoTypeUi(new Ui::EditEntryWidgetAutoType())
+@@ -232,7 +233,7 @@ void EditEntryWidget::useExpiryPreset(QAction* action)
+ {
+     m_mainUi->expireCheck->setChecked(true);
+     TimeDelta delta = action->data().value<TimeDelta>();
+-    QDateTime now = Tools::currentDateTimeUtc().toLocalTime();
++    QDateTime now = QDateTime::currentDateTime();
+     QDateTime expiryDateTime = now + delta;
+     m_mainUi->expireDatePicker->setDateTime(expiryDateTime);
+ }
+@@ -477,8 +478,8 @@ void EditEntryWidget::cancel()
+ void EditEntryWidget::clear()
+ {
+-    m_entry = Q_NULLPTR;
+-    m_database = Q_NULLPTR;
++    m_entry = nullptr;
++    m_database = nullptr;
+     m_entryAttributes->clear();
+     m_entryAttachments->clear();
+     m_autoTypeAssoc->clear();
+@@ -590,7 +591,7 @@ void EditEntryWidget::insertAttachment()
+     QString defaultDir = config()->get("LastAttachmentDir").toString();
+     if (defaultDir.isEmpty() || !QDir(defaultDir).exists()) {
+-        defaultDir = QDesktopServices::storageLocation(QDesktopServices::DocumentsLocation);
++        defaultDir = QStandardPaths::standardLocations(QStandardPaths::DocumentsLocation).value(0);
+     }
+     QString filename = fileDialog()->getOpenFileName(this, tr("Select file"), defaultDir);
+     if (filename.isEmpty() || !QFile::exists(filename)) {
+@@ -624,7 +625,7 @@ void EditEntryWidget::saveCurrentAttachment()
+     QString filename = m_attachmentsModel->keyByIndex(index);
+     QString defaultDirName = config()->get("LastAttachmentDir").toString();
+     if (defaultDirName.isEmpty() || !QDir(defaultDirName).exists()) {
+-        defaultDirName = QDesktopServices::storageLocation(QDesktopServices::DocumentsLocation);
++        defaultDirName = QStandardPaths::writableLocation(QStandardPaths::DocumentsLocation);
+     }
+     QDir dir(defaultDirName);
+     QString savePath = fileDialog()->getSaveFileName(this, tr("Save attachment"),
+diff --git a/src/gui/entry/EditEntryWidget.h b/src/gui/entry/EditEntryWidget.h
+index 03811bf..3c66b2a 100644
+--- a/src/gui/entry/EditEntryWidget.h
++++ b/src/gui/entry/EditEntryWidget.h
+@@ -52,7 +52,7 @@ class EditEntryWidget : public EditWidget
+     Q_OBJECT
+ public:
+-    explicit EditEntryWidget(QWidget* parent = Q_NULLPTR);
++    explicit EditEntryWidget(QWidget* parent = nullptr);
+     ~EditEntryWidget();
+     void loadEntry(Entry* entry, bool create, bool history, const QString& parentName,
+diff --git a/src/gui/entry/EntryAttachmentsModel.cpp b/src/gui/entry/EntryAttachmentsModel.cpp
+index e072d17..39ed69f 100644
+--- a/src/gui/entry/EntryAttachmentsModel.cpp
++++ b/src/gui/entry/EntryAttachmentsModel.cpp
+@@ -20,9 +20,11 @@
+ #include "core/Entry.h"
+ #include "core/Tools.h"
++#include <algorithm>
++
+ EntryAttachmentsModel::EntryAttachmentsModel(QObject* parent)
+     : QAbstractListModel(parent)
+-    , m_entryAttachments(Q_NULLPTR)
++    , m_entryAttachments(nullptr)
+ {
+ }
+@@ -102,7 +104,7 @@ void EntryAttachmentsModel::attachmentAboutToAdd(const QString& key)
+ {
+     QList<QString> rows = m_entryAttachments->keys();
+     rows.append(key);
+-    qSort(rows);
++    std::sort(rows.begin(), rows.end());
+     int row = rows.indexOf(key);
+     beginInsertRows(QModelIndex(), row, row);
+ }
+diff --git a/src/gui/entry/EntryAttachmentsModel.h b/src/gui/entry/EntryAttachmentsModel.h
+index 177cde0..c2e238a 100644
+--- a/src/gui/entry/EntryAttachmentsModel.h
++++ b/src/gui/entry/EntryAttachmentsModel.h
+@@ -20,8 +20,6 @@
+ #include <QAbstractListModel>
+-#include "core/Global.h"
+-
+ class EntryAttachments;
+ class EntryAttachmentsModel : public QAbstractListModel
+@@ -29,11 +27,11 @@ class EntryAttachmentsModel : public QAbstractListModel
+     Q_OBJECT
+ public:
+-    explicit EntryAttachmentsModel(QObject* parent = Q_NULLPTR);
++    explicit EntryAttachmentsModel(QObject* parent = nullptr);
+     void setEntryAttachments(EntryAttachments* entry);
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    int columnCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    int columnCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
+     QString keyByIndex(const QModelIndex& index) const;
+ private Q_SLOTS:
+diff --git a/src/gui/entry/EntryAttributesModel.cpp b/src/gui/entry/EntryAttributesModel.cpp
+index f73a2d2..297740c 100644
+--- a/src/gui/entry/EntryAttributesModel.cpp
++++ b/src/gui/entry/EntryAttributesModel.cpp
+@@ -20,9 +20,11 @@
+ #include "core/Entry.h"
+ #include "core/Tools.h"
++#include <algorithm>
++
+ EntryAttributesModel::EntryAttributesModel(QObject* parent)
+     : QAbstractListModel(parent)
+-    , m_entryAttributes(Q_NULLPTR)
++    , m_entryAttributes(nullptr)
+     , m_nextRenameDataChange(false)
+ {
+ }
+@@ -152,7 +154,7 @@ void EntryAttributesModel::attributeAboutToAdd(const QString& key)
+ {
+     QList<QString> rows = m_attributes;
+     rows.append(key);
+-    qSort(rows);
++    std::sort(rows.begin(), rows.end());
+     int row = rows.indexOf(key);
+     beginInsertRows(QModelIndex(), row, row);
+ }
+@@ -182,7 +184,7 @@ void EntryAttributesModel::attributeAboutToRename(const QString& oldKey, const Q
+     QList<QString> rows = m_attributes;
+     rows.removeOne(oldKey);
+     rows.append(newKey);
+-    qSort(rows);
++    std::sort(rows.begin(), rows.end());
+     int newRow = rows.indexOf(newKey);
+     if (newRow > oldRow) {
+         newRow++;
+diff --git a/src/gui/entry/EntryAttributesModel.h b/src/gui/entry/EntryAttributesModel.h
+index f6ac651..1eec8bf 100644
+--- a/src/gui/entry/EntryAttributesModel.h
++++ b/src/gui/entry/EntryAttributesModel.h
+@@ -20,8 +20,6 @@
+ #include <QAbstractListModel>
+-#include "core/Global.h"
+-
+ class EntryAttributes;
+ class EntryAttributesModel : public QAbstractListModel
+@@ -29,14 +27,14 @@ class EntryAttributesModel : public QAbstractListModel
+     Q_OBJECT
+ public:
+-    explicit EntryAttributesModel(QObject* parent = Q_NULLPTR);
++    explicit EntryAttributesModel(QObject* parent = nullptr);
+     void setEntryAttributes(EntryAttributes* entryAttributes);
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    int columnCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    bool setData(const QModelIndex& index, const QVariant& value, int role = Qt::EditRole) Q_DECL_OVERRIDE;
+-    Qt::ItemFlags flags(const QModelIndex& index) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    int columnCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
++    bool setData(const QModelIndex& index, const QVariant& value, int role = Qt::EditRole) override;
++    Qt::ItemFlags flags(const QModelIndex& index) const override;
+     QModelIndex indexByKey(const QString& key) const;
+     QString keyByIndex(const QModelIndex& index) const;
+diff --git a/src/gui/entry/EntryHistoryModel.h b/src/gui/entry/EntryHistoryModel.h
+index 6c8073a..a7434e0 100644
+--- a/src/gui/entry/EntryHistoryModel.h
++++ b/src/gui/entry/EntryHistoryModel.h
+@@ -20,8 +20,6 @@
+ #include <QAbstractTableModel>
+-#include "core/Global.h"
+-
+ class Entry;
+ class EntryHistoryModel : public QAbstractTableModel
+@@ -29,13 +27,13 @@ class EntryHistoryModel : public QAbstractTableModel
+     Q_OBJECT
+ public:
+-    explicit EntryHistoryModel(QObject* parent = Q_NULLPTR);
++    explicit EntryHistoryModel(QObject* parent = nullptr);
+     Entry* entryFromIndex(const QModelIndex& index) const;
+-    int columnCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    QVariant headerData(int section, Qt::Orientation orientation, int role) const Q_DECL_OVERRIDE;
++    int columnCount(const QModelIndex& parent = QModelIndex()) const override;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
++    QVariant headerData(int section, Qt::Orientation orientation, int role) const override;
+     void setEntries(const QList<Entry*>& entries);
+     void clear();
+diff --git a/src/gui/entry/EntryModel.cpp b/src/gui/entry/EntryModel.cpp
+index 084ad72..efb64de 100644
+--- a/src/gui/entry/EntryModel.cpp
++++ b/src/gui/entry/EntryModel.cpp
+@@ -27,9 +27,8 @@
+ EntryModel::EntryModel(QObject* parent)
+     : QAbstractTableModel(parent)
+-    , m_group(Q_NULLPTR)
++    , m_group(nullptr)
+ {
+-    setSupportedDragActions(Qt::MoveAction | Qt::CopyAction);
+ }
+ Entry* EntryModel::entryFromIndex(const QModelIndex& index) const
+@@ -72,7 +71,7 @@ void EntryModel::setEntryList(const QList<Entry*>& entries)
+     severConnections();
+-    m_group = Q_NULLPTR;
++    m_group = nullptr;
+     m_allGroups.clear();
+     m_entries = entries;
+     m_orgEntries = entries;
+@@ -191,6 +190,11 @@ Qt::DropActions EntryModel::supportedDropActions() const
+     return 0;
+ }
++Qt::DropActions EntryModel::supportedDragActions() const
++{
++    return (Qt::MoveAction | Qt::CopyAction);
++}
++
+ Qt::ItemFlags EntryModel::flags(const QModelIndex& modelIndex) const
+ {
+     if (!modelIndex.isValid()) {
+@@ -211,7 +215,7 @@ QStringList EntryModel::mimeTypes() const
+ QMimeData* EntryModel::mimeData(const QModelIndexList& indexes) const
+ {
+     if (indexes.isEmpty()) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QMimeData* data = new QMimeData();
+@@ -236,7 +240,7 @@ QMimeData* EntryModel::mimeData(const QModelIndexList& indexes) const
+     if (seenEntries.isEmpty()) {
+         delete data;
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     else {
+         data->setData(mimeTypes().at(0), encoded);
+@@ -294,11 +298,11 @@ void EntryModel::entryDataChanged(Entry* entry)
+ void EntryModel::severConnections()
+ {
+     if (m_group) {
+-        disconnect(m_group, Q_NULLPTR, this, Q_NULLPTR);
++        disconnect(m_group, nullptr, this, nullptr);
+     }
+     Q_FOREACH (const Group* group, m_allGroups) {
+-        disconnect(group, Q_NULLPTR, this, Q_NULLPTR);
++        disconnect(group, nullptr, this, nullptr);
+     }
+ }
+diff --git a/src/gui/entry/EntryModel.h b/src/gui/entry/EntryModel.h
+index 20bcad9..0183c47 100644
+--- a/src/gui/entry/EntryModel.h
++++ b/src/gui/entry/EntryModel.h
+@@ -20,8 +20,6 @@
+ #include <QAbstractTableModel>
+-#include "core/Global.h"
+-
+ class Entry;
+ class Group;
+@@ -38,18 +36,19 @@ public:
+         Url = 3
+     };
+-    explicit EntryModel(QObject* parent = Q_NULLPTR);
++    explicit EntryModel(QObject* parent = nullptr);
+     Entry* entryFromIndex(const QModelIndex& index) const;
+     QModelIndex indexFromEntry(Entry* entry) const;
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    int columnCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    Qt::DropActions supportedDropActions() const Q_DECL_OVERRIDE;
+-    Qt::ItemFlags flags(const QModelIndex& modelIndex) const Q_DECL_OVERRIDE;
+-    QStringList mimeTypes() const Q_DECL_OVERRIDE;
+-    QMimeData* mimeData(const QModelIndexList& indexes) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    int columnCount(const QModelIndex& parent = QModelIndex()) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
++    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
++    Qt::DropActions supportedDropActions() const override;
++    Qt::DropActions supportedDragActions() const override;
++    Qt::ItemFlags flags(const QModelIndex& modelIndex) const override;
++    QStringList mimeTypes() const override;
++    QMimeData* mimeData(const QModelIndexList& indexes) const override;
+     void setEntryList(const QList<Entry*>& entries);
+diff --git a/src/gui/entry/EntryView.cpp b/src/gui/entry/EntryView.cpp
+index cd2c6fb..1c900a5 100644
+--- a/src/gui/entry/EntryView.cpp
++++ b/src/gui/entry/EntryView.cpp
+@@ -32,7 +32,6 @@ EntryView::EntryView(QWidget* parent)
+     m_sortModel->setDynamicSortFilter(true);
+     m_sortModel->setSortLocaleAware(true);
+     m_sortModel->setSortCaseSensitivity(Qt::CaseInsensitive);
+-    m_sortModel->setSupportedDragActions(m_model->supportedDragActions());
+     QTreeView::setModel(m_sortModel);
+     setUniformRowHeights(true);
+@@ -75,7 +74,7 @@ void EntryView::setEntryList(const QList<Entry*>& entries)
+ void EntryView::setFirstEntryActive()
+ {
+-    if(m_model->rowCount() > 0) {
++    if (m_model->rowCount() > 0) {
+         QModelIndex index = m_sortModel->mapToSource(m_sortModel->index(0, 0));
+         setCurrentEntry(m_model->entryFromIndex(index));
+     }
+@@ -109,7 +108,7 @@ Entry* EntryView::currentEntry()
+         return m_model->entryFromIndex(m_sortModel->mapToSource(list.first()));
+     }
+     else {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+ }
+@@ -130,7 +129,7 @@ Entry* EntryView::entryFromIndex(const QModelIndex& index)
+         return m_model->entryFromIndex(m_sortModel->mapToSource(index));
+     }
+     else {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+ }
+diff --git a/src/gui/entry/EntryView.h b/src/gui/entry/EntryView.h
+index c11d041..fb9e356 100644
+--- a/src/gui/entry/EntryView.h
++++ b/src/gui/entry/EntryView.h
+@@ -20,8 +20,6 @@
+ #include <QTreeView>
+-#include "core/Global.h"
+-
+ #include "gui/entry/EntryModel.h"
+ class Entry;
+@@ -34,8 +32,8 @@ class EntryView : public QTreeView
+     Q_OBJECT
+ public:
+-    explicit EntryView(QWidget* parent = Q_NULLPTR);
+-    void setModel(QAbstractItemModel* model) Q_DECL_OVERRIDE;
++    explicit EntryView(QWidget* parent = nullptr);
++    void setModel(QAbstractItemModel* model) override;
+     Entry* currentEntry();
+     void setCurrentEntry(Entry* entry);
+     Entry* entryFromIndex(const QModelIndex& index);
+@@ -52,7 +50,7 @@ Q_SIGNALS:
+     void entrySelectionChanged();
+ protected:
+-    void keyPressEvent(QKeyEvent* event) Q_DECL_OVERRIDE;
++    void keyPressEvent(QKeyEvent* event) override;
+ private Q_SLOTS:
+     void emitEntryActivated(const QModelIndex& index);
+diff --git a/src/gui/group/EditGroupWidget.cpp b/src/gui/group/EditGroupWidget.cpp
+index ebe5cb9..7fdec89 100644
+--- a/src/gui/group/EditGroupWidget.cpp
++++ b/src/gui/group/EditGroupWidget.cpp
+@@ -28,8 +28,8 @@ EditGroupWidget::EditGroupWidget(QWidget* parent)
+     , m_editGroupWidgetMain(new QWidget())
+     , m_editGroupWidgetIcons(new EditWidgetIcons())
+     , m_editWidgetProperties(new EditWidgetProperties())
+-    , m_group(Q_NULLPTR)
+-    , m_database(Q_NULLPTR)
++    , m_group(nullptr)
++    , m_database(nullptr)
+ {
+     m_mainUi->setupUi(m_editGroupWidgetMain);
+@@ -142,8 +142,8 @@ void EditGroupWidget::cancel()
+ void EditGroupWidget::clear()
+ {
+-    m_group = Q_NULLPTR;
+-    m_database = Q_NULLPTR;
++    m_group = nullptr;
++    m_database = nullptr;
+ }
+ void EditGroupWidget::addTriStateItems(QComboBox* comboBox, bool inheritDefault)
+diff --git a/src/gui/group/EditGroupWidget.h b/src/gui/group/EditGroupWidget.h
+index c6d91a5..94ad891 100644
+--- a/src/gui/group/EditGroupWidget.h
++++ b/src/gui/group/EditGroupWidget.h
+@@ -37,7 +37,7 @@ class EditGroupWidget : public EditWidget
+     Q_OBJECT
+ public:
+-    explicit EditGroupWidget(QWidget* parent = Q_NULLPTR);
++    explicit EditGroupWidget(QWidget* parent = nullptr);
+     ~EditGroupWidget();
+     void loadGroup(Group* group, bool create, Database* database);
+diff --git a/src/gui/group/GroupModel.cpp b/src/gui/group/GroupModel.cpp
+index 1244ad7..fc6d83e 100644
+--- a/src/gui/group/GroupModel.cpp
++++ b/src/gui/group/GroupModel.cpp
+@@ -28,7 +28,7 @@
+ GroupModel::GroupModel(Database* db, QObject* parent)
+     : QAbstractItemModel(parent)
+-    , m_db(Q_NULLPTR)
++    , m_db(nullptr)
+ {
+     changeDatabase(db);
+ }
+@@ -329,7 +329,7 @@ QStringList GroupModel::mimeTypes() const
+ QMimeData* GroupModel::mimeData(const QModelIndexList& indexes) const
+ {
+     if (indexes.isEmpty()) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     QMimeData* data = new QMimeData();
+@@ -354,7 +354,7 @@ QMimeData* GroupModel::mimeData(const QModelIndexList& indexes) const
+     if (seenGroups.isEmpty()) {
+         delete data;
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     else {
+         data->setData(mimeTypes().at(0), encoded);
+diff --git a/src/gui/group/GroupModel.h b/src/gui/group/GroupModel.h
+index 752eb2b..0ef0ba9 100644
+--- a/src/gui/group/GroupModel.h
++++ b/src/gui/group/GroupModel.h
+@@ -20,8 +20,6 @@
+ #include <QAbstractItemModel>
+-#include "core/Global.h"
+-
+ class Database;
+ class Group;
+@@ -30,23 +28,23 @@ class GroupModel : public QAbstractItemModel
+     Q_OBJECT
+ public:
+-    explicit GroupModel(Database* db, QObject* parent = Q_NULLPTR);
++    explicit GroupModel(Database* db, QObject* parent = nullptr);
+     void changeDatabase(Database* newDb);
+     QModelIndex index(Group* group) const;
+     Group* groupFromIndex(const QModelIndex& index) const;
+-    int rowCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    int columnCount(const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QModelIndex index(int row, int column, const QModelIndex& parent = QModelIndex()) const Q_DECL_OVERRIDE;
+-    QModelIndex parent(const QModelIndex& index) const Q_DECL_OVERRIDE;
+-    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE;
+-    Qt::DropActions supportedDropActions() const Q_DECL_OVERRIDE;
+-    Qt::ItemFlags flags(const QModelIndex& modelIndex) const Q_DECL_OVERRIDE;
++    int rowCount(const QModelIndex& parent = QModelIndex()) const override;
++    int columnCount(const QModelIndex& parent = QModelIndex()) const override;
++    QModelIndex index(int row, int column, const QModelIndex& parent = QModelIndex()) const override;
++    QModelIndex parent(const QModelIndex& index) const override;
++    QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
++    QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
++    Qt::DropActions supportedDropActions() const override;
++    Qt::ItemFlags flags(const QModelIndex& modelIndex) const override;
+     bool dropMimeData(const QMimeData* data, Qt::DropAction action, int row, int column,
+-                      const QModelIndex& parent) Q_DECL_OVERRIDE;
+-    QStringList mimeTypes() const Q_DECL_OVERRIDE;
+-    QMimeData* mimeData(const QModelIndexList& indexes) const Q_DECL_OVERRIDE;
++                      const QModelIndex& parent) override;
++    QStringList mimeTypes() const override;
++    QMimeData* mimeData(const QModelIndexList& indexes) const override;
+ private:
+     QModelIndex parent(Group* group) const;
+diff --git a/src/gui/group/GroupView.cpp b/src/gui/group/GroupView.cpp
+index 3c93662..1f94dc0 100644
+--- a/src/gui/group/GroupView.cpp
++++ b/src/gui/group/GroupView.cpp
+@@ -19,6 +19,7 @@
+ #include <QDragMoveEvent>
+ #include <QMetaObject>
++#include <QMimeData>
+ #include "core/Database.h"
+ #include "core/Group.h"
+@@ -74,7 +75,7 @@ void GroupView::dragMoveEvent(QDragMoveEvent* event)
+ Group* GroupView::currentGroup()
+ {
+     if (currentIndex() == QModelIndex()) {
+-        return Q_NULLPTR;
++        return nullptr;
+     }
+     else {
+         return m_model->groupFromIndex(currentIndex());
+diff --git a/src/gui/group/GroupView.h b/src/gui/group/GroupView.h
+index 06bdbaf..69ca828 100644
+--- a/src/gui/group/GroupView.h
++++ b/src/gui/group/GroupView.h
+@@ -20,8 +20,6 @@
+ #include <QTreeView>
+-#include "core/Global.h"
+-
+ class Database;
+ class Group;
+ class GroupModel;
+@@ -31,9 +29,9 @@ class GroupView : public QTreeView
+     Q_OBJECT
+ public:
+-    explicit GroupView(Database* db, QWidget* parent = Q_NULLPTR);
++    explicit GroupView(Database* db, QWidget* parent = nullptr);
+     void changeDatabase(Database* newDb);
+-    void setModel(QAbstractItemModel* model) Q_DECL_OVERRIDE;
++    void setModel(QAbstractItemModel* model) override;
+     Group* currentGroup();
+     void setCurrentGroup(Group* group);
+     void expandGroup(Group* group, bool expand = true);
+@@ -49,7 +47,7 @@ private Q_SLOTS:
+     void modelReset();
+ protected:
+-    void dragMoveEvent(QDragMoveEvent* event) Q_DECL_OVERRIDE;
++    void dragMoveEvent(QDragMoveEvent* event) override;
+ private:
+     void recInitExpanded(Group* group);
+diff --git a/src/keys/CompositeKey.cpp b/src/keys/CompositeKey.cpp
+index 5bf9cae..d38f466 100644
+--- a/src/keys/CompositeKey.cpp
++++ b/src/keys/CompositeKey.cpp
+@@ -18,8 +18,8 @@
+ #include "CompositeKey.h"
+ #include "CompositeKey_p.h"
+-#include <QtConcurrentRun>
+-#include <QTime>
++#include <QtConcurrent>
++#include <QElapsedTimer>
+ #include "crypto/CryptoHash.h"
+ #include "crypto/SymmetricCipher.h"
+@@ -94,7 +94,8 @@ QByteArray CompositeKey::transform(const QByteArray& seed, quint64 rounds,
+     QByteArray key = rawKey();
+-    QFuture<QByteArray> future = QtConcurrent::run(transformKeyRaw, key.left(16), seed, rounds, &okLeft, &errorStringLeft);
++    QFuture<QByteArray> future = QtConcurrent::run(transformKeyRaw, key.left(16), seed, rounds,
++                                                   &okLeft, &errorStringLeft);
+     QByteArray result2 = transformKeyRaw(key.right(16), seed, rounds, &okRight, &errorStringRight);
+     QByteArray transformed;
+@@ -182,7 +183,7 @@ void TransformKeyBenchmarkThread::run()
+                            SymmetricCipher::Encrypt);
+     cipher.init(seed, iv);
+-    QTime t;
++    QElapsedTimer t;
+     t.start();
+     do {
+@@ -191,5 +192,5 @@ void TransformKeyBenchmarkThread::run()
+             return;
+         }
+         m_rounds += 10000;
+-    } while (t.elapsed() < m_msec);
++    } while (!t.hasExpired(m_msec));
+ }
+diff --git a/src/keys/FileKey.h b/src/keys/FileKey.h
+index f985433..7a9b1ca 100644
+--- a/src/keys/FileKey.h
++++ b/src/keys/FileKey.h
+@@ -20,7 +20,6 @@
+ #include <QXmlStreamReader>
+-#include "core/Global.h"
+ #include "keys/Key.h"
+ class QIODevice;
+@@ -30,11 +29,11 @@ class FileKey : public Key
+ public:
+     FileKey();
+     bool load(QIODevice* device);
+-    bool load(const QString& fileName, QString* errorMsg = Q_NULLPTR);
++    bool load(const QString& fileName, QString* errorMsg = nullptr);
+     QByteArray rawKey() const;
+     FileKey* clone() const;
+     static void create(QIODevice* device);
+-    static bool create(const QString& fileName, QString* errorMsg = Q_NULLPTR);
++    static bool create(const QString& fileName, QString* errorMsg = nullptr);
+ private:
+     bool loadXml(QIODevice* device);
+diff --git a/src/main.cpp b/src/main.cpp
+index bf558f1..04b70a4 100644
+--- a/src/main.cpp
++++ b/src/main.cpp
+@@ -15,11 +15,11 @@
+  *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+  */
++#include <QCommandLineParser>
+ #include <QFile>
+ #include "config-keepassx.h"
+ #include "core/Config.h"
+-#include "core/qcommandlineparser.h"
+ #include "core/Tools.h"
+ #include "core/Translator.h"
+ #include "crypto/Crypto.h"
+@@ -38,7 +38,7 @@ int main(int argc, char** argv)
+     Application::setApplicationName("keepassx");
+     Application::setApplicationVersion(KEEPASSX_VERSION);
+     // don't set organizationName as that changes the return value of
+-    // QDesktopServices::storageLocation(QDesktopServices::DataLocation)
++    // QStandardPaths::writableLocation(QDesktopServices::DataLocation)
+     QApplication::setQuitOnLastWindowClosed(false);
+@@ -47,7 +47,7 @@ int main(int argc, char** argv)
+                                                     "Fatal error while testing the cryptographic functions.");
+         error.append("\n");
+         error.append(Crypto::errorString());
+-        MessageBox::critical(Q_NULLPTR, QCoreApplication::translate("Main", "KeePassX - Error"), error);
++        MessageBox::critical(nullptr, QCoreApplication::translate("Main", "KeePassX - Error"), error);
+         return 1;
+     }
+diff --git a/src/streams/HashedBlockStream.h b/src/streams/HashedBlockStream.h
+index cae4eb4..93e4af5 100644
+--- a/src/streams/HashedBlockStream.h
++++ b/src/streams/HashedBlockStream.h
+@@ -31,12 +31,12 @@ public:
+     HashedBlockStream(QIODevice* baseDevice, qint32 blockSize);
+     ~HashedBlockStream();
+-    bool reset() Q_DECL_OVERRIDE;
+-    void close() Q_DECL_OVERRIDE;
++    bool reset() override;
++    void close() override;
+ protected:
+-    qint64 readData(char* data, qint64 maxSize) Q_DECL_OVERRIDE;
+-    qint64 writeData(const char* data, qint64 maxSize) Q_DECL_OVERRIDE;
++    qint64 readData(char* data, qint64 maxSize) override;
++    qint64 writeData(const char* data, qint64 maxSize) override;
+ private:
+     void init();
+diff --git a/src/streams/LayeredStream.h b/src/streams/LayeredStream.h
+index b243e55..8586b41 100644
+--- a/src/streams/LayeredStream.h
++++ b/src/streams/LayeredStream.h
+@@ -20,8 +20,6 @@
+ #include <QIODevice>
+-#include "core/Global.h"
+-
+ class LayeredStream : public QIODevice
+ {
+     Q_OBJECT
+@@ -30,12 +28,12 @@ public:
+     explicit LayeredStream(QIODevice* baseDevice);
+     virtual ~LayeredStream();
+-    bool isSequential() const Q_DECL_OVERRIDE;
+-    bool open(QIODevice::OpenMode mode) Q_DECL_OVERRIDE;
++    bool isSequential() const override;
++    bool open(QIODevice::OpenMode mode) override;
+ protected:
+-    qint64 readData(char* data, qint64 maxSize) Q_DECL_OVERRIDE;
+-    qint64 writeData(const char* data, qint64 maxSize) Q_DECL_OVERRIDE;
++    qint64 readData(char* data, qint64 maxSize) override;
++    qint64 writeData(const char* data, qint64 maxSize) override;
+     QIODevice* const m_baseDevice;
+diff --git a/src/streams/StoreDataStream.h b/src/streams/StoreDataStream.h
+index 4143438..9f39d6a 100644
+--- a/src/streams/StoreDataStream.h
++++ b/src/streams/StoreDataStream.h
+@@ -26,11 +26,11 @@ class StoreDataStream : public LayeredStream
+ public:
+     explicit StoreDataStream(QIODevice* baseDevice);
+-    bool open(QIODevice::OpenMode mode) Q_DECL_OVERRIDE;
++    bool open(QIODevice::OpenMode mode) override;
+     QByteArray storedData() const;
+ protected:
+-    qint64 readData(char* data, qint64 maxSize) Q_DECL_OVERRIDE;
++    qint64 readData(char* data, qint64 maxSize) override;
+ private:
+     QByteArray m_storedData;
+diff --git a/src/streams/SymmetricCipherStream.h b/src/streams/SymmetricCipherStream.h
+index fa44605..b6228e1 100644
+--- a/src/streams/SymmetricCipherStream.h
++++ b/src/streams/SymmetricCipherStream.h
+@@ -33,13 +33,13 @@ public:
+                           SymmetricCipher::Mode mode, SymmetricCipher::Direction direction);
+     ~SymmetricCipherStream();
+     bool init(const QByteArray& key, const QByteArray& iv);
+-    bool open(QIODevice::OpenMode mode) Q_DECL_OVERRIDE;
+-    bool reset() Q_DECL_OVERRIDE;
+-    void close() Q_DECL_OVERRIDE;
++    bool open(QIODevice::OpenMode mode) override;
++    bool reset() override;
++    void close() override;
+ protected:
+-    qint64 readData(char* data, qint64 maxSize) Q_DECL_OVERRIDE;
+-    qint64 writeData(const char* data, qint64 maxSize) Q_DECL_OVERRIDE;
++    qint64 readData(char* data, qint64 maxSize) override;
++    qint64 writeData(const char* data, qint64 maxSize) override;
+ private:
+     void resetInternalState();
+diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt
+index 2de7094..7ea399f 100644
+--- a/tests/CMakeLists.txt
++++ b/tests/CMakeLists.txt
+@@ -52,10 +52,9 @@ macro(parse_arguments prefix arg_names option_names)
+ endmacro(parse_arguments)
+ macro(add_unit_test)
+-  parse_arguments(TEST "NAME;SOURCES;MOCS;LIBS" "" ${ARGN})
++  parse_arguments(TEST "NAME;SOURCES;LIBS" "" ${ARGN})
+   set(_test_NAME ${TEST_NAME})
+   set(_srcList ${TEST_SOURCES})
+-  qt4_wrap_cpp(_srcList ${TEST_MOCS})
+   add_executable(${_test_NAME} ${_srcList})
+   target_link_libraries(${_test_NAME} ${TEST_LIBS})
+@@ -86,85 +85,80 @@ endmacro(add_unit_test)
+ set(TEST_LIBRARIES
+     keepassx_core
+-    ${QT_QTCORE_LIBRARY}
+-    ${QT_QTGUI_LIBRARY}
+-    ${QT_QTTEST_LIBRARY}
++    Qt5::Core
++    Qt5::Concurrent
++    Qt5::Widgets
++    Qt5::Test
+     ${GCRYPT_LIBRARIES}
+     ${ZLIB_LIBRARIES}
+ )
+ set(testsupport_SOURCES modeltest.cpp FailDevice.cpp)
+-qt4_wrap_cpp(testsupport_SOURCES modeltest.h FailDevice.h)
+ add_library(testsupport STATIC ${testsupport_SOURCES})
++target_link_libraries(testsupport Qt5::Core Qt5::Concurrent Qt5::Widgets Qt5::Test)
+-add_unit_test(NAME testgroup SOURCES TestGroup.cpp MOCS TestGroup.h
++add_unit_test(NAME testgroup SOURCES TestGroup.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testkeepass2xmlreader SOURCES TestKeePass2XmlReader.cpp MOCS TestKeePass2XmlReader.h
++add_unit_test(NAME testkeepass2xmlreader SOURCES TestKeePass2XmlReader.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testkeys SOURCES TestKeys.cpp MOCS TestKeys.h
++add_unit_test(NAME testkeys SOURCES TestKeys.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testkeepass2reader SOURCES TestKeePass2Reader.cpp MOCS TestKeePass2Reader.h
++add_unit_test(NAME testkeepass2reader SOURCES TestKeePass2Reader.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testkeepass2writer SOURCES TestKeePass2Writer.cpp MOCS TestKeePass2Writer.h
++add_unit_test(NAME testkeepass2writer SOURCES TestKeePass2Writer.cpp
+               LIBS testsupport ${TEST_LIBRARIES})
+-add_unit_test(NAME testgroupmodel SOURCES TestGroupModel.cpp MOCS TestGroupModel.h
++add_unit_test(NAME testgroupmodel SOURCES TestGroupModel.cpp
+               LIBS testsupport ${TEST_LIBRARIES})
+-add_unit_test(NAME testentrymodel SOURCES TestEntryModel.cpp MOCS TestEntryModel.h
++add_unit_test(NAME testentrymodel SOURCES TestEntryModel.cpp
+               LIBS testsupport ${TEST_LIBRARIES})
+-add_unit_test(NAME testcryptohash SOURCES TestCryptoHash.cpp MOCS TestCryptoHash.h
++add_unit_test(NAME testcryptohash SOURCES TestCryptoHash.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testsymmetriccipher SOURCES TestSymmetricCipher.cpp MOCS TestSymmetricCipher.h
++add_unit_test(NAME testsymmetriccipher SOURCES TestSymmetricCipher.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testhashedblockstream SOURCES TestHashedBlockStream.cpp MOCS TestHashedBlockStream.h
++add_unit_test(NAME testhashedblockstream SOURCES TestHashedBlockStream.cpp
+               LIBS testsupport ${TEST_LIBRARIES})
+-add_unit_test(NAME testkeepass2randomstream SOURCES TestKeePass2RandomStream.cpp MOCS TestKeePass2RandomStream.h
++add_unit_test(NAME testkeepass2randomstream SOURCES TestKeePass2RandomStream.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testmodified SOURCES TestModified.cpp MOCS TestModified.h
++add_unit_test(NAME testmodified SOURCES TestModified.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testdeletedobjects SOURCES TestDeletedObjects.cpp MOCS TestDeletedObjects.h
++add_unit_test(NAME testdeletedobjects SOURCES TestDeletedObjects.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testkeepass1reader SOURCES TestKeePass1Reader.cpp MOCS TestKeePass1Reader.h
++add_unit_test(NAME testkeepass1reader SOURCES TestKeePass1Reader.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testqsavefile SOURCES TestQSaveFile.cpp MOCS TestQSaveFile.h
++add_unit_test(NAME testwildcardmatcher SOURCES TestWildcardMatcher.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testwildcardmatcher SOURCES TestWildcardMatcher.cpp MOCS TestWildcardMatcher.h
+-              LIBS ${TEST_LIBRARIES})
+-
+-add_unit_test(NAME testautotype SOURCES TestAutoType.cpp MOCS TestAutoType.h
++add_unit_test(NAME testautotype SOURCES TestAutoType.cpp
+               LIBS ${TEST_LIBRARIES})
+ set_target_properties(testautotype PROPERTIES ENABLE_EXPORTS ON)
+-add_unit_test(NAME testentry SOURCES TestEntry.cpp MOCS TestEntry.h
+-              LIBS ${TEST_LIBRARIES})
+-
+-add_unit_test(NAME testqcommandlineparser SOURCES TestQCommandLineParser.cpp MOCS TestQCommandLineParser.h
++add_unit_test(NAME testentry SOURCES TestEntry.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testrandom SOURCES TestRandom.cpp MOCS TestRandom.h
++add_unit_test(NAME testrandom SOURCES TestRandom.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testentrysearcher SOURCES TestEntrySearcher.cpp MOCS TestEntrySearcher.h
++add_unit_test(NAME testentrysearcher SOURCES TestEntrySearcher.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testexporter SOURCES TestExporter.cpp MOCS TestExporter.h
++add_unit_test(NAME testexporter SOURCES TestExporter.cpp
+               LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testcsvexporter SOURCES TestCsvExporter.cpp MOCS TestCsvExporter.h
++add_unit_test(NAME testcsvexporter SOURCES TestCsvExporter.cpp
+               LIBS ${TEST_LIBRARIES})
+ if(WITH_GUI_TESTS)
+diff --git a/tests/FailDevice.h b/tests/FailDevice.h
+index f812593..194d617 100644
+--- a/tests/FailDevice.h
++++ b/tests/FailDevice.h
+@@ -20,19 +20,17 @@
+ #include <QBuffer>
+-#include "core/Global.h"
+-
+ class FailDevice : public QBuffer
+ {
+     Q_OBJECT
+ public:
+-    explicit FailDevice(int failAfter, QObject* parent = Q_NULLPTR);
+-    bool open(QIODevice::OpenMode openMode) Q_DECL_OVERRIDE;
++    explicit FailDevice(int failAfter, QObject* parent = nullptr);
++    bool open(QIODevice::OpenMode openMode) override;
+ protected:
+-    qint64 readData(char* data, qint64 len) Q_DECL_OVERRIDE;
+-    qint64 writeData(const char* data, qint64 len) Q_DECL_OVERRIDE;
++    qint64 readData(char* data, qint64 len) override;
++    qint64 writeData(const char* data, qint64 len) override;
+ private:
+     int m_failAfter;
+diff --git a/tests/TestAutoType.cpp b/tests/TestAutoType.cpp
+index 8968348..cbd927f 100644
+--- a/tests/TestAutoType.cpp
++++ b/tests/TestAutoType.cpp
+@@ -20,7 +20,6 @@
+ #include <QPluginLoader>
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Config.h"
+ #include "core/FilePath.h"
+ #include "core/Entry.h"
+@@ -108,7 +107,7 @@ void TestAutoType::testInternal()
+ void TestAutoType::testAutoTypeWithoutSequence()
+ {
+-    m_autoType->performAutoType(m_entry1, Q_NULLPTR);
++    m_autoType->performAutoType(m_entry1, nullptr);
+     QCOMPARE(m_test->actionCount(), 14);
+     QCOMPARE(m_test->actionChars(),
+@@ -119,7 +118,7 @@ void TestAutoType::testAutoTypeWithoutSequence()
+ void TestAutoType::testAutoTypeWithSequence()
+ {
+-    m_autoType->performAutoType(m_entry1, Q_NULLPTR, "{Username}abc{PaSsWoRd}");
++    m_autoType->performAutoType(m_entry1, nullptr, "{Username}abc{PaSsWoRd}");
+     QCOMPARE(m_test->actionCount(), 15);
+     QCOMPARE(m_test->actionChars(),
+diff --git a/tests/TestCryptoHash.cpp b/tests/TestCryptoHash.cpp
+index 4002aea..c166f55 100644
+--- a/tests/TestCryptoHash.cpp
++++ b/tests/TestCryptoHash.cpp
+@@ -19,7 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "crypto/Crypto.h"
+ #include "crypto/CryptoHash.h"
+diff --git a/tests/TestCsvExporter.cpp b/tests/TestCsvExporter.cpp
+index 5965e60..1fa6634 100644
+--- a/tests/TestCsvExporter.cpp
++++ b/tests/TestCsvExporter.cpp
+@@ -21,8 +21,6 @@
+ #include <QBuffer>
+ #include <QTest>
+-#include "tests.h"
+-
+ #include "core/Database.h"
+ #include "core/Entry.h"
+ #include "core/Group.h"
+@@ -53,7 +51,7 @@ void TestCsvExporter::cleanUp()
+ void TestCsvExporter::testExport()
+ {
+     Group* groupRoot = m_db->rootGroup();
+-    Group* group= new Group();
++    Group* group = new Group();
+     group->setName("Test Group Name");
+     group->setParent(groupRoot);
+     Entry* entry = new Entry();
+@@ -85,10 +83,10 @@ void TestCsvExporter::testEmptyDatabase()
+ void TestCsvExporter::testNestedGroups()
+ {
+     Group* groupRoot = m_db->rootGroup();
+-    Group* group= new Group();
++    Group* group = new Group();
+     group->setName("Test Group Name");
+     group->setParent(groupRoot);
+-    Group* childGroup= new Group();
++    Group* childGroup = new Group();
+     childGroup->setName("Test Sub Group Name");
+     childGroup->setParent(group);
+     Entry* entry = new Entry();
+diff --git a/tests/TestCsvExporter.h b/tests/TestCsvExporter.h
+index a71c936..c8cc4dc 100644
+--- a/tests/TestCsvExporter.h
++++ b/tests/TestCsvExporter.h
+@@ -42,7 +42,6 @@ private Q_SLOTS:
+ private:
+     Database* m_db;
+     CsvExporter* m_csvExporter;
+-
+ };
+ #endif // KEEPASSX_TESTCSVEXPORTER_H
+diff --git a/tests/TestDeletedObjects.cpp b/tests/TestDeletedObjects.cpp
+index cf9e3d1..5af0178 100644
+--- a/tests/TestDeletedObjects.cpp
++++ b/tests/TestDeletedObjects.cpp
+@@ -19,7 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "crypto/Crypto.h"
+diff --git a/tests/TestEntry.cpp b/tests/TestEntry.cpp
+index f918b6c..1eaca32 100644
+--- a/tests/TestEntry.cpp
++++ b/tests/TestEntry.cpp
+@@ -19,7 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Entry.h"
+ #include "crypto/Crypto.h"
+diff --git a/tests/TestEntryModel.cpp b/tests/TestEntryModel.cpp
+index b323a73..3f956d7 100644
+--- a/tests/TestEntryModel.cpp
++++ b/tests/TestEntryModel.cpp
+@@ -21,7 +21,6 @@
+ #include <QTest>
+ #include "modeltest.h"
+-#include "tests.h"
+ #include "core/DatabaseIcons.h"
+ #include "core/Entry.h"
+ #include "core/Group.h"
+diff --git a/tests/TestEntrySearcher.cpp b/tests/TestEntrySearcher.cpp
+index 9f7ca13..6b951c7 100644
+--- a/tests/TestEntrySearcher.cpp
++++ b/tests/TestEntrySearcher.cpp
+@@ -19,8 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+-
+ QTEST_GUILESS_MAIN(TestEntrySearcher)
+ void TestEntrySearcher::initTestCase()
+diff --git a/tests/TestExporter.cpp b/tests/TestExporter.cpp
+index 76a6f75..656b76c 100644
+--- a/tests/TestExporter.cpp
++++ b/tests/TestExporter.cpp
+@@ -20,7 +20,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "core/ToDbExporter.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+@@ -77,6 +76,3 @@ void TestExporter::testToDbExporter()
+     delete dbOrg;
+     delete dbExp;
+ }
+-
+-
+-
+diff --git a/tests/TestGroup.cpp b/tests/TestGroup.cpp
+index 507cf15..13ce82e 100644
+--- a/tests/TestGroup.cpp
++++ b/tests/TestGroup.cpp
+@@ -21,7 +21,6 @@
+ #include <QSignalSpy>
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+diff --git a/tests/TestGroupModel.cpp b/tests/TestGroupModel.cpp
+index 32a4b8e..3608cc4 100644
+--- a/tests/TestGroupModel.cpp
++++ b/tests/TestGroupModel.cpp
+@@ -21,7 +21,6 @@
+ #include <QTest>
+ #include "modeltest.h"
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "crypto/Crypto.h"
+diff --git a/tests/TestHashedBlockStream.cpp b/tests/TestHashedBlockStream.cpp
+index d5a0cea..b78a46b 100644
+--- a/tests/TestHashedBlockStream.cpp
++++ b/tests/TestHashedBlockStream.cpp
+@@ -20,7 +20,6 @@
+ #include <QBuffer>
+ #include <QTest>
+-#include "tests.h"
+ #include "FailDevice.h"
+ #include "crypto/Crypto.h"
+ #include "streams/HashedBlockStream.h"
+diff --git a/tests/TestKeePass1Reader.cpp b/tests/TestKeePass1Reader.cpp
+index d9dff9e..f60846d 100644
+--- a/tests/TestKeePass1Reader.cpp
++++ b/tests/TestKeePass1Reader.cpp
+@@ -21,7 +21,6 @@
+ #include <QTest>
+ #include "config-keepassx-tests.h"
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Entry.h"
+ #include "core/Group.h"
+diff --git a/tests/TestKeePass2RandomStream.cpp b/tests/TestKeePass2RandomStream.cpp
+index cb88133..03dfbe5 100644
+--- a/tests/TestKeePass2RandomStream.cpp
++++ b/tests/TestKeePass2RandomStream.cpp
+@@ -19,7 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "crypto/Crypto.h"
+ #include "crypto/CryptoHash.h"
+ #include "crypto/SymmetricCipher.h"
+diff --git a/tests/TestKeePass2Reader.cpp b/tests/TestKeePass2Reader.cpp
+index d6cb70c..22973ee 100644
+--- a/tests/TestKeePass2Reader.cpp
++++ b/tests/TestKeePass2Reader.cpp
+@@ -20,7 +20,6 @@
+ #include <QTest>
+ #include "config-keepassx-tests.h"
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+diff --git a/tests/TestKeePass2Writer.cpp b/tests/TestKeePass2Writer.cpp
+index c872794..60b7b90 100644
+--- a/tests/TestKeePass2Writer.cpp
++++ b/tests/TestKeePass2Writer.cpp
+@@ -21,7 +21,6 @@
+ #include <QTest>
+ #include "config-keepassx-tests.h"
+-#include "tests.h"
+ #include "FailDevice.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+diff --git a/tests/TestKeePass2XmlReader.cpp b/tests/TestKeePass2XmlReader.cpp
+index dd81327..f04c548 100644
+--- a/tests/TestKeePass2XmlReader.cpp
++++ b/tests/TestKeePass2XmlReader.cpp
+@@ -21,7 +21,6 @@
+ #include <QFile>
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+@@ -112,12 +111,12 @@ void TestKeePass2XmlReader::testMetadata()
+     QCOMPARE(m_db->metadata()->protectUrl(), true);
+     QCOMPARE(m_db->metadata()->protectNotes(), false);
+     QCOMPARE(m_db->metadata()->recycleBinEnabled(), true);
+-    QVERIFY(m_db->metadata()->recycleBin() != Q_NULLPTR);
++    QVERIFY(m_db->metadata()->recycleBin() != nullptr);
+     QCOMPARE(m_db->metadata()->recycleBin()->name(), QString("Recycle Bin"));
+     QCOMPARE(m_db->metadata()->recycleBinChanged(), genDT(2010, 8, 25, 16, 12, 57));
+-    QVERIFY(m_db->metadata()->entryTemplatesGroup() == Q_NULLPTR);
++    QVERIFY(m_db->metadata()->entryTemplatesGroup() == nullptr);
+     QCOMPARE(m_db->metadata()->entryTemplatesGroupChanged(), genDT(2010, 8, 8, 17, 24, 19));
+-    QVERIFY(m_db->metadata()->lastSelectedGroup() != Q_NULLPTR);
++    QVERIFY(m_db->metadata()->lastSelectedGroup() != nullptr);
+     QCOMPARE(m_db->metadata()->lastSelectedGroup()->name(), QString("NewDatabase"));
+     QVERIFY(m_db->metadata()->lastTopVisibleGroup() == m_db->metadata()->lastSelectedGroup());
+     QCOMPARE(m_db->metadata()->historyMaxItems(), -1);
+diff --git a/tests/TestKeys.cpp b/tests/TestKeys.cpp
+index b661775..6c1953f 100644
+--- a/tests/TestKeys.cpp
++++ b/tests/TestKeys.cpp
+@@ -21,7 +21,6 @@
+ #include <QTest>
+ #include "config-keepassx-tests.h"
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Metadata.h"
+ #include "crypto/Crypto.h"
+@@ -177,7 +176,7 @@ void TestKeys::benchmarkTransformKey()
+     QByteArray env = qgetenv("BENCHMARK");
+     if (env.isEmpty() || env == "0" || env == "no") {
+-        QSKIP("Benchmark skipped. Set env variable BENCHMARK=1 to enable.", SkipAll);
++        QSKIP("Benchmark skipped. Set env variable BENCHMARK=1 to enable.");
+     }
+     PasswordKey pwKey;
+diff --git a/tests/TestModified.cpp b/tests/TestModified.cpp
+index e275e83..70a4a48 100644
+--- a/tests/TestModified.cpp
++++ b/tests/TestModified.cpp
+@@ -20,7 +20,6 @@
+ #include <QSignalSpy>
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/Group.h"
+ #include "core/Metadata.h"
+@@ -237,7 +236,7 @@ void TestModified::testEntrySets()
+     entry->setExpires(entry->timeInfo().expires());
+     QCOMPARE(spyModified.count(), spyCount);
+-    entry->setExpiryTime(Tools::currentDateTimeUtc().addYears(1));
++    entry->setExpiryTime(QDateTime::currentDateTimeUtc().addYears(1));
+     QCOMPARE(spyModified.count(), ++spyCount);
+     entry->setExpiryTime(entry->timeInfo().expiryTime());
+     QCOMPARE(spyModified.count(), spyCount);
+diff --git a/tests/TestQCommandLineParser.cpp b/tests/TestQCommandLineParser.cpp
+deleted file mode 100644
+index 4e2c635..0000000
+--- a/tests/TestQCommandLineParser.cpp
++++ /dev/null
+@@ -1,416 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the test suite of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia.  For licensing terms and
+-** conditions see http://qt.digia.com/licensing.  For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.LGPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU Lesser General Public License version 2.1 requirements
+-** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights.  These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU
+-** General Public License version 3.0 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.GPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU General Public License version 3.0 requirements will be
+-** met: http://www.gnu.org/copyleft/gpl.html.
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#include "TestQCommandLineParser.h"
+-
+-#include <QtTest>
+-
+-#include "tests.h"
+-#include "core/qcommandlineparser.h"
+-
+-QTEST_GUILESS_MAIN(TestQCommandLineParser)
+-
+-Q_DECLARE_METATYPE(char**)
+-
+-static char *empty_argv[] = { 0 };
+-static int empty_argc = 1;
+-
+-void TestQCommandLineParser::initTestCase()
+-{
+-    Q_ASSERT(!empty_argv[0]);
+-    empty_argv[0] = const_cast<char*>("TestQCommandLineParser");
+-}
+-
+-Q_DECLARE_METATYPE(QCommandLineParser::SingleDashWordOptionMode)
+-
+-void TestQCommandLineParser::parsingModes_data()
+-{
+-    QTest::addColumn<QCommandLineParser::SingleDashWordOptionMode>("parsingMode");
+-
+-    QTest::newRow("collapsed") << QCommandLineParser::ParseAsCompactedShortOptions;
+-    QTest::newRow("implicitlylong") << QCommandLineParser::ParseAsLongOptions;
+-}
+-
+-void TestQCommandLineParser::testInvalidOptions()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    QTest::ignoreMessage(QtWarningMsg, "QCommandLineOption: Option names cannot start with a '-'");
+-    parser.addOption(QCommandLineOption("-v", "Displays version information."));
+-}
+-
+-void TestQCommandLineParser::testPositionalArguments()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    QVERIFY(parser.parse(QStringList() << "TestQCommandLineParser" << "file.txt"));
+-    QCOMPARE(parser.positionalArguments(), QStringList() << "file.txt");
+-}
+-
+-void TestQCommandLineParser::testBooleanOption_data()
+-{
+-    QTest::addColumn<QStringList>("args");
+-    QTest::addColumn<QStringList>("expectedOptionNames");
+-    QTest::addColumn<bool>("expectedIsSet");
+-
+-    QTest::newRow("set") << (QStringList() << "TestQCommandLineParser" << "-b") << (QStringList() << "b") << true;
+-    QTest::newRow("unset") << (QStringList() << "TestQCommandLineParser") << QStringList() << false;
+-}
+-
+-void TestQCommandLineParser::testBooleanOption()
+-{
+-    QFETCH(QStringList, args);
+-    QFETCH(QStringList, expectedOptionNames);
+-    QFETCH(bool, expectedIsSet);
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    QVERIFY(parser.addOption(QCommandLineOption("b", "a boolean option")));
+-    QVERIFY(parser.parse(args));
+-    QCOMPARE(parser.optionNames(), expectedOptionNames);
+-    QCOMPARE(parser.isSet("b"), expectedIsSet);
+-    QCOMPARE(parser.values("b"), QStringList());
+-    QCOMPARE(parser.positionalArguments(), QStringList());
+-    // Should warn on typos
+-    QTest::ignoreMessage(QtWarningMsg, "QCommandLineParser: option not defined: \"c\"");
+-    QVERIFY(!parser.isSet("c"));
+-}
+-
+-void TestQCommandLineParser::testMultipleNames_data()
+-{
+-    QTest::addColumn<QStringList>("args");
+-    QTest::addColumn<QStringList>("expectedOptionNames");
+-
+-    QTest::newRow("short") << (QStringList() << "TestQCommandLineParser" << "-v") << (QStringList() << "v");
+-    QTest::newRow("long") << (QStringList() << "TestQCommandLineParser" << "--version") << (QStringList() << "version");
+-    QTest::newRow("not_set") << (QStringList() << "TestQCommandLineParser") << QStringList();
+-}
+-
+-void TestQCommandLineParser::testMultipleNames()
+-{
+-    QFETCH(QStringList, args);
+-    QFETCH(QStringList, expectedOptionNames);
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineOption option(QStringList() << "v" << "version", "Show version information");
+-    QCOMPARE(option.names(), QStringList() << "v" << "version");
+-    QCommandLineParser parser;
+-    QVERIFY(parser.addOption(option));
+-    QVERIFY(parser.parse(args));
+-    QCOMPARE(parser.optionNames(), expectedOptionNames);
+-    const bool expectedIsSet = !expectedOptionNames.isEmpty();
+-    QCOMPARE(parser.isSet("v"), expectedIsSet);
+-    QCOMPARE(parser.isSet("version"), expectedIsSet);
+-}
+-
+-void TestQCommandLineParser::testSingleValueOption_data()
+-{
+-    QTest::addColumn<QStringList>("args");
+-    QTest::addColumn<QStringList>("defaults");
+-    QTest::addColumn<bool>("expectedIsSet");
+-
+-    QTest::newRow("short") << (QStringList() << "tst" << "-s" << "oxygen") << QStringList() << true;
+-    QTest::newRow("long") << (QStringList() << "tst" << "--style" << "oxygen") << QStringList() << true;
+-    QTest::newRow("longequal") << (QStringList() << "tst" << "--style=oxygen") << QStringList() << true;
+-    QTest::newRow("default") << (QStringList() << "tst") << (QStringList() << "oxygen") << false;
+-}
+-
+-void TestQCommandLineParser::testSingleValueOption()
+-{
+-    QFETCH(QStringList, args);
+-    QFETCH(QStringList, defaults);
+-    QFETCH(bool, expectedIsSet);
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    QCommandLineOption option(QStringList() << "s" << "style", "style name", "styleName");
+-    option.setDefaultValues(defaults);
+-    QVERIFY(parser.addOption(option));
+-    for (int mode = 0; mode < 2; ++mode) {
+-        parser.setSingleDashWordOptionMode(QCommandLineParser::SingleDashWordOptionMode(mode));
+-        QVERIFY(parser.parse(args));
+-        QCOMPARE(parser.isSet("s"), expectedIsSet);
+-        QCOMPARE(parser.isSet("style"), expectedIsSet);
+-        QCOMPARE(parser.isSet(option), expectedIsSet);
+-        QCOMPARE(parser.value("s"), QString("oxygen"));
+-        QCOMPARE(parser.value("style"), QString("oxygen"));
+-        QCOMPARE(parser.values("s"), QStringList() << "oxygen");
+-        QCOMPARE(parser.values("style"), QStringList() << "oxygen");
+-        QCOMPARE(parser.values(option), QStringList() << "oxygen");
+-        QCOMPARE(parser.positionalArguments(), QStringList());
+-    }
+-    // Should warn on typos
+-    QTest::ignoreMessage(QtWarningMsg, "QCommandLineParser: option not defined: \"c\"");
+-    QVERIFY(parser.values("c").isEmpty());
+-}
+-
+-void TestQCommandLineParser::testValueNotSet()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    // Not set, no default value
+-    QCommandLineParser parser;
+-    QCommandLineOption option(QStringList() << "s" << "style", "style name");
+-    option.setValueName("styleName");
+-    QVERIFY(parser.addOption(option));
+-    QVERIFY(parser.parse(QStringList() << "tst"));
+-    QCOMPARE(parser.optionNames(), QStringList());
+-    QVERIFY(!parser.isSet("s"));
+-    QVERIFY(!parser.isSet("style"));
+-    QCOMPARE(parser.value("s"), QString());
+-    QCOMPARE(parser.value("style"), QString());
+-    QCOMPARE(parser.values("s"), QStringList());
+-    QCOMPARE(parser.values("style"), QStringList());
+-}
+-
+-void TestQCommandLineParser::testMultipleValuesOption()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineOption option("param", "Pass parameter to the backend.");
+-    option.setValueName("key=value");
+-    QCommandLineParser parser;
+-    QVERIFY(parser.addOption(option));
+-    {
+-        QVERIFY(parser.parse(QStringList() << "tst" << "--param" << "key1=value1"));
+-        QVERIFY(parser.isSet("param"));
+-        QCOMPARE(parser.values("param"), QStringList() << "key1=value1");
+-        QCOMPARE(parser.value("param"), QString("key1=value1"));
+-    }
+-    {
+-        QVERIFY(parser.parse(QStringList() << "tst" << "--param" << "key1=value1" << "--param" << "key2=value2"));
+-        QVERIFY(parser.isSet("param"));
+-        QCOMPARE(parser.values("param"), QStringList() << "key1=value1" << "key2=value2");
+-        QCOMPARE(parser.value("param"), QString("key2=value2"));
+-    }
+-
+-    QString expected =
+-        "Usage: TestQCommandLineParser [options]\n"
+-        "\n"
+-        "Options:\n"
+-        "  --param <key=value>  Pass parameter to the backend.\n";
+-
+-    const QString exeName = QCoreApplication::instance()->arguments().first(); // e.g. debug\tst_qcommandlineparser.exe on Windows
+-    expected.replace("TestQCommandLineParser", exeName);
+-    QCOMPARE(parser.helpText(), expected);
+-}
+-
+-void TestQCommandLineParser::testUnknownOptionErrorHandling_data()
+-{
+-    QTest::addColumn<QCommandLineParser::SingleDashWordOptionMode>("parsingMode");
+-    QTest::addColumn<QStringList>("args");
+-    QTest::addColumn<QStringList>("expectedUnknownOptionNames");
+-    QTest::addColumn<QString>("expectedErrorText");
+-
+-    const QStringList args_hello = QStringList() << "TestQCommandLineParser" << "--hello";
+-    const QString error_hello("Unknown option 'hello'.");
+-    QTest::newRow("unknown_name_collapsed") << QCommandLineParser::ParseAsCompactedShortOptions << args_hello << QStringList("hello") << error_hello;
+-    QTest::newRow("unknown_name_long") << QCommandLineParser::ParseAsLongOptions << args_hello << QStringList("hello") << error_hello;
+-
+-    const QStringList args_value = QStringList() << "TestQCommandLineParser" << "-b=1";
+-    QTest::newRow("bool_with_value_collapsed") << QCommandLineParser::ParseAsCompactedShortOptions << args_value << QStringList() << QString("Unexpected value after '-b'.");
+-    QTest::newRow("bool_with_value_long") << QCommandLineParser::ParseAsLongOptions << args_value << QStringList() << QString("Unexpected value after '-b'.");
+-
+-    const QStringList args_dash_long = QStringList() << "TestQCommandLineParser" << "-bool";
+-    const QString error_bool("Unknown options: o, o, l.");
+-    QTest::newRow("unknown_name_long_collapsed") << QCommandLineParser::ParseAsCompactedShortOptions << args_dash_long << (QStringList() << "o" << "o" << "l") << error_bool;
+-}
+-
+-void TestQCommandLineParser::testUnknownOptionErrorHandling()
+-{
+-    QFETCH(QCommandLineParser::SingleDashWordOptionMode, parsingMode);
+-    QFETCH(QStringList, args);
+-    QFETCH(QStringList, expectedUnknownOptionNames);
+-    QFETCH(QString, expectedErrorText);
+-
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    parser.setSingleDashWordOptionMode(parsingMode);
+-    QVERIFY(parser.addOption(QCommandLineOption(QStringList() << "b" << "bool", "a boolean option")));
+-    QCOMPARE(parser.parse(args), expectedErrorText.isEmpty());
+-    QCOMPARE(parser.unknownOptionNames(), expectedUnknownOptionNames);
+-    QCOMPARE(parser.errorText(), expectedErrorText);
+-}
+-
+-void TestQCommandLineParser::testDoubleDash_data()
+-{
+-    parsingModes_data();
+-}
+-
+-void TestQCommandLineParser::testDoubleDash()
+-{
+-    QFETCH(QCommandLineParser::SingleDashWordOptionMode, parsingMode);
+-
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    parser.addOption(QCommandLineOption(QStringList() << "o" << "output", "Output file", "filename"));
+-    parser.setSingleDashWordOptionMode(parsingMode);
+-    QVERIFY(parser.parse(QStringList() << "TestQCommandLineParser" << "--output" << "foo"));
+-    QCOMPARE(parser.value("output"), QString("foo"));
+-    QCOMPARE(parser.positionalArguments(), QStringList());
+-    QCOMPARE(parser.unknownOptionNames(), QStringList());
+-    QVERIFY(parser.parse(QStringList() << "TestQCommandLineParser" << "--" << "--output" << "bar" << "-b" << "bleh"));
+-    QCOMPARE(parser.value("output"), QString());
+-    QCOMPARE(parser.positionalArguments(), QStringList() << "--output" << "bar" << "-b" << "bleh");
+-    QCOMPARE(parser.unknownOptionNames(), QStringList());
+-}
+-
+-void TestQCommandLineParser::testDefaultValue()
+-{
+-    QCommandLineOption opt("name", "desc",
+-                           "valueName", "default");
+-    QCOMPARE(opt.defaultValues(), QStringList("default"));
+-    opt.setDefaultValue("");
+-    QCOMPARE(opt.defaultValues(), QStringList());
+-    opt.setDefaultValue("default");
+-    QCOMPARE(opt.defaultValues(), QStringList("default"));
+-}
+-
+-void TestQCommandLineParser::testProcessNotCalled()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    QVERIFY(parser.addOption(QCommandLineOption("b", "a boolean option")));
+-    QTest::ignoreMessage(QtWarningMsg, "QCommandLineParser: call process() or parse() before isSet");
+-    QVERIFY(!parser.isSet("b"));
+-    QTest::ignoreMessage(QtWarningMsg, "QCommandLineParser: call process() or parse() before values");
+-    QCOMPARE(parser.values("b"), QStringList());
+-}
+-
+-void TestQCommandLineParser::testEmptyArgsList()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    QTest::ignoreMessage(QtWarningMsg, "QCommandLineParser: argument list cannot be empty, it should contain at least the executable name");
+-    QVERIFY(!parser.parse(QStringList())); // invalid call, argv[0] is missing
+-}
+-
+-void TestQCommandLineParser::testMissingOptionValue()
+-{
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    parser.addOption(QCommandLineOption("option", "An option", "value"));
+-    QVERIFY(!parser.parse(QStringList() << "argv0" << "--option")); // the user forgot to pass a value for --option
+-    QCOMPARE(parser.value("option"), QString());
+-    QCOMPARE(parser.errorText(), QString("Missing value after '--option'."));
+-}
+-
+-void TestQCommandLineParser::testStdinArgument_data()
+-{
+-    parsingModes_data();
+-}
+-
+-void TestQCommandLineParser::testStdinArgument()
+-{
+-    QFETCH(QCommandLineParser::SingleDashWordOptionMode, parsingMode);
+-
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    parser.setSingleDashWordOptionMode(parsingMode);
+-    parser.addOption(QCommandLineOption(QStringList() << "i" << "input", "Input file.", "filename"));
+-    parser.addOption(QCommandLineOption("b", "Boolean option."));
+-    QVERIFY(parser.parse(QStringList() << "TestQCommandLineParser" << "--input" << "-"));
+-    QCOMPARE(parser.value("input"), QString("-"));
+-    QCOMPARE(parser.positionalArguments(), QStringList());
+-    QCOMPARE(parser.unknownOptionNames(), QStringList());
+-
+-    QVERIFY(parser.parse(QStringList() << "TestQCommandLineParser" << "--input" << "-" << "-b" << "arg"));
+-    QCOMPARE(parser.value("input"), QString("-"));
+-    QVERIFY(parser.isSet("b"));
+-    QCOMPARE(parser.positionalArguments(), QStringList() << "arg");
+-    QCOMPARE(parser.unknownOptionNames(), QStringList());
+-
+-    QVERIFY(parser.parse(QStringList() << "TestQCommandLineParser" << "-"));
+-    QCOMPARE(parser.value("input"), QString());
+-    QVERIFY(!parser.isSet("b"));
+-    QCOMPARE(parser.positionalArguments(), QStringList() << "-");
+-    QCOMPARE(parser.unknownOptionNames(), QStringList());
+-}
+-
+-void TestQCommandLineParser::testSingleDashWordOptionModes_data()
+-{
+-    QTest::addColumn<QCommandLineParser::SingleDashWordOptionMode>("parsingMode");
+-    QTest::addColumn<QStringList>("commandLine");
+-    QTest::addColumn<QStringList>("expectedOptionNames");
+-    QTest::addColumn<QStringList>("expectedOptionValues");
+-
+-    QTest::newRow("collapsed") << QCommandLineParser::ParseAsCompactedShortOptions << (QStringList() << "-abc" << "val")
+-                               << (QStringList() << "a" << "b" << "c") << (QStringList() << QString() << QString() << "val");
+-    QTest::newRow("collapsed_with_equalsign_value") << QCommandLineParser::ParseAsCompactedShortOptions << (QStringList() << "-abc=val")
+-                               << (QStringList() << "a" << "b" << "c") << (QStringList() << QString() << QString() << "val");
+-    QTest::newRow("collapsed_explicit_longoption") << QCommandLineParser::ParseAsCompactedShortOptions << QStringList("--nn")
+-                               << QStringList("nn") << QStringList();
+-    QTest::newRow("collapsed_longoption_value") << QCommandLineParser::ParseAsCompactedShortOptions << (QStringList() << "--abc" << "val")
+-                               << QStringList("abc") << QStringList("val");
+-    QTest::newRow("compiler")  << QCommandLineParser::ParseAsCompactedShortOptions << QStringList("-cab")
+-                               << QStringList("c") << QStringList("ab");
+-    QTest::newRow("compiler_with_space") << QCommandLineParser::ParseAsCompactedShortOptions << (QStringList() << "-c" << "val")
+-                               << QStringList("c") << QStringList("val");
+-
+-    QTest::newRow("implicitlylong") << QCommandLineParser::ParseAsLongOptions << (QStringList() << "-abc" << "val")
+-                               << QStringList("abc") << QStringList("val");
+-    QTest::newRow("implicitlylong_equal") << QCommandLineParser::ParseAsLongOptions << (QStringList() << "-abc=val")
+-                               << QStringList("abc") << QStringList("val");
+-    QTest::newRow("implicitlylong_longoption") << QCommandLineParser::ParseAsLongOptions << (QStringList() << "--nn")
+-                               << QStringList("nn") << QStringList();
+-    QTest::newRow("implicitlylong_longoption_value") << QCommandLineParser::ParseAsLongOptions << (QStringList() << "--abc" << "val")
+-                               << QStringList("abc") << QStringList("val");
+-    QTest::newRow("implicitlylong_with_space") << QCommandLineParser::ParseAsCompactedShortOptions << (QStringList() << "-c" << "val")
+-                               << QStringList("c") << QStringList("val");
+-}
+-
+-void TestQCommandLineParser::testSingleDashWordOptionModes()
+-{
+-    QFETCH(QCommandLineParser::SingleDashWordOptionMode, parsingMode);
+-    QFETCH(QStringList, commandLine);
+-    QFETCH(QStringList, expectedOptionNames);
+-    QFETCH(QStringList, expectedOptionValues);
+-
+-    commandLine.prepend("TestQCommandLineParser");
+-
+-    QCoreApplication app(empty_argc, empty_argv);
+-    QCommandLineParser parser;
+-    parser.setSingleDashWordOptionMode(parsingMode);
+-    parser.addOption(QCommandLineOption("a", "a option."));
+-    parser.addOption(QCommandLineOption("b", "b option."));
+-    parser.addOption(QCommandLineOption(QStringList() << "c" << "abc", "c option.", "value"));
+-    parser.addOption(QCommandLineOption("nn", "nn option."));
+-    QVERIFY(parser.parse(commandLine));
+-    QCOMPARE(parser.optionNames(), expectedOptionNames);
+-    for (int i = 0; i < expectedOptionValues.count(); ++i)
+-        QCOMPARE(parser.value(parser.optionNames().at(i)), expectedOptionValues.at(i));
+-    QCOMPARE(parser.unknownOptionNames(), QStringList());
+-}
+diff --git a/tests/TestQCommandLineParser.h b/tests/TestQCommandLineParser.h
+deleted file mode 100644
+index 46214cd..0000000
+--- a/tests/TestQCommandLineParser.h
++++ /dev/null
+@@ -1,82 +0,0 @@
+-/****************************************************************************
+-**
+-** Copyright (C) 2013 David Faure <faure@kde.org>
+-** Contact: http://www.qt-project.org/legal
+-**
+-** This file is part of the test suite of the Qt Toolkit.
+-**
+-** $QT_BEGIN_LICENSE:LGPL$
+-** Commercial License Usage
+-** Licensees holding valid commercial Qt licenses may use this file in
+-** accordance with the commercial license agreement provided with the
+-** Software or, alternatively, in accordance with the terms contained in
+-** a written agreement between you and Digia.  For licensing terms and
+-** conditions see http://qt.digia.com/licensing.  For further information
+-** use the contact form at http://qt.digia.com/contact-us.
+-**
+-** GNU Lesser General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU Lesser
+-** General Public License version 2.1 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.LGPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU Lesser General Public License version 2.1 requirements
+-** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+-**
+-** In addition, as a special exception, Digia gives you certain additional
+-** rights.  These rights are described in the Digia Qt LGPL Exception
+-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+-**
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU
+-** General Public License version 3.0 as published by the Free Software
+-** Foundation and appearing in the file LICENSE.GPL included in the
+-** packaging of this file.  Please review the following information to
+-** ensure the GNU General Public License version 3.0 requirements will be
+-** met: http://www.gnu.org/copyleft/gpl.html.
+-**
+-**
+-** $QT_END_LICENSE$
+-**
+-****************************************************************************/
+-
+-#ifndef KEEPASSX_TESTQCOMMANDLINEPARSER_H
+-#define KEEPASSX_TESTQCOMMANDLINEPARSER_H
+-
+-#include <QObject>
+-
+-class TestQCommandLineParser : public QObject
+-{
+-    Q_OBJECT
+-
+-public Q_SLOTS:
+-    void initTestCase();
+-
+-private Q_SLOTS:
+-    void parsingModes_data();
+-
+-    // In-process tests
+-    void testInvalidOptions();
+-    void testPositionalArguments();
+-    void testBooleanOption_data();
+-    void testBooleanOption();
+-    void testMultipleNames_data();
+-    void testMultipleNames();
+-    void testSingleValueOption_data();
+-    void testSingleValueOption();
+-    void testValueNotSet();
+-    void testMultipleValuesOption();
+-    void testUnknownOptionErrorHandling_data();
+-    void testUnknownOptionErrorHandling();
+-    void testDoubleDash_data();
+-    void testDoubleDash();
+-    void testDefaultValue();
+-    void testProcessNotCalled();
+-    void testEmptyArgsList();
+-    void testMissingOptionValue();
+-    void testStdinArgument_data();
+-    void testStdinArgument();
+-    void testSingleDashWordOptionModes_data();
+-    void testSingleDashWordOptionModes();
+-};
+-
+-#endif // KEEPASSX_TESTQCOMMANDLINEPARSER_H
+diff --git a/tests/TestQSaveFile.cpp b/tests/TestQSaveFile.cpp
+deleted file mode 100644
+index 443db52..0000000
+--- a/tests/TestQSaveFile.cpp
++++ /dev/null
+@@ -1,204 +0,0 @@
+-/*
+- *  Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
+- *  Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies)
+- *
+- *  This program is free software: you can redistribute it and/or modify
+- *  it under the terms of the GNU General Public License as published by
+- *  the Free Software Foundation, either version 2 or (at your option)
+- *  version 3 of the License.
+- *
+- *  This program is distributed in the hope that it will be useful,
+- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+- *  GNU General Public License for more details.
+- *
+- *  You should have received a copy of the GNU General Public License
+- *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+- */
+-
+-#include "TestQSaveFile.h"
+-
+-#include <QtTest>
+-
+-#include <unistd.h>
+-
+-#if defined(Q_OS_WIN)
+-# include <windows.h>
+-#endif
+-
+-#include "tests.h"
+-#include "core/qsavefile.h"
+-
+-QTEST_GUILESS_MAIN(TestQSaveFile)
+-
+-class DirCleanup
+-{
+-public:
+-    DirCleanup(const QString& dir, const QString& filePrefix) : m_dir(dir), m_filePrefix(filePrefix) {}
+-    ~DirCleanup() {
+-        QDir dir(m_dir);
+-        QStringList files = dir.entryList(QStringList() << (m_filePrefix + "*"), QDir::Files);
+-        Q_FOREACH (const QString& file, files) {
+-            QFile::remove(m_dir + "/" + file);
+-        }
+-
+-        QDir().rmdir(m_dir);
+-    }
+-
+-private:
+-    QString m_dir;
+-    QString m_filePrefix;
+-};
+-
+-void TestQSaveFile::transactionalWrite()
+-{
+-    const QString dir = tmpDir();
+-    QVERIFY(!dir.isEmpty());
+-    const QString targetFile = dir + QString::fromLatin1("/outfile");
+-    DirCleanup dirCleanup(dir, "outfile");
+-    QFile::remove(targetFile);
+-    QSaveFile file(targetFile);
+-    QVERIFY(file.open(QIODevice::WriteOnly));
+-    QVERIFY(file.isOpen());
+-    QCOMPARE(file.fileName(), targetFile);
+-    QVERIFY(!QFile::exists(targetFile));
+-
+-    QTextStream ts(&file);
+-    ts << "This is test data one.\n";
+-    ts.flush();
+-    QCOMPARE(file.error(), QFile::NoError);
+-    QVERIFY(!QFile::exists(targetFile));
+-
+-    QVERIFY(file.commit());
+-    QVERIFY(QFile::exists(targetFile));
+-    QCOMPARE(file.fileName(), targetFile);
+-
+-    // Check that we can reuse a QSaveFile object
+-    // (and test the case of an existing target file)
+-    QVERIFY(file.open(QIODevice::WriteOnly));
+-    QCOMPARE(file.write("Hello"), 5LL);
+-    QVERIFY(file.commit());
+-
+-    QFile reader(targetFile);
+-    QVERIFY(reader.open(QIODevice::ReadOnly));
+-    QCOMPARE(QString::fromLatin1(reader.readAll().constData()), QString::fromLatin1("Hello"));
+-    reader.close();
+-
+-    QVERIFY(QFile::remove(targetFile));
+-}
+-
+-void TestQSaveFile::autoFlush()
+-{
+-    const QString dir = tmpDir();
+-    QVERIFY(!dir.isEmpty());
+-    const QString targetFile = dir + QString::fromLatin1("/outfile");
+-    DirCleanup dirCleanup(dir, "outfile");
+-    QFile::remove(targetFile);
+-    QSaveFile file(targetFile);
+-    QVERIFY(file.open(QIODevice::WriteOnly));
+-
+-    QTextStream ts(&file);
+-    ts << "Auto-flush.";
+-    // no flush
+-    QVERIFY(file.commit()); // close will emit aboutToClose, which will flush the stream
+-    QFile reader(targetFile);
+-    QVERIFY(reader.open(QIODevice::ReadOnly));
+-    QCOMPARE(QString::fromLatin1(reader.readAll().constData()), QString::fromLatin1("Auto-flush."));
+-    reader.close();
+-
+-    QVERIFY(QFile::remove(targetFile));
+-}
+-
+-void TestQSaveFile::transactionalWriteNoPermissions()
+-{
+-#ifdef Q_OS_UNIX
+-    if (::geteuid() == 0) {
+-        QSKIP("not valid running this test as root", SkipAll);
+-    }
+-
+-    // You can write into /dev/zero, but you can't create a /dev/zero.XXXXXX temp file.
+-    QSaveFile file("/dev/zero");
+-    if (!QDir("/dev").exists()) {
+-        QSKIP("/dev doesn't exist on this system", SkipAll);
+-    }
+-
+-    QVERIFY(!file.open(QIODevice::WriteOnly));
+-    QCOMPARE(static_cast<int>(file.error()), static_cast<int>(QFile::OpenError));
+-    QVERIFY(!file.commit());
+-#endif
+-}
+-
+-void TestQSaveFile::transactionalWriteCanceled()
+-{
+-    const QString dir = tmpDir();
+-    QVERIFY(!dir.isEmpty());
+-    const QString targetFile = dir + QString::fromLatin1("/outfile");
+-    DirCleanup dirCleanup(dir, "outfile");
+-    QFile::remove(targetFile);
+-    QSaveFile file(targetFile);
+-    QVERIFY(file.open(QIODevice::WriteOnly));
+-
+-    QTextStream ts(&file);
+-    ts << "This writing operation will soon be canceled.\n";
+-    ts.flush();
+-    QCOMPARE(file.error(), QFile::NoError);
+-    QVERIFY(!QFile::exists(targetFile));
+-
+-    // We change our mind, let's abort writing
+-    file.cancelWriting();
+-
+-    QVERIFY(!file.commit());
+-
+-    QVERIFY(!QFile::exists(targetFile)); // temp file was discarded
+-    QCOMPARE(file.fileName(), targetFile);
+-}
+-
+-void TestQSaveFile::transactionalWriteErrorRenaming()
+-{
+-#ifndef Q_OS_WIN
+-    if (::geteuid() == 0) {
+-        QSKIP("not valid running this test as root", SkipAll);
+-    }
+-    const QString dir = tmpDir();
+-    QVERIFY(!dir.isEmpty());
+-    const QString targetFile = dir + QString::fromLatin1("/outfile");
+-    DirCleanup dirCleanup(dir, "outfile");
+-    QSaveFile file(targetFile);
+-    QVERIFY(file.open(QIODevice::WriteOnly));
+-    QCOMPARE(file.write("Hello"), qint64(5));
+-    QVERIFY(!QFile::exists(targetFile));
+-
+-#ifdef Q_OS_UNIX
+-    QFile dirAsFile(dir); // yay, I have to use QFile to change a dir's permissions...
+-    QVERIFY(dirAsFile.setPermissions(QFile::Permissions(0))); // no permissions
+-#else
+-    QVERIFY(file.setPermissions(QFile::ReadOwner));
+-#endif
+-
+-    QVERIFY(!file.commit());
+-    QVERIFY(!QFile::exists(targetFile)); // renaming failed
+-    QCOMPARE(file.error(), QFile::RenameError);
+-
+-    // Restore permissions so that the cleanup can happen
+-#ifdef Q_OS_UNIX
+-    QVERIFY(dirAsFile.setPermissions(QFile::Permissions(QFile::ReadOwner | QFile::WriteOwner | QFile::ExeOwner)));
+-#else
+-    QVERIFY(file.setPermissions(QFile::ReadOwner | QFile::WriteOwner));
+-#endif
+-#endif // !Q_OS_WIN
+-}
+-
+-QString TestQSaveFile::tmpDir()
+-{
+-    QTemporaryFile* tmpFile = new QTemporaryFile(QDir::tempPath() + "/qttest_temp.XXXXXX");
+-    if (!tmpFile->open()) {
+-        return QString();
+-    }
+-    QString dirName = tmpFile->fileName();
+-    delete tmpFile;
+-    if (!QDir().mkdir(dirName)) {
+-        return QString();
+-    }
+-
+-    return dirName;
+-}
+diff --git a/tests/TestQSaveFile.h b/tests/TestQSaveFile.h
+deleted file mode 100644
+index 8e1caf0..0000000
+--- a/tests/TestQSaveFile.h
++++ /dev/null
+@@ -1,39 +0,0 @@
+-/*
+- *  Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
+- *  Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies)
+- *
+- *  This program is free software: you can redistribute it and/or modify
+- *  it under the terms of the GNU General Public License as published by
+- *  the Free Software Foundation, either version 2 or (at your option)
+- *  version 3 of the License.
+- *
+- *  This program is distributed in the hope that it will be useful,
+- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+- *  GNU General Public License for more details.
+- *
+- *  You should have received a copy of the GNU General Public License
+- *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+- */
+-
+-#ifndef KEEPASSX_TESTQSAVEFILE_H
+-#define KEEPASSX_TESTQSAVEFILE_H
+-
+-#include <QObject>
+-
+-class TestQSaveFile : public QObject
+-{
+-    Q_OBJECT
+-
+-private Q_SLOTS:
+-    void transactionalWrite();
+-    void autoFlush();
+-    void transactionalWriteNoPermissions();
+-    void transactionalWriteCanceled();
+-    void transactionalWriteErrorRenaming();
+-
+-private:
+-    QString tmpDir();
+-};
+-
+-#endif // KEEPASSX_TESTQSAVEFILE_H
+diff --git a/tests/TestRandom.cpp b/tests/TestRandom.cpp
+index 40ab702..6c5b1f7 100644
+--- a/tests/TestRandom.cpp
++++ b/tests/TestRandom.cpp
+@@ -17,8 +17,8 @@
+ #include "TestRandom.h"
+-#include "tests.h"
+ #include "core/Endian.h"
++#include "core/Global.h"
+ #include <QTest>
+diff --git a/tests/TestRandom.h b/tests/TestRandom.h
+index a308f36..c879f94 100644
+--- a/tests/TestRandom.h
++++ b/tests/TestRandom.h
+@@ -18,7 +18,6 @@
+ #ifndef KEEPASSX_TESTRANDOM_H
+ #define KEEPASSX_TESTRANDOM_H
+-#include "core/Global.h"
+ #include "crypto/Random.h"
+ #include <QObject>
+@@ -27,7 +26,7 @@ class RandomBackendTest : public RandomBackend
+ {
+ public:
+     RandomBackendTest();
+-    void randomize(void* data, int len) Q_DECL_OVERRIDE;
++    void randomize(void* data, int len) override;
+     void setNextBytes(const QByteArray& nextBytes);
+ private:
+diff --git a/tests/TestSymmetricCipher.cpp b/tests/TestSymmetricCipher.cpp
+index 578d250..698ecb2 100644
+--- a/tests/TestSymmetricCipher.cpp
++++ b/tests/TestSymmetricCipher.cpp
+@@ -20,7 +20,6 @@
+ #include <QBuffer>
+ #include <QTest>
+-#include "tests.h"
+ #include "crypto/Crypto.h"
+ #include "crypto/SymmetricCipher.h"
+ #include "streams/SymmetricCipherStream.h"
+diff --git a/tests/TestWildcardMatcher.cpp b/tests/TestWildcardMatcher.cpp
+index dc9991d..dffe1c8 100644
+--- a/tests/TestWildcardMatcher.cpp
++++ b/tests/TestWildcardMatcher.cpp
+@@ -19,7 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "autotype/WildcardMatcher.h"
+ QTEST_GUILESS_MAIN(TestWildcardMatcher)
+diff --git a/tests/gui/CMakeLists.txt b/tests/gui/CMakeLists.txt
+index 91fcd69..a1ca914 100644
+--- a/tests/gui/CMakeLists.txt
++++ b/tests/gui/CMakeLists.txt
+@@ -13,6 +13,6 @@
+ #  You should have received a copy of the GNU General Public License
+ #  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+-add_unit_test(NAME testgui SOURCES TestGui.cpp MOCS TestGui.h LIBS ${TEST_LIBRARIES})
++add_unit_test(NAME testgui SOURCES TestGui.cpp LIBS ${TEST_LIBRARIES})
+-add_unit_test(NAME testguipixmaps SOURCES TestGuiPixmaps.cpp MOCS TestGuiPixmaps.h LIBS ${TEST_LIBRARIES})
++add_unit_test(NAME testguipixmaps SOURCES TestGuiPixmaps.cpp LIBS ${TEST_LIBRARIES})
+diff --git a/tests/gui/TestGui.cpp b/tests/gui/TestGui.cpp
+index 6aa49b8..1585c8a 100644
+--- a/tests/gui/TestGui.cpp
++++ b/tests/gui/TestGui.cpp
+@@ -21,6 +21,7 @@
+ #include <QApplication>
+ #include <QDialogButtonBox>
+ #include <QLineEdit>
++#include <QMimeData>
+ #include <QPushButton>
+ #include <QSpinBox>
+ #include <QTemporaryFile>
+@@ -29,7 +30,6 @@
+ #include <QToolButton>
+ #include "config-keepassx-tests.h"
+-#include "tests.h"
+ #include "core/Config.h"
+ #include "core/Database.h"
+ #include "core/Entry.h"
+@@ -56,6 +56,7 @@ void TestGui::initTestCase()
+     m_mainWindow = new MainWindow();
+     m_tabWidget = m_mainWindow->findChild<DatabaseTabWidget*>("tabWidget");
+     m_mainWindow->show();
++    m_mainWindow->activateWindow();
+     Tools::wait(50);
+     QByteArray tmpData;
+@@ -184,7 +185,7 @@ void TestGui::testSearch()
+     QLineEdit* searchEdit = m_dbWidget->findChild<QLineEdit*>("searchEdit");
+     QToolButton* clearSearch = m_dbWidget->findChild<QToolButton*>("clearButton");
+-    QVERIFY(!searchEdit->hasFocus());
++    QVERIFY(!searchEdit->isVisible());
+     // Enter search
+     QTest::mouseClick(searchActionWidget, Qt::LeftButton);
+@@ -439,8 +440,8 @@ void TestGui::testDatabaseLocking()
+     triggerAction("actionLockDatabases");
+-    QCOMPARE(m_tabWidget->tabText(0), QString("Save [locked]"));
+-    QCOMPARE(m_tabWidget->tabText(1), QString("basic [New database]*"));
++    QCOMPARE(m_tabWidget->tabText(0).remove('&'), QString("Save [locked]"));
++    QCOMPARE(m_tabWidget->tabText(1).remove('&'), QString("basic [New database]*"));
+     QWidget* dbWidget = m_tabWidget->currentDatabaseWidget();
+     QWidget* unlockDatabaseWidget = dbWidget->findChild<QWidget*>("unlockDatabaseWidget");
+@@ -450,7 +451,7 @@ void TestGui::testDatabaseLocking()
+     QTest::keyClicks(editPassword, "masterpw");
+     QTest::keyClick(editPassword, Qt::Key_Enter);
+-    QCOMPARE(m_tabWidget->tabText(m_tabWidget->currentIndex()), QString("basic [New database]*"));
++    QCOMPARE(m_tabWidget->tabText(m_tabWidget->currentIndex()).remove('&'), QString("basic [New database]*"));
+ }
+ void TestGui::cleanupTestCase()
+diff --git a/tests/gui/TestGuiPixmaps.cpp b/tests/gui/TestGuiPixmaps.cpp
+index 87e3f24..3637494 100644
+--- a/tests/gui/TestGuiPixmaps.cpp
++++ b/tests/gui/TestGuiPixmaps.cpp
+@@ -19,7 +19,6 @@
+ #include <QTest>
+-#include "tests.h"
+ #include "core/Database.h"
+ #include "core/DatabaseIcons.h"
+ #include "core/Entry.h"
+diff --git a/tests/modeltest.cpp b/tests/modeltest.cpp
+index 19f02d9..360a7be 100644
+--- a/tests/modeltest.cpp
++++ b/tests/modeltest.cpp
+@@ -1,50 +1,40 @@
+ /****************************************************************************
+ **
+-** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
+-** Contact: http://www.qt-project.org/
++** Copyright (C) 2015 The Qt Company Ltd.
++** Contact: http://www.qt.io/licensing/
+ **
+ ** This file is part of the test suite of the Qt Toolkit.
+ **
+-** $QT_BEGIN_LICENSE:LGPL$
++** $QT_BEGIN_LICENSE:LGPL21$
++** Commercial License Usage
++** Licensees holding valid commercial Qt licenses may use this file in
++** accordance with the commercial license agreement provided with the
++** Software or, alternatively, in accordance with the terms contained in
++** a written agreement between you and The Qt Company. For licensing terms
++** and conditions see http://www.qt.io/terms-conditions. For further
++** information use the contact form at http://www.qt.io/contact-us.
++**
+ ** GNU Lesser General Public License Usage
+-** This file may be used under the terms of the GNU Lesser General Public
+-** License version 2.1 as published by the Free Software Foundation and
+-** appearing in the file LICENSE.LGPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU Lesser
+-** General Public License version 2.1 requirements will be met:
++** Alternatively, this file may be used under the terms of the GNU Lesser
++** General Public License version 2.1 or version 3 as published by the Free
++** Software Foundation and appearing in the file LICENSE.LGPLv21 and
++** LICENSE.LGPLv3 included in the packaging of this file. Please review the
++** following information to ensure the GNU Lesser General Public License
++** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+ ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ **
+-** In addition, as a special exception, Nokia gives you certain additional
+-** rights. These rights are described in the Nokia Qt LGPL Exception
++** As a special exception, The Qt Company gives you certain additional
++** rights. These rights are described in The Qt Company LGPL Exception
+ ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+ **
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU General
+-** Public License version 3.0 as published by the Free Software Foundation
+-** and appearing in the file LICENSE.GPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU General
+-** Public License version 3.0 requirements will be met:
+-** http://www.gnu.org/copyleft/gpl.html.
+-**
+-** Other Usage
+-** Alternatively, this file may be used in accordance with the terms and
+-** conditions contained in a signed written agreement between you and Nokia.
+-**
+-**
+-**
+-**
+-**
+ ** $QT_END_LICENSE$
+ **
+ ****************************************************************************/
+-
+ #include "modeltest.h"
+-#include <QDebug>
+-#include <QTest>
+-
+-Q_DECLARE_METATYPE ( QModelIndex )
++#include <QtCore>
++#include <QtTest>
+ /*!
+     Connect to all of the models signals.  Whenever anything happens recheck everything.
+@@ -54,50 +44,52 @@ ModelTest::ModelTest ( QAbstractItemModel *_model, QObject *parent ) : QObject (
+     if (!model)
+         qFatal("%s: model must not be null", Q_FUNC_INFO);
+-    connect ( model, SIGNAL ( columnsAboutToBeInserted ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( columnsAboutToBeRemoved ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( columnsInserted ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( columnsRemoved ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( dataChanged ( const QModelIndex &, const QModelIndex & ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( headerDataChanged ( Qt::Orientation, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( layoutAboutToBeChanged () ), this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( layoutChanged () ), this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( modelReset () ), this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( rowsAboutToBeInserted ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( rowsAboutToBeRemoved ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( rowsInserted ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-    connect ( model, SIGNAL ( rowsRemoved ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( runAllTests() ) );
+-
+-    // Special checks for inserting/removing
+-    connect ( model, SIGNAL ( layoutAboutToBeChanged() ),
+-              this, SLOT ( layoutAboutToBeChanged() ) );
+-    connect ( model, SIGNAL ( layoutChanged() ),
+-              this, SLOT ( layoutChanged() ) );
+-
+-    connect ( model, SIGNAL ( rowsAboutToBeInserted ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( rowsAboutToBeInserted ( const QModelIndex &, int, int ) ) );
+-    connect ( model, SIGNAL ( rowsAboutToBeRemoved ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( rowsAboutToBeRemoved ( const QModelIndex &, int, int ) ) );
+-    connect ( model, SIGNAL ( rowsInserted ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( rowsInserted ( const QModelIndex &, int, int ) ) );
+-    connect ( model, SIGNAL ( rowsRemoved ( const QModelIndex &, int, int ) ),
+-              this, SLOT ( rowsRemoved ( const QModelIndex &, int, int ) ) );
+-
+-    connect ( model, SIGNAL (rowsAboutToBeMoved(QModelIndex,int,int,QModelIndex,int)),
+-              this, SLOT (rowsAboutToBeMoved(QModelIndex,int,int,QModelIndex,int)) );
+-    connect ( model, SIGNAL (rowsMoved(QModelIndex,int,int,QModelIndex,int)),
+-              this, SLOT (rowsMoved(QModelIndex,int,int,QModelIndex,int)) );
+-
++    connect(model, SIGNAL(columnsAboutToBeInserted(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(columnsAboutToBeRemoved(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(columnsInserted(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(columnsRemoved(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(dataChanged(QModelIndex,QModelIndex)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(headerDataChanged(Qt::Orientation,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(layoutAboutToBeChanged()), this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(layoutChanged()), this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(modelReset()), this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(rowsAboutToBeInserted(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(rowsAboutToBeRemoved(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(rowsInserted(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++    connect(model, SIGNAL(rowsRemoved(QModelIndex,int,int)),
++            this, SLOT(runAllTests()) );
++
++    // Special checks for changes
++    connect(model, SIGNAL(layoutAboutToBeChanged()),
++            this, SLOT(layoutAboutToBeChanged()) );
++    connect(model, SIGNAL(layoutChanged()),
++            this, SLOT(layoutChanged()) );
++
++    connect(model, SIGNAL(rowsAboutToBeInserted(QModelIndex,int,int)),
++            this, SLOT(rowsAboutToBeInserted(QModelIndex,int,int)) );
++    connect(model, SIGNAL(rowsAboutToBeRemoved(QModelIndex,int,int)),
++            this, SLOT(rowsAboutToBeRemoved(QModelIndex,int,int)) );
++    connect(model, SIGNAL(rowsInserted(QModelIndex,int,int)),
++            this, SLOT(rowsInserted(QModelIndex,int,int)) );
++    connect(model, SIGNAL(rowsRemoved(QModelIndex,int,int)),
++            this, SLOT(rowsRemoved(QModelIndex,int,int)) );
++    connect(model, SIGNAL (rowsAboutToBeMoved(QModelIndex,int,int,QModelIndex,int)),
++            this, SLOT (rowsAboutToBeMoved(QModelIndex,int,int,QModelIndex,int)) );
++    connect(model, SIGNAL (rowsMoved(QModelIndex,int,int,QModelIndex,int)),
++            this, SLOT (rowsMoved(QModelIndex,int,int,QModelIndex,int)) );
++    connect(model, SIGNAL(dataChanged(QModelIndex,QModelIndex)),
++            this, SLOT(dataChanged(QModelIndex,QModelIndex)) );
++    connect(model, SIGNAL(headerDataChanged(Qt::Orientation,int,int)),
++            this, SLOT(headerDataChanged(Qt::Orientation,int,int)) );
+     runAllTests();
+ }
+@@ -257,7 +249,7 @@ void ModelTest::index()
+ void ModelTest::parent()
+ {
+ //     qDebug() << "p";
+-    // Make sure the model wont crash and will return an invalid QModelIndex
++    // Make sure the model won't crash and will return an invalid QModelIndex
+     // when asked for the parent of an invalid index.
+     QVERIFY( model->parent ( QModelIndex() ) == QModelIndex() );
+@@ -339,6 +331,8 @@ void ModelTest::checkChildren ( const QModelIndex &parent, int currentDepth )
+     //qDebug() << "parent:" << model->data(parent).toString() << "rows:" << rows
+     //         << "columns:" << columns << "parent column:" << parent.column();
++    const QModelIndex topLeftChild = model->index( 0, 0, parent );
++
+     QVERIFY( !model->hasIndex ( rows + 1, 0, parent ) );
+     for ( int r = 0; r < rows; ++r ) {
+         if ( model->canFetchMore ( parent ) ) {
+@@ -362,6 +356,15 @@ void ModelTest::checkChildren ( const QModelIndex &parent, int currentDepth )
+             QModelIndex b = model->index ( r, c, parent );
+             QVERIFY( a == b );
++            {
++                const QModelIndex sibling = model->sibling( r, c, topLeftChild );
++                QVERIFY( index == sibling );
++            }
++            {
++                const QModelIndex sibling = topLeftChild.sibling( r, c );
++                QVERIFY( index == sibling );
++            }
++
+             // Some basic checking on the index that is returned
+             QVERIFY( index.model() == model );
+             QCOMPARE( index.row(), r );
+@@ -474,9 +477,9 @@ void ModelTest::data()
+     \sa rowsInserted()
+  */
+-void ModelTest::rowsAboutToBeInserted ( const QModelIndex &parent, int start, int end )
++void ModelTest::rowsAboutToBeInserted ( const QModelIndex &parent, int start, int /* end */)
+ {
+-    Q_UNUSED(end);
++//     Q_UNUSED(end);
+ //    qDebug() << "rowsAboutToBeInserted" << "start=" << start << "end=" << end << "parent=" << model->data ( parent ).toString()
+ //    << "current count of parent=" << model->rowCount ( parent ); // << "display of last=" << model->data( model->index(start-1, 0, parent) );
+ //     qDebug() << model->index(start-1, 0, parent) << model->data( model->index(start-1, 0, parent) );
+@@ -565,6 +568,30 @@ void ModelTest::rowsRemoved ( const QModelIndex & parent, int start, int end )
+     QVERIFY( c.next == model->data ( model->index ( start, 0, c.parent ) ) );
+ }
++void ModelTest::dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight)
++{
++    QVERIFY(topLeft.isValid());
++    QVERIFY(bottomRight.isValid());
++    QModelIndex commonParent = bottomRight.parent();
++    QVERIFY(topLeft.parent() == commonParent);
++    QVERIFY(topLeft.row() <= bottomRight.row());
++    QVERIFY(topLeft.column() <= bottomRight.column());
++    int rowCount = model->rowCount(commonParent);
++    int columnCount = model->columnCount(commonParent);
++    QVERIFY(bottomRight.row() < rowCount);
++    QVERIFY(bottomRight.column() < columnCount);
++}
++
++void ModelTest::headerDataChanged(Qt::Orientation orientation, int start, int end)
++{
++    QVERIFY(start >= 0);
++    QVERIFY(end >= 0);
++    QVERIFY(start <= end);
++    int itemCount = orientation == Qt::Vertical ? model->rowCount() : model->columnCount();
++    QVERIFY(start < itemCount);
++    QVERIFY(end < itemCount);
++}
++
+ void ModelTest::rowsAboutToBeMoved( const QModelIndex &srcParent, int start, int end, const QModelIndex &destParent, int destinationRow )
+ {
+     Changing cs;
+@@ -589,8 +616,8 @@ void ModelTest::rowsMoved( const QModelIndex &srcParent, int start, int end, con
+         QVERIFY ( cd.oldSize == model->rowCount ( destParent ) );
+         // TODO: Find out what I can assert here about last and next.
+-        // QVERIFY ( cd.last == model->data ( model->index ( destinationRow - 1, 0, cd.parent ) ) );
+-        // QVERIFY ( cd.next == model->data ( model->index ( destinationRow + (end - start + 1), 0, cd.parent ) ) );
++        // Q_ASSERT ( cd.last == model->data ( model->index ( destinationRow - 1, 0, cd.parent ) ) );
++        // Q_ASSERT ( cd.next == model->data ( model->index ( destinationRow + (end - start + 1), 0, cd.parent ) ) );
+     }
+     else {
+         QVERIFY ( cd.oldSize + ( end - start + 1 ) == model->rowCount ( destParent ) );
+@@ -602,12 +629,12 @@ void ModelTest::rowsMoved( const QModelIndex &srcParent, int start, int end, con
+     Changing cs = remove.pop();
+     QVERIFY ( cs.parent == srcParent );
+     if (srcParent == destParent) {
+-      QVERIFY ( cs.oldSize == model->rowCount ( srcParent ) );
++        QVERIFY ( cs.oldSize == model->rowCount ( srcParent ) );
+     }
+     else {
+-      QVERIFY ( cs.oldSize - ( end - start + 1 ) == model->rowCount ( srcParent ) );
++        QVERIFY ( cs.oldSize - ( end - start + 1 ) == model->rowCount ( srcParent ) );
+-      QVERIFY ( cs.last == model->data ( model->index ( start - 1, 0, srcParent ) ) );
+-      QVERIFY ( cs.next == model->data ( model->index ( start, 0, srcParent ) ) );
++        QVERIFY ( cs.last == model->data ( model->index ( start - 1, 0, srcParent ) ) );
++        QVERIFY ( cs.next == model->data ( model->index ( start, 0, srcParent ) ) );
+     }
+ }
+diff --git a/tests/modeltest.h b/tests/modeltest.h
+index 9eb343d..3dcf18c 100644
+--- a/tests/modeltest.h
++++ b/tests/modeltest.h
+@@ -1,40 +1,32 @@
+ /****************************************************************************
+ **
+-** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
+-** All rights reserved.
+-** Contact: Nokia Corporation (qt-info@nokia.com)
++** Copyright (C) 2015 The Qt Company Ltd.
++** Contact: http://www.qt.io/licensing/
+ **
+ ** This file is part of the test suite of the Qt Toolkit.
+ **
+-** $QT_BEGIN_LICENSE:LGPL$
++** $QT_BEGIN_LICENSE:LGPL21$
++** Commercial License Usage
++** Licensees holding valid commercial Qt licenses may use this file in
++** accordance with the commercial license agreement provided with the
++** Software or, alternatively, in accordance with the terms contained in
++** a written agreement between you and The Qt Company. For licensing terms
++** and conditions see http://www.qt.io/terms-conditions. For further
++** information use the contact form at http://www.qt.io/contact-us.
++**
+ ** GNU Lesser General Public License Usage
+-** This file may be used under the terms of the GNU Lesser General Public
+-** License version 2.1 as published by the Free Software Foundation and
+-** appearing in the file LICENSE.LGPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU Lesser
+-** General Public License version 2.1 requirements will be met:
++** Alternatively, this file may be used under the terms of the GNU Lesser
++** General Public License version 2.1 or version 3 as published by the Free
++** Software Foundation and appearing in the file LICENSE.LGPLv21 and
++** LICENSE.LGPLv3 included in the packaging of this file. Please review the
++** following information to ensure the GNU Lesser General Public License
++** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+ ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+ **
+-** In addition, as a special exception, Nokia gives you certain additional
+-** rights. These rights are described in the Nokia Qt LGPL Exception
++** As a special exception, The Qt Company gives you certain additional
++** rights. These rights are described in The Qt Company LGPL Exception
+ ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+ **
+-** GNU General Public License Usage
+-** Alternatively, this file may be used under the terms of the GNU General
+-** Public License version 3.0 as published by the Free Software Foundation
+-** and appearing in the file LICENSE.GPL included in the packaging of this
+-** file. Please review the following information to ensure the GNU General
+-** Public License version 3.0 requirements will be met:
+-** http://www.gnu.org/copyleft/gpl.html.
+-**
+-** Other Usage
+-** Alternatively, this file may be used in accordance with the terms and
+-** conditions contained in a signed written agreement between you and Nokia.
+-**
+-**
+-**
+-**
+-**
+ ** $QT_END_LICENSE$
+ **
+ ****************************************************************************/
+@@ -43,8 +35,8 @@
+ #ifndef MODELTEST_H
+ #define MODELTEST_H
+-#include <QAbstractItemModel>
+ #include <QObject>
++#include <QAbstractItemModel>
+ #include <QStack>
+ class ModelTest : public QObject
+@@ -73,7 +65,8 @@ protected Q_SLOTS:
+   void rowsRemoved( const QModelIndex & parent, int start, int end );
+   void rowsAboutToBeMoved ( const QModelIndex &srcParent, int start, int end, const QModelIndex &destParent, int destinationRow );
+   void rowsMoved ( const QModelIndex &srcParent, int start, int end, const QModelIndex &destParent, int destinationRow );
+-
++  void dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight);
++  void headerDataChanged(Qt::Orientation orientation, int start, int end);
+ private:
+   void checkChildren( const QModelIndex &parent, int currentDepth = 0 );
+diff --git a/tests/tests.h b/tests/tests.h
+deleted file mode 100644
+index e719a0b..0000000
+--- a/tests/tests.h
++++ /dev/null
+@@ -1,72 +0,0 @@
+-/*
+- *  Copyright (C) 2011 Felix Geyer <debfx@fobos.de>
+- *  Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
+- *
+- *  This program is free software: you can redistribute it and/or modify
+- *  it under the terms of the GNU General Public License as published by
+- *  the Free Software Foundation, either version 2 or (at your option)
+- *  version 3 of the License.
+- *
+- *  This program is distributed in the hope that it will be useful,
+- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+- *  GNU General Public License for more details.
+- *
+- *  You should have received a copy of the GNU General Public License
+- *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+- */
+-
+-#ifndef KEEPASSX_TESTS_H
+-#define KEEPASSX_TESTS_H
+-
+-#include <QTest>
+-
+-// backport QTEST_GUILESS_MAIN, QTRY_VERIFY and QTRY_COMPARE from Qt 5
+-
+-#ifndef QTEST_GUILESS_MAIN
+-#define QTEST_GUILESS_MAIN(TestObject) \
+-int main(int argc, char* argv[]) \
+-{ \
+-    QCoreApplication app(argc, argv); \
+-    TestObject tc; \
+-    return QTest::qExec(&tc, argc, argv); \
+-}
+-#endif // QTEST_GUILESS_MAIN
+-
+-
+-#ifndef QTRY_VERIFY
+-#define KEEPASSX_VERIFY_WITH_TIMEOUT(__expr, __timeout) \
+-do { \
+-    const int __step = 50; \
+-    const int __timeoutValue = __timeout; \
+-    if (!(__expr)) { \
+-        QTest::qWait(0); \
+-    } \
+-    for (int __i = 0; __i < __timeoutValue && !(__expr); __i+=__step) { \
+-        QTest::qWait(__step); \
+-    } \
+-    QVERIFY(__expr); \
+-} while (0)
+-
+-#define QTRY_VERIFY(__expr) KEEPASSX_VERIFY_WITH_TIMEOUT(__expr, 5000)
+-#endif // QTRY_VERIFY
+-
+-
+-#ifndef QTRY_COMPARE
+-#define KEEPASSX_COMPARE_WITH_TIMEOUT(__expr, __expected, __timeout) \
+-do { \
+-    const int __step = 50; \
+-    const int __timeoutValue = __timeout; \
+-    if ((__expr) != (__expected)) { \
+-        QTest::qWait(0); \
+-    } \
+-    for (int __i = 0; __i < __timeoutValue && ((__expr) != (__expected)); __i+=__step) { \
+-        QTest::qWait(__step); \
+-    } \
+-    QCOMPARE(__expr, __expected); \
+-} while (0)
+-
+-#define QTRY_COMPARE(__expr, __expected) KEEPASSX_COMPARE_WITH_TIMEOUT(__expr, __expected, 5000)
+-#endif // QTRY_COMPARE
+-
+-#endif // KEEPASSX_TESTS_H
+diff --git a/utils/CMakeLists.txt b/utils/CMakeLists.txt
+index c4aa5fa..7988467 100644
+--- a/utils/CMakeLists.txt
++++ b/utils/CMakeLists.txt
+@@ -18,7 +18,8 @@ include_directories(../src)
+ add_executable(kdbx-extract kdbx-extract.cpp)
+ target_link_libraries(kdbx-extract
+                       keepassx_core
+-                      ${QT_QTCORE_LIBRARY}
+-                      ${QT_QTGUI_LIBRARY}
++                      Qt5::Core
++                      Qt5::Concurrent
++                      Qt5::Widgets
+                       ${GCRYPT_LIBRARIES}
+                       ${ZLIB_LIBRARIES})
index e02a43faac89f15101976fe3a510bf526bd7ebc0..212610b91b513c2fe4df3014dcec116732a819ca 100644 (file)
@@ -2,11 +2,12 @@ Summary:      KeePassX - Cross Platform Password Manager
 Summary(pl.UTF-8):     KeePassX - Wieloplatformowy zarządca haseł
 Name:          keepassx
 Version:       2.0.2
-Release:       1
+Release:       2
 License:       GPL v2+
 Group:         X11/Applications
 Source0:       http://www.keepassx.org/releases/%{version}/keepassx-%{version}.tar.gz
 # Source0-md5: 65d098dff663768911847a1e92d0f01d
+Patch0:                git.patch
 URL:           https://www.keepassx.org/
 BuildRequires: Qt5Concurrent-devel >= 5.2.0
 BuildRequires: Qt5Core-devel >= 5.2.0
@@ -51,6 +52,7 @@ szyfrowania jakie są do tej pory znane (AES i TwoFish).
 
 %prep
 %setup -q
+%patch0 -p1
 
 %build
 install -d build
@@ -93,7 +95,7 @@ rm -rf $RPM_BUILD_ROOT
 %{_datadir}/keepassx/icons
 %dir %{_datadir}/keepassx/translations
 %dir %{_libdir}/keepassx
-%attr(755,root,root) %{_libdir}/keepassx/libkeepassx-autotype-x11.so
+%attr(755,root,root) %{_libdir}/keepassx/libkeepassx-autotype-xcb.so
 %{_iconsdir}/hicolor/*x*/apps/keepassx.png
 %{_iconsdir}/hicolor/*x*/mimetypes/application-x-keepassx.png
 %{_iconsdir}/hicolor/scalable/apps/keepassx.svgz
This page took 0.464038 seconds and 4 git commands to generate.