summaryrefslogtreecommitdiffstats
path: root/x11vnc/win_utils.c
diff options
context:
space:
mode:
Diffstat (limited to 'x11vnc/win_utils.c')
-rw-r--r--x11vnc/win_utils.c771
1 files changed, 0 insertions, 771 deletions
diff --git a/x11vnc/win_utils.c b/x11vnc/win_utils.c
deleted file mode 100644
index 7aa9b4c..0000000
--- a/x11vnc/win_utils.c
+++ /dev/null
@@ -1,771 +0,0 @@
-/*
- Copyright (C) 2002-2010 Karl J. Runge <runge@karlrunge.com>
- All rights reserved.
-
-This file is part of x11vnc.
-
-x11vnc is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or (at
-your option) any later version.
-
-x11vnc is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with x11vnc; if not, write to the Free Software
-Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA
-or see <http://www.gnu.org/licenses/>.
-
-In addition, as a special exception, Karl J. Runge
-gives permission to link the code of its release of x11vnc with the
-OpenSSL project's "OpenSSL" library (or with modified versions of it
-that use the same license as the "OpenSSL" library), and distribute
-the linked executables. You must obey the GNU General Public License
-in all respects for all of the code used other than "OpenSSL". If you
-modify this file, you may extend this exception to your version of the
-file, but you are not obligated to do so. If you do not wish to do
-so, delete this exception statement from your version.
-*/
-
-/* -- win_utils.c -- */
-
-#include "x11vnc.h"
-#include "xinerama.h"
-#include "winattr_t.h"
-#include "cleanup.h"
-#include "xwrappers.h"
-#include "connections.h"
-#include "xrandr.h"
-#include "macosx.h"
-
-winattr_t *stack_list = NULL;
-int stack_list_len = 0;
-int stack_list_num = 0;
-
-
-Window parent_window(Window win, char **name);
-int valid_window(Window win, XWindowAttributes *attr_ret, int bequiet);
-Bool xtranslate(Window src, Window dst, int src_x, int src_y, int *dst_x,
- int *dst_y, Window *child, int bequiet);
-int get_window_size(Window win, int *w, int *h);
-void snapshot_stack_list(int free_only, double allowed_age);
-int get_boff(void);
-int get_bwin(void);
-void update_stack_list(void);
-Window query_pointer(Window start);
-unsigned int mask_state(void);
-int pick_windowid(unsigned long *num);
-Window descend_pointer(int depth, Window start, char *name_info, int len);
-void id_cmd(char *cmd);
-
-
-Window parent_window(Window win, char **name) {
-#if !NO_X11
- Window r, parent;
- Window *list;
- XErrorHandler old_handler;
- unsigned int nchild;
- int rc;
-#endif
-
- if (name != NULL) {
- *name = NULL;
- }
- RAWFB_RET(None)
-#if NO_X11
- nox11_exit(1);
- if (!name || !win) {}
- return None;
-#else
-
- old_handler = XSetErrorHandler(trap_xerror);
- trapped_xerror = 0;
- rc = XQueryTree_wr(dpy, win, &r, &parent, &list, &nchild);
- XSetErrorHandler(old_handler);
-
- if (! rc || trapped_xerror) {
- trapped_xerror = 0;
- return None;
- }
- trapped_xerror = 0;
-
- if (list) {
- XFree_wr(list);
- }
- if (parent && name) {
- XFetchName(dpy, parent, name);
- }
- return parent;
-#endif /* NO_X11 */
-}
-
-/* trapping utility to check for a valid window: */
-int valid_window(Window win, XWindowAttributes *attr_ret, int bequiet) {
- XWindowAttributes attr, *pattr;
-#if !NO_X11
- XErrorHandler old_handler;
- int ok = 0;
-#endif
-
- if (attr_ret == NULL) {
- pattr = &attr;
- } else {
- pattr = attr_ret;
- }
-
- if (win == None) {
- return 0;
- }
-
-#ifdef MACOSX
- if (macosx_console) {
- return macosx_valid_window(win, attr_ret);
- }
-#endif
-
- RAWFB_RET(0)
-
-#if NO_X11
- nox11_exit(1);
- if (!win || !attr_ret || !bequiet) {}
- return 0;
-#else
-
- old_handler = XSetErrorHandler(trap_xerror);
- trapped_xerror = 0;
- if (XGetWindowAttributes(dpy, win, pattr)) {
- ok = 1;
- }
- if (trapped_xerror && trapped_xerror_event) {
- if (! quiet && ! bequiet) {
- rfbLog("valid_window: trapped XError: %s (0x%lx)\n",
- xerror_string(trapped_xerror_event), win);
- }
- ok = 0;
- }
- XSetErrorHandler(old_handler);
- trapped_xerror = 0;
-
- return ok;
-#endif /* NO_X11 */
-}
-
-Bool xtranslate(Window src, Window dst, int src_x, int src_y, int *dst_x,
- int *dst_y, Window *child, int bequiet) {
- XErrorHandler old_handler = NULL;
- Bool ok = False;
-
- RAWFB_RET(False)
-#if NO_X11
- nox11_exit(1);
- if (!src || !dst || !src_x || !src_y || !dst_x || !dst_y || !child || !bequiet) {}
- if (!old_handler || !ok) {}
- return False;
-#else
-
- trapped_xerror = 0;
- old_handler = XSetErrorHandler(trap_xerror);
- if (XTranslateCoordinates(dpy, src, dst, src_x, src_y, dst_x,
- dst_y, child)) {
- ok = True;
- }
- if (trapped_xerror && trapped_xerror_event) {
- if (! quiet && ! bequiet) {
- rfbLog("xtranslate: trapped XError: %s (0x%lx)\n",
- xerror_string(trapped_xerror_event), src);
- }
- ok = False;
- }
- XSetErrorHandler(old_handler);
- trapped_xerror = 0;
-
- return ok;
-#endif /* NO_X11 */
-}
-
-int get_window_size(Window win, int *w, int *h) {
- XWindowAttributes attr;
- /* valid_window? */
- if (valid_window(win, &attr, 1)) {
- *w = attr.width;
- *h = attr.height;
- return 1;
- } else {
- return 0;
- }
-}
-
-/*
- * For use in the -wireframe stuff, save the stacking order of the direct
- * children of the root window. Ideally done before we send ButtonPress
- * to the X server.
- */
-void snapshot_stack_list(int free_only, double allowed_age) {
- static double last_snap = 0.0, last_free = 0.0;
- double now;
- int num, rc, i, j;
- unsigned int ui;
- Window r, w;
- Window *list;
-
- if (! stack_list) {
- stack_list = (winattr_t *) malloc(256*sizeof(winattr_t));
- stack_list_num = 0;
- stack_list_len = 256;
- }
-
- dtime0(&now);
- if (free_only) {
- /* we really don't free it, just reset to zero windows */
- stack_list_num = 0;
- last_free = now;
- return;
- }
-
- if (stack_list_num && now < last_snap + allowed_age) {
- return;
- }
-
- stack_list_num = 0;
- last_free = now;
-
-#ifdef MACOSX
- if (! macosx_console) {
- RAWFB_RET_VOID
- }
-#else
- RAWFB_RET_VOID
-#endif
-
-#if NO_X11 && !defined(MACOSX)
- num = rc = i = j = 0; /* compiler warnings */
- ui = 0;
- r = w = None;
- list = NULL;
- return;
-#else
-
- X_LOCK;
- /* no need to trap error since rootwin */
- rc = XQueryTree_wr(dpy, rootwin, &r, &w, &list, &ui);
- num = (int) ui;
-
- if (! rc) {
- stack_list_num = 0;
- last_free = now;
- last_snap = 0.0;
- X_UNLOCK;
- return;
- }
-
- last_snap = now;
- if (num > stack_list_len + blackouts) {
- int n = 2*num;
- free(stack_list);
- stack_list = (winattr_t *) malloc(n*sizeof(winattr_t));
- stack_list_len = n;
- }
- j = 0;
- for (i=0; i<num; i++) {
- stack_list[j].win = list[i];
- stack_list[j].fetched = 0;
- stack_list[j].valid = 0;
- stack_list[j].time = now;
- j++;
- }
- for (i=0; i<blackouts; i++) {
- stack_list[j].win = get_boff() + 1;
- stack_list[j].fetched = 1;
- stack_list[j].valid = 1;
- stack_list[j].x = blackr[i].x1;
- stack_list[j].y = blackr[i].y1;
- stack_list[j].width = blackr[i].x2 - blackr[i].x1;
- stack_list[j].height = blackr[i].y2 - blackr[i].y1;
- stack_list[j].time = now;
- stack_list[j].map_state = IsViewable;
- stack_list[j].rx = -1;
- stack_list[j].ry = -1;
- j++;
-
-if (0) fprintf(stderr, "blackr: %d %dx%d+%d+%d\n", i,
- stack_list[j-1].width, stack_list[j-1].height,
- stack_list[j-1].x, stack_list[j-1].y);
-
- }
- stack_list_num = num + blackouts;
- if (debug_wireframe > 1) {
- fprintf(stderr, "snapshot_stack_list: num=%d len=%d\n",
- stack_list_num, stack_list_len);
- }
-
- XFree_wr(list);
- X_UNLOCK;
-#endif /* NO_X11 */
-}
-
-int get_boff(void) {
- if (macosx_console) {
- return 0x1000000;
- } else {
- return 0;
- }
-}
-
-int get_bwin(void) {
- return 10;
-}
-
-void update_stack_list(void) {
- int k;
- double now;
- XWindowAttributes attr;
- int boff, bwin;
-
- if (! stack_list) {
- return;
- }
- if (! stack_list_num) {
- return;
- }
-
- dtime0(&now);
-
- boff = get_boff();
- bwin = get_bwin();
-
- X_LOCK;
- for (k=0; k < stack_list_num; k++) {
- Window win = stack_list[k].win;
- if (win != None && boff <= (int) win && (int) win < boff + bwin) {
- ; /* special, blackout */
- } else if (!valid_window(win, &attr, 1)) {
- stack_list[k].valid = 0;
- } else {
- stack_list[k].valid = 1;
- stack_list[k].x = attr.x;
- stack_list[k].y = attr.y;
- stack_list[k].width = attr.width;
- stack_list[k].height = attr.height;
- stack_list[k].border_width = attr.border_width;
- stack_list[k].depth = attr.depth;
- stack_list[k].class = attr.class;
- stack_list[k].backing_store = attr.backing_store;
- stack_list[k].map_state = attr.map_state;
-
- /* root_x, root_y not used for stack_list usage: */
- stack_list[k].rx = -1;
- stack_list[k].ry = -1;
- }
- stack_list[k].fetched = 1;
- stack_list[k].time = now;
- }
- X_UNLOCK;
-if (0) fprintf(stderr, "update_stack_list[%d]: %.4f %.4f\n", stack_list_num, now - x11vnc_start, dtime(&now));
-}
-
-Window query_pointer(Window start) {
- int rx, ry;
-#if !NO_X11
- Window r, c; /* compiler warnings */
- int wx, wy;
- unsigned int mask;
-#endif
-
-#ifdef MACOSX
- if (macosx_console) {
- macosx_get_cursor_pos(&rx, &ry);
- }
-#endif
-
- RAWFB_RET(None)
-
-#if NO_X11
- if (!start) { rx = ry = 0; }
- return None;
-#else
- if (start == None) {
- start = rootwin;
- }
- if (XQueryPointer_wr(dpy, start, &r, &c, &rx, &ry, &wx, &wy, &mask)) {
- return c;
- } else {
- return None;
- }
-#endif /* NO_X11 */
-}
-
-unsigned int mask_state(void) {
-#if NO_X11
- RAWFB_RET(0)
- return 0;
-#else
- Window r, c;
- int rx, ry, wx, wy;
- unsigned int mask;
-
- RAWFB_RET(0)
-
- if (XQueryPointer_wr(dpy, rootwin, &r, &c, &rx, &ry, &wx, &wy, &mask)) {
- return mask;
- } else {
- return 0;
- }
-#endif /* NO_X11 */
-}
-
-int pick_windowid(unsigned long *num) {
- char line[512];
- int ok = 0, n = 0, msec = 10, secmax = 15;
- FILE *p;
-
- RAWFB_RET(0)
-
- if (use_dpy) {
- set_env("DISPLAY", use_dpy);
- }
- /* id */
- if (no_external_cmds || !cmd_ok("id")) {
- rfbLogEnable(1);
- rfbLog("cannot run external commands in -nocmds mode:\n");
- rfbLog(" \"%s\"\n", "xwininfo");
- rfbLog(" exiting.\n");
- clean_up_exit(1);
- }
- close_exec_fds();
- p = popen("xwininfo", "r");
-
- if (! p) {
- return 0;
- }
-
- fprintf(stderr, "\n");
- fprintf(stderr, " Please select the window for x11vnc to poll\n");
- fprintf(stderr, " by clicking the mouse in that window.\n");
- fprintf(stderr, "\n");
-
- while (msec * n++ < 1000 * secmax) {
- unsigned long tmp;
- char *q;
- fd_set set;
- struct timeval tv;
-
- if (screen && screen->clientHead) {
- /* they may be doing the pointer-pick thru vnc: */
- int nfds;
- tv.tv_sec = 0;
- tv.tv_usec = msec * 1000;
- FD_ZERO(&set);
- FD_SET(fileno(p), &set);
-
- nfds = select(fileno(p)+1, &set, NULL, NULL, &tv);
-
- if (nfds == 0 || nfds < 0) {
- /*
- * select timedout or error.
- * note this rfbPE takes about 30ms too:
- */
- rfbPE(-1);
- XFlush_wr(dpy);
- continue;
- }
- }
-
- if (fgets(line, 512, p) == NULL) {
- break;
- }
- q = strstr(line, " id: 0x");
- if (q) {
- q += 5;
- if (sscanf(q, "0x%lx ", &tmp) == 1) {
- ok = 1;
- *num = tmp;
- fprintf(stderr, " Picked: 0x%lx\n\n", tmp);
- break;
- }
- }
- }
- pclose(p);
- return ok;
-}
-
-Window descend_pointer(int depth, Window start, char *name_info, int len) {
-#if NO_X11
- RAWFB_RET(None)
- if (!depth || !start || !name_info || !len) {}
- return None;
-#else
- Window r, c, clast = None;
- int i, rx, ry, wx, wy;
- int written = 0, filled = 0;
- char *store = NULL;
- unsigned int m;
- static XClassHint *classhint = NULL;
- static char *nm_cache = NULL;
- static int nm_cache_len = 0;
- static Window prev_start = None;
-
- RAWFB_RET(None)
-
- if (! classhint) {
- classhint = XAllocClassHint();
- }
-
- if (! nm_cache) {
- nm_cache = (char *) malloc(1024);
- nm_cache_len = 1024;
- nm_cache[0] = '\0';
- }
- if (name_info && nm_cache_len < len) {
- if (nm_cache) {
- free(nm_cache);
- }
- nm_cache_len = 2*len;
- nm_cache = (char *) malloc(nm_cache_len);
- }
-
- if (name_info) {
- if (start != None && start == prev_start) {
- store = NULL;
- strncpy(name_info, nm_cache, len);
- } else {
- store = name_info;
- name_info[0] = '\0';
- }
- }
-
- if (start != None) {
- c = start;
- if (name_info) {
- prev_start = start;
- }
- } else {
- c = rootwin;
- }
-
- for (i=0; i<depth; i++) {
- clast = c;
- if (store && ! filled) {
- char *name;
- if (XFetchName(dpy, clast, &name) && name != NULL) {
- int l = strlen(name);
- if (written + l+2 < len) {
- strcat(store, "^^");
- written += 2;
- strcat(store, name);
- written += l;
- } else {
- filled = 1;
- }
- XFree_wr(name);
- }
- }
- if (store && classhint && ! filled) {
- classhint->res_name = NULL;
- classhint->res_class = NULL;
- if (XGetClassHint(dpy, clast, classhint)) {
- int l = 0;
- if (classhint->res_class) {
- l += strlen(classhint->res_class);
- }
- if (classhint->res_name) {
- l += strlen(classhint->res_name);
- }
- if (written + l+4 < len) {
- strcat(store, "##");
- if (classhint->res_class) {
- strcat(store,
- classhint->res_class);
- }
- strcat(store, "++");
- if (classhint->res_name) {
- strcat(store,
- classhint->res_name);
- }
- written += l+4;
- } else {
- filled = 1;
- }
- if (classhint->res_class) {
- XFree_wr(classhint->res_class);
- }
- if (classhint->res_name) {
- XFree_wr(classhint->res_name);
- }
- }
- }
- if (! XQueryPointer_wr(dpy, c, &r, &c, &rx, &ry, &wx, &wy, &m)) {
- break;
- }
- if (! c) {
- break;
- }
- }
- if (start != None && name_info) {
- strncpy(nm_cache, name_info, nm_cache_len);
- }
-
- return clast;
-#endif /* NO_X11 */
-}
-
-void id_cmd(char *cmd) {
- int rc, dx = 0, dy = 0, dw = 0, dh = 0;
- int x0, y0, w0, h0;
- int x, y, w, h, do_move = 0, do_resize = 0;
- int disp_x = DisplayWidth(dpy, scr);
- int disp_y = DisplayHeight(dpy, scr);
- Window win = subwin;
- XWindowAttributes attr;
- XErrorHandler old_handler = NULL;
- Window twin;
-
- if (!cmd || !strcmp(cmd, "")) {
- return;
- }
- if (strstr(cmd, "win=") == cmd) {
- if (! scan_hexdec(cmd + strlen("win="), &win)) {
- rfbLog("id_cmd: incorrect win= hex/dec number: %s\n", cmd);
- return;
- } else {
- char *q = strchr(cmd, ':');
- if (!q) {
- rfbLog("id_cmd: incorrect win=...: hex/dec number: %s\n", cmd);
- return;
- }
- rfbLog("id_cmd:%s set window id to 0x%lx\n", cmd, win);
- cmd = q+1;
- }
- }
- if (!win) {
- rfbLog("id_cmd:%s not in sub-window mode or no win=0xNNNN.\n", cmd);
- return;
- }
-#if !NO_X11
- X_LOCK;
- if (!valid_window(win, &attr, 1)) {
- X_UNLOCK;
- return;
- }
- w0 = w = attr.width;
- h0 = h = attr.height;
- old_handler = XSetErrorHandler(trap_xerror);
- trapped_xerror = 0;
- XTranslateCoordinates(dpy, win, rootwin, 0, 0, &x, &y, &twin);
- x0 = x;
- y0 = y;
- if (strstr(cmd, "move:") == cmd) {
- if (sscanf(cmd, "move:%d%d", &dx, &dy) == 2) {
- x = x + dx;
- y = y + dy;
- do_move = 1;
- }
- } else if (strstr(cmd, "resize:") == cmd) {
- if (sscanf(cmd, "resize:%d%d", &dw, &dh) == 2) {
- w = w + dw;
- h = h + dh;
- do_move = 1;
- do_resize = 1;
- }
- } else if (strstr(cmd, "geom:") == cmd) {
- if (parse_geom(cmd+strlen("geom:"), &w, &h, &x, &y, disp_x, disp_y)) {
- do_move = 1;
- do_resize = 1;
- if (w <= 0) {
- w = w0;
- }
- if (h <= 0) {
- h = h0;
- }
- if (scaling && getenv("X11VNC_APPSHARE_ACTIVE")) {
- x /= scale_fac_x;
- y /= scale_fac_y;
- }
- }
- } else if (!strcmp(cmd, "raise")) {
- rc = XRaiseWindow(dpy, win);
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (!strcmp(cmd, "lower")) {
- rc = XLowerWindow(dpy, win);
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (!strcmp(cmd, "map")) {
- rc= XMapRaised(dpy, win);
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (!strcmp(cmd, "unmap")) {
- rc= XUnmapWindow(dpy, win);
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (!strcmp(cmd, "iconify")) {
- rc= XIconifyWindow(dpy, win, scr);
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (strstr(cmd, "wm_name:") == cmd) {
- rc= XStoreName(dpy, win, cmd+strlen("wm_name:"));
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (strstr(cmd, "icon_name:") == cmd) {
- rc= XSetIconName(dpy, win, cmd+strlen("icon_name:"));
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else if (!strcmp(cmd, "wm_delete")) {
- XClientMessageEvent ev;
- memset(&ev, 0, sizeof(ev));
- ev.type = ClientMessage;
- ev.send_event = True;
- ev.display = dpy;
- ev.window = win;
- ev.message_type = XInternAtom(dpy, "WM_PROTOCOLS", False);
- ev.format = 32;
- ev.data.l[0] = XInternAtom(dpy, "WM_DELETE_WINDOW", False);
- rc = XSendEvent(dpy, win, False, 0, (XEvent *) &ev);
- rfbLog("id_cmd:%s rc=%d\n", cmd, rc);
- } else {
- rfbLog("id_cmd:%s unrecognized command.\n", cmd);
- }
- if (do_move || do_resize) {
- if (w >= disp_x) {
- w = disp_x - 4;
- }
- if (h >= disp_y) {
- h = disp_y - 4;
- }
- if (w < 1) {
- w = 1;
- }
- if (h < 1) {
- h = 1;
- }
- if (x + w > disp_x) {
- x = disp_x - w - 1;
- }
- if (y + h > disp_y) {
- y = disp_y - h - 1;
- }
- if (x < 0) {
- x = 1;
- }
- if (y < 0) {
- y = 1;
- }
- rc = 0;
- rc += XMoveWindow(dpy, win, x, y);
- off_x = x;
- off_y = y;
-
- rc += XResizeWindow(dpy, win, w, h);
-
- rfbLog("id_cmd:%s rc=%d dx=%d dy=%d dw=%d dh=%d %dx%d+%d+%d -> %dx%d+%d+%d\n",
- cmd, rc, dx, dy, dw, dh, w0, h0, x0, y0, w, h, x, h);
- }
- XSync(dpy, False);
- XSetErrorHandler(old_handler);
- if (trapped_xerror) {
- rfbLog("id_cmd:%s trapped_xerror.\n", cmd);
- }
- trapped_xerror = 0;
- if (do_resize) {
- rfbLog("id_cmd:%s calling check_xrandr_event.\n", cmd);
- check_xrandr_event("id_cmd");
- }
- X_UNLOCK;
-#endif
-}
-
OpenPOWER on IntegriCloud