VirtualBox

source: vbox/trunk/src/VBox/Additions/x11/VBoxClient/seamless-x11.h@ 78750

Last change on this file since 78750 was 76563, checked in by vboxsync, 6 years ago

Additions: Use GA_INCLUDED_ and variations_ as header guard prefixes with scm.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id Revision
File size: 8.3 KB
Line 
1/* $Id: seamless-x11.h 76563 2019-01-01 03:53:56Z vboxsync $ */
2/** @file
3 *
4 * Seamless mode:
5 * Linux guest.
6 */
7
8/*
9 * Copyright (C) 2006-2019 Oracle Corporation
10 *
11 * This file is part of VirtualBox Open Source Edition (OSE), as
12 * available from http://www.virtualbox.org. This file is free software;
13 * you can redistribute it and/or modify it under the terms of the GNU
14 * General Public License (GPL) as published by the Free Software
15 * Foundation, in version 2 as it comes in the "COPYING" file of the
16 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
17 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
18 */
19
20#ifndef GA_INCLUDED_SRC_x11_VBoxClient_seamless_x11_h
21#define GA_INCLUDED_SRC_x11_VBoxClient_seamless_x11_h
22#ifndef RT_WITHOUT_PRAGMA_ONCE
23# pragma once
24#endif
25
26#include <VBox/log.h>
27#include <iprt/avl.h>
28
29#include <X11/Xlib.h>
30#include <X11/Xutil.h>
31#include <X11/extensions/shape.h>
32
33#define WM_TYPE_PROP "_NET_WM_WINDOW_TYPE"
34#define WM_TYPE_DESKTOP_PROP "_NET_WM_WINDOW_TYPE_DESKTOP"
35
36/* This is defined wrong in my X11 header files! */
37#define VBoxShapeNotify 64
38
39/**
40 * Callback which provides the interface for notifying the host of changes to
41 * the X11 window configuration, mainly split out from @a VBoxGuestSeamlessHost
42 * to simplify the unit test.
43 */
44typedef void FNSENDREGIONUPDATE(RTRECT *pRects, size_t cRects);
45typedef FNSENDREGIONUPDATE *PFNSENDREGIONUPDATE;
46
47/** Structure containing information about a guest window's position and visible area.
48 Used inside of VBoxGuestWindowList. */
49struct VBoxGuestWinInfo {
50public:
51 /** Header structure for insertion into an AVL tree */
52 AVLU32NODECORE Core;
53 /** Is the window currently mapped? */
54 bool mhasShape;
55 /** Co-ordinates in the guest screen. */
56 int mX, mY;
57 /** Window dimensions. */
58 int mWidth, mHeight;
59 /** Number of rectangles used to represent the visible area. */
60 int mcRects;
61 /** Rectangles representing the visible area. These must be allocated
62 * by XMalloc and will be freed automatically if non-null when the class
63 * is destroyed. */
64 XRectangle *mpRects;
65 /** Constructor. */
66 VBoxGuestWinInfo(bool hasShape, int x, int y, int w, int h, int cRects,
67 XRectangle *pRects)
68 : mhasShape(hasShape), mX(x), mY(y), mWidth(w), mHeight(h),
69 mcRects(cRects), mpRects(pRects) {}
70
71 /** Destructor */
72 ~VBoxGuestWinInfo()
73 {
74 if (mpRects)
75 XFree(mpRects);
76 }
77
78private:
79 // We don't want a copy constructor or assignment operator
80 VBoxGuestWinInfo(const VBoxGuestWinInfo&);
81 VBoxGuestWinInfo& operator=(const VBoxGuestWinInfo&);
82};
83
84/** Callback type used for "DoWithAll" calls */
85typedef DECLCALLBACK(int) VBOXGUESTWINCALLBACK(VBoxGuestWinInfo *, void *);
86/** Pointer to VBOXGUESTWINCALLBACK */
87typedef VBOXGUESTWINCALLBACK *PVBOXGUESTWINCALLBACK;
88
89DECLCALLBACK(int) inline VBoxGuestWinCleanup(VBoxGuestWinInfo *pInfo, void *)
90{
91 delete pInfo;
92 return VINF_SUCCESS;
93}
94
95/**
96 * This class is just a wrapper around a map of structures containing
97 * information about the windows on the guest system. It has a function for
98 * adding a structure (see addWindow) and one for removing it by window
99 * handle (see removeWindow).
100 */
101class VBoxGuestWindowList
102{
103private:
104 // We don't want a copy constructor or an assignment operator
105 VBoxGuestWindowList(const VBoxGuestWindowList&);
106 VBoxGuestWindowList& operator=(const VBoxGuestWindowList&);
107
108 // Private class members
109 AVLU32TREE mWindows;
110
111public:
112 // Constructor
113 VBoxGuestWindowList(void) : mWindows(NULL) {}
114 // Destructor
115 ~VBoxGuestWindowList()
116 {
117 /** @todo having this inside the container class hard codes that the
118 * elements have to be allocated with the "new" operator, and
119 * I don't see a need to require this. */
120 doWithAll(VBoxGuestWinCleanup, NULL);
121 }
122
123 // Standard operations
124 VBoxGuestWinInfo *find(Window hWin)
125 {
126 return (VBoxGuestWinInfo *)RTAvlU32Get(&mWindows, hWin);
127 }
128
129 void detachAll(PVBOXGUESTWINCALLBACK pCallback, void *pvParam)
130 {
131 RTAvlU32Destroy(&mWindows, (PAVLU32CALLBACK)pCallback, pvParam);
132 }
133
134 int doWithAll(PVBOXGUESTWINCALLBACK pCallback, void *pvParam)
135 {
136 return RTAvlU32DoWithAll(&mWindows, 1, (PAVLU32CALLBACK)pCallback,
137 pvParam);
138 }
139
140 bool addWindow(Window hWin, bool isMapped, int x, int y, int w, int h, int cRects,
141 XRectangle *pRects)
142 {
143 LogRelFlowFunc(("hWin=%lu, isMapped=%RTbool, x=%d, y=%d, w=%d, h=%d, cRects=%d\n",
144 (unsigned long) hWin, isMapped, x, y, w, h, cRects));
145 VBoxGuestWinInfo *pInfo = new VBoxGuestWinInfo(isMapped, x, y, w, h, cRects,
146 pRects);
147 pInfo->Core.Key = hWin;
148 LogRelFlowFunc(("returning\n"));
149 return RTAvlU32Insert(&mWindows, &pInfo->Core);
150 }
151
152 VBoxGuestWinInfo *removeWindow(Window hWin)
153 {
154 LogRelFlowFunc(("called\n"));
155 return (VBoxGuestWinInfo *)RTAvlU32Remove(&mWindows, hWin);
156 }
157};
158
159class SeamlessX11
160{
161private:
162 // We don't want a copy constructor or assignment operator
163 SeamlessX11(const SeamlessX11&);
164 SeamlessX11& operator=(const SeamlessX11&);
165
166 // Private member variables
167 /** Pointer to the host callback. */
168 PFNSENDREGIONUPDATE mHostCallback;
169 /** Our connection to the X11 display we are running on. */
170 Display *mDisplay;
171 /** Class to keep track of visible guest windows. */
172 VBoxGuestWindowList mGuestWindows;
173 /** The current set of seamless rectangles. */
174 RTRECT *mpRects;
175 /** The current number of seamless rectangles. */
176 int mcRects;
177 /** Do we support the X shaped window extension? */
178 bool mSupportsShape;
179 /** Is seamless mode currently enabled? */
180 bool mEnabled;
181 /** Have there been changes since the last time we sent a notification? */
182 bool mChanged;
183
184 // Private methods
185
186 // Methods to manage guest window information
187 /**
188 * Store information about a desktop window and register for structure events on it.
189 * If it is mapped, go through the list of it's children and add information about
190 * mapped children to the tree of visible windows, making sure that those windows are
191 * not already in our list of desktop windows.
192 *
193 * @param hWin the window concerned - should be a "desktop" window
194 */
195 void monitorClientList(void);
196 void unmonitorClientList(void);
197 void rebuildWindowTree(void);
198 void addClients(const Window hRoot);
199 bool isVirtualRoot(Window hWin);
200 void addClientWindow(Window hWin);
201 void freeWindowTree(void);
202 void updateHostSeamlessInfo(void);
203 int updateRects(void);
204
205public:
206 /**
207 * Initialise the guest and ensure that it is capable of handling seamless mode
208 * @param pHostCallback Host interface callback to notify of window configuration
209 * changes.
210 *
211 * @returns iprt status code
212 */
213 int init(PFNSENDREGIONUPDATE pHostCallback);
214
215 /**
216 * Shutdown seamless event monitoring.
217 */
218 void uninit(void)
219 {
220 if (mHostCallback)
221 stop();
222 mHostCallback = NULL;
223 if (mDisplay)
224 XCloseDisplay(mDisplay);
225 mDisplay = NULL;
226 }
227
228 /**
229 * Initialise seamless event reporting in the guest.
230 *
231 * @returns IPRT status code
232 */
233 int start(void);
234 /** Stop reporting seamless events. */
235 void stop(void);
236 /** Get the current list of visible rectangles. */
237 RTRECT *getRects(void);
238 /** Get the number of visible rectangles in the current list */
239 size_t getRectCount(void);
240
241 /** Process next event in the guest event queue - called by the event thread. */
242 void nextConfigurationEvent(void);
243 /** Wake up the event thread if it is waiting for an event so that it can exit. */
244 bool interruptEventWait(void);
245
246 /* Methods to handle X11 events. These are public so that the unit test
247 * can call them. */
248 void doConfigureEvent(Window hWin);
249 void doShapeEvent(Window hWin);
250
251 SeamlessX11(void)
252 : mHostCallback(NULL), mDisplay(NULL), mpRects(NULL), mcRects(0),
253 mSupportsShape(false), mEnabled(false), mChanged(false) {}
254
255 ~SeamlessX11()
256 {
257 uninit();
258 }
259};
260
261#endif /* !GA_INCLUDED_SRC_x11_VBoxClient_seamless_x11_h */
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette