diff options
author | runge <runge@karlrunge.com> | 2009-12-29 19:07:15 -0500 |
---|---|---|
committer | runge <runge@karlrunge.com> | 2009-12-29 19:07:15 -0500 |
commit | a795da8d7ba2a0cc2cd1ea841ecf1dbe60bb1953 (patch) | |
tree | eb9f606f48cd61b5c268d1c4b35648b34c7a1e4c /x11vnc/misc/Xdummy | |
parent | 5764cd3fdd669096a84c7e40a2893cd45df090e4 (diff) | |
download | libtdevnc-a795da8d7ba2a0cc2cd1ea841ecf1dbe60bb1953.tar.gz libtdevnc-a795da8d7ba2a0cc2cd1ea841ecf1dbe60bb1953.zip |
x11vnc: rename -create_x to -create_xsrv. Hopefully done fixing Xdummy.
Diffstat (limited to 'x11vnc/misc/Xdummy')
-rwxr-xr-x | x11vnc/misc/Xdummy | 334 |
1 files changed, 212 insertions, 122 deletions
diff --git a/x11vnc/misc/Xdummy b/x11vnc/misc/Xdummy index 3abc199..452eb4d 100755 --- a/x11vnc/misc/Xdummy +++ b/x11vnc/misc/Xdummy @@ -5,17 +5,19 @@ # # Run "Xdummy -help" for more info. # -xserver="" -geom="" -geom="" install="" uninstall="" +runit=1 +prconf="" +notweak="" root="" +nosudo="" +xserver="" +geom="" +depth="" debug="" strace="" -runit=1 -prconf="" -noconf="" +cmdline_config="" PATH=$PATH:/bin:/usr/bin export PATH @@ -24,55 +26,62 @@ program=`basename "$0"` help () { ${PAGER:-more} << END +$program: -$program: a hack to run a stock Xorg(1) or XFree86(1) X server with the -"dummy" video driver such that it AVOIDS the Linux VT switching, keyboard -mouse conflicts, etc associated with normal use of "dummy". + A hack to run a stock Xorg(1) or XFree86(1) X server with the "dummy" + (RAM-only framebuffer) video driver such that it AVOIDS the Linux VT + switching, opening device files in /dev, keyboard and mouse conflicts, + and other problems associated with the normal use of "dummy". -In other words, try to make Xorg/XFree86 with the Device "dummy" driver -act more like Xvfb(1). + In other words, it tries to make Xorg/XFree86 with the "dummy" + device driver act more like Xvfb(1). -To achieve this, while running the real Xserver $program intercepts system -and library calls via the LD_PRELOAD method and modifies the behavior -to make it work correctly (i.e. avoid the VT stuff). LD_PRELOAD tricks -are usually "clever hacks" and so might not work in all situations or -break when something changes. + The primary motivation for the Xdummy script is to provide a virtual X + server for x11vnc but with more features than Xvfb (or Xvnc); however + it could be used for other reasons (e.g. better automated testing + than with Xvfb.) One nice thing is the dummy server supports RANDR + dynamic resizing while Xvfb does not. -The primary motivation for the Xdummy script is to provide a virtual X -server for x11vnc but with more features than Xvfb (or Xvnc), however -it could be used for other reasons (e.g. better automated testing than -with Xvfb). A nice by-product is the dummy server supports RANDR dynamic -resizing while Xvfb does not. So, for example x11vnc+Xdummy terminal -services are a little better than x11vnc+Xvfb. + So, for example, x11vnc+Xdummy terminal services are a little better + than x11vnc+Xvfb. -This program does not need to be run as root as of 12/2009. However, -if there are problems for certain situations it may perform better -if run as root (-root option.) + To achieve this, while running the real Xserver $program intercepts + system and library calls via the LD_PRELOAD method and modifies + the behavior to make it work correctly (e.g. avoid the VT stuff.) + LD_PRELOAD tricks are usually "clever hacks" and so might not work + in all situations or break when something changes. -Also, gcc/cc is required to compile the LD_PRELOAD shared object. -See -install and -uninstall described below. + This program does not need to be run as root as of 12/2009. However, + if there are problems for certain situations (usually older servers) + it may perform better if run as root (use the -root option.) + Also, gcc/cc and other build tools are required for this script to + be able to compile the LD_PRELOAD shared object. Be sure they are + installed on the system. See -install and -uninstall described below. -Your Linux distribution may not install the dummy driver by default, e.g: - - /usr/lib/xorg/modules/drivers/dummy_drv.so - -some have it in a package named xserver-xorg-video-dummy you need -to install. + Your Linux distribution may not install the dummy driver by default, + e.g: + /usr/lib/xorg/modules/drivers/dummy_drv.so + + some have it in a package named xserver-xorg-video-dummy you that + need to install. Usage: - $program <${program}-args> [--] <Xserver-args> + $program <${program}-args> <Xserver-args> + (actually, the arguments can be supplied in any order.) Examples: + $program -install + $program :1 - $program -debug -tmpdir ~/mytmp :1 + $program -debug :1 - $program -install + $program -tmpdir ~/mytmp :1 -nolisten tcp startx example: @@ -95,6 +104,8 @@ xdm example: :1 local /usr/local/dummy/Xdummy :1 -debug :2 local /usr/local/dummy/Xdummy :2 -debug + (-debug is optional) + gdm/kdm example: TBD. @@ -102,11 +113,12 @@ gdm/kdm example: Root permission and x11vnc: Update: as of 12/2009 this program no longer must be run as root. + So try it as non-root before running it as root and/or the + following schemes. - However, in some circumstances program may need to be run as - root. If so, one could run x11vnc as root with -unixpw (it - switches to the user that logs in) and that may be OK, some - other ideas: + In some circumstances X server program may need to be run as root. + If so, one could run x11vnc as root with -unixpw (it switches + to the user that logs in) and that may be OK, some other ideas: - add this to sudo via visudo: @@ -145,25 +157,38 @@ Options: ${program}-args: -install Compile the LD_PRELOAD shared object and install it - next to the $program script file as: $0.so + next to the $program script file as: + + $0.so When that file exists it is used as the LD_PRELOAD shared object without recompiling. Otherwise, each time $program is run the LD_PRELOAD shared - object is compiled as a file in /tmp (or -tmpdir). + object is compiled as a file in /tmp (or -tmpdir) + + If you set the environment variable + INTERPOSE_GETUID=1 when building, then when + $program is run as an ordinary user, the shared + object will interpose getuid() calls and pretend + to be root. Otherwise it doesn't pretend to + be root. + + You can also set the CFLAGS environment variable + to anything else you want on the compile cmdline. + + -uninstall Remove the file: + + $0.so - -uninstall Remove the file: $0.so The LD_PRELOAD shared object will then be compiled each time this program is run. - Note: the X server is not started under -install or -uninstall. + The X server is not started under -install, -uninstall, or -prconf. - :N The DISPLAY can be the first $program argument. - It is passed to the real X server. This is to - aid use with startx(1), xinit(1), xdm(1), etc. - If one is not provided it tries to choose one - automatically. + :N The DISPLAY (e.g. :15) is often the first + argument. It is passed to the real X server and + also used by the Xdummy script as an identifier. -geom geom1[,geom2...] Take the geometry (e.g. 1024x768) or list of geometries and insert them into the @@ -171,6 +196,13 @@ Options: config file. Use this to have a smaller geometry than the one in the system config file. + -depth n Use pixel color depth n (e.g. 8, 16, or 24). This + makes sure the X config file has a Screen.Display + subsection of this depth. Note this option is + ALSO passed to the X server. + + -DEPTH n Same as -depth, except not passed to X server. + -tmpdir dir Specify a temporary directory, owned by you and only writable by you. This is used in place of /tmp/Xdummy.\$USER/.. to place the $program.so @@ -179,56 +211,70 @@ Options: -nonroot Run in non-root mode (working 12/2009, now default) -root Run as root (may still be needed in some - environments.) + environments.) Same as XDUMMY_RUN_AS_ROOT=1. -nosudo Do not try to use sudo(1) when re-running as root, use su(1) instead. -xserver path Specify the path to the Xserver to use. Default is to try "Xorg" first and then "XFree86". If - those are not in \$PATH, use these locations: + those are not in \$PATH, it tries these locations: + /usr/bin/Xorg /usr/X11R6/bin/Xorg /usr/X11R6/bin/XFree86 -n Do not run the command to start the X server, just show the command that $program would run. The LD_PRELOAD shared object will be built, - if needed. + if needed. Also note any XDUMMY* environment + variables that need to be set. - -prconf Print, to stdout, the tweaked Xorg or XFree86 + -prconf Print, to stdout, the tweaked Xorg/XFree86 config file (-config and -xf86config server - options, respectively). The Xserver is not + options, respectively.) The Xserver is not started. - -noconf Do not tweak the Xorg or XFree86 config file - (system or server command line) at all. It is - up to you to make sure it is a working config - file (e.g. "dummy" driver, etc). Perhaps you - want to use a file based on -prconf output. + -notweak Do not tweak (modify) the Xorg/XFree86 config file + (system or server command line) at all. The -geom + and similar config file modifications are ignored. + + It is up to you to make sure it is a working + config file (e.g. "dummy" driver, etc.) + Perhaps you want to use a file based on the + -prconf output. -debug Extra debugging output. - -strace strace(1) the Xserver process (for troubleshooting). + -strace strace(1) the Xserver process (for troubleshooting.) + -ltrace ltrace(1) instead of strace (can be slow.) -h, -help Print out this help. Xserver-args: - Most of the Xorg and XFree86 options will work. Important ones - that may be supplied if missing: + Most of the Xorg and XFree86 options will work and are simply + passed along if you supply them. Important ones that may be + supplied if missing: :N X Display number for server to use. vtNN Linux virtual terminal (VT) to use (a VT is currently - still used, just not switched to and from). + still used, just not switched to and from.) -config file Driver "dummy" tweaked config file, a -xf86config file number of settings are tweaked besides Driver. - If -config/-xf86config is not given, the system one is used. - Any settings in the config file that are not consistent with - "dummy" mode will be overwritten (unless -noconf is used). + If -config/-xf86config is not given, the system one + (e.g. /etc/X11/xorg.conf) is used. If the system one cannot be + found, a built-in one is used. Any settings in the config file + that are not consistent with "dummy" mode will be overwritten + (unless -notweak is specified.) + + If "file" is only a basename (e.g. "xorg.dummy.conf") with no /'s, + then no tweaking of it is done: the X server will look for that + basename via its normal search algorithm. If the found file does + not refer to the "dummy" driver, etc, then the X server will fail. Notes: @@ -236,17 +282,20 @@ Notes: well in this mode, but it is evidently not intended for end-users. So it could be removed or broken at any time. - If the display Xserver-arg (e.g. :1) is not given, or ":" or ":9999" - is given that indicates $program should try to find a free one. + If the display Xserver-arg (e.g. :1) is not given, or ":" is given + that indicates $program should try to find a free one (based on + tcp ports.) If the display virtual terminal, VT, (e.g. vt9) is not given that - indicates $program should try to find a free one (or guess a high one). + indicates $program should try to find a free one (or guess a high one.) This program is not completely secure WRT files in /tmp (but it tries - to a good degree). Better is to use the -tmpdir option to supply a + to a good degree.) Better is to use the -tmpdir option to supply a directory only writable by you. Even better is to get rid of users on the local machine you do not trust :-) + Set XDUMMY_SET_XV=1 to turn on debugging output for this script. + END } @@ -311,8 +360,6 @@ if [ "X$XDUMMY_SU_EXEC" = "X" -a "X$root" = "X1" -a "X`id -u`" != "X0" ]; then dosu="" elif [ "X$arg" = "X-prconf" ]; then dosu="" - elif [ "X$arg" = "X--" ]; then - break fi done if [ $dosu ]; then @@ -337,6 +384,7 @@ if [ "X$XDUMMY_SU_EXEC" = "X" -a "X$root" = "X1" -a "X`id -u`" != "X0" ]; then exec su -c "$0 $*" fi fi + # DONE: exit fi fi @@ -345,17 +393,21 @@ fi # disp="" args="" +cmdline_config="" # Process Xdummy args: # while [ "X$1" != "X" ] do + if [ "X$1" = "X-config" -o "X$1" = "X-xf86config" ]; then + cmdline_config="$2" + fi case $1 in ":"*) disp=$1 ;; - "-install") install=1 + "-install") install=1; runit="" ;; - "-uninstall") uninstall=1 + "-uninstall") uninstall=1; runit="" ;; "-n") runit="" ;; @@ -363,9 +415,11 @@ do ;; "-norun") runit="" ;; - "-prconf") prconf=1 + "-prconf") prconf=1; runit="" ;; - "-noconf") noconf=1 + "-notweak") notweak=1 + ;; + "-noconf") notweak=1 ;; "-nonroot") root="" ;; @@ -378,21 +432,26 @@ do "-uid") XDUMMY_UID="$2"; shift export XDUMMY_UID ;; - "-geom"*) geom="$2"; shift + "-geom") geom="$2"; shift + ;; + "-depth") depth="$2"; args="$args -depth $2"; + shift ;; - "-depth") depth="$2"; shift + "-DEPTH") depth="$2"; shift ;; "-tmpdir") XDUMMY_TMPDIR="$2"; shift ;; - "-debug") debug=1 + "-debug") debug=1 ;; "-nodebug") debug="" ;; "-strace") strace=1 ;; - "-h"*) help; exit 0 + "-ltrace") strace=2 + ;; + "-h") help; exit 0 ;; - "--") shift; break + "-help") help; exit 0 ;; *) args="$args $1" ;; @@ -433,32 +492,45 @@ fi # Function to compile the LD_PRELOAD shared object: # make_so() { - # extract code embedded in this script into a tmp C file: n1=`grep -n '^#code_begin' $0 | head -1 | awk -F: '{print $1}'` n2=`grep -n '^#code_end' $0 | head -1 | awk -F: '{print $1}'` n1=`expr $n1 + 1` dn=`expr $n2 - $n1` - tmp=$tdir/Xdummy.$$.c + tmp=$tdir/Xdummy.$RANDOM$$.c rm -f $tmp if [ -e $tmp -o -h $tmp ]; then warn "$tmp still exists." exit 1 fi + touch $tmp || exit 1 tail -n +$n1 $0 | head -n $dn > $tmp # compile it to Xdummy.so: + if [ -f $SO ]; then + mv $SO $SO.$$ + rm -f $SO.$$ + fi rm -f $SO touch $SO if [ ! -f $SO ]; then SO=$tdir/Xdummy.$user.so warn "warning switching LD_PRELOAD shared object to: $SO" fi + + if [ -f $SO ]; then + mv $SO $SO.$$ + rm -f $SO.$$ + fi rm -f $SO # we assume gcc: - cc -shared -fPIC -o $SO $tmp + if [ "X$INTERPOSE_GETUID" = "X1" ]; then + CFLAGS="$CFLAGS -DINTERPOSE_GETUID" + fi + echo "$program:" cc -shared -fPIC $CFLAGS -o $SO $tmp + cc -shared -fPIC $CFLAGS -o $SO $tmp rc=$? rm -f $tmp if [ $rc != 0 ]; then @@ -485,6 +557,10 @@ if [ "X$install" != "X" -o "X$uninstall" != "X" ]; then if [ -e $SO -o -h $SO ]; then warn "$program: removing $SO" fi + if [ -f $SO ]; then + mv $SO $SO.$$ + rm -f $SO.$$ + fi rm -f $SO if [ -e $SO -o -h $SO ]; then warn "warning: $SO still exists." @@ -736,37 +812,12 @@ fi # Decide flavor of Xserver: # stype=`basename "$xserver"` -if echo "$stype" | grep -i xorg > /dev/null; then - stype=xorg -else +if echo "$stype" | grep -i xfree86 > /dev/null; then stype=xfree86 +else + stype=xorg fi -# Work out config file and tweak it. -# -next="" -config="" -got_config="" -for arg in $* -do - if [ $next ]; then - config="$arg" - got_config=1 - break - fi - if [ "X$arg" = "X-xf86config" ]; then - if [ "X$stype" = "X" ]; then - stype="xfree86" - fi - next=1 - elif [ "X$arg" = "X-config" ]; then - if [ "X$stype" = "X" ]; then - stype="xorg" - fi - next=1 - fi -done - tweak_config() { in="$1" config2="$XDUMMY_TMPDIR/xdummy_modified_xconfig.conf" @@ -795,6 +846,10 @@ tweak_config() { $geom = $tmp; } while (<>) { + if ($ENV{XDUMMY_NOTWEAK}) { + print $_; + next; + } $n++; if (/^\s*#/) { # pass comments straight thru @@ -967,6 +1022,9 @@ tweak_config() { } print; } + if ($ENV{XDUMMY_NOTWEAK}) { + exit; + } # create any crucial sections that are missing: if (! exists($sects{serverflags})) { print "\n##Xdummy:##\n"; @@ -1021,14 +1079,31 @@ tweak_config() { '; } -if [ ! $noconf ]; then +# Work out config file and tweak it. +# +if [ "X$cmdline_config" = "X" ]; then + : +elif echo "$cmdline_config" | grep '/' > /dev/null; then + : +else + # ignore basename only case (let server handle it) + cmdline_config="" + notweak=1 +fi + +config=$cmdline_config + +if [ "X$notweak" = "X1" -a "X$root" = "X" -a -f "$cmdline_config" ]; then + # if not root we need to copy (but not tweak) the specified config. + XDUMMY_NOTWEAK=1 + export XDUMMY_NOTWEAK + notweak="" +fi + +if [ ! $notweak ]; then # tweaked config will be put in $config2: config2="" - if [ "X$config" != "X" ]; then - if [ ! -f $config ]; then - config="/etc/X11/$config" - fi - else + if [ "X$config" = "X" ]; then # use the default one: if [ "X$stype" = "Xxorg" ]; then config=/etc/X11/xorg.conf @@ -1052,6 +1127,7 @@ if [ ! $noconf ]; then if [ ! -f $config ]; then config="$XDUMMY_TMPDIR/xorg.conf" + warn "$program: using minimal built-in xorg.conf settings." cat > $config <<END Section "ServerLayout" @@ -1119,7 +1195,7 @@ END fi # now we need to get our tweaked config file onto the command line: - if [ ! $got_config ]; then + if [ "X$cmdline_config" = "X" ]; then # append to cmdline (FUBAR will be substituted below.) if [ "X$stype" = "Xxorg" ]; then args="$args -config FUBAR" @@ -1142,7 +1218,7 @@ fi if [ $prconf ]; then warn "" - warn "The Xorg/XFree86 server config file is:" + warn "Printing out the Xorg/XFree86 server config file:" warn "" if [ "X$config2" = "X" ]; then warn "NO CONFIG GENERATED." @@ -1195,7 +1271,11 @@ if [ "X$debug" != "X" -o "X$runit" = "X" ]; then fi if [ $strace ]; then - strace -f env LD_PRELOAD=$SO $xserver $disp $args $vt + if [ "X$strace" = "X2" ]; then + ltrace -f env LD_PRELOAD=$SO $xserver $disp $args $vt + else + strace -f env LD_PRELOAD=$SO $xserver $disp $args $vt + fi else exec env LD_PRELOAD=$SO $xserver $disp $args $vt fi @@ -1597,6 +1677,10 @@ int chown(const char *path, uid_t owner, gid_t group) { return(real_chown(path, owner, group)); } +extern int *__errno_location (void); +#ifndef ENODEV +#define ENODEV 19 +#endif int ioperm(unsigned long from, unsigned long num, int turn_on) { static int (*real_ioperm)(unsigned long, unsigned long, int) = NULL; @@ -1610,6 +1694,12 @@ int ioperm(unsigned long from, unsigned long num, int turn_on) { if (root) { return(real_ioperm(from, num, turn_on)); } + if (from == 0 && num == 1024 && turn_on == 1) { + /* we want xf86EnableIO to fail */ + if (debug) fprintf(stderr, "IOPERM: setting ENODEV.\n"); + *__errno_location() = ENODEV; + return -1; + } return 0; } @@ -1627,7 +1717,7 @@ int iopl(int level) { return 0; } -#if 0 +#ifdef INTERPOSE_GETUID /* * we got things to work w/o pretending to be root. |