diff --git a/src/client/client.c b/src/client/client.c index 0535c1cf..956d7f58 100644 --- a/src/client/client.c +++ b/src/client/client.c @@ -189,12 +189,14 @@ static void process_socket_message (MSG *msg) /* Since 5.2.0 */ int slot = (int)msg->wParam; HWND hwnd = (HWND)msg->lParam; + unsigned dirty_age = (unsigned)msg->time; if (__mg_client_check_znode_hwnd(slot, hwnd, __mg_client_id)) { GAL_Surface *ssurf = ((PMAINWIN)hwnd)->surf; assert(ssurf->shared_header); __mg_lock_file_for_write(ssurf->fd); - ssurf->dirty_info->nr_dirty_rcs = 0; - ssurf->dirty_info->dirty_age++; + if (ssurf->dirty_info->dirty_age == dirty_age) { + ssurf->dirty_info->nr_dirty_rcs = 0; + } __mg_unlock_file_for_write(ssurf->fd); } } diff --git a/src/kernel/compsor-fallback.c b/src/kernel/compsor-fallback.c index 7c35ac3f..7d71c9f2 100644 --- a/src/kernel/compsor-fallback.c +++ b/src/kernel/compsor-fallback.c @@ -679,6 +679,19 @@ static BOOL merge_dirty_ppp (CompositorCtxt* ctxt, MG_Layer* layer, int zidx) return rc; } +#if 0 +static void dump_dirty_region(CompositorCtxt* ctxt, const char *prefix, int zidx) +{ + CLIPRGN* rgn = &ctxt->dirty_rgn; + _WRN_PRINTF("%s (%d): dirty region on screen: (%d, %d) %d x %d; " + "highest dirty win: %d; lowest dirty win: %d\n", + prefix, zidx, + rgn->rcBound.left, rgn->rcBound.top, + RECTW (rgn->rcBound), RECTH (rgn->rcBound), + ctxt->highest_dirty_win, ctxt->lowest_dirty_win); +} +#endif + static BOOL merge_dirty_win (CompositorCtxt* ctxt, MG_Layer* layer, int zidx) { BOOL rc = FALSE; @@ -722,9 +735,13 @@ static BOOL merge_dirty_wpp (CompositorCtxt* ctxt, MG_Layer* layer) static BOOL refresh_dirty_region (CompositorCtxt* ctxt, MG_Layer* layer) { /* the fallback compositor only manages znodes on the topmost layer. */ - if (layer != mgTopmostLayer || IsEmptyClipRgn (&ctxt->dirty_rgn)) + if (layer != mgTopmostLayer) return FALSE; + if (IsEmptyClipRgn (&ctxt->dirty_rgn)) { + return FALSE; + } + if (ctxt->highest_dirty_ppp >= 0) { composite_ppp_znodes (ctxt); } diff --git a/src/kernel/compsor-manager.c b/src/kernel/compsor-manager.c index fea53aaf..044775d0 100644 --- a/src/kernel/compsor-manager.c +++ b/src/kernel/compsor-manager.c @@ -68,6 +68,7 @@ #include "constants.h" #include "zorder.h" #include "dc.h" +#include "server.h" #define MAX_NR_COMPOSITORS 8 #define LEN_COMPOSITOR_NAME 15 @@ -138,7 +139,6 @@ static void lock_znode_surface (PDC pdc, ZORDERNODE* node) node->dirty_age = pdc->surface->dirty_info->dirty_age; node->nr_dirty_rcs = pdc->surface->dirty_info->nr_dirty_rcs; node->dirty_rcs = pdc->surface->dirty_info->dirty_rcs; - } node->lock_count++; @@ -174,8 +174,9 @@ static void reset_znode_surface_dirty (PDC pdc, ZORDERNODE* node, int slot) pdc->surface->dirty_info->nr_dirty_rcs = 0; } else if (node->hwnd) { - MSG msg = { HWND_NULL, MSG_WINCOMPOSITED, slot, (LPARAM)node->hwnd }; - __mg_send2client(&msg, node); + MSG msg = { HWND_NULL, MSG_WINCOMPOSITED, + slot, (LPARAM)node->hwnd, (DWORD)node->changes }; + __mg_send2client(&msg, mgClients + node->cli); } } diff --git a/src/kernel/desktop.c b/src/kernel/desktop.c index 5ab17cb0..c6e63fd7 100644 --- a/src/kernel/desktop.c +++ b/src/kernel/desktop.c @@ -1654,6 +1654,8 @@ static int srvStartTrackPopupMenu (int cli, const RECT* rc, HWND ptmi, menu_nodes [zi->nr_popupmenus].ct = CT_OPAQUE; menu_nodes [zi->nr_popupmenus].ct_arg = 0; menu_nodes [zi->nr_popupmenus].mem_dc = memdc; + menu_nodes [zi->nr_popupmenus].dirty_age = 0; + menu_nodes [zi->nr_popupmenus].nr_dirty_rcs = 0; menu_nodes [zi->nr_popupmenus].dirty_rcs = NULL; #endif menu_nodes [zi->nr_popupmenus].priv_data = NULL; @@ -2359,6 +2361,8 @@ static int AllocZOrderNodeEx (ZORDERINFO* zi, int cli, HWND hwnd, HWND main_win, nodes [free_slot].ct = validate_compositing_type (flags, ct); nodes [free_slot].ct_arg = ct_arg; nodes [free_slot].mem_dc = mem_dc; + nodes [free_slot].dirty_age = 0; + nodes [free_slot].nr_dirty_rcs = 0; nodes [free_slot].dirty_rcs = NULL; #else nodes [free_slot].age = 1; diff --git a/src/misc/lock_file.c b/src/misc/lock_file.c index 5f73fc02..878e8b67 100644 --- a/src/misc/lock_file.c +++ b/src/misc/lock_file.c @@ -63,22 +63,50 @@ void __mg_lock_file_for_read(int fd) { - while (flock(fd, LOCK_SH) == -1 && errno == EINTR); + struct flock lock; + + lock.l_type = F_RDLCK; + lock.l_whence = SEEK_SET; + lock.l_start = 0; + lock.l_len = 0; + + while (fcntl(fd, F_SETLKW, &lock) == -1 && errno == EINTR); } void __mg_unlock_file_for_read(int fd) { - flock(fd, LOCK_UN); + struct flock lock; + + lock.l_type = F_UNLCK; + lock.l_whence = SEEK_SET; + lock.l_start = 0; + lock.l_len = 0; + + fcntl(fd, F_SETLK, &lock); } void __mg_lock_file_for_write(int fd) { - while (flock(fd, LOCK_EX) == -1 && errno == EINTR); + struct flock lock; + + lock.l_type = F_WRLCK; + lock.l_whence = SEEK_SET; + lock.l_start = 0; + lock.l_len = 0; + + while (fcntl(fd, F_SETLKW, &lock) == -1 && errno == EINTR); } void __mg_unlock_file_for_write(int fd) { - flock(fd, LOCK_UN); + struct flock lock; + + lock.l_type = F_UNLCK; + lock.l_whence = SEEK_SET; + lock.l_start = 0; + lock.l_len = 0; + + fcntl(fd, F_SETLK, &lock); } #endif /* __NOUNIX__ */ diff --git a/src/newgdi/region.c b/src/newgdi/region.c index 8576665d..0c8a63d7 100644 --- a/src/newgdi/region.c +++ b/src/newgdi/region.c @@ -269,7 +269,7 @@ void GUIAPI GetClipRgnBoundRect (PCLIPRGN pRgn, PRECT pRect) BOOL GUIAPI IsEmptyClipRgn (const CLIPRGN* pRgn) { - if (pRgn->head == NULL) + if (pRgn->head == NULL || IsRectEmpty (&pRgn->rcBound)) return TRUE; return FALSE;