2025-08-08 20:00:36 +02:00

201 lines
6.4 KiB
C

/**************************************************************************/
/* */
/* Copyright (c) 2001, 2011 NoMachine (http://www.nomachine.com) */
/* Copyright (c) 2008-2017 Oleksandr Shneyder <o.shneyder@phoca-gmbh.de> */
/* Copyright (c) 2011-2022 Mike Gabriel <mike.gabriel@das-netzwerkteam.de>*/
/* Copyright (c) 2014-2019 Mihai Moldovan <ionic@ionic.de> */
/* Copyright (c) 2014-2022 Ulrich Sibiller <uli42@gmx.de> */
/* Copyright (c) 2015-2016 Qindel Group (http://www.qindel.com) */
/* */
/* NXAGENT, NX protocol compression and NX extensions to this software */
/* are copyright of the aforementioned persons and companies. */
/* */
/* Redistribution and use of the present software is allowed according */
/* to terms specified in the file LICENSE which comes in the source */
/* distribution. */
/* */
/* All rights reserved. */
/* */
/* NOTE: This software has received contributions from various other */
/* contributors, only the core maintainers and supporters are listed as */
/* copyright holders. Please contact us, if you feel you should be listed */
/* as copyright holder, as well. */
/* */
/**************************************************************************/
#include "scrnintstr.h"
#include "windowstr.h"
#include "Agent.h"
#include "Screen.h"
#include "Display.h"
#include "Options.h"
#include "Windows.h"
#include "X11/include/Xcomposite_nxagent.h"
/*
* Set here the required log level.
*/
#define PANIC
#define WARNING
#undef TEST
#undef DEBUG
/*
* Set if the composite extension is supported by the remote display.
*/
Bool nxagentCompositeEnable = False;
void nxagentCompositeExtensionInit(void)
{
/*
* Set the flag only if the initialization completes.
*/
nxagentCompositeEnable = False;
if (nxagentOption(Composite))
{
int eventBase, errorBase;
#ifdef TEST
fprintf(stderr, "nxagentCompositeExtensionInit: Checking if the composite extension is supported.\n");
#endif
if (XCompositeQueryExtension(nxagentDisplay, &eventBase, &errorBase) == 1)
{
/*
* At the moment we don't need to care the version of the
* extension.
*/
#ifdef TEST
int major = -1;
int minor = -1;
XCompositeQueryVersion(nxagentDisplay, &major, &minor);
fprintf(stderr, "nxagentCompositeExtensionInit: The remote display supports version [%d] "
"minor [%d].\n", major, minor);
if (major < 0 || minor < 2)
{
#ifdef WARNING
fprintf(stderr, "nxagentCompositeExtensionInit: WARNING! Potentially incompatible version "
"[%d] minor [%d] detected.\n", major, minor);
#endif
}
#endif
#ifdef TEST
fprintf(stderr, "nxagentCompositeExtensionInit: Enabling the use of the composite extension.\n");
#endif
nxagentCompositeEnable = True;
}
#ifdef TEST
else
{
fprintf(stderr, "nxagentCompositeExtensionInit: Composite extension not supported on this display.\n");
}
#endif
}
#ifdef TEST
else
{
fprintf(stderr, "nxagentCompositeExtensionInit: Use of the composite extension not enabled.\n");
}
#endif
}
void nxagentRedirectDefaultWindows(void)
{
if (nxagentOption(Rootless) || !nxagentCompositeEnable)
{
#ifdef TEST
fprintf(stderr, "nxagentRedirectDefaultWindows: Not redirecting default "
"windows with rootless mode [%d] and composite [%d].\n",
nxagentOption(Rootless), nxagentCompositeEnable);
#endif
return;
}
for (int i = 0; i < screenInfo.numScreens; i++)
{
WindowPtr pWin = screenInfo.screens[i]->root;
ScreenPtr pScreen = pWin -> drawable.pScreen;
#ifdef TEST
fprintf(stderr, "nxagentRedirectDefaultWindows: WARNING! Redirecting default window id [%ld] "
"to off-screen memory.\n", (long int)nxagentDefaultWindows[pScreen->myNum]);
#endif
/*
* When trying to redirect only the top level window, and not the
* subwindows, we incur in a strange behaviour. The top level is
* unmapped, mapped, unmapped and then reparented. This at first
* makes the agent think that the window manager is gone, then the
* agent window disappears. To make things even more weird, this
* happens only at reconnection.
*/
XCompositeRedirectSubwindows(nxagentDisplay, nxagentDefaultWindows[pScreen->myNum],
CompositeRedirectAutomatic);
}
}
void nxagentRedirectWindow(WindowPtr pWin)
{
if (!nxagentOption(Rootless) || !nxagentCompositeEnable)
{
#ifdef TEST
fprintf(stderr, "nxagentRedirectWindow: Not redirecting window id [%ld] "
"to off-screen memory with rootless mode [%d] and composite [%d].\n",
nxagentWindow(pWin), nxagentOption(Rootless),
nxagentCompositeEnable);
#endif
return;
}
#ifdef TEST
fprintf(stderr, "nxagentRedirectWindow: WARNING! Redirecting window id [%ld] "
"to off-screen memory.\n", (long int)nxagentWindow(pWin));
#endif
XCompositeRedirectWindow(nxagentDisplay, nxagentWindow(pWin),
CompositeRedirectAutomatic);
nxagentWindowPriv(pWin) -> isRedirected = 1;
}
void nxagentUnredirectWindow(WindowPtr pWin)
{
if (nxagentWindowPriv(pWin) -> isRedirected == 1)
{
#ifdef TEST
fprintf(stderr, "nxagentUnredirectWindow: Disabling redirection of window id [%ld] "
"to off-screen memory.\n", nxagentWindow(pWin));
#endif
XCompositeUnredirectWindow(nxagentDisplay, nxagentWindow(pWin),
CompositeRedirectAutomatic);
nxagentWindowPriv(pWin) -> isRedirected = 0;
}
#ifdef WARNING
else
{
fprintf(stderr, "nxagentUnredirectWindow: WARNING! The window id [%ld] "
"was not redirected.\n", (long int)nxagentWindow(pWin));
}
#endif
}