Commit 203eee7c authored by runge's avatar runge

x11vnc: -capslock -skip_lockkeys; Alt keys under -rawfb cons.

parent 84176182
2006-06-03 Karl Runge <runge@karlrunge.com>
* x11vnc: -capslock and -skip_lockkeys options. map some Alt keys
to Latin under linuxfb. switch to new stats API. Handle more
cases carefully when switching fb.
2006-05-06 Karl Runge <runge@karlrunge.com>
* x11vnc: improved support for webcams and tv tuners with
video4linux /dev/video: -rawfb video, -freqtab etc.
......
This source diff could not be displayed because it is too large. You can view the blob instead.
......@@ -51,8 +51,6 @@ static void interrupted (int sig);
void clean_shm(int quick) {
int i, cnt = 0;
if (raw_fb) quick = 1; /* raw_fb hack */
/*
* to avoid deadlock, etc, under quick=1 we just delete the shm
* areas and leave the X stuff hanging.
......
......@@ -644,6 +644,7 @@ void client_gone(rfbClientPtr client) {
* we disconnect after 1 successful connection).
*/
if ((client->state == RFB_PROTOCOL_VERSION ||
client->state == RFB_SECURITY_TYPE ||
client->state == RFB_AUTHENTICATION) && accepted_client) {
rfbLog("connect_once: invalid password or early "
"disconnect.\n");
......
......@@ -425,6 +425,7 @@ void print_help(int mode) {
" and last line be \"__BEGIN_VIEWONLY__\" to have 2\n"
" full-access passwords)\n"
"\n"
#ifndef REL81
"-unixpw [list] Use Unix username and password authentication. x11vnc\n"
" uses the su(1) program to verify the user's password.\n"
" [list] is an optional comma separated list of allowed\n"
......@@ -1055,6 +1056,7 @@ void print_help(int mode) {
" -httpdir option. If not supplied it will try to guess\n"
" the directory as though the -http option was supplied.\n"
"\n"
#endif
"-usepw If no other password method was supplied on the command\n"
" line, first look for ~/.vnc/passwd and if found use it\n"
" with -rfbauth; next, look for ~/.vnc/passwdfile and\n"
......@@ -1063,9 +1065,11 @@ void print_help(int mode) {
" the -rfbauth option. If none of these succeed x11vnc\n"
" exits immediately.\n"
"\n"
#ifndef REL81
" Note: -unixpw currently does not count as a password\n"
" method by this option.\n"
"\n"
#endif
"-storepasswd pass file Store password \"pass\" as the VNC password in the\n"
" file \"file\". Once the password is stored the\n"
" program exits. Use the password via \"-rfbauth file\"\n"
......@@ -1356,6 +1360,36 @@ void print_help(int mode) {
" e.g. !, @, [, are only accessible via -xkb mode and if\n"
" so then automatically enable the mode. To disable this\n"
" automatic detection use -noxkb.\n"
"\n"
"-capslock When in -modtweak (the default) or -xkb mode,\n"
" if a keysym in the range A-Z comes in check the X\n"
" server to see if the Caps_Lock is set. If it is do\n"
" not artificially press Shift to generate the keysym.\n"
" This will enable the CapsLock key to behave correctly\n"
" in some circumstances: namely *both* the VNC viewer\n"
" machine and the x11vnc X server are in the CapsLock\n"
" on state. If one side has CapsLock on and the other\n"
" off and the keyboard is not behaving as you think it\n"
" should you should correct the CapsLock states (hint:\n"
" pressing CapsLock inside and outside of the viewer can\n"
" help toggle them both to the correct state). However,\n"
" for best results do not use this option, but rather\n"
" *only* enable CapsLock on the VNC viewer side (i.e. by\n"
" pressing CapsLock outside of the viewer window, also\n"
" -skip_lockkeys below). Also try -nomodtweak for a\n"
" possible workaround.\n"
"\n"
"-skip_lockkeys Have x11vnc ignore all Caps_Lock, Shift_Lock, Num_Lock,\n"
" Scroll_Lock keysyms received from viewers. The idea is\n"
" you press Caps_Lock on the VNC Viewer side but that does\n"
" not change the lock state in the x11vnc-side X server.\n"
" Nevertheless your capitalized letters come in over\n"
" the wire and are applied correctly to the x11vnc-side\n"
" X server. Note this mode probably won't do what you\n"
" want in -nomodtweak mode. Also, a kludge for KP_n\n"
" digits is always done it this mode: they are mapped to\n"
" regular digit keysyms. See also -capslock above.\n"
"\n"
"-skip_keycodes string Ignore the comma separated list of decimal keycodes.\n"
" Perhaps these are keycodes not on your keyboard but\n"
" your X server thinks exist. Currently only applies\n"
......@@ -1410,6 +1444,9 @@ void print_help(int mode) {
" \"Button1\", ..., etc. E.g: \"-remap Super_R-Button2\"\n"
" (useful for pasting on a laptop)\n"
"\n"
" To disable a keysym (i.e. make it so it will not be\n"
" injected), remap it to \"NoSymbol\" or \"None\".\n"
"\n"
" Dead keys: \"dead\" (or silent, mute) keys are keys that\n"
" do not produce a character but must be followed by a 2nd\n"
" keystroke. This is often used for accenting characters,\n"
......@@ -2401,6 +2438,10 @@ void print_help(int mode) {
" format to HI240, RGB565, RGB24, RGB32, RGB555, and\n"
" GREY respectively. See -rawfb video for details.\n"
"\n"
" If cmd is \"CONS\" or \"CONSn\" where n is a Linux\n"
" console number, then the linux console keystroke\n"
" insertion (see -rawfb cons) is performed.\n"
"\n"
"-gui [gui-opts] Start up a simple tcl/tk gui based on the the remote\n"
" control options -remote/-query described below.\n"
" Requires the \"wish\" program to be installed on the\n"
......@@ -2642,6 +2683,10 @@ void print_help(int mode) {
" nomodtweak enable -nomodtweak mode.\n"
" xkb enable -xkb modtweak mode.\n"
" noxkb disable -xkb modtweak mode.\n"
" capslock enable -capslock mode.\n"
" nocapslock disable -capslock mode.\n"
" skip_lockkeys enable -skip_lockkeys mode.\n"
" noskip_lockkeys disable -skip_lockkeys mode.\n"
" skip_keycodes:str enable -xkb -skip_keycodes \"str\".\n"
" sloppy_keys enable -sloppy_keys mode.\n"
" nosloppy_keys disable -sloppy_keys mode.\n"
......@@ -2835,8 +2880,9 @@ void print_help(int mode) {
" listen lookup nolookup accept afteraccept gone shm\n"
" noshm flipbyteorder noflipbyteorder onetile noonetile\n"
" solid_color solid nosolid blackout xinerama noxinerama\n"
" xtrap noxtrap xrandr noxrandr xrandr_mode padgeom quiet\n"
" q noquiet modtweak nomodtweak xkb noxkb skip_keycodes\n"
" xtrap noxtrap xrandr noxrandr xrandr_mode padgeom\n"
" quiet q noquiet modtweak nomodtweak xkb noxkb capslock\n"
" nocapslock skip_lockkeys noskip_lockkeys skip_keycodes\n"
" sloppy_keys nosloppy_keys skip_dups noskip_dups\n"
" add_keysyms noadd_keysyms clear_mods noclear_mods\n"
" clear_keys noclear_keys remap repeat norepeat fb nofb\n"
......@@ -2874,8 +2920,12 @@ void print_help(int mode) {
" scale_str scaled_x scaled_y scale_numer scale_denom\n"
" scale_fac scaling_blend scaling_nomult4 scaling_pad\n"
" scaling_interpolate inetd privremote unsafe safer nocmds\n"
#ifndef REL81
" passwdfile unixpw unixpw_nis unixpw_list ssl ssl_pem\n"
" sslverify stunnel stunnel_pem https usepw using_shm\n"
#else
" passwdfile usepw using_shm\n"
#endif
" logfile o flag rc norc h help V version lastmod bg\n"
" sigpipe threads readrate netrate netlatency pipeinput\n"
" clients client_count pid ext_xtest ext_xtrap ext_xrecord\n"
......
......@@ -531,8 +531,10 @@ static void add_remap(char *line) {
}
}
if (ksym1 == NoSymbol || ksym2 == NoSymbol) {
rfbLog("warning: skipping invalid remap line: %s", line);
return;
if (strcasecmp(str2, "NoSymbol") && strcasecmp(str2, "None")) {
rfbLog("warning: skipping invalid remap line: %s", line);
return;
}
}
remap = (keyremap_t *) malloc((size_t) sizeof(keyremap_t));
remap->before = ksym1;
......@@ -1860,6 +1862,22 @@ static void xkb_tweak_keyboard(rfbBool down, rfbKeySym keysym,
} else if (ks == XK_ISO_Level3_Shift) {
skip = 0;
}
if (watch_capslock && kbstate.locked_mods & LockMask) {
if (keysym >= 'A' && keysym <= 'Z') {
if (ks == XK_Shift_L || ks == XK_Shift_R) {
if (debug_keyboard > 1) {
fprintf(stderr, " A-Z caplock skip Shift\n");
}
skip = 1;
} else if (ks == XK_Caps_Lock) {
if (debug_keyboard > 1) {
fprintf(stderr, " A-Z caplock noskip CapsLock\n");
}
skip = 0;
}
}
}
/*
* Alt, Meta, Control, Super,
* Hyper, Num, Caps are skipped.
......@@ -2328,9 +2346,23 @@ static void modifier_tweak_keyboard(rfbBool down, rfbKeySym keysym,
ADJUSTMOD(XK_Mode_switch, ALTGR)
if ( down && keysym >= ' ' && keysym < 0x100 ) {
unsigned int state = 0;
tweak = 1;
tweak_mod(modifiers[keysym], True);
k = keycodes[keysym];
if (watch_capslock && keysym >= 'A' && keysym <= 'Z') {
X_LOCK;
state = mask_state();
X_UNLOCK;
}
if (state & LockMask) {
/* capslock set for A-Z, so no tweak */
X_LOCK;
k = XKeysymToKeycode(dpy, (KeySym) keysym);
X_UNLOCK;
tweak = 0;
} else {
tweak_mod(modifiers[keysym], True);
k = keycodes[keysym];
}
} else {
X_LOCK;
k = XKeysymToKeycode(dpy, (KeySym) keysym);
......@@ -2618,6 +2650,31 @@ void keyboard(rfbBool down, rfbKeySym keysym, rfbClientPtr client) {
}
}
if (skip_lockkeys) {
/* we don't handle XK_ISO*_Lock or XK_Kana_Lock ... */
if (keysym == XK_Scroll_Lock || keysym == XK_Num_Lock ||
keysym == XK_Caps_Lock || keysym == XK_Shift_Lock) {
if (debug_keyboard) {
rfbLog("skipping lock key event: %d 0x%x\n",
down, keysym);
}
return;
} else if (keysym >= XK_KP_0 && keysym <= XK_KP_9) {
/* ugh this is probably what they meant... assume NumLock. */
if (debug_keyboard) {
rfbLog("changed KP digit to regular digit: %d 0x%x\n",
down, keysym);
}
keysym = (keysym - XK_KP_0) + XK_0;
} else if (keysym == XK_KP_Decimal) {
if (debug_keyboard) {
rfbLog("changed XK_KP_Decimal to XK_period: %d 0x%x\n",
down, keysym);
}
keysym = XK_period;
}
}
last_down = down;
last_keysym = keysym;
last_keyboard_time = tnow;
......
......@@ -142,7 +142,7 @@ char *console_guess(char *str, int *fd) {
}
void console_key_command(rfbBool down, rfbKeySym keysym, rfbClientPtr client) {
static int control = 0;
static int control = 0, alt = 0;
if (debug_keyboard) fprintf(stderr, "console_key_command: %d %s\n", (int) keysym, down ? "down" : "up");
if (pipeinput_cons_fd < 0) {
return;
......@@ -159,6 +159,16 @@ void console_key_command(rfbBool down, rfbKeySym keysym, rfbClientPtr client) {
}
return;
}
if (keysym == XK_Alt_L || keysym == XK_Alt_R) {
if (! down) {
if (alt > 0) {
alt--;
}
} else {
alt++;
}
return;
}
if (!down) {
return;
}
......@@ -166,6 +176,7 @@ void console_key_command(rfbBool down, rfbKeySym keysym, rfbClientPtr client) {
keysym = 27;
}
if (control) {
/* shift down to the "control" zone */
if (keysym >= 'a' && keysym <= 'z') {
keysym -= ('a' - 1);
} else if (keysym >= 'A' && keysym <= 'Z') {
......@@ -173,10 +184,16 @@ void console_key_command(rfbBool down, rfbKeySym keysym, rfbClientPtr client) {
} else {
keysym = 0xffff;
}
} else if (alt) {
/* shift up to the upper half Latin zone */
if (keysym >= '!' && keysym <= '~') {
keysym += 128;
}
}
if (debug_keyboard) fprintf(stderr, "keysym now: %d\n", (int) keysym);
if (keysym == XK_Tab) {
keysym = '\t';
} else if (keysym == XK_Return) {
} else if (keysym == XK_Return || keysym == XK_KP_Enter) {
keysym = '\r';
} else if (keysym == XK_BackSpace) {
keysym = 8;
......@@ -196,6 +213,10 @@ void console_key_command(rfbBool down, rfbKeySym keysym, rfbClientPtr client) {
keysym = 2;
} else if (keysym == XK_Prior || keysym == XK_KP_Prior) {
keysym = 2;
} else {
if (keysym >= XK_KP_Multiply && keysym <= XK_KP_Equal) {
keysym -= 0xFF80;
}
}
#if LIBVNCSERVER_HAVE_SYS_IOCTL_H && defined(TIOCSTI)
if (keysym < 0x100) {
......
......@@ -108,6 +108,8 @@ char *cmap8to24_str = NULL;
int launch_gui = 0; /* -gui */
int use_modifier_tweak = 1; /* use the shift/altgr modifier tweak */
int watch_capslock = 0; /* -capslock */
int skip_lockkeys = 0; /* -skip_lockkeys */
int use_iso_level3 = 0; /* ISO_Level3_Shift instead of Mode_switch */
int clear_mods = 0; /* -clear_mods (1) and -clear_keys (2) */
int nofb = 0; /* do not send any fb updates */
......
......@@ -83,6 +83,8 @@ extern int xform24to32;
extern int launch_gui;
extern int use_modifier_tweak;
extern int watch_capslock;
extern int skip_lockkeys;
extern int use_iso_level3;
extern int clear_mods;
extern int nofb;
......
......@@ -350,8 +350,16 @@ db = 0;
}
nclients++;
#if 0
for (i=0; i<MAX_ENCODINGS; i++) {
cbs += cl->bytesSent[i];
}
rbs = cl->rawBytesEquivalent;
#else
cbs = rfbStatGetSentBytes(cl);
rbs = rfbStatGetSentBytesIfRaw(cl);
#endif
if (init) {
......@@ -432,7 +440,13 @@ if (db) fprintf(stderr, "%d client num rects req: %d mod: %d cbs: %d "
if (db) fprintf(stderr, "dt2 calc: num rects req: %d/%d mod: %d/%d "
"fbu-sent: %d dt: %.4f dt2: %.4f tm: %.4f\n",
req0, req1, mod0, mod1, rfbStatGetMessageCountSent(cl, rfbFramebufferUpdate), dt, dt2, tm);
req0, req1, mod0, mod1,
#if 0
cl->framebufferUpdateMessagesSent,
#else
rfbStatGetMessageCountSent(cl, rfbFramebufferUpdate),
#endif
dt, dt2, tm);
if (req1 != 0 && mod1 == 0) {
got_t2 = 1;
break;
......@@ -499,7 +513,13 @@ if (db) fprintf(stderr, "dt2 calc: num rects req: %d/%d mod: %d/%d "
if (db) fprintf(stderr, "dt3 calc: num rects req: %d/%d mod: %d/%d "
"fbu-sent: %d dt: %.4f dt3: %.4f tm: %.4f\n",
req0, req1, mod0, mod1, rfbStatGetMessageCountSent(cl, rfbFramebufferUpdate), dt, dt3, tm);
req0, req1, mod0, mod1,
#if 0
cl->framebufferUpdateMessagesSent,
#else
rfbStatGetMessageCountSent(cl, rfbFramebufferUpdate),
#endif
dt, dt3, tm);
if (req1 != 0 && mod1 == 0) {
dts[got_t3++] = dt3;
......
......@@ -1957,6 +1957,38 @@ char *process_remote_cmd(char *cmd, int stringonly) {
got_noxkb = 1;
initialize_modtweak();
} else if (!strcmp(p, "capslock")) {
if (query) {
snprintf(buf, bufn, "ans=%s:%d", p, watch_capslock);
goto qry;
}
rfbLog("remote_cmd: enabling -capslock mode\n");
watch_capslock = 1;
} else if (!strcmp(p, "nocapslock")) {
if (query) {
snprintf(buf, bufn, "ans=%s:%d", p, !watch_capslock);
goto qry;
}
rfbLog("remote_cmd: disabling -capslock mode\n");
watch_capslock = 0;
} else if (!strcmp(p, "skip_lockkeys")) {
if (query) {
snprintf(buf, bufn, "ans=%s:%d", p, skip_lockkeys);
goto qry;
}
rfbLog("remote_cmd: enabling -skip_lockkeys mode\n");
skip_lockkeys = 1;
} else if (!strcmp(p, "noskip_lockkeys")) {
if (query) {
snprintf(buf, bufn, "ans=%s:%d", p, !skip_lockkeys);
goto qry;
}
rfbLog("remote_cmd: disabling -skip_lockkeys mode\n");
skip_lockkeys = 0;
} else if (strstr(p, "skip_keycodes") == p) {
COLON_CHECK("skip_keycodes:")
if (query) {
......@@ -3336,7 +3368,9 @@ char *process_remote_cmd(char *cmd, int stringonly) {
set_raw_fb_params(1);
}
rfbLog("hang on tight, here we go...\n");
raw_fb_back_to_X = 1;
do_new_fb(1);
raw_fb_back_to_X = 0;
} else if (strstr(p, "progressive") == p) {
int f;
......@@ -3869,6 +3903,7 @@ char *process_remote_cmd(char *cmd, int stringonly) {
snprintf(buf, bufn, "aro=%s:%d", p, no_external_cmds);
} else if (!strcmp(p, "passwdfile")) {
snprintf(buf, bufn, "aro=%s:%s", p, NONUL(passwdfile));
#ifndef REL81
} else if (!strcmp(p, "unixpw")) {
snprintf(buf, bufn, "aro=%s:%d", p, unixpw);
} else if (!strcmp(p, "unixpw_nis")) {
......@@ -3887,6 +3922,7 @@ char *process_remote_cmd(char *cmd, int stringonly) {
snprintf(buf, bufn, "aro=%s:%s", p, NONUL(stunnel_pem));
} else if (!strcmp(p, "https")) {
snprintf(buf, bufn, "aro=%s:%d", p, https_port_num);
#endif
} else if (!strcmp(p, "usepw")) {
snprintf(buf, bufn, "aro=%s:%d", p, usepw);
} else if (!strcmp(p, "using_shm")) {
......
......@@ -213,6 +213,7 @@ static int shm_create(XShmSegmentInfo *shm, XImage **ximg_ptr, int w, int h,
XImage *xim;
static int reported_flip = 0;
int db = 0;
shm->shmid = -1;
shm->shmaddr = (char *) -1;
......@@ -239,6 +240,7 @@ static int shm_create(XShmSegmentInfo *shm, XImage **ximg_ptr, int w, int h,
}
return 0;
}
if (db) fprintf(stderr, "shm_create simple %d %d\t0x%x %s\n", w, h, xim, name);
xim->data = (char *) malloc(xim->bytes_per_line * xim->height);
if (xim->data == NULL) {
rfbErr("XCreateImage(%s) data malloc failed.\n", name);
......@@ -345,27 +347,28 @@ void shm_delete(XShmSegmentInfo *shm) {
}
void shm_clean(XShmSegmentInfo *shm, XImage *xim) {
int db = 0;
if (db) fprintf(stderr, "shm_clean: called: 0x%x\n", xim);
X_LOCK;
#if LIBVNCSERVER_HAVE_XSHM
if (shm != NULL && shm->shmid != -1 && dpy) { /* raw_fb hack */
if (shm != NULL && shm->shmid != -1 && dpy) {
if (db) fprintf(stderr, "shm_clean: XShmDetach_wr\n");
XShmDetach_wr(dpy, shm);
}
#endif
if (xim != NULL) {
#if 0
/*
* This would be needed if you want to crazily switch
* back and forth between rawfb and X. You will also
* need to supply -noviewonly. xim->f is public ABI,
* but we choose not to use it. One could also
* clean up the switch.
*/
if (xim->f.destroy_image) {
#else
{
#endif
XDestroyImage(xim);
if (! raw_fb_back_to_X) { /* raw_fb hack */
if (xim->bitmap_unit != -1) {
if (db) fprintf(stderr, "shm_clean: XDestroyImage 0x%x\n", xim);
XDestroyImage(xim);
} else {
if (xim->data) {
if (db) fprintf(stderr, "shm_clean: free xim->data 0x%x 0x%x\n", xim, xim->data);
free(xim->data);
xim->data = NULL;
}
}
}
xim = NULL;
}
......
......@@ -29,7 +29,7 @@ void set_colormap(int reset);
void set_nofb_params(int restore);
void set_raw_fb_params(int restore);
void do_new_fb(int reset_mem);
void free_old_fb(char *old_main, char *old_rfb, char *old_8to24);
void free_old_fb(char *old_main, char *old_rfb, char *old_8to24, char *old_snap_fb);
void check_padded_fb(void);
void install_padded_fb(char *geom);
XImage *initialize_xdisplay_fb(void);
......@@ -545,6 +545,9 @@ void set_raw_fb_params(int restore) {
if (dpy) {
if (! quiet) rfbLog("reopened DISPLAY: %s\n",
raw_fb_orig_dpy);
scr = DefaultScreen(dpy);
rootwin = RootWindow(dpy, scr);
check_xevents(1);
} else {
if (! quiet) rfbLog("WARNING: failed to reopen "
"DISPLAY: %s\n", raw_fb_orig_dpy);
......@@ -648,23 +651,30 @@ static void nofb_hook(rfbClientPtr cl) {
screen->displayHook = NULL;
}
void free_old_fb(char *old_main, char *old_rfb, char *old_8to24) {
void free_old_fb(char *old_main, char *old_rfb, char *old_8to24, char *old_snap_fb) {
if (old_main) {
free(old_main);
}
if (old_rfb && old_rfb != old_main) {
free(old_rfb);
if (old_rfb) {
if (old_rfb != old_main) {
free(old_rfb);
}
}
if (old_8to24) {
if (old_8to24 != old_main && old_8to24 != old_rfb) {
free(old_8to24);
}
}
if (old_8to24 && old_8to24 != old_main && old_8to24 != old_rfb) {
free(old_8to24);
if (old_snap_fb) {
if (old_snap_fb != old_main && old_snap_fb != old_rfb &&
old_snap_fb != old_8to24) {
free(old_snap_fb);
}
}
}
void do_new_fb(int reset_mem) {
XImage *fb;
char *old_main = main_fb;
char *old_rfb = rfb_fb;
char *old_8to24 = cmap8to24_fb;
/* for threaded we really should lock libvncserver out. */
if (use_threads) {
......@@ -678,6 +688,16 @@ void do_new_fb(int reset_mem) {
free_tiles();
}
free_old_fb(main_fb, rfb_fb, cmap8to24_fb, snap_fb);
if (raw_fb == main_fb || raw_fb == rfb_fb) {
raw_fb = NULL;
}
main_fb = NULL;
rfb_fb = NULL;
cmap8to24_fb = NULL;
snap_fb = NULL;
fb = initialize_xdisplay_fb();
initialize_screen(NULL, NULL, fb);
......@@ -688,9 +708,6 @@ void do_new_fb(int reset_mem) {
initialize_polling_images();
}
free_old_fb(old_main, old_rfb, old_8to24);
fb0 = fb;
}
static void remove_fake_fb(void) {
......@@ -922,6 +939,14 @@ if (db) fprintf(stderr, "initialize_raw_fb reset\n");
free(last_file);
last_file = NULL;
}
if (strstr(str, "Video") == str) {
if (pipeinput_str != NULL) {
free(pipeinput_str);
}
pipeinput_str = strdup("VID");
initialize_pipeinput();
str[0] = 'v';
}
if (strstr(str, "video") == str || strstr(str, "/dev/video") == str) {
char *str2 = v4l_guess(str, &raw_fb_fd);
......@@ -1169,6 +1194,7 @@ if (db) fprintf(stderr, "initialize_raw_fb reset\n");
raw_fb_image->height = dpy_y;
raw_fb_image->bits_per_pixel = b;
raw_fb_image->bytes_per_line = dpy_x*b/8;
raw_fb_image->bitmap_unit = -1;
if (use_snapfb && (raw_fb_seek || raw_fb_mmap)) {
int b_use = b;
......@@ -1186,6 +1212,7 @@ if (db) fprintf(stderr, "initialize_raw_fb reset\n");
snap->height = dpy_y;
snap->bits_per_pixel = b_use;
snap->bytes_per_line = dpy_x*b_use/8;
snap->bitmap_unit = -1;
}
if (rm == 0 && gm == 0 && bm == 0) {
......@@ -2174,9 +2201,11 @@ void initialize_screen(int *argc, char **argv, XImage *fb) {
}
screen->frameBuffer = rfb_fb;
if (!quiet) {
fprintf(stderr, " main_fb: %p\n", main_fb);
fprintf(stderr, " rfb_fb: %p\n", rfb_fb);
fprintf(stderr, " main_fb: %p\n", main_fb);
fprintf(stderr, " 8to24_fb: %p\n", cmap8to24_fb);
fprintf(stderr, " snap_fb: %p\n", snap_fb);
fprintf(stderr, " raw_fb: %p\n", raw_fb);
fprintf(stderr, "\n");
}
......
......@@ -10,7 +10,7 @@ extern void set_colormap(int reset);
extern void set_nofb_params(int restore);
extern void set_raw_fb_params(int restore);
extern void do_new_fb(int reset_mem);
extern void free_old_fb(char *old_main, char *old_rfb, char *old_8to24);
extern void free_old_fb(char *old_main, char *old_rfb, char *old_8to24, char *old_snap_fb);
extern void check_padded_fb(void);
extern void install_padded_fb(char *geom);
extern XImage *initialize_xdisplay_fb(void);
......
......@@ -14,6 +14,10 @@
#endif
#endif
#ifdef REL81
#undef SSLCMDS
#endif
void check_stunnel(void);
int start_stunnel(int stunnel_port, int x11vnc_port);
......@@ -39,9 +43,13 @@ void check_stunnel(void) {
if (stunnel_pid > 0) {
int status;
#ifdef SSLCMDS
waitpid(stunnel_pid, &status, WNOHANG);
#endif
if (kill(stunnel_pid, 0) != 0) {
#ifdef SSLCMDS
waitpid(stunnel_pid, &status, WNOHANG);
#endif
rfbLog("stunnel subprocess %d died.\n", stunnel_pid);
stunnel_pid = 0;
clean_up_exit(1);
......@@ -74,7 +82,7 @@ int start_stunnel(int stunnel_port, int x11vnc_port) {
strcat(path, extra);
}
exe = (char *) malloc(strlen(path) + strlen("stunnel") + 1);
exe = (char *) malloc(strlen(path) + 1 + strlen("stunnel") + 1);
p = strtok(path, ":");
......@@ -123,7 +131,7 @@ int start_stunnel(int stunnel_port, int x11vnc_port) {
stunnel_pem = get_saved_pem(stunnel_pem, 1);
if (! stunnel_pem) {
rfbLog("start_stunnel: could not create or open"
" saved PEM:\n", stunnel_pem);
" saved PEM.\n");
clean_up_exit(1);
}
}
......@@ -278,7 +286,7 @@ void setup_stunnel(int rport, int *argc, char **argv) {
}
if (start_stunnel(rport, xport)) {
int tweaked = 0;
char tmp[10];
char tmp[20];
sprintf(tmp, "%d", xport);
if (argv) {
for (i=0; i< *argc; i++) {
......@@ -539,6 +547,7 @@ void sslEncKey(char *path, int mode) {
strcat(tca, " | xargs ls -ld ");
}
system(tca);
depth--;
return;
} else if (info_only && (!strcasecmp(path, "HASHON")
......@@ -565,6 +574,7 @@ void sslEncKey(char *path, int mode) {
}
system(scr);
unlink(tmp);
depth--;
return;
}
......@@ -624,7 +634,7 @@ void sslEncKey(char *path, int mode) {
}
if (! info_only) {
cert = (char *) malloc(2*sbuf.st_size);
cert = (char *) malloc(2*(sbuf.st_size + 100));
file = fopen(path, "r");
if (file == NULL) {
rfbLog("sslEncKey: %s\n", path);
......@@ -638,7 +648,9 @@ void sslEncKey(char *path, int mode) {
incert = 1;
}
if (incert) {
strcat(cert, line);
if (strlen(cert) + strlen(line) < 2*sbuf.st_size) {
strcat(cert, line);
}
}
if (strstr(line, "-----END CERTIFICATE-----") == line) {
incert = 0;
......
......@@ -12,12 +12,21 @@
#define OPENSSL_VNC 2
#define OPENSSL_HTTPS 3
#define DO_DH 0
#if LIBVNCSERVER_HAVE_FORK
#if LIBVNCSERVER_HAVE_SYS_WAIT_H && LIBVNCSERVER_HAVE_WAITPID
#define FORK_OK
#endif
#endif
#ifdef REL81
#undef FORK_OK
#undef LIBVNCSERVER_HAVE_LIBSSL
#define LIBVNCSERVER_HAVE_LIBSSL 0
#endif
int openssl_sock = -1;
int openssl_port_num = 0;
int https_sock = -1;
......@@ -64,6 +73,7 @@ static SSL *ssl = NULL;
static void init_prng(void);
static void sslerrexit(void);
static char *get_input(char *tag, char **in);
static char *create_tmp_pem(char *path, int prompt);
static int ssl_init(int s_in, int s_out);
static void raw_xfer(int csock, int s_in, int s_out);
......@@ -146,9 +156,6 @@ static char *get_input(char *tag, char **in) {
str = lblanks(line);
if (! strcmp(str, "")) {
return *in;
} else if (0 && !strcmp(str, "none")) {
free(*in);
return strdup("");
} else {
free(*in);
return strdup(line);
......@@ -200,7 +207,7 @@ static char *create_tmp_pem(char *pathin, int prompt) {
FILE *in, *out;
char cnf[] = "/tmp/x11vnc-cnf.XXXXXX";
char pem[] = "/tmp/x11vnc-pem.XXXXXX";
char str[7*1024], line[1024], *exe;
char str[8*1024], line[1024], *exe;
int cnf_fd, pem_fd, status, show_cert = 1;
char *days;
char *C, *L, *OU, *O, *CN, *EM;
......@@ -431,9 +438,9 @@ static char *create_tmp_pem(char *pathin, int prompt) {
if (show_cert) {
char cmd[100];
if (inetd) {
sprintf(cmd, "openssl x509 -text -in %s 1>&2", pem);
sprintf(cmd, "openssl x509 -text -in '%s' 1>&2", pem);
} else {
sprintf(cmd, "openssl x509 -text -in %s", pem);
sprintf(cmd, "openssl x509 -text -in '%s'", pem);
}
fprintf(stderr, "\n");
system(cmd);
......@@ -600,11 +607,7 @@ void openssl_init(void) {
double ds;
long mode;
#if DO_DH
do_dh = 1;
#else
do_dh = 0;
#endif
do_dh = DO_DH;
if (! quiet) {
rfbLog("\n");
......@@ -630,7 +633,7 @@ void openssl_init(void) {
}
ds = dnow();
rsa_512 = RSA_generate_key(512,RSA_F4,NULL,NULL);
rsa_512 = RSA_generate_key(512, RSA_F4, NULL, NULL);
if (rsa_512 == NULL) {
rfbLog("openssl_init: RSA_generate_key(512) failed.\n");
sslerrexit();
......@@ -639,7 +642,7 @@ void openssl_init(void) {
rfbLog("created 512 bit temporary RSA key: %.3fs\n", dnow() - ds);
ds = dnow();
rsa_1024 = RSA_generate_key(1024,RSA_F4,NULL,NULL);
rsa_1024 = RSA_generate_key(1024, RSA_F4, NULL, NULL);
if (rsa_1024 == NULL) {
rfbLog("openssl_init: RSA_generate_key(1024) failed.\n");
sslerrexit();
......@@ -717,7 +720,7 @@ void openssl_init(void) {
rfbLog("openssl_init: SSL_CTX_use_certificate_chain_file() failed.\n");
sslerrexit();
}
if(! SSL_CTX_use_RSAPrivateKey_file(ctx, openssl_pem,
if (! SSL_CTX_use_RSAPrivateKey_file(ctx, openssl_pem,
SSL_FILETYPE_PEM)) {
rfbLog("openssl_init: SSL_CTX_set_tmp_rsa(1024) failed.\n");
sslerrexit();
......@@ -739,7 +742,6 @@ void openssl_init(void) {
fprintf(stderr, "\n");
fclose(in);
}
}
unlink(openssl_pem);
free(openssl_pem);
......@@ -866,15 +868,15 @@ static void lose_ram(void) {
* without doing exec(). we really should re-exec, but a pain
* to redo all SSL ctx.
*/
free_old_fb(main_fb, rfb_fb, cmap8to24_fb);
free_old_fb(main_fb, rfb_fb, cmap8to24_fb, snap_fb);
if (raw_fb == main_fb || raw_fb == rfb_fb) {
raw_fb = NULL;
}
main_fb = NULL;
rfb_fb = NULL;
cmap8to24_fb = NULL;
snap_fb = NULL;
if (snap_fb) {
free(snap_fb);
snap_fb = NULL;
}
free_tiles();
}
......@@ -991,7 +993,6 @@ static int is_ssl_readable(int s_in, time_t last_https, char *last_get,
tv.tv_sec = 2;
tv.tv_usec = 0;
if (mode == OPENSSL_INETD) {
/*
* https via inetd is icky because x11vnc is restarted
......@@ -1037,7 +1038,7 @@ static int watch_for_http_traffic(char *buf_a, int *n_a) {
* sniff the first couple bytes of the stream and try to see
* if it is http or not. if we read them OK, we must read the
* rest of the available data otherwise we may deadlock.
* what has be read is returned in buf_a and n_a.
* what has been read is returned in buf_a and n_a.
* *buf_a is ABSIZE+1 long and zeroed.
*/
if (getenv("ACCEPT_OPENSSL_DEBUG")) {
......@@ -1081,6 +1082,7 @@ static int watch_for_http_traffic(char *buf_a, int *n_a) {
}
*n_a = n;
if (n > 0) {
/* XXX memcpy? */
strncpy(buf_a, buf, n);
}
return is_http;
......@@ -1160,18 +1162,16 @@ if (db) fprintf(stderr, "ssl_init FAILED\n");
{
char *buf;
int n, ptr;
int n = 0, ptr = 0;
buf = (char *) calloc((8192+1), 1);
n = 0;
ptr = 0;
while (ptr < 8192) {
n = SSL_read(ssl, buf + ptr, 8192 - ptr);
if (n > 0) {
ptr += n;
}
if (db) fprintf(stderr, "buf: '%s'\n", buf);
if (strstr(buf, "\r\n\r\n") || strstr(buf, "\n\n")) {
if (strstr(buf, "\r\n\r\n")) {
break;
}
}
......@@ -1708,7 +1708,7 @@ static int ssl_init(int s_in, int s_out) {
fprintf(stderr, "SSL_new failed\n");
return 0;
}
if (db > 1) fprintf(stderr, "a\n");
if (db > 1) fprintf(stderr, "ssl_init: 1\n");
SSL_set_session_id_context(ssl, sid, strlen((char *)sid));
......@@ -1727,13 +1727,15 @@ if (db > 1) fprintf(stderr, "a\n");
return 0;
}
}
if (db > 1) fprintf(stderr, "b\n");
if (db > 1) fprintf(stderr, "ssl_init: 2\n");
SSL_set_accept_state(ssl);
if (db > 1) fprintf(stderr, "c\n");
if (db > 1) fprintf(stderr, "ssl_init: 3\n");
name = get_remote_host(ssock);
if (db > 1) fprintf(stderr, "d\n");
if (db > 1) fprintf(stderr, "ssl_init: 4\n");
while (1) {
if (db) fprintf(stderr, "calling SSL_accept...\n");
......@@ -1751,33 +1753,44 @@ if (db > 1) fprintf(stderr, "d\n");
if (err == SSL_ERROR_NONE) {
break;
} else if (err == SSL_ERROR_WANT_READ) {
if (db) fprintf(stderr, "got SSL_ERROR_WANT_READ\n");
rfbLog("SSL: ssl_helper: SSL_accept() failed for: %s\n",
name);
return 0;
} else if (err == SSL_ERROR_WANT_WRITE) {
if (db) fprintf(stderr, "got SSL_ERROR_WANT_WRITE\n");
rfbLog("SSL: ssl_helper: SSL_accept() failed for: %s\n",
name);
return 0;
} else if (err == SSL_ERROR_SYSCALL) {
if (db) fprintf(stderr, "got SSL_ERROR_SYSCALL\n");
rfbLog("SSL: ssl_helper: SSL_accept() failed for: %s\n",
name);
return 0;
} else if (err == SSL_ERROR_ZERO_RETURN) {
if (db) fprintf(stderr, "got SSL_ERROR_ZERO_RETURN\n");
rfbLog("SSL: ssl_helper: SSL_accept() failed for: %s\n",
name);
return 0;
} else if (rc < 0) {
rfbLog("SSL: ssl_helper: SSL_accept() fatal: %d\n", rc);
return 0;
} else if (dnow() > start + 3.0) {
rfbLog("SSL: ssl_helper: timeout looping SSL_accept() "
"fatal.\n");
return 0;
} else {
BIO *bio = SSL_get_rbio(ssl);
if (bio == NULL) {
......@@ -1819,7 +1832,7 @@ static void raw_xfer(int csock, int s_in, int s_out) {
break;
} else if (n > 0) {
m = write(s_out, buf, n);
if (db > 1) write(2, buf, n);
if (db > 1) write(2, buf, n);
if (m != n) {
if (db) fprintf(stderr, "raw_xfer bad write: %d -> %d | %d/%d\n", csock, s_out, m, n);
break;
......
......@@ -8,8 +8,6 @@
#define OPENSSL_VNC 2
#define OPENSSL_HTTPS 3
#define DO_DH 0
extern int openssl_sock;
extern int openssl_port_num;
extern int https_sock;
......
......@@ -187,12 +187,14 @@ Keyboard
modtweak
xkb
--
=FP remap:
capslock
skip_lockkeys
--
skip_keycodes:
sloppy_keys
skip_dups
sloppy_keys
--
=FP remap:
clear_mods
clear_keys
......
......@@ -198,12 +198,14 @@ char gui_code[] = "";
" modtweak\n"
" xkb\n"
" --\n"
" =FP remap:\n"
" capslock\n"
" skip_lockkeys\n"
" --\n"
" skip_keycodes:\n"
" sloppy_keys\n"
" skip_dups\n"
" sloppy_keys\n"
" --\n"
" =FP remap:\n"
" clear_mods\n"
" clear_keys\n"
"\n"
......
......@@ -40,6 +40,11 @@ extern char *crypt(const char*, const char *);
#define IS_BSD
#endif
#ifdef REL81
#undef UNIXPW_SU
#undef UNIXPW_CRYPT
#endif
void unixpw_screen(int init);
void unixpw_keystroke(rfbBool down, rfbKeySym keysym, int init);
void unixpw_accept(char *user);
......
......@@ -4082,7 +4082,11 @@ int fb_update_sent(int *count) {
i = rfbGetClientIterator(screen);
while( (cl = rfbClientIteratorNext(i)) ) {
#if 0
sent += cl->framebufferUpdateMessagesSent;
#else
sent += rfbStatGetMessageCountSent(cl, rfbFramebufferUpdate);
#endif
}
rfbReleaseClientIterator(i);
if (sent != last_count) {
......
......@@ -19,6 +19,7 @@ int get_window_size(Window win, int *x, int *y);
void snapshot_stack_list(int free_only, double allowed_age);
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);
......@@ -279,6 +280,20 @@ Window query_pointer(Window start) {
}
}
unsigned int mask_state(void) {
Window r, c;
int rx, ry, wx, wy;
unsigned int mask;
RAWFB_RET(0)
if (XQueryPointer(dpy, rootwin, &r, &c, &rx, &ry, &wx, &wy, &mask)) {
return mask;
} else {
return 0;
}
}
int pick_windowid(unsigned long *num) {
char line[512];
int ok = 0, n = 0, msec = 10, secmax = 15;
......
......@@ -17,6 +17,7 @@ extern int get_window_size(Window win, int *x, int *y);
extern void snapshot_stack_list(int free_only, double allowed_age);
extern void update_stack_list(void);
extern Window query_pointer(Window start);
extern unsigned int mask_state(void);
extern int pick_windowid(unsigned long *num);
extern Window descend_pointer(int depth, Window start, char *name_info, int len);
......
This diff is collapsed.
......@@ -239,7 +239,11 @@ static void record_last_fb_update(void) {
iter = rfbGetClientIterator(screen);
while( (cl = rfbClientIteratorNext(iter)) ) {
#if 0
rbs += cl->rawBytesEquivalent;
#else
rbs += rfbStatGetSentBytesIfRaw(cl);
#endif
}
rfbReleaseClientIterator(iter);
......@@ -467,7 +471,7 @@ if (debug_scroll) fprintf(stderr, "watch_loop: LOOP-BACK: %d\n", ret);
}
check_new_clients();
check_xevents();
check_xevents(0);
check_autorepeat();
check_pm();
check_keycode_state();
......@@ -1384,6 +1388,7 @@ int main(int argc, char* argv[]) {
int dt = 0, bg = 0;
int got_rfbwait = 0;
int got_httpdir = 0, try_http = 0;
XImage *fb0 = NULL;
/* used to pass args we do not know about to rfbGetScreen(): */
int argc_vnc = 1; char *argv_vnc[128];
......@@ -1592,6 +1597,7 @@ int main(int argc, char* argv[]) {
CHECK_ARGC
passwdfile = strdup(argv[++i]);
got_passwdfile = 1;
#ifndef REL81
} else if (strstr(arg, "-unixpw") == arg) {
unixpw = 1;
if (strstr(arg, "-unixpw_nis")) {
......@@ -1709,6 +1715,7 @@ int main(int argc, char* argv[]) {
i++;
}
}
#endif
} else if (!strcmp(arg, "-nopw")) {
nopw = 1;
} else if (!strcmp(arg, "-usepw")) {
......@@ -1826,6 +1833,10 @@ int main(int argc, char* argv[]) {
} else if (!strcmp(arg, "-noxkb")) {
use_xkb_modtweak = 0;
got_noxkb = 1;
} else if (!strcmp(arg, "-capslock")) {
watch_capslock = 1;
} else if (!strcmp(arg, "-skip_lockkeys")) {
skip_lockkeys = 1;
} else if (!strcmp(arg, "-xkbcompat")) {
xkbcompat = 1;
} else if (!strcmp(arg, "-skip_keycodes")) {
......
......@@ -114,6 +114,8 @@
#define PASSWD_UNLESS_NOPW 0
#endif
#define REL81
/*
* Beginning of support for small binary footprint build for embedded
* systems, PDA's etc. It currently just cuts out the low-hanging
......@@ -234,7 +236,6 @@ extern int h_errno;
#include <arpa/inet.h>
#endif
/* XXX autoconf */
#if LIBVNCSERVER_HAVE_PWD_H
#include <pwd.h>
#endif
......@@ -334,8 +335,7 @@ extern int num_buttons;
/* image structures */
extern XImage *scanline;
extern XImage *fullscreen;
extern XImage **tile_row; /* for all possible row runs */
extern XImage *fb0;
extern XImage **tile_row; /* for all possible row runs */
extern XImage *snaprect; /* for XShmGetImage (fs_factor) */
extern XImage *snap; /* the full snap fb */
extern XImage *raw_fb_image; /* the raw fb */
......@@ -373,6 +373,7 @@ extern int raw_fb_shm;
extern int raw_fb_mmap;
extern int raw_fb_seek;
extern int raw_fb_fd;
extern int raw_fb_back_to_X;
extern int rfb_bytes_per_line;
extern int main_bytes_per_line;
......
......@@ -15,7 +15,7 @@ int xtrap_base_event_type = 0;
int xdamage_base_event_type = 0;
/* date +'lastmod: %Y-%m-%d' */
char lastmod[] = "0.8.1 lastmod: 2006-05-06";
char lastmod[] = "0.8.1 lastmod: 2006-06-03";
/* X display info */
......@@ -37,7 +37,6 @@ int num_buttons = -1;
XImage *scanline = NULL;
XImage *fullscreen = NULL;
XImage **tile_row = NULL; /* for all possible row runs */
XImage *fb0 = NULL;
XImage *snaprect = NULL; /* for XShmGetImage (fs_factor) */
XImage *snap = NULL; /* the full snap fb */
XImage *raw_fb_image = NULL; /* the raw fb */
......@@ -58,13 +57,14 @@ char *rfb_fb = NULL; /* same as main_fb unless transformation */
char *fake_fb = NULL; /* used under -padgeom */
char *snap_fb = NULL; /* used under -snapfb */
char *cmap8to24_fb = NULL; /* used under -8to24 */
char *raw_fb = NULL;
char *raw_fb = NULL; /* when used should be main_fb */
char *raw_fb_addr = NULL;
int raw_fb_offset = 0;
int raw_fb_shm = 0;
int raw_fb_mmap = 0;
int raw_fb_seek = 0;
int raw_fb_fd = -1;
int raw_fb_back_to_X = 0; /* kludge for testing rawfb -> X */
int rfb_bytes_per_line;
int main_bytes_per_line;
......
......@@ -12,6 +12,7 @@
#include "gui.h"
#include "connections.h"
#include "unixpw.h"
#include "cleanup.h"
/* XXX CHECK BEFORE RELEASE */
int grab_buster = 0;
......@@ -24,11 +25,11 @@ void spawn_grab_buster(void);
void sync_tod_with_servertime(void);
void check_keycode_state(void);
void check_autorepeat(void);
void check_xevents(void);
void check_xevents(int reset);
void xcut_receive(char *text, int len, rfbClientPtr cl);
static void initialize_xevents(void);
static void initialize_xevents(int reset);
static void print_xevent_bases(void);
static void get_prop(char *str, int len, Atom prop);
static void bust_grab(int reset);
......@@ -62,7 +63,7 @@ void initialize_clipboard_atom(void) {
}
}
static void initialize_xevents(void) {
static void initialize_xevents(int reset) {
static int did_xselect_input = 0;
static int did_xcreate_simple_window = 0;
static int did_vnc_connect_prop = 0;
......@@ -73,6 +74,18 @@ static void initialize_xevents(void) {
static int did_xrandr = 0;
RAWFB_RET_VOID
if (reset) {
did_xselect_input = 0;
did_xcreate_simple_window = 0;
did_vnc_connect_prop = 0;
did_x11vnc_remote_prop = 0;
did_clipboard_atom = 0;
did_xfixes = 0;
did_xdamage = 0;
did_xrandr = 0;
}
if ((watch_selection || vnc_connect) && !did_xselect_input) {
/*
* register desired event(s) for notification.
......@@ -688,7 +701,7 @@ void check_autorepeat(void) {
* This routine is periodically called to check for selection related
* and other X11 events and respond to them as needed.
*/
void check_xevents(void) {
void check_xevents(int reset) {
XEvent xev;
int tmp, have_clients = 0;
static int sent_some_sel = 0;
......@@ -699,14 +712,18 @@ void check_xevents(void) {
static time_t last_time_sync = 0;
time_t now = time(0);
static double last_request = 0.0;
XErrorHandler old_handler;
RAWFB_RET_VOID
if (unixpw_in_progress) return;
if (now > last_init_check+1) {
if (now > last_init_check+1 || reset) {
last_init_check = now;
initialize_xevents();
initialize_xevents(reset);
if (reset) {
return;
}
}
if (screen && screen->clientHead) {
......@@ -719,6 +736,7 @@ void check_xevents(void) {
* the client... so instead of sending right away we wait a
* the few seconds.
*/
if (have_clients && watch_selection && !sent_some_sel
&& now > last_client + sel_waittime) {
if (XGetSelectionOwner(dpy, XA_PRIMARY) == None) {
......@@ -741,6 +759,10 @@ void check_xevents(void) {
if (now > last_call+1) {
/* we only check these once a second or so. */
int n = 0;
trapped_xerror = 0;
old_handler = XSetErrorHandler(trap_xerror);
while (XCheckTypedEvent(dpy, MappingNotify, &xev)) {
XRefreshKeyboardMapping((XMappingEvent *) &xev);
n++;
......@@ -769,6 +791,9 @@ void check_xevents(void) {
while (XCheckTypedEvent(dpy, ClientMessage, &xev)) {
;
}
XSetErrorHandler(old_handler);
trapped_xerror = 0;
}
/* check for CUT_BUFFER0 and VNC_CONNECT changes: */
......@@ -908,6 +933,9 @@ void check_xevents(void) {
if (own_primary || own_clipboard) {
/* we own PRIMARY or CLIPBOARD, see if someone requested it: */
trapped_xerror = 0;
old_handler = XSetErrorHandler(trap_xerror);
if (XCheckTypedEvent(dpy, SelectionRequest, &xev)) {
if (own_primary && xev.type == SelectionRequest &&
xev.xselectionrequest.selection == XA_PRIMARY) {
......@@ -944,6 +972,9 @@ void check_xevents(void) {
}
}
}
XSetErrorHandler(old_handler);
trapped_xerror = 0;
}
if (watch_bell || now > last_bell+1) {
......
......@@ -13,7 +13,7 @@ extern void spawn_grab_buster(void);
extern void sync_tod_with_servertime(void);
extern void check_keycode_state(void);
extern void check_autorepeat(void);
extern void check_xevents(void);
extern void check_xevents(int reset);
extern void xcut_receive(char *text, int len, rfbClientPtr cl);
#endif /* _X11VNC_XEVENTS_H */
......@@ -265,6 +265,7 @@ XImage *XCreateImage_wr(Display *disp, Visual *visual, unsigned int depth,
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;
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment