On Thu, Jun 23, 2011 at 11:48:22AM -0700, Jason Gerecke wrote: > On Wed, Jun 22, 2011 at 6:27 PM, Peter Hutterer > <peter.hutte...@who-t.net> wrote: > > The NVIDIA binary driver doesn't support RandR 1.2 but it does support > > Xinerama. Test for RandR and then fall back to Xinerama if we need to. > > > > User commands: > > xsetwacom set "device name" MapToOutput HEAD-0 > > xsetwacom set "device name" MapToOutput HEAD-1 > > > > Signed-off-by: Peter Hutterer <peter.hutte...@who-t.net> > > --- > > Changes to v1: > > - rename set_output_twinview to set_output_xinerama > > - test for RandR first, fall back to Xinerama if it fails. Only test for > > NVidia for tracing/debugging purposes > > - use convert_value_from_user for arg parsing > > > > configure.ac | 2 +- > > man/xsetwacom.man | 3 +- > > tools/xsetwacom.c | 91 > > ++++++++++++++++++++++++++++++++++++++++++---------- > > 3 files changed, 76 insertions(+), 20 deletions(-) > > > > diff --git a/configure.ac b/configure.ac > > index 408e75f..c151e54 100644 > > --- a/configure.ac > > +++ b/configure.ac > > @@ -53,7 +53,7 @@ AC_CHECK_LIB([m], [rint]) > > PKG_CHECK_MODULES(XORG, [xorg-server >= 1.7.0] xproto xext kbproto > > inputproto randrproto) > > > > # Obtain compiler/linker options for the xsetwacom tool > > -PKG_CHECK_MODULES(X11, x11 xi xrandr) > > +PKG_CHECK_MODULES(X11, x11 xi xrandr xinerama) > > > > # Obtain compiler/linker options for libudev used by ISDV4 code > > PKG_CHECK_MODULES(UDEV, libudev) > > diff --git a/man/xsetwacom.man b/man/xsetwacom.man > > index 3a5fa40..564e1d0 100644 > > --- a/man/xsetwacom.man > > +++ b/man/xsetwacom.man > > @@ -126,7 +126,8 @@ outputs may be obtained with the xrandr tool. The > > output mapping > > configuration is a onetime setting and does not track output > > reconfigurations; the command needs to be re-run whenever the output > > configuration changes. When used with tablet rotation, the tablet must be > > -rotated before it is mapped to the new screen. > > +rotated before it is mapped to the new screen. When running the NVIDIA > > +binary driver, the output names are "HEAD-0" and "HEAD-1". > > This parameter is write-only and cannot be queried. > > .TP > > \fBMode\fR Absolute|Relative > > diff --git a/tools/xsetwacom.c b/tools/xsetwacom.c > > index c0cf707..9f75e83 100644 > > --- a/tools/xsetwacom.c > > +++ b/tools/xsetwacom.c > > @@ -37,6 +37,7 @@ > > #include <X11/Xatom.h> > > #include <X11/extensions/XInput.h> > > #include <X11/extensions/Xrandr.h> > > +#include <X11/extensions/Xinerama.h> > > #include <X11/XKBlib.h> > > > > #define TRACE(...) \ > > @@ -57,6 +58,7 @@ enum prop_flags { > > PROP_FLAG_READONLY = 2, > > PROP_FLAG_WRITEONLY = 4, > > PROP_FLAG_INVERTED = 8, /* only valid with PROP_FLAG_BOOLEAN */ > > + PROP_FLAG_OUTPUT = 16, > > }; > > > > > > @@ -416,7 +418,7 @@ static param_t parameters[] = > > .desc = "Map the device to the given output. ", > > .set_func = set_output, > > .arg_count = 1, > > - .prop_flags = PROP_FLAG_WRITEONLY > > + .prop_flags = PROP_FLAG_WRITEONLY | PROP_FLAG_OUTPUT, > > }, > > { > > .name = "all", > > @@ -1483,7 +1485,16 @@ static Bool convert_value_from_user(const param_t > > *param, const char *value, int > > if (param->prop_flags & PROP_FLAG_INVERTED) > > *return_value = !(*return_value); > > } > > - else > > + else if (param->prop_flags & PROP_FLAG_OUTPUT) > > + { > > + const char *prefix = "HEAD-"; > > + /* We currently support HEAD-X, where X is 0-9 */ > > + if (strlen(value) != strlen(prefix) + 1 || > > + strncasecmp(value, prefix, strlen(prefix)) != 0) > > + return False; > > + > > + *return_value = value[strlen(prefix)] - '0'; > > + } else > > { > > char *end; > > long conversion = strtol(value, &end, 10); > > @@ -2000,7 +2011,6 @@ static void _set_matrix(Display *dpy, XDevice *dev, > > > > static void set_output_xrandr(Display *dpy, XDevice *dev, param_t *param, > > int argc, char **argv) > > { > > - int min, maj; > > int i, found = 0; > > char *output_name; > > XRRScreenResources *res; > > @@ -2009,20 +2019,6 @@ static void set_output_xrandr(Display *dpy, XDevice > > *dev, param_t *param, int ar > > > > output_name = argv[0]; > > > > - if (!XRRQueryExtension(dpy, &maj, &min)) /* using min/maj as dummy > > */ > > - { > > - fprintf(stderr, "Server does not support RandR"); > > - return; > > - } > > - > > - if (!XRRQueryVersion(dpy, &maj, &min) || > > - (maj * 1000 + min) < 1002) > > - { > > - fprintf(stderr, "Server does not support RandR 1.2"); > > - return; > > - } > > - > > - > > res = XRRGetScreenResources(dpy, DefaultRootWindow(dpy)); > > > > for (i = 0; i < res->noutput && !found; i++) > > @@ -2058,8 +2054,58 @@ static void set_output_xrandr(Display *dpy, XDevice > > *dev, param_t *param, int ar > > XRRFreeScreenResources(res); > > } > > > > +/** > > + * Adjust the transformation matrix based on the Xinerama settings. For > > + * TwinView This would better be done with libXNVCtrl but until they learn > > + * to package it properly, rely on Xinerama. Besides, libXNVCtrl isn't > > + * available on RHEL, so we'd have to do it through Xinerama there anyway. > > + */ > > +static void set_output_xinerama(Display *dpy, XDevice *dev, param_t > > *param, int argc, char **argv) > > +{ > > + int event, error; > > + XineramaScreenInfo *screens; > > + int nscreens; > > + int head; > > + > > + if (!XineramaQueryExtension(dpy, &event, &error)) > > + { > > + fprintf(stderr, "Unable to set screen mapping. Xinerama > > extension not found\n"); > > + return; > > + } > > + > > + if (!convert_value_from_user(param, argv[0], &head)) > > + { > > + fprintf(stderr, "Please specify the output name as HEAD-X," > > + "where X is the screen number\n"); > > + return; > > + } > > + > > + screens = XineramaQueryScreens(dpy, &nscreens); > > + > > + if (nscreens == 0) > > + { > > + fprintf(stderr, "Xinerama failed to query screens.\n"); > > + goto out; > > + } else if (nscreens <= head) > > + { > > + fprintf(stderr, "Found %d screens, but you requested %s.\n", > > + nscreens, argv[0]); > > + goto out; > > + } > > + > > + _set_matrix(dpy, dev, > > + screens[head].x_org, screens[head].y_org, > > + screens[head].width, screens[head].height); > > + > > +out: > > + XFree(screens); > > +} > > + > > static void set_output(Display *dpy, XDevice *dev, param_t *param, int > > argc, char **argv) > > { > > + int opcode, event, error; > > + int maj, min; > > + > > if (argc != param->arg_count) > > { > > fprintf(stderr, "'%s' requires exactly %d value(s).\n", > > param->name, > > @@ -2067,7 +2113,16 @@ static void set_output(Display *dpy, XDevice *dev, > > param_t *param, int argc, cha > > return; > > } > > > > - set_output_xrandr(dpy, dev, param, argc, argv); > > + /* Check for RandR 1.2 */ > > + if (!XQueryExtension(dpy, "RANDR", &opcode, &event, &error) || > > + !XRRQueryVersion(dpy, &maj, &min) || (maj * 1000 + min) < 1002) > > + { > > + if (XQueryExtension(dpy, "NV-CONTROL", &opcode, &event, > > &error)) > > + TRACE("Nvidia binary driver detected.\n"); > > + set_output_xinerama(dpy, dev, param, argc, argv); > > + } else { > > + set_output_xrandr(dpy, dev, param, argc, argv); > > + } > > } > > > > > > -- > > 1.7.5.4 > > > > > > Xinerama code works properly, but set_output isn't executing it. It > looks like my nVidia driver (173.14.30-3) is actually reporting the > entire desktop as a single screen through xrandr:
urgh. this seems to be a server bug that it reports the version _it_ supports, not the driver. at least with the nvidia driver not sure about others. easy enough to work around for our use-case, we can just check for NV-CONTROL first. Patch coming up in a tick. > xrandr: Failed to get size of gamma for output default > Screen 0: minimum 2880 x 1200, current 2880 x 1200, maximum 2880 x 1200 > default connected 2880x1200+0+0 0mm x 0mm > 2880x1200 50.0* > > A number of solutions exist, though I like checking > convert_value_from_user (in addition to the existing RandR checks) for > its trivial implementation and ability to allow 'HEAD-N' to override > the RandR codepath. > > That aside, > > Tested-by: Jason Gerecke <killert...@gmail.com> Thanks. Cheers, Peter ------------------------------------------------------------------------------ All the data continuously generated in your IT infrastructure contains a definitive record of customers, application performance, security threats, fraudulent activity and more. Splunk takes this data and makes sense of it. Business sense. IT sense. Common sense.. http://p.sf.net/sfu/splunk-d2d-c1 _______________________________________________ Linuxwacom-devel mailing list Linuxwacom-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/linuxwacom-devel