From a447191925f08638cc1acab8191ea40b1c3699c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Axel=20D=C3=B6rfler?= Date: Sat, 10 Dec 2005 13:47:13 +0000 Subject: [PATCH] The fWindowLock is now responsible for all window activities - no need to sometimes lock the Desktop itself, and sometimes not - that also fixes some potential deadlock situations. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@15463 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- src/servers/app/Desktop.cpp | 50 ++++++++++++++++++++--------------- src/servers/app/Workspace.cpp | 4 +-- 2 files changed, 30 insertions(+), 24 deletions(-) diff --git a/src/servers/app/Desktop.cpp b/src/servers/app/Desktop.cpp index a4b85b04ae..d8cededb34 100644 --- a/src/servers/app/Desktop.cpp +++ b/src/servers/app/Desktop.cpp @@ -144,7 +144,8 @@ KeyboardFilter::Filter(BMessage* message, EventTarget** _target, bigtime_t now = system_time(); - fDesktop->ReadLockWindows(); + if (!fDesktop->ReadLockWindows()) + return B_DISPATCH_MESSAGE; EventTarget* focus = NULL; if (fDesktop->FocusWindow() != NULL) @@ -195,7 +196,8 @@ MouseFilter::Filter(BMessage* message, EventTarget** _target, int32* _viewToken) if (message->FindPoint("where", &where) != B_OK) return B_DISPATCH_MESSAGE; - fDesktop->WriteLockWindows(); + if (!fDesktop->WriteLockWindows()) + return B_DISPATCH_MESSAGE; WindowLayer* window = fDesktop->MouseEventWindow(); if (window == NULL) @@ -572,13 +574,13 @@ Desktop::UpdateWorkspaces() void Desktop::SetWorkspace(int32 index) { - BAutolock _(this); + WriteLockWindows(); DesktopSettings settings(this); - if (index < 0 || index >= settings.WorkspacesCount() || index == fCurrentWorkspace) + if (index < 0 || index >= settings.WorkspacesCount() || index == fCurrentWorkspace) { + WriteUnlockWindows(); return; - - WriteLockWindows(); + } int32 previousIndex = fCurrentWorkspace; @@ -679,10 +681,8 @@ Desktop::SetWorkspace(int32 index) SetFocusWindow(FrontWindow()); _WindowChanged(NULL); - MarkDirty(dirty); - //_WindowsChanged(); WriteUnlockWindows(); } @@ -693,10 +693,6 @@ Desktop::ScreenChanged(Screen* screen) // TODO: confirm that everywhere this is used, // the Window WriteLock is held -// TODO: can this be removed? I would think it can. -// In fact, this lock should nowhere be used anymore, no? -// BAutolock locker(this); - // the entire screen is dirty, because we're actually // operating on an all new buffer in memory BRegion dirty(screen->Frame()); @@ -1360,19 +1356,20 @@ Desktop::_ChangeWindowWorkspaces(WindowLayer* window, uint32 oldWorkspaces, void Desktop::SetWindowWorkspaces(WindowLayer* window, uint32 workspaces) { - BAutolock _(this); + WriteLockWindows(); if (window->IsNormal() && workspaces == B_CURRENT_WORKSPACE) workspaces = workspace_to_workspaces(CurrentWorkspace()); _ChangeWindowWorkspaces(window, window->Workspaces(), workspaces); + WriteUnlockWindows(); } void Desktop::AddWindow(WindowLayer *window) { - BAutolock _(this); + WriteLockWindows(); fAllWindows.AddWindow(window); if (!window->IsNormal()) @@ -1387,13 +1384,14 @@ Desktop::AddWindow(WindowLayer *window) } _ChangeWindowWorkspaces(window, 0, window->Workspaces()); + WriteUnlockWindows(); } void Desktop::RemoveWindow(WindowLayer *window) { - BAutolock _(this); + WriteLockWindows(); if (!window->IsHidden()) HideWindow(window); @@ -1403,6 +1401,7 @@ Desktop::RemoveWindow(WindowLayer *window) fSubsetWindows.RemoveWindow(window); _ChangeWindowWorkspaces(window, window->Workspaces(), 0); + WriteUnlockWindows(); // make sure this window won't get any events anymore @@ -1460,7 +1459,7 @@ Desktop::SetWindowFeel(WindowLayer *window, window_feel newFeel) if (window->Feel() == newFeel) return; - BAutolock _(this); + WriteLockWindows(); bool wasNormal = window->IsNormal(); @@ -1510,6 +1509,8 @@ Desktop::SetWindowFeel(WindowLayer *window, window_feel newFeel) if (window == FocusWindow() && !window->IsVisible()) SetFocusWindow(FrontWindow()); + + WriteUnlockWindows(); } @@ -1560,11 +1561,13 @@ Desktop::SetWindowTitle(WindowLayer *window, const char* title) } +/*! + Returns the window under the mouse cursor. + You need to have the window write lock acquired when calling this method. +*/ WindowLayer* Desktop::WindowAt(BPoint where) { -// TODO: BAutolock locker(this); ?!? - for (WindowLayer* window = _CurrentWindows().LastWindow(); window; window = window->PreviousWindow(fCurrentWorkspace)) { if (window->VisibleRegion().Contains(where)) @@ -1585,15 +1588,18 @@ Desktop::SetMouseEventWindow(WindowLayer* window) WindowLayer * Desktop::FindWindowLayerByClientToken(int32 token, team_id teamID) { - BAutolock locker(this); + ReadLockWindows(); for (WindowLayer *window = fAllWindows.FirstWindow(); window != NULL; window = window->NextWindow(kAllWindowList)) { if (window->ServerWindow()->ClientToken() == token - && window->ServerWindow()->ClientTeam() == teamID) + && window->ServerWindow()->ClientTeam() == teamID) { + ReadUnlockWindows(); return window; + } } + ReadUnlockWindows(); return NULL; } @@ -1601,7 +1607,7 @@ Desktop::FindWindowLayerByClientToken(int32 token, team_id teamID) void Desktop::WriteWindowList(team_id team, BPrivate::LinkSender& sender) { - BAutolock locker(this); + BAutolock locker(fWindowLock); // compute the number of windows @@ -1633,7 +1639,7 @@ Desktop::WriteWindowList(team_id team, BPrivate::LinkSender& sender) void Desktop::WriteWindowInfo(int32 serverToken, BPrivate::LinkSender& sender) { - BAutolock locker(this); + BAutolock locker(fWindowLock); BAutolock tokenLocker(BPrivate::gDefaultTokens); ::ServerWindow* window; diff --git a/src/servers/app/Workspace.cpp b/src/servers/app/Workspace.cpp index 3d92179a9e..031c34f844 100644 --- a/src/servers/app/Workspace.cpp +++ b/src/servers/app/Workspace.cpp @@ -72,14 +72,14 @@ Workspace::Workspace(Desktop& desktop, int32 index) fDesktop(desktop), fCurrentWorkspace(index == desktop.CurrentWorkspace()) { - fDesktop.Lock(); + fDesktop.ReadLockWindows(); RewindWindows(); } Workspace::~Workspace() { - fDesktop.Unlock(); + fDesktop.ReadUnlockWindows(); }