Fixed a bug in the screen saver code that could cause someone to get locked out
of their machine: if the password check is turned on, and the password window is shown but times out (when the screen saver starts again after the standard delay), the input filter never knew about this and would never try to end the screen saver again. The solution is to take the logic for turning off the screen saver out of the input filter and put it in the screen blanker itself. Also while working in the input filter I removed some debugging and a TODO that I think cannot be fixed. In the screen_blanker the exit after loading the settings file was removed since the default settings now work for the screen_blanker. Plus obviously code was added to handle exit upon user input as well as the timing out of the password window. If anyone has a better solution for the 250ms timeout to ignore initial mouse moves, let me know. Also I think the new calls should be nothrow, but I am not sure what the rule is for that. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@29488 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
parent
f451e14bc2
commit
cb6a084f20
@ -1,11 +1,12 @@
|
||||
/*
|
||||
* Copyright 2003-2008, Haiku.
|
||||
* Copyright 2003-2009, Haiku.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Authors:
|
||||
* Michael Phipps
|
||||
* Jérôme Duval, jerome.duval@free.fr
|
||||
* Axel Dörfler, axeld@pinc-software.de
|
||||
* Ryan Leavengood, leavengood@gmail.com
|
||||
*/
|
||||
|
||||
|
||||
@ -19,11 +20,8 @@
|
||||
#include <Roster.h>
|
||||
#include <Screen.h>
|
||||
|
||||
#include <Debug.h>
|
||||
|
||||
#include <new>
|
||||
|
||||
#define CALLED() SERIAL_PRINT(("%s\n", __PRETTY_FUNCTION__))
|
||||
#include <syslog.h>
|
||||
|
||||
|
||||
static const int32 kNeverBlankCornerSize = 10;
|
||||
@ -38,8 +36,7 @@ static const int32 kMsgCornerInvoke = 'Scin';
|
||||
extern "C" _EXPORT BInputServerFilter* instantiate_input_filter();
|
||||
|
||||
|
||||
/** required C func to build the IS Filter */
|
||||
|
||||
/** Required C func to build the IS Filter */
|
||||
BInputServerFilter*
|
||||
instantiate_input_filter()
|
||||
{
|
||||
@ -54,16 +51,12 @@ ScreenSaverController::ScreenSaverController(ScreenSaverFilter *filter)
|
||||
: BLooper("screensaver controller", B_LOW_PRIORITY),
|
||||
fFilter(filter)
|
||||
{
|
||||
CALLED();
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ScreenSaverController::MessageReceived(BMessage *message)
|
||||
{
|
||||
CALLED();
|
||||
SERIAL_PRINT(("what %lx\n", message->what));
|
||||
|
||||
switch (message->what) {
|
||||
case B_NODE_MONITOR:
|
||||
fFilter->ReloadSettings();
|
||||
@ -76,14 +69,9 @@ ScreenSaverController::MessageReceived(BMessage *message)
|
||||
&& strcasecmp(signature, SCREEN_BLANKER_SIG) == 0) {
|
||||
fFilter->SetEnabled(message->what == B_SOME_APP_LAUNCHED);
|
||||
}
|
||||
SERIAL_PRINT(("mime_sig %s\n", signature));
|
||||
break;
|
||||
}
|
||||
|
||||
case kMsgSuspendScreenSaver:
|
||||
//fFilter->Suspend(msg);
|
||||
break;
|
||||
|
||||
case kMsgCheckTime:
|
||||
fFilter->CheckTime();
|
||||
break;
|
||||
@ -114,7 +102,6 @@ ScreenSaverFilter::ScreenSaverFilter()
|
||||
fWatchingFile(false),
|
||||
fEnabled(false)
|
||||
{
|
||||
CALLED();
|
||||
fController = new (std::nothrow) ScreenSaverController(this);
|
||||
if (fController == NULL)
|
||||
return;
|
||||
@ -185,40 +172,20 @@ ScreenSaverFilter::_WatchSettings()
|
||||
void
|
||||
ScreenSaverFilter::_Invoke()
|
||||
{
|
||||
CALLED();
|
||||
if (fCurrentCorner == fNeverBlankCorner && fNeverBlankCorner != NO_CORNER
|
||||
|| fSettings.TimeFlags() == SAVER_DISABLED
|
||||
|| fEnabled
|
||||
|| be_roster->IsRunning(SCREEN_BLANKER_SIG))
|
||||
return;
|
||||
|
||||
SERIAL_PRINT(("we run screenblanker\n"));
|
||||
if (be_roster->Launch(SCREEN_BLANKER_SIG) == B_OK)
|
||||
fEnabled = true;
|
||||
}
|
||||
|
||||
|
||||
/*! Stops the running screen saver, if any */
|
||||
void
|
||||
ScreenSaverFilter::_Banish()
|
||||
{
|
||||
CALLED();
|
||||
if (!fEnabled)
|
||||
return;
|
||||
|
||||
SERIAL_PRINT(("we quit screenblanker\n"));
|
||||
|
||||
// Don't care if it fails
|
||||
BMessenger blankerMessenger(SCREEN_BLANKER_SIG, -1, NULL);
|
||||
blankerMessenger.SendMessage(B_QUIT_REQUESTED);
|
||||
fEnabled = false;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ScreenSaverFilter::ReloadSettings()
|
||||
{
|
||||
CALLED();
|
||||
BAutolock _(this);
|
||||
bool isFirst = !fWatchingDirectory && !fWatchingFile;
|
||||
|
||||
@ -251,7 +218,7 @@ ScreenSaverFilter::ReloadSettings()
|
||||
fRunner = new (std::nothrow) BMessageRunner(fController, &check,
|
||||
fSnoozeTime);
|
||||
if (fRunner == NULL || fRunner->InitCheck() != B_OK) {
|
||||
SERIAL_PRINT(("screen saver filter runner init failed\n"));
|
||||
syslog(LOG_ERR, "screen saver filter runner init failed\n");
|
||||
}
|
||||
}
|
||||
|
||||
@ -267,7 +234,6 @@ ScreenSaverFilter::SetEnabled(bool enabled)
|
||||
void
|
||||
ScreenSaverFilter::CheckTime()
|
||||
{
|
||||
CALLED();
|
||||
BAutolock _(this);
|
||||
|
||||
bigtime_t now = system_time();
|
||||
@ -307,9 +273,6 @@ ScreenSaverFilter::CheckCornerInvoke()
|
||||
void
|
||||
ScreenSaverFilter::_UpdateRectangles()
|
||||
{
|
||||
// TODO: make this better if possible at all (in a clean way)
|
||||
CALLED();
|
||||
|
||||
fBlankRect = _ScreenCorner(fBlankCorner, kBlankCornerSize);
|
||||
fNeverBlankRect = _ScreenCorner(fNeverBlankCorner, kNeverBlankCornerSize);
|
||||
}
|
||||
@ -382,20 +345,8 @@ ScreenSaverFilter::Filter(BMessage *message, BList *outList)
|
||||
fCurrentCorner = NO_CORNER;
|
||||
break;
|
||||
}
|
||||
|
||||
case B_KEY_UP:
|
||||
case B_KEY_DOWN:
|
||||
{
|
||||
// we ignore the Print-Screen key to make screen shots of
|
||||
// screen savers possible
|
||||
int32 key;
|
||||
if (fEnabled && message->FindInt32("key", &key) == B_OK
|
||||
&& key == 0xe)
|
||||
return B_DISPATCH_MESSAGE;
|
||||
}
|
||||
}
|
||||
|
||||
_Banish();
|
||||
return B_DISPATCH_MESSAGE;
|
||||
}
|
||||
|
||||
|
@ -19,8 +19,6 @@
|
||||
#include <Node.h>
|
||||
|
||||
|
||||
static const uint32 kMsgSuspendScreenSaver = 'susp';
|
||||
|
||||
class BMessageRunner;
|
||||
class ScreenSaverFilter;
|
||||
|
||||
@ -59,7 +57,6 @@ private:
|
||||
uint32 cornerSize);
|
||||
|
||||
void _Invoke();
|
||||
void _Banish();
|
||||
|
||||
ScreenSaverSettings fSettings;
|
||||
bigtime_t fLastEventTime;
|
||||
|
@ -1,11 +1,12 @@
|
||||
/*
|
||||
* Copyright 2003-2007, Haiku.
|
||||
* Copyright 2003-2009, Haiku.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Authors:
|
||||
* Michael Phipps
|
||||
* Jérôme Duval, jerome.duval@free.fr
|
||||
* Axel Dörfler, axeld@pinc-software.de
|
||||
* Ryan Leavengood, leavengood@gmail.com
|
||||
*/
|
||||
|
||||
|
||||
@ -58,8 +59,7 @@ void
|
||||
ScreenBlanker::ReadyToRun()
|
||||
{
|
||||
if (!fSettings.Load()) {
|
||||
fprintf(stderr, "could not load settings\n");
|
||||
exit(1);
|
||||
fprintf(stderr, "could not load settings, using defaults\n");
|
||||
}
|
||||
|
||||
// create a BDirectWindow and start the render thread.
|
||||
@ -123,7 +123,8 @@ ScreenBlanker::_ShowPasswordWindow()
|
||||
fWindow->Sync();
|
||||
// TODO: is that needed?
|
||||
ShowCursor();
|
||||
fPasswordWindow->Show();
|
||||
if (fPasswordWindow->IsHidden())
|
||||
fPasswordWindow->Show();
|
||||
|
||||
fWindow->Unlock();
|
||||
}
|
||||
@ -193,7 +194,7 @@ ScreenBlanker::_QueueTurnOffScreen()
|
||||
fSuspendScreenRunner = new BMessageRunner(BMessenger(this), &dpms,
|
||||
fSettings.SuspendTime(), 1);
|
||||
if (fSuspendScreenRunner->InitCheck() != B_OK)
|
||||
syslog(LOG_ERR, "turn off screen saver runner failed\n");
|
||||
syslog(LOG_ERR, "suspend screen saver runner failed\n");
|
||||
}
|
||||
|
||||
if (flags & ENABLE_DPMS_OFF) {
|
||||
@ -226,6 +227,7 @@ ScreenBlanker::MessageReceived(BMessage* message)
|
||||
}
|
||||
|
||||
case kMsgResumeSaver:
|
||||
{
|
||||
if (fWindow->Lock()) {
|
||||
HideCursor();
|
||||
fPasswordWindow->Hide();
|
||||
@ -234,8 +236,13 @@ ScreenBlanker::MessageReceived(BMessage* message)
|
||||
fWindow->Unlock();
|
||||
}
|
||||
|
||||
// Turn on the message filter again
|
||||
BMessage enable(kMsgEnableFilter);
|
||||
BMessenger(fWindow).SendMessage(&enable);
|
||||
|
||||
_QueueTurnOffScreen();
|
||||
break;
|
||||
}
|
||||
|
||||
case kMsgTurnOffScreen:
|
||||
_SetDPMSMode(B_DPMS_OFF);
|
||||
|
@ -1,10 +1,11 @@
|
||||
/*
|
||||
* Copyright 2003-2008, Haiku.
|
||||
* Copyright 2003-2009, Haiku.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Authors:
|
||||
* Michael Phipps
|
||||
* Jérôme Duval, jerome.duval@free.fr
|
||||
* Ryan Leavengood, leavengood@gmail.com
|
||||
*/
|
||||
|
||||
|
||||
@ -15,6 +16,44 @@
|
||||
|
||||
#include <WindowPrivate.h>
|
||||
|
||||
#include <syslog.h>
|
||||
|
||||
|
||||
/* This message filter is what will close the screensaver upon user activity. */
|
||||
filter_result
|
||||
ScreenSaverFilter::Filter(BMessage* message, BHandler** target)
|
||||
{
|
||||
// This guard is used to avoid sending multiple B_QUIT_REQUESTED messages
|
||||
if (fEnabled) {
|
||||
switch (message->what) {
|
||||
case B_KEY_DOWN:
|
||||
{
|
||||
// we ignore the Print-Screen key to make screen shots of
|
||||
// screen savers possible
|
||||
int32 key;
|
||||
if (message->FindInt32("key", &key) == B_OK && key == 0xe)
|
||||
return B_DISPATCH_MESSAGE;
|
||||
|
||||
// Fall through
|
||||
}
|
||||
case B_MOUSE_MOVED:
|
||||
case B_MOUSE_DOWN:
|
||||
fEnabled = false;
|
||||
be_app->PostMessage(B_QUIT_REQUESTED);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return B_DISPATCH_MESSAGE;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ScreenSaverFilter::SetEnabled(bool enabled)
|
||||
{
|
||||
fEnabled = enabled;
|
||||
}
|
||||
|
||||
|
||||
/*!
|
||||
This is the BDirectWindow subclass that rendering occurs in.
|
||||
@ -29,13 +68,31 @@ ScreenSaverWindow::ScreenSaverWindow(BRect frame)
|
||||
frame.OffsetTo(0, 0);
|
||||
fTopView = new BView(frame, "ScreenSaver View", B_FOLLOW_ALL, B_WILL_DRAW);
|
||||
fTopView->SetViewColor(0, 0, 0);
|
||||
|
||||
fFilter = new ScreenSaverFilter();
|
||||
fTopView->AddFilter(fFilter);
|
||||
|
||||
AddChild(fTopView);
|
||||
|
||||
// Ensure that this view receives keyboard input
|
||||
fTopView->MakeFocus(true);
|
||||
fTopView->SetEventMask(B_KEYBOARD_EVENTS, 0);
|
||||
|
||||
// A delay is necessary (250ms was chosen arbitrarily) before enabling the
|
||||
// message filter because when the window first shows some mouse moved
|
||||
// messages are sent to it automatically.
|
||||
BMessage enable(kMsgEnableFilter);
|
||||
fEnableRunner = new BMessageRunner(BMessenger(this), &enable, 250000LL, 1);
|
||||
if (fEnableRunner->InitCheck() != B_OK)
|
||||
syslog(LOG_ERR, "Runner to enable screen saver message filtering failed!\n");
|
||||
}
|
||||
|
||||
|
||||
ScreenSaverWindow::~ScreenSaverWindow()
|
||||
{
|
||||
Hide();
|
||||
delete fEnableRunner;
|
||||
delete fFilter;
|
||||
}
|
||||
|
||||
|
||||
@ -46,6 +103,21 @@ ScreenSaverWindow::SetSaver(BScreenSaver *saver)
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ScreenSaverWindow::MessageReceived(BMessage *message)
|
||||
{
|
||||
switch (message->what) {
|
||||
case kMsgEnableFilter:
|
||||
fFilter->SetEnabled(true);
|
||||
break;
|
||||
|
||||
default:
|
||||
BWindow::MessageReceived(message);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
ScreenSaverWindow::QuitRequested()
|
||||
{
|
||||
|
@ -9,6 +9,26 @@
|
||||
#include "ScreenSaver.h"
|
||||
|
||||
#include <DirectWindow.h>
|
||||
#include <MessageFilter.h>
|
||||
#include <MessageRunner.h>
|
||||
|
||||
|
||||
const static uint32 kMsgEnableFilter = 'eflt';
|
||||
|
||||
|
||||
class ScreenSaverFilter : public BMessageFilter {
|
||||
public:
|
||||
ScreenSaverFilter()
|
||||
: BMessageFilter(B_ANY_DELIVERY, B_ANY_SOURCE),
|
||||
fEnabled(false) {}
|
||||
|
||||
virtual filter_result Filter(BMessage* message, BHandler** target);
|
||||
|
||||
void SetEnabled(bool enabled);
|
||||
|
||||
private:
|
||||
bool fEnabled;
|
||||
};
|
||||
|
||||
|
||||
class ScreenSaverWindow : public BDirectWindow {
|
||||
@ -18,12 +38,15 @@ class ScreenSaverWindow : public BDirectWindow {
|
||||
|
||||
void SetSaver(BScreenSaver *saver);
|
||||
|
||||
virtual void MessageReceived(BMessage *message);
|
||||
virtual bool QuitRequested();
|
||||
virtual void DirectConnected(direct_buffer_info *info);
|
||||
|
||||
private:
|
||||
BView *fTopView;
|
||||
BScreenSaver *fSaver;
|
||||
ScreenSaverFilter *fFilter;
|
||||
BMessageRunner *fEnableRunner;
|
||||
};
|
||||
|
||||
#endif // SCREEN_SAVER_WINDOW_H
|
||||
|
Loading…
Reference in New Issue
Block a user