diff options
Diffstat (limited to 'x11vnc/xwrappers.c')
-rw-r--r-- | x11vnc/xwrappers.c | 1522 |
1 files changed, 0 insertions, 1522 deletions
diff --git a/x11vnc/xwrappers.c b/x11vnc/xwrappers.c deleted file mode 100644 index e7158cf..0000000 --- a/x11vnc/xwrappers.c +++ /dev/null @@ -1,1522 +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. -*/ - -/* -- xwrappers.c -- */ - -#include "x11vnc.h" -#include "xrecord.h" -#include "keyboard.h" -#include "xevents.h" -#include "connections.h" -#include "cleanup.h" -#include "macosx.h" - -int xshm_present = 0; -int xshm_opcode = 0; -int xtest_present = 0; -int xtrap_present = 0; -int xrecord_present = 0; -int xkb_present = 0; -int xinerama_present = 0; - -int keycode_state[256]; -int rootshift = 0; -int clipshift = 0; - - -int guess_bits_per_color(int bits_per_pixel); - -int XFlush_wr(Display *disp); - -Status XShmGetImage_wr(Display *disp, Drawable d, XImage *image, int x, int y, - unsigned long mask); -XImage *XShmCreateImage_wr(Display* disp, Visual* vis, unsigned int depth, - int format, char* data, XShmSegmentInfo* shminfo, unsigned int width, - unsigned int height); -Status XShmAttach_wr(Display *disp, XShmSegmentInfo *shminfo); -Status XShmDetach_wr(Display *disp, XShmSegmentInfo *shminfo); -Bool XShmQueryExtension_wr(Display *disp); -int XShmGetEventBase_wr(Display *disp); - -XImage *xreadscreen(Display *disp, Drawable d, int x, int y, - unsigned int width, unsigned int height, Bool show_cursor); -XImage *XGetSubImage_wr(Display *disp, Drawable d, int x, int y, - unsigned int width, unsigned int height, unsigned long plane_mask, - int format, XImage *dest_image, int dest_x, int dest_y); -XImage *XGetImage_wr(Display *disp, Drawable d, int x, int y, - unsigned int width, unsigned int height, unsigned long plane_mask, - int format); -XImage *XCreateImage_wr(Display *disp, Visual *visual, unsigned int depth, - int format, int offset, char *data, unsigned int width, - unsigned int height, int bitmap_pad, int bytes_per_line); -void copy_image(XImage *dest, int x, int y, unsigned int w, unsigned int h); -void init_track_keycode_state(void); - -void XTRAP_FakeKeyEvent_wr(Display* dpy, KeyCode key, Bool down, - unsigned long delay); -void XTestFakeKeyEvent_wr(Display* dpy, KeyCode key, Bool down, - unsigned long delay); -void XTRAP_FakeButtonEvent_wr(Display* dpy, unsigned int button, Bool is_press, - unsigned long delay); -void XTestFakeButtonEvent_wr(Display* dpy, unsigned int button, Bool is_press, - unsigned long delay); -void XTRAP_FakeMotionEvent_wr(Display* dpy, int screen, int x, int y, - unsigned long delay); -void XTestFakeMotionEvent_wr(Display* dpy, int screen, int x, int y, - unsigned long delay); - -Bool XTestCompareCurrentCursorWithWindow_wr(Display* dpy, Window w); -Bool XTestCompareCursorWithWindow_wr(Display* dpy, Window w, Cursor cursor); -Bool XTestQueryExtension_wr(Display *dpy, int *ev, int *er, int *maj, - int *min); -void XTestDiscard_wr(Display *dpy); -Bool XETrapQueryExtension_wr(Display *dpy, int *ev, int *er, int *op); -int XTestGrabControl_wr(Display *dpy, Bool impervious); -int XTRAP_GrabControl_wr(Display *dpy, Bool impervious); -void disable_grabserver(Display *in_dpy, int change); - -Bool XRecordQueryVersion_wr(Display *dpy, int *maj, int *min); - -int xauth_raw(int on); -Display *XOpenDisplay_wr(char *display_name); -int XCloseDisplay_wr(Display *display); - -Bool XQueryPointer_wr(Display *display, Window w, Window *root_return, - Window *child_return, int *root_x_return, int *root_y_return, - int *win_x_return, int *win_y_return, unsigned int *mask_return); - -Status XQueryTree_wr(Display *display, Window w, Window *root_return, - Window *parent_return, Window **children_return, - unsigned int *nchildren_return); - -int XFree_wr(void *data); -int XSelectInput_wr(Display *display, Window w, long event_mask); - -void copy_raw_fb(XImage *dest, int x, int y, unsigned int w, unsigned int h); -static void upup_downdown_warning(KeyCode key, Bool down); - -/* - * used in rfbGetScreen and rfbNewFramebuffer: and estimate to the number - * of bits per color, of course for some visuals, e.g. 565, the number - * is not the same for each color. This is just a sane default. - */ -int guess_bits_per_color(int bits_per_pixel) { - int bits_per_color; - - /* first guess, spread them "evenly" over R, G, and B */ - bits_per_color = bits_per_pixel/3; - if (bits_per_color < 1) { - bits_per_color = 1; /* 1bpp, 2bpp... */ - } - - /* choose safe values for usual cases: */ - if (bits_per_pixel == 8) { - bits_per_color = 2; - } else if (bits_per_pixel == 15 || bits_per_pixel == 16) { - bits_per_color = 5; - } else if (bits_per_pixel == 24 || bits_per_pixel == 32) { - bits_per_color = 8; - } - return bits_per_color; -} - -int XFlush_wr(Display *disp) { -#if NO_X11 - if (!disp) {} - return 1; -#else - if (disp) { - return XFlush(disp); - } else { - return 1; - } -#endif /* NO_X11 */ -} - -/* - * Kludge to interpose image gets and limit to a subset rectangle of - * the rootwin. This is the -sid option trying to work around invisible - * saveUnders menu, etc, windows. Also -clip option. - */ - -#define ADJUST_ROOTSHIFT \ - if (rootshift && subwin) { \ - d = rootwin; \ - x += off_x; \ - y += off_y; \ - } \ - if (clipshift) { \ - x += coff_x; \ - y += coff_y; \ - } - -/* - * Wrappers for Image related X calls - */ -Status XShmGetImage_wr(Display *disp, Drawable d, XImage *image, int x, int y, - unsigned long mask) { - - ADJUST_ROOTSHIFT - - /* Note: the Solaris overlay stuff is all non-shm (using_shm = 0) */ - -#if LIBVNCSERVER_HAVE_XSHM - return XShmGetImage(disp, d, image, x, y, mask); -#else - if (!disp || !d || !image || !x || !y || !mask) {} - return (Status) 0; -#endif -} - -XImage *XShmCreateImage_wr(Display* disp, Visual* vis, unsigned int depth, - int format, char* data, XShmSegmentInfo* shminfo, unsigned int width, - unsigned int height) { - -#if LIBVNCSERVER_HAVE_XSHM - return XShmCreateImage(disp, vis, depth, format, data, shminfo, - width, height); -#else - if (!disp || !vis || !depth || !format || !data || !shminfo || !width || !height) {} - return (XImage *) 0; -#endif -} - -Status XShmAttach_wr(Display *disp, XShmSegmentInfo *shminfo) { -#if LIBVNCSERVER_HAVE_XSHM - return XShmAttach(disp, shminfo); -#else - if (!disp || !shminfo) {} - return (Status) 0; -#endif -} - -Status XShmDetach_wr(Display *disp, XShmSegmentInfo *shminfo) { -#if LIBVNCSERVER_HAVE_XSHM - if (getenv("X11VNC_SHM_DEBUG")) fprintf(stderr, "XShmDetach_wr: %p disp: %p\n", (void *)shminfo, (void *)disp); - return XShmDetach(disp, shminfo); -#else - if (!disp || !shminfo) {} - return (Status) 0; -#endif -} - -Bool XShmQueryExtension_wr(Display *disp) { -#if LIBVNCSERVER_HAVE_XSHM - return XShmQueryExtension(disp); -#else - if (!disp) {} - return False; -#endif -} - -int XShmGetEventBase_wr(Display *disp) { -#if LIBVNCSERVER_HAVE_XSHM - return XShmGetEventBase(disp); -#else - if (!disp) {} - return 0; -#endif -} - -/* wrapper for overlay screen reading: */ - -XImage *xreadscreen(Display *disp, Drawable d, int x, int y, - unsigned int width, unsigned int height, Bool show_cursor) { -#if NO_X11 - if (!disp || !d || !x || !y || !width || !height || !show_cursor) {} - return NULL; -#else - -#ifdef SOLARIS_OVERLAY - return XReadScreen(disp, d, x, y, width, height, - show_cursor); -#else -# ifdef IRIX_OVERLAY - { unsigned long hints = 0, hints_ret; - if (show_cursor) hints |= XRD_READ_POINTER; - return XReadDisplay(disp, d, x, y, width, height, - hints, &hints_ret); - } -# else - /* unused vars warning: */ - if (disp || d || x || y || width || height || show_cursor) {} - - return NULL; -# endif -#endif - -#endif /* NO_X11 */ -} - -XImage *XGetSubImage_wr(Display *disp, Drawable d, int x, int y, - unsigned int width, unsigned int height, unsigned long plane_mask, - int format, XImage *dest_image, int dest_x, int dest_y) { -#if NO_X11 - nox11_exit(1); - if (!disp || !d || !x || !y || !width || !height || !plane_mask || !format || !dest_image || !dest_x || !dest_y) {} - return NULL; -#else - ADJUST_ROOTSHIFT - - if (overlay && dest_x == 0 && dest_y == 0) { - size_t size = dest_image->height * dest_image->bytes_per_line; - XImage *xi; - - xi = xreadscreen(disp, d, x, y, width, height, - (Bool) overlay_cursor); - - if (! xi) return NULL; - - /* - * There is extra overhead from memcpy and free... - * this is not like the real XGetSubImage(). We hope - * this significant overhead is still small compared to - * the time to retrieve the fb data. - */ - memcpy(dest_image->data, xi->data, size); - - XDestroyImage(xi); - return (dest_image); - } - return XGetSubImage(disp, d, x, y, width, height, plane_mask, - format, dest_image, dest_x, dest_y); -#endif /* NO_X11 */ -} - -XImage *XGetImage_wr(Display *disp, Drawable d, int x, int y, - unsigned int width, unsigned int height, unsigned long plane_mask, - int format) { -#if NO_X11 - if (!disp || !d || !x || !y || !width || !height || !plane_mask || !format) {} - nox11_exit(1); - return NULL; -#else - - ADJUST_ROOTSHIFT - - if (overlay) { - return xreadscreen(disp, d, x, y, width, height, - (Bool) overlay_cursor); - } - return XGetImage(disp, d, x, y, width, height, plane_mask, format); -#endif /* NO_X11 */ -} - -XImage *XCreateImage_wr(Display *disp, Visual *visual, unsigned int depth, - int format, int offset, char *data, unsigned int width, - unsigned int height, int bitmap_pad, int bytes_per_line) { - /* - * This is a kludge to get a created XImage to exactly match what - * XReadScreen returns: we noticed the rgb masks are different - * from XCreateImage with the high color visual (red mask <-> - * blue mask). Note we read from the root window(!) then free - * the data. - */ - - if (raw_fb) { /* raw_fb hack */ - XImage *xi; - xi = (XImage *) malloc(sizeof(XImage)); - memset(xi, 0, sizeof(XImage)); - xi->depth = depth; - if (depth >= 24) { - xi->bits_per_pixel = 32; - } else if (depth > 16) { - xi->bits_per_pixel = 24; - } else if (depth > 8) { - xi->bits_per_pixel = 16; - } else { - xi->bits_per_pixel = 8; - } - xi->format = format; - xi->xoffset = offset; - xi->data = data; - xi->width = width; - xi->height = height; - xi->bitmap_pad = bitmap_pad; - xi->bytes_per_line = bytes_per_line ? bytes_per_line : - xi->width * xi->bits_per_pixel / 8; - xi->bitmap_unit = -1; /* hint to not call XDestroyImage */ - return xi; - } - -#if NO_X11 - nox11_exit(1); - if (!disp || !visual || !depth || !format || !offset || !data || !width - || !height || !width || !bitmap_pad || !bytes_per_line) {} - return NULL; -#else - if (overlay) { - XImage *xi; - xi = xreadscreen(disp, window, 0, 0, width, height, False); - if (xi == NULL) { - return xi; - } - if (xi->data != NULL) { - free(xi->data); - } - xi->data = data; - return xi; - } - - return XCreateImage(disp, visual, depth, format, offset, data, - width, height, bitmap_pad, bytes_per_line); -#endif /* NO_X11 */ -} - -static void copy_raw_fb_low_bpp(XImage *dest, int x, int y, unsigned int w, - unsigned int h) { - char *src, *dst; - unsigned int line; - static char *buf = NULL; - static int buflen = -1; - int bpl = wdpy_x * raw_fb_native_bpp / 8; - int n, ix, len, del, sz = wdpy_x * raw_fb_expand_bytes; - - unsigned int rm_n = raw_fb_native_red_mask; - unsigned int gm_n = raw_fb_native_green_mask; - unsigned int bm_n = raw_fb_native_blue_mask; - unsigned int rm_f = main_red_mask; - unsigned int gm_f = main_green_mask; - unsigned int bm_f = main_blue_mask; - - unsigned int rs_n = raw_fb_native_red_shift; - unsigned int gs_n = raw_fb_native_green_shift; - unsigned int bs_n = raw_fb_native_blue_shift; - unsigned int rs_f = main_red_shift; - unsigned int gs_f = main_green_shift; - unsigned int bs_f = main_blue_shift; - - unsigned int rx_n = raw_fb_native_red_max; - unsigned int gx_n = raw_fb_native_green_max; - unsigned int bx_n = raw_fb_native_blue_max; - unsigned int rx_f = main_red_max; - unsigned int gx_f = main_green_max; - unsigned int bx_f = main_blue_max; - - static unsigned int msk[8]; - static int last_bpp = -1; - static int cga = -1; - - if (rm_f | gm_f | bm_f) {} - - if (cga < 0) { - if (getenv("RAWFB_CGA")) { - cga = 1; - } else { - cga = 0; - } - } - - if (sz > buflen || buf == NULL) { - if (buf) { - free(buf); - } - buflen = sz + 1000; - buf = (char *) malloc(buflen); - } - - if (clipshift && ! use_snapfb) { - x += coff_x; - y += coff_y; - } - - if (last_bpp != raw_fb_native_bpp) { - int br; - for (br = 0; br < 8; br++) { - unsigned int pbit, k, m = 0; - - for (k=0; k < (unsigned int) raw_fb_native_bpp; k++) { - pbit = 1 << (br+k); - m |= pbit; - } - msk[br] = m; - } - last_bpp = raw_fb_native_bpp; - } - - dst = dest->data; -if (0) fprintf(stderr, "x=%d y=%d w=%d h=%d bpl=%d d_bpl=%d-%dx%dx%d/%d %p\n", - x, y, w, h, bpl, dest->bytes_per_line, dest->width, dest->height, dest->bits_per_pixel, dest->depth, dst); - - for (line = 0; line < h; line++) { - - if (! raw_fb_seek) { - /* mmap */ - src = raw_fb_addr + raw_fb_offset + bpl*(y+line); - - memcpy(buf, src, bpl); - } else { - /* lseek */ - off_t off; - off = (off_t) (raw_fb_offset + bpl*(y+line)); - - lseek(raw_fb_fd, off, SEEK_SET); - - len = bpl; - del = 0; - while (len > 0) { - n = read(raw_fb_fd, buf + del, len); - - if (n > 0) { - del += n; - len -= n; - } else if (n == 0) { - break; - } else if (errno != EINTR && errno != EAGAIN) { - break; - } - } - } - for (ix = 0; ix < (int) w; ix++) { - int bx = (x + ix) * raw_fb_native_bpp; - int ib = bx / 8; - int br = bx - ib * 8; - unsigned char val; - - val = *((unsigned char*) (buf + ib)); - - val = msk[br] & val; - val = val >> br; - - if (cga) { - /* this is expt for CGA */ - double r, g, b; - int ir, ig, ib; - r = (2./3)*(val & 4) + (1./3)*(val & 8); - g = (2./3)*(val & 2) + (1./3)*(val & 8); - b = (2./3)*(val & 1) + (1./3)*(val & 8); - if (val == 6) { - g = g/2.; - } - ir = rx_f * r; - ig = gx_f * g; - ib = bx_f * b; - val = (ib << bs_f) | (ig << gs_f) | (ir << rs_f); - } else { - unsigned char rval, gval, bval; - - rval = (val & rm_n) >> rs_n; - gval = (val & gm_n) >> gs_n; - bval = (val & bm_n) >> bs_n; - - rval = (rx_f * rval) / rx_n; - gval = (gx_f * gval) / gx_n; - bval = (bx_f * bval) / bx_n; - - rval = rval << rs_f; - gval = gval << gs_f; - bval = bval << bs_f; - - val = rval | gval | bval; - } - - *(dst+ix) = (char) val; - } - - dst += dest->bytes_per_line; - } -} - -static void copy_raw_fb_24_to_32(XImage *dest, int x, int y, unsigned int w, - unsigned int h) { - /* - * kludge to read 1 byte at a time and dynamically transform - * 24bpp -> 32bpp by inserting a extra 0 byte into dst. - */ - char *src, *dst; - unsigned int line; - static char *buf = NULL; - static int buflen = -1; - int bpl = wdpy_x * 3; /* pixelsize == 3 */ - int LE, n, stp, len, del, sz = w * 3; - int insert_zeroes = 1; - -#define INSERT_ZEROES \ - len = sz; \ - del = 0; \ - stp = 0; \ - while (len > 0) { \ - if (insert_zeroes && (del - LE) % 4 == 0) { \ - *(dst + del) = 0; \ - del++; \ - } \ - *(dst + del) = *(buf + stp); \ - del++; \ - len--; \ - stp++; \ - } - - if (rfbEndianTest) { - LE = 3; /* little endian */ - } else { - LE = 0; /* big endian */ - } - - if (sz > buflen || buf == NULL) { - if (buf) { - free(buf); - } - buf = (char *) malloc(4*(sz + 1000)); - } - - if (clipshift && ! use_snapfb) { - x += coff_x; - y += coff_y; - } - - if (use_snapfb && dest != snap) { - /* snapfb src */ - src = snap->data + snap->bytes_per_line*y + 3*x; - dst = dest->data; - for (line = 0; line < h; line++) { - memcpy(buf, src, sz); - - INSERT_ZEROES - - src += snap->bytes_per_line; - dst += dest->bytes_per_line; - } - - } else if (! raw_fb_seek) { - /* mmap */ - bpl = raw_fb_bytes_per_line; - if (clipshift && wdpy_x != cdpy_x) { - bpl = wdpy_x * 3; - } - src = raw_fb_addr + raw_fb_offset + bpl*y + 3*x; - dst = dest->data; - - if (use_snapfb && dest == snap) { - /* - * writing *to* snap_fb: need the x,y offset, - * and also do not do inserts. - */ - dst += bpl*y + 3*x; - insert_zeroes = 0; - } - - for (line = 0; line < h; line++) { - memcpy(buf, src, sz); - - INSERT_ZEROES - - src += bpl; - dst += dest->bytes_per_line; - } - - } else { - /* lseek */ - off_t off; - bpl = raw_fb_bytes_per_line; - if (clipshift && wdpy_x != cdpy_x) { - bpl = wdpy_x * 3; - } - off = (off_t) (raw_fb_offset + bpl*y + 3*x); - - lseek(raw_fb_fd, off, SEEK_SET); - dst = dest->data; - - if (use_snapfb && dest == snap) { - /* - * writing *to* snap_fb: need the x,y offset, - * and also do not do inserts. - */ - dst += bpl*y + 3*x; - insert_zeroes = 0; - } - - for (line = 0; line < h; line++) { - len = sz; - del = 0; - while (len > 0) { - n = read(raw_fb_fd, buf + del, len); - - if (n > 0) { - del += n; - len -= n; - } else if (n == 0) { - break; - } else if (errno != EINTR && errno != EAGAIN) { - break; - } - } - - INSERT_ZEROES - - if (bpl > sz) { - off = (off_t) (bpl - sz); - lseek(raw_fb_fd, off, SEEK_CUR); - } - dst += dest->bytes_per_line; - } - } -} - -#ifdef MACOSX -void macosx_copy_opengl(char *, int, int, unsigned int, unsigned int); -#endif - -void copy_raw_fb(XImage *dest, int x, int y, unsigned int w, unsigned int h) { - char *src, *dst; - unsigned int line; - int pixelsize = bpp/8; - static int db = -1; - -#ifdef MACOSX - if (macosx_console && macosx_read_opengl) { - macosx_copy_opengl(dest->data, x, y, w, h); - return; - } -#endif - - if (xform24to32) { - copy_raw_fb_24_to_32(dest, x, y, w, h); - return; - } - if (raw_fb_native_bpp < 8) { - copy_raw_fb_low_bpp(dest, x, y, w, h); - return; - } - if (db < 0) { - if (getenv("DEBUG_COPY_RAW_FB")) { - db = atoi(getenv("DEBUG_COPY_RAW_FB")); - } else { - db = 0; - } - } - - if (clipshift && ! use_snapfb) { - x += coff_x; - y += coff_y; - } - - - if (use_snapfb && dest != snap) { - /* snapfb src */ - src = snap->data + snap->bytes_per_line*y + pixelsize*x; - dst = dest->data; - -if (db) fprintf(stderr, "snap->bytes_per_line: %d, dest->bytes_per_line: %d, w: %d h: %d dpy_x: %d wdpy_x: %d cdpy_x: %d bpp: %d pixelsize: %d\n", snap->bytes_per_line, dest->bytes_per_line, w, h, dpy_x, wdpy_x, cdpy_x, bpp, pixelsize); - - for (line = 0; line < h; line++) { - memcpy(dst, src, w * pixelsize); - src += snap->bytes_per_line; - dst += dest->bytes_per_line; - } - - } else if (! raw_fb_seek) { - /* mmap */ - int bpl = raw_fb_bytes_per_line; - - if (clipshift && wdpy_x != cdpy_x) { - bpl = wdpy_x * pixelsize; - } - - src = raw_fb_addr + raw_fb_offset + bpl*y + pixelsize*x; - dst = dest->data; - -if (db) fprintf(stderr, "bpl: %d, dest->bytes_per_line: %d, w: %d h: %d dpy_x: %d wdpy_x: %d cdpy_x: %d bpp: %d pixelsize: %d\n", bpl, dest->bytes_per_line, w, h, dpy_x, wdpy_x, cdpy_x, bpp, pixelsize); - - for (line = 0; line < h; line++) { - memcpy(dst, src, w * pixelsize); - src += bpl; - dst += dest->bytes_per_line; - } - - } else { - /* lseek */ - int n, len, del, sz = w * pixelsize; - off_t off; - int bpl = raw_fb_bytes_per_line; - - if (clipshift && wdpy_x != cdpy_x) { - bpl = wdpy_x * pixelsize; - } - - off = (off_t) (raw_fb_offset + bpl*y + pixelsize*x); - - lseek(raw_fb_fd, off, SEEK_SET); - dst = dest->data; - -if (db) fprintf(stderr, "lseek 0 ps: %d sz: %d off: %d bpl: %d\n", pixelsize, sz, (int) off, bpl); - - for (line = 0; line < h; line++) { - len = sz; - del = 0; - while (len > 0) { - n = read(raw_fb_fd, dst + del, len); - - if (n > 0) { - del += n; - len -= n; - } else if (n == 0) { - break; - } else if (errno != EINTR && errno != EAGAIN) { - break; - } - } - if (bpl > sz) { - off = (off_t) (bpl - sz); - lseek(raw_fb_fd, off, SEEK_CUR); - } - dst += dest->bytes_per_line; - } - } -} - -void copy_image(XImage *dest, int x, int y, unsigned int w, unsigned int h) { - /* default (w=0, h=0) is the fill the entire XImage */ - if (dest == NULL) { - return; - } - if (w < 1) { - w = dest->width; - } - if (h < 1) { - h = dest->height; - } - - if (raw_fb) { - copy_raw_fb(dest, x, y, w, h); - - } else if (use_snapfb && snap_fb && dest != snaprect) { - char *src, *dst; - unsigned int line; - int pixelsize = bpp/8; - - src = snap->data + snap->bytes_per_line*y + pixelsize*x; - dst = dest->data; - for (line = 0; line < h; line++) { - memcpy(dst, src, w * pixelsize); - src += snap->bytes_per_line; - dst += dest->bytes_per_line; - } - - } else if ((using_shm && ! xform24to32) && (int) w == dest->width && - (int) h == dest->height) { - XShmGetImage_wr(dpy, window, dest, x, y, AllPlanes); - - } else { - XGetSubImage_wr(dpy, window, x, y, w, h, AllPlanes, - ZPixmap, dest, 0, 0); - } -} - -#define DEBUG_SKIPPED_INPUT(dbg, str) \ - if (dbg) { \ - rfbLog("skipped input: %s\n", str); \ - } - -void init_track_keycode_state(void) { - int i; - for (i=0; i<256; i++) { - keycode_state[i] = 0; - } - get_keystate(keycode_state); -} - -static void upup_downdown_warning(KeyCode key, Bool down) { - RAWFB_RET_VOID -#if NO_X11 - if (!key || !down) {} - return; -#else - if ((down ? 1:0) == keycode_state[(int) key]) { - char *str = XKeysymToString(XKeycodeToKeysym(dpy, key, 0)); - rfbLog("XTestFakeKeyEvent: keycode=0x%x \"%s\" is *already* " - "%s\n", key, str ? str : "null", down ? "down":"up"); - } -#endif /* NO_X11 */ -} - -/* - * wrappers for XTestFakeKeyEvent, etc.. - * also for XTrap equivalents XESimulateXEventRequest - */ - -void XTRAP_FakeKeyEvent_wr(Display* dpy, KeyCode key, Bool down, - unsigned long delay) { - - RAWFB_RET_VOID -#if NO_X11 - nox11_exit(1); - if (!dpy || !key || !down || !delay) {} - return; -#else - - if (! xtrap_present) { - DEBUG_SKIPPED_INPUT(debug_keyboard, "keyboard: no-XTRAP"); - return; - } - /* unused vars warning: */ - if (key || down || delay) {} - -# if LIBVNCSERVER_HAVE_LIBXTRAP - XESimulateXEventRequest(trap_ctx, down ? KeyPress : KeyRelease, - key, 0, 0, 0); - if (debug_keyboard) { - upup_downdown_warning(key, down); - } - keycode_state[(int) key] = down ? 1 : 0; -# else - DEBUG_SKIPPED_INPUT(debug_keyboard, "keyboard: no-XTRAP-build"); -# endif - -#endif /* NO_X11 */ -} - -void XTestFakeKeyEvent_wr(Display* dpy, KeyCode key, Bool down, - unsigned long delay) { - static int first = 1; - int regrab = 0; - - RAWFB_RET_VOID - -#if NO_X11 - nox11_exit(1); - if (!dpy || !key || !down || !delay || !first) {} - return; -#else - if (debug_keyboard) { - char *str = XKeysymToString(XKeycodeToKeysym(dpy, key, 0)); - rfbLog("XTestFakeKeyEvent(dpy, keycode=0x%x \"%s\", %s)\n", - key, str ? str : "null", down ? "down":"up"); - } - if (first) { - init_track_keycode_state(); - first = 0; - } - if (down) { - last_keyboard_keycode = -key; - } else { - last_keyboard_keycode = key; - } - - if (grab_kbd) { - XUngrabKeyboard(dpy, CurrentTime); - regrab = 1; - } - if (grab_ptr && ungrab_both) { - XUngrabPointer(dpy, CurrentTime); - regrab = 1; - } - - if (xtrap_input) { - XTRAP_FakeKeyEvent_wr(dpy, key, down, delay); - if (regrab) { - adjust_grabs(1, 1); - } - return; - } - - if (! xtest_present) { - DEBUG_SKIPPED_INPUT(debug_keyboard, "keyboard: no-XTEST"); - return; - } - if (debug_keyboard) { - rfbLog("calling XTestFakeKeyEvent(%d, %d) %.4f\n", - key, down, dnowx()); - } -#if LIBVNCSERVER_HAVE_XTEST - XTestFakeKeyEvent(dpy, key, down, delay); - if (regrab) { - adjust_grabs(1, 1); - } - if (debug_keyboard) { - upup_downdown_warning(key, down); - } - keycode_state[(int) key] = down ? 1 : 0; -#endif - -#endif /* NO_X11 */ -} - -void XTRAP_FakeButtonEvent_wr(Display* dpy, unsigned int button, Bool is_press, - unsigned long delay) { - - RAWFB_RET_VOID -#if NO_X11 - nox11_exit(1); - if (!dpy || !button || !is_press || !delay) {} - return; -#else - - if (! xtrap_present) { - DEBUG_SKIPPED_INPUT(debug_keyboard, "button: no-XTRAP"); - return; - } - /* unused vars warning: */ - if (button || is_press || delay) {} - -#if LIBVNCSERVER_HAVE_LIBXTRAP - XESimulateXEventRequest(trap_ctx, - is_press ? ButtonPress : ButtonRelease, button, 0, 0, 0); -#else - DEBUG_SKIPPED_INPUT(debug_keyboard, "button: no-XTRAP-build"); -#endif - -#endif /* NO_X11 */ -} - -void XTestFakeButtonEvent_wr(Display* dpy, unsigned int button, Bool is_press, - unsigned long delay) { - int regrab = 0; - - RAWFB_RET_VOID -#if NO_X11 - nox11_exit(1); - if (!dpy || !button || !is_press || !delay) {} - return; -#else - - if (grab_ptr) { - XUngrabPointer(dpy, CurrentTime); - regrab = 1; - } - if (grab_kbd && ungrab_both) { - XUngrabKeyboard(dpy, CurrentTime); - regrab = 1; - } - - if (xtrap_input) { - XTRAP_FakeButtonEvent_wr(dpy, button, is_press, delay); - if (regrab) { - adjust_grabs(1, 1); - } - return; - } - - if (! xtest_present) { - DEBUG_SKIPPED_INPUT(debug_keyboard, "button: no-XTEST"); - return; - } - if (debug_pointer) { - rfbLog("calling XTestFakeButtonEvent(%d, %d) %.4f\n", - button, is_press, dnowx()); - } -#if LIBVNCSERVER_HAVE_XTEST - XTestFakeButtonEvent(dpy, button, is_press, delay); -#endif - if (regrab) { - adjust_grabs(1, 1); - } -#endif /* NO_X11 */ -} - -void XTRAP_FakeMotionEvent_wr(Display* dpy, int screen, int x, int y, - unsigned long delay) { - - RAWFB_RET_VOID - -#if NO_X11 - nox11_exit(1); - if (!dpy || !screen || !x || !y || !delay) {} - return; -#else - if (! xtrap_present) { - DEBUG_SKIPPED_INPUT(debug_keyboard, "motion: no-XTRAP"); - return; - } - /* unused vars warning: */ - if (dpy || screen || x || y || delay) {} - -#if LIBVNCSERVER_HAVE_LIBXTRAP - XESimulateXEventRequest(trap_ctx, MotionNotify, 0, x, y, 0); -#else - DEBUG_SKIPPED_INPUT(debug_keyboard, "motion: no-XTRAP-build"); -#endif - -#endif /* NO_X11 */ -} - -void XTestFakeMotionEvent_wr(Display* dpy, int screen, int x, int y, - unsigned long delay) { - int regrab = 0; - - RAWFB_RET_VOID -#if NO_X11 - nox11_exit(1); - if (!dpy || !screen || !x || !y || !delay) {} - return; -#else - - if (grab_ptr) { - XUngrabPointer(dpy, CurrentTime); - regrab = 1; - } - if (grab_kbd && ungrab_both) { - XUngrabKeyboard(dpy, CurrentTime); - regrab = 1; - } - - if (xtrap_input) { - XTRAP_FakeMotionEvent_wr(dpy, screen, x, y, delay); - if (regrab) { - adjust_grabs(1, 1); - } - return; - } - - if (debug_pointer) { - rfbLog("calling XTestFakeMotionEvent(%d, %d) %.4f\n", - x, y, dnowx()); - } -#if LIBVNCSERVER_HAVE_XTEST - XTestFakeMotionEvent(dpy, screen, x, y, delay); -#endif - if (regrab) { - adjust_grabs(1, 1); - } -#endif /* NO_X11 */ -} - -Bool XTestCompareCurrentCursorWithWindow_wr(Display* dpy, Window w) { - if (! xtest_present) { - return False; - } - RAWFB_RET(False) - -#if LIBVNCSERVER_HAVE_XTEST - return XTestCompareCurrentCursorWithWindow(dpy, w); -#else - if (!w) {} - return False; -#endif -} - -Bool XTestCompareCursorWithWindow_wr(Display* dpy, Window w, Cursor cursor) { - if (! xtest_present) { - return False; - } - RAWFB_RET(False) -#if LIBVNCSERVER_HAVE_XTEST - return XTestCompareCursorWithWindow(dpy, w, cursor); -#else - if (!dpy || !w || !cursor) {} - return False; -#endif -} - -Bool XTestQueryExtension_wr(Display *dpy, int *ev, int *er, int *maj, - int *min) { - RAWFB_RET(False) -#if LIBVNCSERVER_HAVE_XTEST - return XTestQueryExtension(dpy, ev, er, maj, min); -#else - if (!dpy || !ev || !er || !maj || !min) {} - return False; -#endif -} - -void XTestDiscard_wr(Display *dpy) { - if (! xtest_present) { - return; - } - RAWFB_RET_VOID -#if LIBVNCSERVER_HAVE_XTEST - XTestDiscard(dpy); -#else - if (!dpy) {} -#endif -} - -Bool XETrapQueryExtension_wr(Display *dpy, int *ev, int *er, int *op) { - RAWFB_RET(False) -#if LIBVNCSERVER_HAVE_LIBXTRAP - return XETrapQueryExtension(dpy, (INT32 *)ev, (INT32 *)er, - (INT32 *)op); -#else - /* unused vars warning: */ - if (ev || er || op) {} - return False; -#endif -} - -int XTestGrabControl_wr(Display *dpy, Bool impervious) { - if (! xtest_present) { - return 0; - } - RAWFB_RET(0) -#if LIBVNCSERVER_HAVE_XTEST && LIBVNCSERVER_HAVE_XTESTGRABCONTROL - XTestGrabControl(dpy, impervious); - return 1; -#else - if (!dpy || !impervious) {} - return 0; -#endif -} - -int XTRAP_GrabControl_wr(Display *dpy, Bool impervious) { - if (! xtrap_present) { - /* unused vars warning: */ - if (dpy || impervious) {} - return 0; - } - RAWFB_RET(0) -#if LIBVNCSERVER_HAVE_LIBXTRAP - else { - ReqFlags requests; - - if (! impervious) { - if (trap_ctx) { - XEFreeTC(trap_ctx); - } - trap_ctx = NULL; - return 1; - } - - if (! trap_ctx) { - trap_ctx = XECreateTC(dpy, 0, NULL); - if (! trap_ctx) { - rfbLog("DEC-XTRAP XECreateTC failed. Watch " - "out for XGrabServer from wm's\n"); - return 0; - } - XEStartTrapRequest(trap_ctx); - memset(requests, 0, sizeof(requests)); - BitTrue(requests, X_GrabServer); - BitTrue(requests, X_UngrabServer); - XETrapSetRequests(trap_ctx, True, requests); - XETrapSetGrabServer(trap_ctx, True); - } - return 1; - } -#endif - return 0; -} - -void disable_grabserver(Display *in_dpy, int change) { - int ok = 0; - static int didmsg = 0; - - if (debug_grabs) { - fprintf(stderr, "disable_grabserver/%d %.5f\n", - xserver_grabbed, dnowx()); - didmsg = 0; - } - - if (! xtrap_input) { - if (XTestGrabControl_wr(in_dpy, True)) { - if (change) { - XTRAP_GrabControl_wr(in_dpy, False); - } - if (! didmsg && ! raw_fb_str) { - rfbLog("GrabServer control via XTEST.\n"); - didmsg = 1; - } - ok = 1; - } else { - if (XTRAP_GrabControl_wr(in_dpy, True)) { - ok = 1; - if (! didmsg && ! raw_fb_str) { - rfbLog("Using DEC-XTRAP for protection" - " from XGrabServer.\n"); - didmsg = 1; - } - } - } - } else { - if (XTRAP_GrabControl_wr(in_dpy, True)) { - if (change) { - XTestGrabControl_wr(in_dpy, False); - } - if (! didmsg && ! raw_fb_str) { - rfbLog("GrabServer control via DEC-XTRAP.\n"); - didmsg = 1; - } - ok = 1; - } else { - if (XTestGrabControl_wr(in_dpy, True)) { - ok = 1; - if (! didmsg && ! raw_fb_str) { - rfbLog("DEC-XTRAP XGrabServer " - "protection not available, " - "using XTEST.\n"); - didmsg = 1; - } - } - } - } - if (! ok && ! didmsg) { - rfbLog("*********************************************************\n"); - rfbLog("* No XTEST or DEC-XTRAP protection from XGrabServer !!! *\n"); - rfbLog("* DEADLOCK if your window manager calls XGrabServer !!! *\n"); - rfbLog("*********************************************************\n"); - } - XFlush_wr(in_dpy); -} - -Bool XRecordQueryVersion_wr(Display *dpy, int *maj, int *min) { - RAWFB_RET(False) -#if LIBVNCSERVER_HAVE_RECORD - return XRecordQueryVersion(dpy, maj, min); -#else - if (!dpy || !maj || !min) {} - return False; -#endif -} - -int xauth_raw(int on) { - char tmp[] = "/tmp/x11vnc-xauth.XXXXXX"; - int tmp_fd = -1; - static char *old_xauthority = NULL; - static char *old_tmp = NULL; - int db = 0; - - if (on) { - if (old_xauthority) { - free(old_xauthority); - old_xauthority = NULL; - } - if (old_tmp) { - free(old_tmp); - old_tmp = NULL; - } - if (xauth_raw_data) { - tmp_fd = mkstemp(tmp); - if (tmp_fd < 0) { - rfbLog("could not create tmp xauth file: %s\n", tmp); - return 0; - } - if (db) fprintf(stderr, "XAUTHORITY tmp: %s\n", tmp); - write(tmp_fd, xauth_raw_data, xauth_raw_len); - close(tmp_fd); - if (getenv("XAUTHORITY")) { - old_xauthority = strdup(getenv("XAUTHORITY")); - } else { - old_xauthority = strdup(""); - } - set_env("XAUTHORITY", tmp); - old_tmp = strdup(tmp); - } - return 1; - } else { - if (old_xauthority) { - if (!strcmp(old_xauthority, "")) { - char *xauth = getenv("XAUTHORITY"); - if (xauth) { - *(xauth-2) = '_'; /* yow */ - } - } else { - set_env("XAUTHORITY", old_xauthority); - } - free(old_xauthority); - old_xauthority = NULL; - } - if (old_tmp) { - unlink(old_tmp); - free(old_tmp); - old_tmp = NULL; - } - return 1; - } -} - -Display *XOpenDisplay_wr(char *display_name) { - Display *d = NULL; - int db = 0; - - if (! xauth_raw(1)) { - return NULL; - } -#if NO_X11 - rfbLog("This x11vnc was built without X11 support (-rawfb only).\n"); - if (!display_name || !d || !db) {} - return NULL; -#else - - d = XOpenDisplay(display_name); - if (db) fprintf(stderr, "XOpenDisplay_wr: %s %p\n", display_name, (void *)d); - - if (d == NULL && !getenv("NO_XAUTHLOCALHOSTNAME")) { - char *xalhn = getenv("XAUTHLOCALHOSTNAME"); - if (1 || !xalhn) { - rfbLog("XOpenDisplay(\"%s\") failed.\n", - display_name ? display_name : ""); - rfbLog("Trying again with XAUTHLOCALHOSTNAME=localhost ...\n"); - set_env("XAUTHLOCALHOSTNAME", "localhost"); - d = XOpenDisplay(display_name); - if (d == NULL && xalhn) { - char *ptr = getenv("XAUTHLOCALHOSTNAME"); - if (ptr) { - *(ptr-2) = '_'; /* yow */ - rfbLog("XOpenDisplay(\"%s\") failed.\n", - display_name ? display_name : ""); - rfbLog("Trying again with unset XAUTHLOCALHOSTNAME ...\n"); - d = XOpenDisplay(display_name); - } - } - } - } - - xauth_raw(0); - - return d; -#endif /* NO_X11 */ -} - -int XCloseDisplay_wr(Display *display) { - int db = 0; - if (db) fprintf(stderr, "XCloseDisplay_wr: %p\n", (void *)display); -#if NO_X11 - return 0; -#else - return XCloseDisplay(display); -#endif /* NO_X11 */ -} - -static unsigned int Bmask = (Button1Mask|Button2Mask|Button3Mask|Button4Mask|Button5Mask); -static unsigned int Mmask = (ShiftMask|LockMask|ControlMask|Mod1Mask|Mod2Mask|Mod3Mask|Mod4Mask|Mod5Mask); - -static unsigned int last_local_button_mask = 0; -static unsigned int last_local_mod_mask = 0; -static int last_local_x = 0; -static int last_local_y = 0; - -Bool XQueryPointer_wr(Display *display, Window w, Window *root_return, - Window *child_return, int *root_x_return, int *root_y_return, - int *win_x_return, int *win_y_return, unsigned int *mask_return) { -#if NO_X11 - if (!display || !w || !root_return || !child_return || !root_x_return - || !root_y_return || !win_x_return || !win_y_return || !mask_return) {} - return False; -#else - Bool rc; - XErrorHandler old_handler; - - - if (! display) { - return False; - } - old_handler = XSetErrorHandler(trap_xerror); - trapped_xerror = 0; - - rc = XQueryPointer(display, w, root_return, child_return, - root_x_return, root_y_return, win_x_return, win_y_return, - mask_return); - - XSetErrorHandler(old_handler); - if (trapped_xerror) { - rc = 0; - } - if (rc) { - display_button_mask = (*mask_return) & Bmask; - display_mod_mask = (*mask_return) & Mmask; - if (last_local_button_mask != display_button_mask) { - got_local_pointer_input++; - } else if (*root_x_return != last_local_x || - *root_y_return != last_local_y) { - got_local_pointer_input++; - } - last_local_button_mask = display_button_mask; - last_local_mod_mask = display_mod_mask; - last_local_x = *root_x_return; - last_local_y = *root_y_return; - } - return rc; -#endif /* NO_X11 */ -} - - -Status XQueryTree_wr(Display *display, Window w, Window *root_return, - Window *parent_return, Window **children_return, - unsigned int *nchildren_return) { - -#ifdef MACOSX - if (macosx_console) { - return macosx_xquerytree(w, root_return, parent_return, - children_return, nchildren_return); - } -#endif -#if NO_X11 - if (!display || !w || !root_return || !parent_return - || !children_return || !nchildren_return) {} - return (Status) 0; -#else - if (! display) { - return (Status) 0; - } - return XQueryTree(display, w, root_return, parent_return, - children_return, nchildren_return); -#endif /* NO_X11 */ - -} - -int XFree_wr(void *data) { - if (data == NULL) { - return 1; - } - if (! dpy) { - return 1; - } -#if NO_X11 - return 1; -#else - return XFree(data); -#endif -} - -int XSelectInput_wr(Display *display, Window w, long event_mask) { -#if NO_X11 - if (!display || !w || !event_mask) {} - return 0; -#else - int rc; - XErrorHandler old_handler; - if (display == NULL || w == None) { - return 0; - } - old_handler = XSetErrorHandler(trap_xerror); - trapped_xerror = 0; - rc = XSelectInput(display, w, event_mask); - XSetErrorHandler(old_handler); - if (trapped_xerror) { - rc = 0; - } - return rc; -#endif -} - -void nox11_exit(int rc) { -#if NO_X11 - rfbLog("This x11vnc was not built with X11 support.\n"); - clean_up_exit(rc); -#else - if (0) {rc = 0;} -#endif -} - - -#if NO_X11 -#include "nox11_funcs.h" -#endif - |