Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[Qt] catch Windows shutdown events while client is running
- prevents unsafe shutdowns on Windows, which is known to be able to cause problems with wallet.dat - if a users ends a Windows session, this will initiate a client shutdown and show a Windows dialog, that tells the user what is going on (for Windows Vista and higher it will even show a reason for blocking the Windows session end)
- Loading branch information
Philip Kaufmann
committed
Apr 15, 2014
1 parent
74dd52a
commit d282c1f
Showing
4 changed files
with
111 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
// Copyright (c) 2014 The Bitcoin developers | ||
// Distributed under the MIT/X11 software license, see the accompanying | ||
// file COPYING or http://www.opensource.org/licenses/mit-license.php. | ||
|
||
#include "winshutdownmonitor.h" | ||
|
||
#if defined(Q_OS_WIN) && QT_VERSION >= 0x050000 | ||
#include "init.h" | ||
|
||
#include <windows.h> | ||
|
||
#include <QDebug> | ||
|
||
// If we don't want a message to be processed by Qt, return true and set result to | ||
// the value that the window procedure should return. Otherwise return false. | ||
bool WinShutdownMonitor::nativeEventFilter(const QByteArray &eventType, void *pMessage, long *pnResult) | ||
{ | ||
Q_UNUSED(eventType); | ||
|
||
MSG *pMsg = static_cast<MSG *>(pMessage); | ||
|
||
switch(pMsg->message) | ||
{ | ||
case WM_QUERYENDSESSION: | ||
{ | ||
// Initiate a client shutdown after receiving a WM_QUERYENDSESSION and block | ||
// Windows session end until we have finished client shutdown. | ||
StartShutdown(); | ||
*pnResult = FALSE; | ||
return true; | ||
} | ||
|
||
case WM_ENDSESSION: | ||
{ | ||
*pnResult = FALSE; | ||
return true; | ||
} | ||
} | ||
|
||
return false; | ||
} | ||
|
||
void WinShutdownMonitor::registerShutdownBlockReason(const QString& strReason, const HWND& mainWinId) | ||
{ | ||
typedef BOOL (WINAPI *PSHUTDOWNBRCREATE)(HWND, LPCWSTR); | ||
PSHUTDOWNBRCREATE shutdownBRCreate = (PSHUTDOWNBRCREATE)GetProcAddress(GetModuleHandleA("User32.dll"), "ShutdownBlockReasonCreate"); | ||
if (shutdownBRCreate == NULL) { | ||
qDebug() << "registerShutdownBlockReason : GetProcAddress for ShutdownBlockReasonCreate failed"; | ||
return; | ||
} | ||
|
||
if (shutdownBRCreate(mainWinId, strReason.toStdWString().c_str())) | ||
qDebug() << "registerShutdownBlockReason : Successfully registered: " + strReason; | ||
else | ||
qDebug() << "registerShutdownBlockReason : Failed to register: " + strReason; | ||
} | ||
#endif |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
// Copyright (c) 2014 The Bitcoin developers | ||
// Distributed under the MIT/X11 software license, see the accompanying | ||
// file COPYING or http://www.opensource.org/licenses/mit-license.php. | ||
|
||
#ifndef WINSHUTDOWNMONITOR_H | ||
#define WINSHUTDOWNMONITOR_H | ||
|
||
#ifdef WIN32 | ||
#include <QByteArray> | ||
#include <QString> | ||
|
||
#if QT_VERSION >= 0x050000 | ||
#include <windef.h> // for HWND | ||
|
||
#include <QAbstractNativeEventFilter> | ||
|
||
class WinShutdownMonitor : public QAbstractNativeEventFilter | ||
{ | ||
public: | ||
/** Implements QAbstractNativeEventFilter interface for processing Windows messages */ | ||
bool nativeEventFilter(const QByteArray &eventType, void *pMessage, long *pnResult); | ||
|
||
/** Register the reason for blocking shutdown on Windows to allow clean client exit */ | ||
static void registerShutdownBlockReason(const QString& strReason, const HWND& mainWinId); | ||
}; | ||
#endif | ||
#endif | ||
|
||
#endif // WINSHUTDOWNMONITOR_H |