xserver: Branch 'master' - 8 commits

Peter Hutterer whot at kemper.freedesktop.org
Mon Jul 13 18:46:24 PDT 2009


 Makefile.am                             |    3 
 configure.ac                            |    1 
 test/Makefile.am                        |    4 
 test/xi2/Makefile.am                    |   37 +++
 test/xi2/protocol-common.c              |  132 +++++++++++++
 test/xi2/protocol-common.h              |  143 ++++++++++++++
 test/xi2/protocol-xigetclientpointer.c  |  169 ++++++++++++++++
 test/xi2/protocol-xigetselectedevents.c |  241 ++++++++++++++++++++++++
 test/xi2/protocol-xiquerydevice.c       |  316 +++++++++++++++++++++++++++++++
 test/xi2/protocol-xiqueryversion.c      |  186 ++++++++++++++++++
 test/xi2/protocol-xiselectevents.c      |  321 ++++++++++++++++++++++++++++++++
 test/xi2/protocol-xisetclientpointer.c  |  149 ++++++++++++++
 12 files changed, 1698 insertions(+), 4 deletions(-)

New commits:
commit cc575a3ba4a52265e410b325c2291fe900a54f33
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:38:46 2009 +1000

    test: add tests for ProcXIGetClientPointer.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
index ad2d4a2..c565442 100644
--- a/test/xi2/Makefile.am
+++ b/test/xi2/Makefile.am
@@ -4,7 +4,8 @@ check_PROGRAMS =  \
 	protocol-xiquerydevice \
 	protocol-xiselectevents \
 	protocol-xigetselectedevents \
-        protocol-xisetclientpointer
+        protocol-xisetclientpointer \
+        protocol-xigetclientpointer
 
 TESTS=$(check_PROGRAMS)
 
@@ -18,16 +19,19 @@ protocol_xiquerydevice_LDADD=$(TEST_LDADD)
 protocol_xiselectevents_LDADD=$(TEST_LDADD)
 protocol_xigetselectedevents_LDADD=$(TEST_LDADD)
 protocol_xisetclientpointer_LDADD=$(TEST_LDADD)
+protocol_xigetclientpointer_LDADD=$(TEST_LDADD)
 
 protocol_xiqueryversion_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiquerydevice_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiselectevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,dixLookupWindow -Wl,-wrap,XISetEventMask
 protocol_xigetselectedevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient -Wl,-wrap,dixLookupWindow -Wl,-wrap,AddResource
 protocol_xisetclientpointer_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,dixLookupClient
+protocol_xigetclientpointer_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient -Wl,-wrap,dixLookupClient
 
 protocol_xiqueryversion_SOURCES=$(COMMON_SOURCES) protocol-xiqueryversion.c
 protocol_xiquerydevice_SOURCES=$(COMMON_SOURCES) protocol-xiquerydevice.c
 protocol_xiselectevents_SOURCES=$(COMMON_SOURCES) protocol-xiselectevents.c
 protocol_xigetselectedevents_SOURCES=$(COMMON_SOURCES) protocol-xigetselectedevents.c
 protocol_xisetclientpointer_SOURCES=$(COMMON_SOURCES) protocol-xisetclientpointer.c
+protocol_xigetclientpointer_SOURCES=$(COMMON_SOURCES) protocol-xigetclientpointer.c
 endif
diff --git a/test/xi2/protocol-xigetclientpointer.c b/test/xi2/protocol-xigetclientpointer.c
new file mode 100644
index 0000000..d4923f3
--- /dev/null
+++ b/test/xi2/protocol-xigetclientpointer.c
@@ -0,0 +1,169 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+/*
+ * Protocol testing for XIGetClientPointer request.
+ */
+#include <stdint.h>
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/XI2proto.h>
+#include "inputstr.h"
+#include "windowstr.h"
+#include "scrnintstr.h"
+#include "xigetclientpointer.h"
+#include "exevents.h"
+
+#include "protocol-common.h"
+#include <glib.h>
+
+#define FAKE_WINDOW_ID  12345
+
+struct {
+    int cp_is_set;
+    DeviceIntPtr dev;
+    int win;
+} test_data;
+
+static ClientRec client_window;
+static ClientRec client_request;
+
+int __wrap_dixLookupClient(ClientPtr *pClient, XID rid, ClientPtr client, Mask access)
+{
+    if (rid == ROOT_WINDOW_ID)
+        return BadWindow;
+
+    if (rid == CLIENT_WINDOW_ID)
+    {
+        *pClient = &client_window;
+        return Success;
+    }
+
+    return __real_dixLookupClient(pClient, rid, client, access);
+}
+
+
+static void reply_XIGetClientPointer(ClientPtr client, int len, char *data, void *userdata)
+{
+    xXIGetClientPointerReply *rep = (xXIGetClientPointerReply*)data;
+
+    if (client->swapped)
+    {
+        char n;
+        swapl(&rep->length, n);
+        swaps(&rep->sequenceNumber, n);
+        swaps(&rep->deviceid, n);
+    }
+
+    reply_check_defaults(rep, len, XIGetClientPointer);
+
+    g_assert(rep->set == test_data.cp_is_set);
+    if (rep->set)
+        g_assert(rep->deviceid == test_data.dev->id);
+}
+
+static void request_XIGetClientPointer(ClientPtr client, xXIGetClientPointerReq* req, int error)
+{
+    char n;
+    int rc;
+
+    test_data.win = req->win;
+
+    rc = ProcXIGetClientPointer(&client_request);
+    g_assert(rc == error);
+
+    if (rc == BadWindow)
+        g_assert(client_request.errorValue == req->win);
+
+    client_request.swapped = TRUE;
+    swapl(&req->win, n);
+    swaps(&req->length, n);
+    rc = SProcXIGetClientPointer(&client_request);
+    g_assert(rc == error);
+
+    if (rc == BadWindow)
+        g_assert(client_request.errorValue == req->win);
+
+}
+
+static void test_XIGetClientPointer(void)
+{
+    xXIGetClientPointerReq request;
+
+    request_init(&request, XIGetClientPointer);
+
+    request.win = CLIENT_WINDOW_ID;
+
+
+    reply_handler = reply_XIGetClientPointer;
+
+    client_request = init_client(request.length, &request);
+
+    g_test_message("Testing invalid window 12345");
+    request.win = FAKE_WINDOW_ID;
+    request_XIGetClientPointer(&client_request, &request, BadWindow);
+
+    test_data.cp_is_set = FALSE;
+
+    g_test_message("Testing window None, unset ClientPointer.");
+    request.win = None;
+    request_XIGetClientPointer(&client_request, &request, Success);
+
+    g_test_message("Testing valid window, unset ClientPointer.");
+    request.win = CLIENT_WINDOW_ID;
+    request_XIGetClientPointer(&client_request, &request, Success);
+
+    g_test_message("Testing valid window, set ClientPointer.");
+    client_window.clientPtr = devices.vcp;
+    test_data.dev = devices.vcp;
+    test_data.cp_is_set = TRUE;
+    request.win = CLIENT_WINDOW_ID;
+    request_XIGetClientPointer(&client_request, &request, Success);
+
+    client_window.clientPtr = NULL;
+
+    g_test_message("Testing window None, set ClientPointer.");
+    client_request.clientPtr = devices.vcp;
+    test_data.dev = devices.vcp;
+    test_data.cp_is_set = TRUE;
+    request.win = None;
+    request_XIGetClientPointer(&client_request, &request, Success);
+}
+
+int main(int argc, char** argv)
+{
+    g_test_init(&argc, &argv,NULL);
+    g_test_bug_base("https://bugzilla.freedesktop.org/show_bug.cgi?id=");
+
+    init_simple();
+    client_window = init_client(0, NULL);
+
+
+    g_test_add_func("/xi2/protocol/XIGetClientPointer", test_XIGetClientPointer);
+
+    return g_test_run();
+}
commit 92b0065a19dcde50494d2528e19a4ee76723b3da
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:38:00 2009 +1000

    test: add ProcXISetClientPointer tests.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
index 6a2618b..ad2d4a2 100644
--- a/test/xi2/Makefile.am
+++ b/test/xi2/Makefile.am
@@ -3,7 +3,8 @@ check_PROGRAMS =  \
 	protocol-xiqueryversion \
 	protocol-xiquerydevice \
 	protocol-xiselectevents \
-	protocol-xigetselectedevents
+	protocol-xigetselectedevents \
+        protocol-xisetclientpointer
 
 TESTS=$(check_PROGRAMS)
 
@@ -16,14 +17,17 @@ protocol_xiqueryversion_LDADD=$(TEST_LDADD)
 protocol_xiquerydevice_LDADD=$(TEST_LDADD)
 protocol_xiselectevents_LDADD=$(TEST_LDADD)
 protocol_xigetselectedevents_LDADD=$(TEST_LDADD)
+protocol_xisetclientpointer_LDADD=$(TEST_LDADD)
 
 protocol_xiqueryversion_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiquerydevice_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiselectevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,dixLookupWindow -Wl,-wrap,XISetEventMask
 protocol_xigetselectedevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient -Wl,-wrap,dixLookupWindow -Wl,-wrap,AddResource
+protocol_xisetclientpointer_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,dixLookupClient
 
 protocol_xiqueryversion_SOURCES=$(COMMON_SOURCES) protocol-xiqueryversion.c
 protocol_xiquerydevice_SOURCES=$(COMMON_SOURCES) protocol-xiquerydevice.c
 protocol_xiselectevents_SOURCES=$(COMMON_SOURCES) protocol-xiselectevents.c
 protocol_xigetselectedevents_SOURCES=$(COMMON_SOURCES) protocol-xigetselectedevents.c
+protocol_xisetclientpointer_SOURCES=$(COMMON_SOURCES) protocol-xisetclientpointer.c
 endif
diff --git a/test/xi2/protocol-xisetclientpointer.c b/test/xi2/protocol-xisetclientpointer.c
new file mode 100644
index 0000000..e72d016
--- /dev/null
+++ b/test/xi2/protocol-xisetclientpointer.c
@@ -0,0 +1,149 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+/*
+ * Protocol testing for XISetClientPointer request.
+ *
+ * Tests include:
+ * BadDevice of all devices except master pointers.
+ * Success for a valid window.
+ * Success for window None.
+ * BadWindow for invalid windows.
+ */
+#include <stdint.h>
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/XI2proto.h>
+#include "inputstr.h"
+#include "windowstr.h"
+#include "extinit.h" /* for XInputExtensionInit */
+#include "scrnintstr.h"
+#include "xisetclientpointer.h"
+#include "exevents.h"
+
+#include "protocol-common.h"
+#include <glib.h>
+
+static ClientRec client_window;
+static ClientRec client_request;
+
+int __wrap_dixLookupClient(ClientPtr *pClient, XID rid, ClientPtr client, Mask access)
+{
+    if (rid == ROOT_WINDOW_ID)
+        return BadWindow;
+
+    if (rid == CLIENT_WINDOW_ID)
+    {
+        *pClient = &client_window;
+        return Success;
+    }
+
+    return __real_dixLookupClient(pClient, rid, client, access);
+}
+
+static void request_XISetClientPointer(xXISetClientPointerReq* req, int error)
+{
+    char n;
+    int rc;
+    client_request = init_client(req->length, req);
+
+    rc = ProcXISetClientPointer(&client_request);
+    g_assert(rc == error);
+
+    if (rc == BadDevice)
+        g_assert(client_request.errorValue == req->deviceid);
+
+    client_request.swapped = TRUE;
+    swapl(&req->win, n);
+    swaps(&req->length, n);
+    swaps(&req->deviceid, n);
+    rc = SProcXISetClientPointer(&client_request);
+    g_assert(rc == error);
+
+    if (rc == BadDevice)
+        g_assert(client_request.errorValue == req->deviceid);
+
+}
+
+static void test_XISetClientPointer(void)
+{
+    int i;
+    xXISetClientPointerReq request;
+
+    request_init(&request, XISetClientPointer);
+
+    request.win = CLIENT_WINDOW_ID;
+
+    g_test_message("Testing BadDevice error for XIAllDevices and XIMasterDevices.");
+    request.deviceid = XIAllDevices;
+    request_XISetClientPointer(&request, BadDevice);
+
+    request.deviceid = XIAllMasterDevices;
+    request_XISetClientPointer(&request, BadDevice);
+
+    g_test_message("Testing Success for VCP and VCK.");
+    request.deviceid = devices.vcp->id; /* 2 */
+    request_XISetClientPointer(&request, Success);
+    g_assert(client_window.clientPtr->id == 2);
+
+    request.deviceid = devices.vck->id; /* 3 */
+    request_XISetClientPointer(&request, Success);
+    g_assert(client_window.clientPtr->id == 2);
+
+    g_test_message("Testing BadDevice error for all other devices.");
+    for (i = 4; i <= 0xFFFF; i++)
+    {
+        request.deviceid = i;
+        request_XISetClientPointer(&request, BadDevice);
+    }
+
+    g_test_message("Testing window None");
+    request.win = None;
+    request.deviceid = devices.vcp->id; /* 2 */
+    request_XISetClientPointer(&request, Success);
+    g_assert(client_request.clientPtr->id == 2);
+
+    g_test_message("Testing invalid window 12345");
+    request.win = 12345;
+    request.deviceid = devices.vcp->id;
+    request_XISetClientPointer(&request, BadWindow);
+
+}
+
+
+int main(int argc, char** argv)
+{
+    g_test_init(&argc, &argv,NULL);
+    g_test_bug_base("https://bugzilla.freedesktop.org/show_bug.cgi?id=");
+
+    init_simple();
+    client_window = init_client(0, NULL);
+
+    g_test_add_func("/xi2/protocol/XISetClientPointer", test_XISetClientPointer);
+
+    return g_test_run();
+}
commit 019bc9d70c5b3beb69ca20b6bca3551e00415992
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:37:17 2009 +1000

    test: add ProcXIGetSelectedEvents tests.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
index 8699299..6a2618b 100644
--- a/test/xi2/Makefile.am
+++ b/test/xi2/Makefile.am
@@ -2,7 +2,8 @@ if UNITTESTS
 check_PROGRAMS =  \
 	protocol-xiqueryversion \
 	protocol-xiquerydevice \
-	protocol-xiselectevents
+	protocol-xiselectevents \
+	protocol-xigetselectedevents
 
 TESTS=$(check_PROGRAMS)
 
@@ -14,12 +15,15 @@ COMMON_SOURCES=protocol-common.h protocol-common.c
 protocol_xiqueryversion_LDADD=$(TEST_LDADD)
 protocol_xiquerydevice_LDADD=$(TEST_LDADD)
 protocol_xiselectevents_LDADD=$(TEST_LDADD)
+protocol_xigetselectedevents_LDADD=$(TEST_LDADD)
 
 protocol_xiqueryversion_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiquerydevice_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiselectevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,dixLookupWindow -Wl,-wrap,XISetEventMask
+protocol_xigetselectedevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient -Wl,-wrap,dixLookupWindow -Wl,-wrap,AddResource
 
 protocol_xiqueryversion_SOURCES=$(COMMON_SOURCES) protocol-xiqueryversion.c
 protocol_xiquerydevice_SOURCES=$(COMMON_SOURCES) protocol-xiquerydevice.c
 protocol_xiselectevents_SOURCES=$(COMMON_SOURCES) protocol-xiselectevents.c
+protocol_xigetselectedevents_SOURCES=$(COMMON_SOURCES) protocol-xigetselectedevents.c
 endif
diff --git a/test/xi2/protocol-xigetselectedevents.c b/test/xi2/protocol-xigetselectedevents.c
new file mode 100644
index 0000000..97aae15
--- /dev/null
+++ b/test/xi2/protocol-xigetselectedevents.c
@@ -0,0 +1,241 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+/*
+ * Protocol testing for XIGetSelectedEvents request.
+ *
+ * Tests include:
+ * BadWindow on wrong window.
+ * Zero-length masks if no masks are set.
+ * Valid masks for valid devices.
+ * Masks set on non-existent devices are not returned.
+ *
+ * Note that this test is not connected to the XISelectEvents request.
+ */
+#include <stdint.h>
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/XI2proto.h>
+#include "inputstr.h"
+#include "windowstr.h"
+#include "extinit.h" /* for XInputExtensionInit */
+#include "scrnintstr.h"
+#include "xiselectev.h"
+#include "exevents.h"
+
+#include "protocol-common.h"
+#include <glib.h>
+
+static void reply_XIGetSelectedEvents(ClientPtr client, int len, char *data, void *userdata);
+static void reply_XIGetSelectedEvents_data(ClientPtr client, int len, char *data, void *userdata);
+
+
+struct {
+    int num_masks_expected;
+    unsigned char mask[MAXDEVICES][XI2LASTEVENT]; /* intentionally bigger */
+    int mask_len;
+} test_data;
+
+/* dixLookupWindow requires a lot of setup not necessary for this test.
+ * Simple wrapper that returns either one of the fake root window or the
+ * fake client window. If the requested ID is neither of those wanted,
+ * return whatever the real dixLookupWindow does.
+ */
+int __wrap_dixLookupWindow(WindowPtr *win, XID id, ClientPtr client, Mask access)
+{
+    if (id == root.drawable.id)
+    {
+        *win = &root;
+        return Success;
+    } else if (id == window.drawable.id)
+    {
+        *win = &window;
+        return Success;
+    }
+
+    return __real_dixLookupWindow(win, id, client, access);
+}
+
+/* AddResource is called from XISetSEventMask, we don't need this */
+Bool __wrap_AddResource(XID id, RESTYPE type, pointer value)
+{
+    return TRUE;
+}
+
+static void reply_XIGetSelectedEvents(ClientPtr client, int len, char *data, void *userdata)
+{
+    xXIGetSelectedEventsReply *rep = (xXIGetSelectedEventsReply*)data;
+
+    if (client->swapped)
+    {
+        char n;
+        swapl(&rep->length, n);
+        swaps(&rep->sequenceNumber, n);
+        swaps(&rep->num_masks, n);
+    }
+
+    reply_check_defaults(rep, len, XIGetSelectedEvents);
+
+    g_assert(rep->num_masks == test_data.num_masks_expected);
+
+    reply_handler = reply_XIGetSelectedEvents_data;
+}
+
+static void reply_XIGetSelectedEvents_data(ClientPtr client, int len, char *data, void *userdata)
+{
+    int i;
+    xXIEventMask *mask;
+    unsigned char *bitmask;
+
+    mask = (xXIEventMask*)data;
+    for (i = 0; i < test_data.num_masks_expected; i++)
+    {
+        if (client->swapped)
+        {
+            char n;
+            swaps(&mask->deviceid, n);
+            swaps(&mask->mask_len, n);
+        }
+
+        g_assert(mask->deviceid < 6);
+        g_assert(mask->mask_len <= (((XI2LASTEVENT + 8)/8) + 3)/4) ;
+
+        bitmask = (unsigned char*)&mask[1];
+        g_assert(memcmp(bitmask,
+                    test_data.mask[mask->deviceid],
+                    mask->mask_len * 4) == 0);
+
+        mask = (xXIEventMask*)((char*)mask + mask->mask_len * 4 + sizeof(xXIEventMask));
+    }
+
+
+}
+
+static void request_XIGetSelectedEvents(xXIGetSelectedEventsReq* req, int error)
+{
+    char n;
+    int rc;
+    ClientRec client;
+    client = init_client(req->length, req);
+
+    reply_handler = reply_XIGetSelectedEvents;
+
+    rc = ProcXIGetSelectedEvents(&client);
+    g_assert(rc == error);
+
+    reply_handler = reply_XIGetSelectedEvents;
+    client.swapped = TRUE;
+    swapl(&req->win, n);
+    swaps(&req->length, n);
+    rc = SProcXIGetSelectedEvents(&client);
+    g_assert(rc == error);
+}
+
+static void test_XIGetSelectedEvents(void)
+{
+    int i, j;
+    xXIGetSelectedEventsReq request;
+    ClientRec client = init_client(0, NULL);
+    unsigned char *mask;
+    DeviceIntRec dev;
+
+    request_init(&request, XIGetSelectedEvents);
+
+    g_test_message("Testing for BadWindow on invalid window.");
+    request.win = None;
+    request_XIGetSelectedEvents(&request, BadWindow);
+
+    g_test_message("Testing for zero-length (unset) masks.");
+    /* No masks set yet */
+    test_data.num_masks_expected = 0;
+    request.win = ROOT_WINDOW_ID;
+    request_XIGetSelectedEvents(&request, Success);
+
+    request.win = CLIENT_WINDOW_ID;
+    request_XIGetSelectedEvents(&request, Success);
+
+    memset(test_data.mask, 0,
+           sizeof(test_data.mask));
+
+    g_test_message("Testing for valid masks");
+    memset(&dev, 0, sizeof(dev)); /* dev->id is enough for XISetEventMask */
+    request.win = ROOT_WINDOW_ID;
+
+    /* devices 6 - MAXDEVICES don't exist, they mustn't be included in the
+     * reply even if a mask is set */
+    for (j = 0; j < MAXDEVICES; j++)
+    {
+        test_data.num_masks_expected = min(j + 1, devices.num_devices + 2);
+        dev.id = j;
+        mask = test_data.mask[j];
+        /* bits one-by-one */
+        for (i = 0; i < XI2LASTEVENT; i++)
+        {
+            SetBit(mask, i);
+            XISetEventMask(&dev, &root, &client, (i + 8)/8, mask);
+            request_XIGetSelectedEvents(&request, Success);
+            ClearBit(mask, i);
+        }
+
+        /* all valid mask bits */
+        for (i = 0; i < XI2LASTEVENT; i++)
+        {
+            SetBit(mask, i);
+            XISetEventMask(&dev, &root, &client, (i + 8)/8, mask);
+            request_XIGetSelectedEvents(&request, Success);
+        }
+    }
+
+    g_test_message("Testing removing all masks");
+    /* Unset all masks one-by-one */
+    for (j = MAXDEVICES - 1; j >= 0; j--)
+    {
+        if (j < devices.num_devices + 2)
+            test_data.num_masks_expected--;
+
+        mask = test_data.mask[j];
+        memset(mask, 0, XI2LASTEVENT);
+
+        dev.id = j;
+        XISetEventMask(&dev, &root, &client, 0, NULL);
+
+        request_XIGetSelectedEvents(&request, Success);
+    }
+}
+
+int main(int argc, char** argv)
+{
+    g_test_init(&argc, &argv,NULL);
+    g_test_bug_base("https://bugzilla.freedesktop.org/show_bug.cgi?id=");
+
+    init_simple();
+
+    g_test_add_func("/xi2/protocol/XIGetSelectedEvents", test_XIGetSelectedEvents);
+
+    return g_test_run();
+}
+
commit 8579d39c12b065d8e82fe75af4b254c8ad4f4ab8
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:36:22 2009 +1000

    test: add ProcXISelectEvents tests.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
index 58556cb..8699299 100644
--- a/test/xi2/Makefile.am
+++ b/test/xi2/Makefile.am
@@ -1,7 +1,8 @@
 if UNITTESTS
 check_PROGRAMS =  \
 	protocol-xiqueryversion \
-	protocol-xiquerydevice
+	protocol-xiquerydevice \
+	protocol-xiselectevents
 
 TESTS=$(check_PROGRAMS)
 
@@ -12,10 +13,13 @@ COMMON_SOURCES=protocol-common.h protocol-common.c
 
 protocol_xiqueryversion_LDADD=$(TEST_LDADD)
 protocol_xiquerydevice_LDADD=$(TEST_LDADD)
+protocol_xiselectevents_LDADD=$(TEST_LDADD)
 
 protocol_xiqueryversion_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 protocol_xiquerydevice_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
+protocol_xiselectevents_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,dixLookupWindow -Wl,-wrap,XISetEventMask
 
 protocol_xiqueryversion_SOURCES=$(COMMON_SOURCES) protocol-xiqueryversion.c
 protocol_xiquerydevice_SOURCES=$(COMMON_SOURCES) protocol-xiquerydevice.c
+protocol_xiselectevents_SOURCES=$(COMMON_SOURCES) protocol-xiselectevents.c
 endif
diff --git a/test/xi2/protocol-xiselectevents.c b/test/xi2/protocol-xiselectevents.c
new file mode 100644
index 0000000..825eeb6
--- /dev/null
+++ b/test/xi2/protocol-xiselectevents.c
@@ -0,0 +1,321 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+/*
+ * Protocol testing for XISelectEvents request.
+ *
+ * Test approach:
+ *
+ * Wrap XISetEventMask to intercept when the server tries to apply the event
+ * mask. Ensure that the mask passed in is equivalent to the one supplied by
+ * the client. Ensure that invalid devices and invalid masks return errors
+ * as appropriate.
+ *
+ * Tests included:
+ * BadValue for num_masks < 0
+ * BadWindow for invalid windows
+ * BadDevice for non-existing devices
+ * BadImplemenation for devices >= 0xFF
+ * BadValue if HierarchyChanged bit is set for devices other than
+ *          XIAllDevices
+ * BadValue for invalid mask bits
+ * Sucecss for excessive mask lengths
+ *
+ */
+
+#include <stdint.h>
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/XI2proto.h>
+#include "inputstr.h"
+#include "windowstr.h"
+#include "extinit.h" /* for XInputExtensionInit */
+#include "scrnintstr.h"
+#include "xiselectev.h"
+
+#include "protocol-common.h"
+#include <glib.h>
+
+static unsigned char *data[4096 * 16]; /* the request data buffer */
+
+void __wrap_XISetEventMask(DeviceIntPtr dev, WindowPtr win, int len, unsigned char* mask)
+{
+}
+
+/* dixLookupWindow requires a lot of setup not necessary for this test.
+ * Simple wrapper that returns either one of the fake root window or the
+ * fake client window. If the requested ID is neither of those wanted,
+ * return whatever the real dixLookupWindow does.
+ */
+int __wrap_dixLookupWindow(WindowPtr *win, XID id, ClientPtr client, Mask access)
+{
+    if (id == root.drawable.id)
+    {
+        *win = &root;
+        return Success;
+    } else if (id == window.drawable.id)
+    {
+        *win = &window;
+        return Success;
+    }
+
+    return __real_dixLookupWindow(win, id, client, access);
+}
+
+
+static void request_XISelectEvent(xXISelectEventsReq *req, int error)
+{
+    char n;
+    int i;
+    int rc;
+    ClientRec client;
+    xXIEventMask *mask, *next;
+
+    req->length = (sz_xXISelectEventsReq/4) + req->num_masks;
+    client = init_client(req->length, req);
+
+    rc = ProcXISelectEvents(&client);
+    g_assert(rc == error);
+
+    client.swapped = TRUE;
+
+    mask = (xXIEventMask*)&req[1];
+    for (i = 0; i < req->num_masks; i++)
+    {
+        next = (xXIEventMask*)((char*)mask) + mask->mask_len;
+        swaps(&mask->deviceid, n);
+        swaps(&mask->mask_len, n);
+        mask = next;
+    }
+
+    swapl(&req->win, n);
+    swaps(&req->length, n);
+    swaps(&req->num_masks, n);
+    rc = SProcXISelectEvents(&client);
+    g_assert(rc == error);
+}
+
+static void request_XISelectEvents_masks(xXISelectEventsReq *req)
+{
+    int i, j;
+    xXIEventMask *mask;
+    int nmasks = (XI_LASTEVENT + 7)/8;
+    unsigned char *bits;
+
+    mask = (xXIEventMask*)&req[1];
+    req->win = ROOT_WINDOW_ID;
+
+    /* if a clients submits more than 100 masks, consider it insane and untested */
+    for (i = 1; i <= 1000; i++)
+    {
+        req->num_masks = i;
+        mask->deviceid = XIAllDevices;
+
+        /* Test 0:
+         * mask_len is 0 -> Success
+         */
+        mask->mask_len = 0;
+        request_XISelectEvent(req, Success);
+
+        /* Test 1:
+         * mask may be larger than needed for XI_LASTEVENT.
+         * Test setting each valid mask bit, while leaving unneeded bits 0.
+         * -> Success
+         */
+        bits = (unsigned char*)&mask[1];
+        mask->mask_len = (nmasks + 3)/4 * 10;
+        memset(bits, 0, mask->mask_len * 4);
+        for (j = 0; j <= XI_LASTEVENT; j++)
+        {
+            SetBit(bits, j);
+            request_XISelectEvent(req, Success);
+            ClearBit(bits, j);
+        }
+
+        /* Test 2:
+         * mask may be larger than needed for XI_LASTEVENT.
+         * Test setting all valid mask bits, while leaving unneeded bits 0.
+         * -> Success
+         */
+        bits = (unsigned char*)&mask[1];
+        mask->mask_len = (nmasks + 3)/4 * 10;
+        memset(bits, 0, mask->mask_len * 4);
+
+        for (j = 0; j <= XI_LASTEVENT; j++)
+        {
+            SetBit(bits, j);
+            request_XISelectEvent(req, Success);
+        }
+
+        /* Test 3:
+         * mask is larger than needed for XI_LASTEVENT. If any unneeded bit
+         * is set -> BadValue
+         */
+        bits = (unsigned char*)&mask[1];
+        mask->mask_len = (nmasks + 3)/4 * 10;
+        memset(bits, 0, mask->mask_len * 4);
+
+        for (j = XI_LASTEVENT + 1; j < mask->mask_len * 4; j++)
+        {
+            SetBit(bits, j);
+            request_XISelectEvent(req, BadValue);
+            ClearBit(bits, j);
+        }
+
+        /* Test 4:
+         * Mask len is a sensible length, only valid bits are set -> Success
+         */
+        bits = (unsigned char*)&mask[1];
+        mask->mask_len = (nmasks + 3)/4;
+        memset(bits, 0, mask->mask_len * 4);
+        for (j = 0; j <= XI_LASTEVENT; j++)
+        {
+            SetBit(bits, j);
+            request_XISelectEvent(req, Success);
+        }
+
+        /* Test 5:
+         * HierarchyChanged bit is BadValue for devices other than
+         * XIAllDevices
+         */
+        bits = (unsigned char*)&mask[1];
+        mask->mask_len = (nmasks + 3)/4;
+        memset(bits, 0, mask->mask_len * 4);
+        SetBit(bits, XI_HierarchyChanged);
+        mask->deviceid = XIAllDevices;
+        request_XISelectEvent(req, Success);
+        for (j = 1; j < devices.num_devices; j++)
+        {
+            mask->deviceid = j;
+            request_XISelectEvent(req, BadValue);
+        }
+
+        /* Test 6:
+         * All bits set minus hierarchy changed bit -> Success
+         */
+        bits = (unsigned char*)&mask[1];
+        mask->mask_len = (nmasks + 3)/4;
+        memset(bits, 0, mask->mask_len * 4);
+        for (j = 0; j <= XI_LASTEVENT; j++)
+            SetBit(bits, j);
+        ClearBit(bits, XI_HierarchyChanged);
+        for (j = 1; j < 6; j++)
+        {
+            mask->deviceid = j;
+            request_XISelectEvent(req, Success);
+        }
+
+        mask = (xXIEventMask*)((char*)mask + sizeof(xXIEventMask) + mask->mask_len * 4);
+    }
+}
+
+static void test_XISelectEvents(void)
+{
+    int i;
+    xXIEventMask *mask;
+    xXISelectEventsReq *req;
+    req = (xXISelectEventsReq*)data;
+
+    request_init(req, XISelectEvents);
+
+    g_test_message("Testing for BadValue on zero-length masks");
+    /* zero masks are BadValue, regardless of the window */
+    req->num_masks = 0;
+
+    req->win = None;
+    request_XISelectEvent(req, BadValue);
+
+    req->win = ROOT_WINDOW_ID;
+    request_XISelectEvent(req, BadValue);
+
+    req->win = CLIENT_WINDOW_ID;
+    request_XISelectEvent(req, BadValue);
+
+    g_test_message("Testing for BadWindow.");
+    /* None window is BadWindow, regardless of the masks.
+     * We don't actually need to set the masks here, BadWindow must occur
+     * before checking the masks.
+     */
+    req->win = None;
+    req->num_masks = 1;
+    request_XISelectEvent(req, BadWindow);
+
+    req->num_masks = 2;
+    request_XISelectEvent(req, BadWindow);
+
+    req->num_masks = 0xFF;
+    request_XISelectEvent(req, BadWindow);
+
+    /* request size is 3, so 0xFFFC is the highest num_mask that doesn't
+     * overflow req->length */
+    req->num_masks = 0xFFFC;
+    request_XISelectEvent(req, BadWindow);
+
+    g_test_message("Triggering num_masks/length overflow");
+    /* Integer overflow - req->length can't hold that much */
+    req->num_masks = 0xFFFF;
+    request_XISelectEvent(req, BadLength);
+
+    /* testing various device ids */
+    req->win = ROOT_WINDOW_ID;
+    req->num_masks = 1;
+
+    g_test_message("Testing existing device ids.");
+    for (i = 0; i < 6; i++)
+    {
+        mask = (xXIEventMask*)&req[1];
+        mask->deviceid = i;
+        mask->mask_len = 1;
+        request_XISelectEvent(req, Success);
+    }
+
+    g_test_message("Testing non-existing device ids.");
+    for (i = 6; i <= 0xFFFF; i++)
+    {
+        req->win = ROOT_WINDOW_ID;
+        req->num_masks = 1;
+        mask = (xXIEventMask*)&req[1];
+        mask->deviceid = i;
+        mask->mask_len = 1;
+        request_XISelectEvent(req, BadDevice);
+    }
+
+    request_XISelectEvents_masks(req);
+}
+
+int main(int argc, char** argv)
+{
+    g_test_init(&argc, &argv,NULL);
+    g_test_bug_base("https://bugzilla.freedesktop.org/show_bug.cgi?id=");
+
+    init_simple();
+
+    g_test_add_func("/xi2/protocol/XISelectEvents", test_XISelectEvents);
+
+    return g_test_run();
+}
+
commit 60b7a7990003a22be5cc26ebe4d8d2d0803b97de
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:33:22 2009 +1000

    test: add ProcXIQueryDevice tests.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
index e9f9a06..58556cb 100644
--- a/test/xi2/Makefile.am
+++ b/test/xi2/Makefile.am
@@ -1,6 +1,7 @@
 if UNITTESTS
 check_PROGRAMS =  \
-	protocol-xiqueryversion
+	protocol-xiqueryversion \
+	protocol-xiquerydevice
 
 TESTS=$(check_PROGRAMS)
 
@@ -10,8 +11,11 @@ TEST_LDADD=../libxservertest.la $(XORG_SYS_LIBS) $(XSERVER_SYS_LIBS) $(GLIB_LIBS
 COMMON_SOURCES=protocol-common.h protocol-common.c
 
 protocol_xiqueryversion_LDADD=$(TEST_LDADD)
+protocol_xiquerydevice_LDADD=$(TEST_LDADD)
 
 protocol_xiqueryversion_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
+protocol_xiquerydevice_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
 
 protocol_xiqueryversion_SOURCES=$(COMMON_SOURCES) protocol-xiqueryversion.c
+protocol_xiquerydevice_SOURCES=$(COMMON_SOURCES) protocol-xiquerydevice.c
 endif
diff --git a/test/xi2/protocol-xiquerydevice.c b/test/xi2/protocol-xiquerydevice.c
new file mode 100644
index 0000000..508fc4d
--- /dev/null
+++ b/test/xi2/protocol-xiquerydevice.c
@@ -0,0 +1,316 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+#include <stdint.h>
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/XI2proto.h>
+#include <X11/Xatom.h>
+#include "inputstr.h"
+#include "extinit.h"
+#include "scrnintstr.h"
+#include "xkbsrv.h"
+
+#include "xiquerydevice.h"
+
+#include "protocol-common.h"
+#include <glib.h>
+/*
+ * Protocol testing for XIQueryDevice request and reply.
+ *
+ * Test approach:
+ * Wrap WriteToClient to intercept server's reply. ProcXIQueryDevice returns
+ * data in two batches, once for the request, once for the trailing data
+ * with the device information.
+ * Repeatedly test with varying deviceids and check against data in reply.
+ */
+
+struct test_data {
+    int which_device;
+    int num_devices_in_reply;
+};
+
+static void reply_XIQueryDevice_data(ClientPtr client, int len, char *data, void *userdata);
+static void reply_XIQueryDevice(ClientPtr client, int len, char* data, void *userdata);
+
+/* reply handling for the first bytes that constitute the reply */
+static void reply_XIQueryDevice(ClientPtr client, int len, char* data, void *userdata)
+{
+    xXIQueryDeviceReply *rep = (xXIQueryDeviceReply*)data;
+    struct test_data *querydata = (struct test_data*)userdata;
+
+    if (client->swapped)
+    {
+        char n;
+        swapl(&rep->length, n);
+        swaps(&rep->sequenceNumber, n);
+        swaps(&rep->num_devices, n);
+    }
+
+    reply_check_defaults(rep, len, XIQueryDevice);
+
+    if (querydata->which_device == XIAllDevices)
+        g_assert(rep->num_devices == devices.num_devices);
+    else if (querydata->which_device == XIAllMasterDevices)
+        g_assert(rep->num_devices == devices.num_master_devices);
+    else
+        g_assert(rep->num_devices == 1);
+
+    querydata->num_devices_in_reply = rep->num_devices;
+    reply_handler = reply_XIQueryDevice_data;
+}
+
+/* reply handling for the trailing bytes that constitute the device info */
+static void reply_XIQueryDevice_data(ClientPtr client, int len, char *data, void *userdata)
+{
+    char n;
+    int i, j;
+    struct test_data *querydata = (struct test_data*)userdata;
+
+    DeviceIntPtr dev;
+    xXIDeviceInfo *info = (xXIDeviceInfo*)data;
+    xXIAnyInfo *any;
+
+    for (i = 0; i < querydata->num_devices_in_reply; i++)
+    {
+        if (client->swapped)
+        {
+            swaps(&info->deviceid, n);
+            swaps(&info->attachment, n);
+            swaps(&info->use, n);
+            swaps(&info->num_classes, n);
+            swaps(&info->name_len, n);
+        }
+
+        if (querydata->which_device > XIAllMasterDevices)
+            g_assert(info->deviceid == querydata->which_device);
+
+        g_assert(info->deviceid >=  2); /* 0 and 1 is reserved */
+
+
+        switch(info->deviceid)
+        {
+            case 2:  /* VCP */
+                dev = devices.vcp;
+                g_assert(info->use == XIMasterPointer);
+                g_assert(info->attachment == devices.vck->id);
+                g_assert(info->num_classes == 3); /* 2 axes + button */
+                break;
+            case 3:  /* VCK */
+                dev = devices.vck;
+                g_assert(info->use == XIMasterKeyboard);
+                g_assert(info->attachment == devices.vcp->id);
+                g_assert(info->num_classes == 1);
+                break;
+            case 4:  /* mouse */
+                dev = devices.mouse;
+                g_assert(info->use == XISlavePointer);
+                g_assert(info->attachment == devices.vcp->id);
+                g_assert(info->num_classes == 3); /* 2 axes + button */
+                break;
+            case 5:  /* keyboard */
+                dev = devices.kbd;
+                g_assert(info->use == XISlaveKeyboard);
+                g_assert(info->attachment == devices.vck->id);
+                g_assert(info->num_classes == 1);
+                break;
+
+            default:
+                /* We shouldn't get here */
+                g_assert(0);
+                break;
+        }
+        g_assert(info->enabled == dev->enabled);
+        g_assert(info->name_len == strlen(dev->name));
+        g_assert(strncmp((char*)&info[1], dev->name, info->name_len) == 0);
+
+        any = (xXIAnyInfo*)((char*)&info[1] + ((info->name_len + 3)/4) * 4);
+        for (j = 0; j < info->num_classes; j++)
+        {
+            if (client->swapped)
+            {
+                swaps(&any->type, n);
+                swaps(&any->length, n);
+                swaps(&any->sourceid, n);
+            }
+
+            switch(info->deviceid)
+            {
+                case 3: /* VCK and kbd have the same properties */
+                case 5:
+                    {
+                        int k;
+                        xXIKeyInfo *ki = (xXIKeyInfo*)any;
+                        XkbDescPtr xkb = devices.vck->key->xkbInfo->desc;
+                        uint32_t *kc;
+
+                        if (client->swapped)
+                            swaps(&ki->num_keycodes, n);
+
+                        g_assert(any->type == XIKeyClass);
+                        g_assert(ki->num_keycodes == (xkb->max_key_code - xkb->min_key_code + 1));
+                        g_assert(any->length == (2 + ki->num_keycodes));
+
+                        kc = (uint32_t*)&ki[1];
+                        for (k = 0; k < ki->num_keycodes; k++, kc++)
+                        {
+                            if (client->swapped)
+                                swapl(kc, n);
+
+                            g_assert(*kc >= xkb->min_key_code);
+                            g_assert(*kc <= xkb->max_key_code);
+                        }
+                        break;
+                    }
+                case 2: /* VCP and mouse have the same properties */
+                case 4:
+                    {
+                        g_assert(any->type == XIButtonClass ||
+                                any->type == XIValuatorClass);
+
+                        if (any->type == XIButtonClass)
+                        {
+                            int len;
+                            xXIButtonInfo *bi = (xXIButtonInfo*)any;
+
+                            if (client->swapped)
+                                swaps(&bi->num_buttons, n);
+
+                            g_assert(bi->num_buttons == devices.vcp->button->numButtons);
+
+                            len = 2 + bi->num_buttons + bytes_to_int32(bits_to_bytes(bi->num_buttons));
+                            g_assert(bi->length == len);
+                        } else if (any->type == XIValuatorClass)
+                        {
+                            xXIValuatorInfo *vi = (xXIValuatorInfo*)any;
+
+                            if (client->swapped)
+                            {
+                                swaps(&vi->number, n);
+                                swapl(&vi->label, n);
+                                swapl(&vi->min.integral, n);
+                                swapl(&vi->min.frac, n);
+                                swapl(&vi->max.integral, n);
+                                swapl(&vi->max.frac, n);
+                                swapl(&vi->resolution, n);
+                            }
+
+                            g_assert(vi->length == 11);
+                            g_assert(vi->number == 0 ||
+                                     vi->number == 1);
+                            g_assert(vi->mode == XIModeRelative);
+                            /* device was set up as relative, so standard
+                             * values here. */
+                            g_assert(vi->min.integral == -1);
+                            g_assert(vi->min.frac == 0);
+                            g_assert(vi->max.integral == -1);
+                            g_assert(vi->max.frac == 0);
+                            g_assert(vi->resolution == 0);
+                        }
+                    }
+                    break;
+            }
+            any = (xXIAnyInfo*)(((char*)any) + any->length * 4);
+        }
+
+        info = (xXIDeviceInfo*)any;
+    }
+}
+
+static void request_XIQueryDevice(struct test_data *querydata,
+                                 int deviceid, int error)
+{
+    int rc;
+    char n;
+    ClientRec client;
+    xXIQueryDeviceReq request;
+
+    request_init(&request, XIQueryDevice);
+    client = init_client(request.length, &request);
+    reply_handler = reply_XIQueryDevice;
+
+    querydata->which_device = deviceid;
+
+    request.deviceid = deviceid;
+    rc = ProcXIQueryDevice(&client);
+    g_assert(rc == error);
+
+    if (rc != Success)
+        g_assert(client.errorValue == deviceid);
+
+    reply_handler = reply_XIQueryDevice;
+
+    client.swapped = TRUE;
+    swaps(&request.length, n);
+    swaps(&request.deviceid, n);
+    rc = SProcXIQueryDevice(&client);
+    g_assert(rc == error);
+
+    if (rc != Success)
+        g_assert(client.errorValue == deviceid);
+}
+
+static void test_XIQueryDevice(void)
+{
+    int i;
+    xXIQueryDeviceReq request;
+    struct test_data data;
+
+    reply_handler = reply_XIQueryDevice;
+    userdata = &data;
+    request_init(&request, XIQueryDevice);
+
+    g_test_message("Testing XIAllDevices.");
+    request_XIQueryDevice(&data, XIAllDevices, Success);
+    g_test_message("Testing XIAllMasterDevices.");
+    request_XIQueryDevice(&data, XIAllMasterDevices, Success);
+
+    g_test_message("Testing existing device ids.");
+    for (i = 2; i < 6; i++)
+        request_XIQueryDevice(&data, i, Success);
+
+    g_test_message("Testing non-existing device ids.");
+    for (i = 6; i <= 0xFFFF; i++)
+        request_XIQueryDevice(&data, i, BadDevice);
+
+
+    reply_handler = NULL;
+
+}
+
+int main(int argc, char** argv)
+{
+    g_test_init(&argc, &argv,NULL);
+    g_test_bug_base("https://bugzilla.freedesktop.org/show_bug.cgi?id=");
+
+    init_simple();
+
+    g_test_add_func("/dix/xi2protocol/XIQueryDevice", test_XIQueryDevice);
+
+    return g_test_run();
+}
+
commit 441c91be05912e2665cc1d3ee72fb70dcd32e7a2
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:32:15 2009 +1000

    test: Add ProcXIQueryVersion tests.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
index 0185c31..e9f9a06 100644
--- a/test/xi2/Makefile.am
+++ b/test/xi2/Makefile.am
@@ -1,6 +1,17 @@
 if UNITTESTS
+check_PROGRAMS =  \
+	protocol-xiqueryversion
+
+TESTS=$(check_PROGRAMS)
+
 AM_CFLAGS = $(DIX_CFLAGS) $(GLIB_CFLAGS) @XORG_CFLAGS@
 INCLUDES = @XORG_INCS@
 TEST_LDADD=../libxservertest.la $(XORG_SYS_LIBS) $(XSERVER_SYS_LIBS) $(GLIB_LIBS)
 COMMON_SOURCES=protocol-common.h protocol-common.c
+
+protocol_xiqueryversion_LDADD=$(TEST_LDADD)
+
+protocol_xiqueryversion_CFLAGS=$(AM_CFLAGS) -Wl,-wrap,WriteToClient
+
+protocol_xiqueryversion_SOURCES=$(COMMON_SOURCES) protocol-xiqueryversion.c
 endif
diff --git a/test/xi2/protocol-xiqueryversion.c b/test/xi2/protocol-xiqueryversion.c
new file mode 100644
index 0000000..46e62ac
--- /dev/null
+++ b/test/xi2/protocol-xiqueryversion.c
@@ -0,0 +1,186 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+/*
+ * Protocol testing for XIQueryVersion request and reply.
+ *
+ * Test approach:
+ * Wrap WriteToClient to intercept the server's reply.
+ * Repeatedly test a client/server version combination, compare version in
+ * reply with versions given. Version must be equal to either
+ * server version or client version, whichever is smaller.
+ * Client version less than 2 must return BadValue.
+ */
+
+#include <stdint.h>
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/XI2proto.h>
+#include "inputstr.h"
+#include "extinit.h" /* for XInputExtensionInit */
+#include "scrnintstr.h"
+#include "xiqueryversion.h"
+
+#include "protocol-common.h"
+#include <glib.h>
+
+extern XExtensionVersion XIVersion;
+
+struct test_data {
+    int major_client;
+    int minor_client;
+    int major_server;
+    int minor_server;
+};
+
+static void reply_XIQueryVersion(ClientPtr client, int len, char* data, void *userdata)
+{
+    xXIQueryVersionReply *rep = (xXIQueryVersionReply*)data;
+    struct test_data *versions = (struct test_data*)userdata;
+    unsigned int sver, cver, ver;
+
+    if (client->swapped)
+    {
+        char n;
+        swapl(&rep->length, n);
+        swaps(&rep->sequenceNumber, n);
+        swaps(&rep->major_version, n);
+        swaps(&rep->minor_version, n);
+    }
+
+    reply_check_defaults(rep, len, XIQueryVersion);
+
+    g_assert(rep->length == 0);
+
+    sver = versions->major_server * 1000 + versions->minor_server;
+    cver = versions->major_client * 1000 + versions->minor_client;
+    ver = rep->major_version * 1000 + rep->minor_version;
+
+    g_assert(ver >= 2000);
+    g_assert((sver > cver) ? ver == cver : ver == sver);
+}
+
+/**
+ * Run a single test with server version smaj.smin and client
+ * version cmaj.cmin. Verify that return code is equal to 'error'.
+ *
+ * Test is run normal, then for a swapped client.
+ */
+static void request_XIQueryVersion(int smaj, int smin, int cmaj, int cmin, int error)
+{
+    char n;
+    int rc;
+    struct test_data versions;
+    xXIQueryVersionReq request;
+    ClientRec client;
+
+    request_init(&request, XIQueryVersion);
+    client = init_client(request.length, &request);
+    userdata = (void*)&versions;
+
+    /* Change the server to support smaj.smin */
+    XIVersion.major_version = smaj;
+    XIVersion.minor_version = smin;
+
+    /* remember versions we send and expect */
+    versions.major_client = cmaj;
+    versions.minor_client = cmin;
+    versions.major_server = XIVersion.major_version;
+    versions.minor_server = XIVersion.minor_version;
+
+    request.major_version = versions.major_client;
+    request.minor_version = versions.minor_client;
+    rc = ProcXIQueryVersion(&client);
+    g_assert(rc == error);
+
+    client.swapped = TRUE;
+
+    swaps(&request.length, n);
+    swaps(&request.major_version, n);
+    swaps(&request.minor_version, n);
+
+    rc = SProcXIQueryVersion(&client);
+    g_assert(rc == error);
+}
+
+/* Client version less than 2.0 must return BadValue, all other combinations
+ * Success */
+static void test_XIQueryVersion(void)
+{
+    reply_handler = reply_XIQueryVersion;
+
+    g_test_message("Server version 2.0 - client versions [1..3].0");
+    /* some simple tests to catch common errors quickly */
+    request_XIQueryVersion(2, 0, 1, 0, BadValue);
+    request_XIQueryVersion(2, 0, 2, 0, Success);
+    request_XIQueryVersion(2, 0, 3, 0, Success);
+
+    g_test_message("Server version 3.0 - client versions [1..3].0");
+    request_XIQueryVersion(3, 0, 1, 0, BadValue);
+    request_XIQueryVersion(3, 0, 2, 0, Success);
+    request_XIQueryVersion(3, 0, 3, 0, Success);
+
+    g_test_message("Server version 2.0 - client versions [1..3].[1..3]");
+    request_XIQueryVersion(2, 0, 1, 1, BadValue);
+    request_XIQueryVersion(2, 0, 2, 2, Success);
+    request_XIQueryVersion(2, 0, 3, 3, Success);
+
+    g_test_message("Server version 2.2 - client versions [1..3].0");
+    request_XIQueryVersion(2, 2, 1, 0, BadValue);
+    request_XIQueryVersion(2, 2, 2, 0, Success);
+    request_XIQueryVersion(2, 2, 3, 0, Success);
+
+#if 0
+    /* this one takes a while */
+    unsigned int cmin, cmaj, smin, smaj;
+
+    g_test_message("Testing all combinations.");
+    for (smaj = 2; smaj <= 0xFFFF; smaj++)
+        for (smin = 0; smin <= 0xFFFF; smin++)
+            for (cmin = 0; cmin <= 0xFFFF; cmin++)
+                for (cmaj = 0; cmaj <= 0xFFFF; cmaj++)
+                {
+                    int error = (cmaj < 2) ? BadValue : Success;
+                    request_XIQueryVersion(smaj, smin, cmaj, cmin, error);
+                }
+
+#endif
+
+    reply_handler = NULL;
+}
+
+int main(int argc, char** argv)
+{
+    g_test_init(&argc, &argv,NULL);
+    g_test_bug_base("https://bugzilla.freedesktop.org/show_bug.cgi?id=");
+
+    init_simple();
+
+    g_test_add_func("/xi2/protocol/XIQueryVersion", test_XIQueryVersion);
+
+    return g_test_run();
+}
commit 1d635ae65b217e124b3bd5a8844e73f447eb1b79
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Fri Jun 12 11:30:53 2009 +1000

    test: add xi2 directory, prepare for protocol testing.
    
    These two files provide a couple of common defines, functions and variables
    that will be used in a number of protocol tests.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/configure.ac b/configure.ac
index 25c5c5e..be39c76 100644
--- a/configure.ac
+++ b/configure.ac
@@ -2012,5 +2012,6 @@ hw/kdrive/linux/Makefile
 hw/kdrive/sdl/Makefile
 hw/kdrive/src/Makefile
 test/Makefile
+test/xi2/Makefile
 xorg-server.pc
 ])
diff --git a/test/Makefile.am b/test/Makefile.am
index c5fc4cd..df08b5b 100644
--- a/test/Makefile.am
+++ b/test/Makefile.am
@@ -1,4 +1,5 @@
 if UNITTESTS
+SUBDIRS= . xi2
 check_PROGRAMS = xkb input
 check_LTLIBRARIES = libxservertest.la
 
diff --git a/test/xi2/Makefile.am b/test/xi2/Makefile.am
new file mode 100644
index 0000000..0185c31
--- /dev/null
+++ b/test/xi2/Makefile.am
@@ -0,0 +1,6 @@
+if UNITTESTS
+AM_CFLAGS = $(DIX_CFLAGS) $(GLIB_CFLAGS) @XORG_CFLAGS@
+INCLUDES = @XORG_INCS@
+TEST_LDADD=../libxservertest.la $(XORG_SYS_LIBS) $(XSERVER_SYS_LIBS) $(GLIB_LIBS)
+COMMON_SOURCES=protocol-common.h protocol-common.c
+endif
diff --git a/test/xi2/protocol-common.c b/test/xi2/protocol-common.c
new file mode 100644
index 0000000..1a4ad24
--- /dev/null
+++ b/test/xi2/protocol-common.c
@@ -0,0 +1,132 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+#include <stdint.h>
+#include "extinit.h" /* for XInputExtensionInit */
+#include <glib.h>
+
+#include "protocol-common.h"
+
+struct devices devices;
+WindowRec root;
+WindowRec window;
+
+void *userdata;
+
+/**
+ * Create and init 2 master devices (VCP + VCK) and two slave devices, one
+ * default mouse, one default keyboard.
+ */
+struct devices init_devices(void)
+{
+    ClientRec client;
+    struct devices devices;
+
+    client = init_client(0, NULL);
+
+    AllocDevicePair(&client, "Virtual core", &devices.vcp, &devices.vck, TRUE);
+    inputInfo.pointer = devices.vcp;
+    inputInfo.keyboard = devices.vck;
+    ActivateDevice(devices.vcp, FALSE);
+    ActivateDevice(devices.vck, FALSE);
+    EnableDevice(devices.vcp, FALSE);
+    EnableDevice(devices.vck, FALSE);
+
+    AllocDevicePair(&client, "", &devices.mouse, &devices.kbd, FALSE);
+    ActivateDevice(devices.mouse, FALSE);
+    ActivateDevice(devices.kbd, FALSE);
+    EnableDevice(devices.mouse, FALSE);
+    EnableDevice(devices.kbd, FALSE);
+
+    devices.num_devices = 4;
+    devices.num_master_devices = 2;
+
+    return devices;
+}
+
+
+/* Create minimal client, with the given buffer and len as request buffer */
+ClientRec init_client(int len, void *data)
+{
+    ClientRec client = { 0 };
+
+    /* we store the privates now and reassign it after the memset. this way
+     * we can share them across multiple test runs and don't have to worry
+     * about freeing them after each test run. */
+    PrivateRec *privates = client.devPrivates;
+
+    client.index = CLIENT_INDEX;
+    client.clientAsMask = CLIENT_MASK;
+    client.sequence = CLIENT_SEQUENCE;
+    client.req_len = len;
+
+    client.requestBuffer = data;
+    client.devPrivates = privates;
+    return client;
+}
+
+void init_window(WindowPtr window, WindowPtr parent, int id)
+{
+    memset(window, 0, sizeof(window));
+
+    window->drawable.id = id;
+    window->parent = parent;
+    window->optional = xcalloc(1, sizeof(WindowOptRec));
+    g_assert(window->optional);
+}
+
+/* Needed for the screen setup, otherwise we crash during sprite initialization */
+static Bool device_cursor_init(DeviceIntPtr dev, ScreenPtr screen) { return TRUE; }
+void init_simple(void)
+{
+    static ScreenRec screen;
+
+    screenInfo.arraySize = MAXSCREENS;
+    screenInfo.numScreens = 1;
+    screenInfo.screens[0] = &screen;
+
+    screen.myNum = 0;
+    screen.id = 100;
+    screen.width = 640;
+    screen.height = 480;
+    screen.DeviceCursorInitialize = device_cursor_init;
+
+    dixResetPrivates();
+    XInputExtensionInit();
+    init_window(&root, NULL, ROOT_WINDOW_ID);
+    init_window(&window, &root, CLIENT_WINDOW_ID);
+
+    devices = init_devices();
+}
+
+void __wrap_WriteToClient(ClientPtr client, int len, void *data)
+{
+    g_assert(reply_handler != NULL);
+
+    (*reply_handler)(client, len, data, userdata);
+}
+
diff --git a/test/xi2/protocol-common.h b/test/xi2/protocol-common.h
new file mode 100644
index 0000000..bf8b875
--- /dev/null
+++ b/test/xi2/protocol-common.h
@@ -0,0 +1,143 @@
+/**
+ * Copyright © 2009 Red Hat, Inc.
+ *
+ *  Permission is hereby granted, free of charge, to any person obtaining a
+ *  copy of this software and associated documentation files (the "Software"),
+ *  to deal in the Software without restriction, including without limitation
+ *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ *  and/or sell copies of the Software, and to permit persons to whom the
+ *  Software is furnished to do so, subject to the following conditions:
+ *
+ *  The above copyright notice and this permission notice (including the next
+ *  paragraph) shall be included in all copies or substantial portions of the
+ *  Software.
+ *
+ *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
+ *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ *  DEALINGS IN THE SOFTWARE.
+ */
+
+#ifdef HAVE_DIX_CONFIG_H
+#include <dix-config.h>
+#endif
+
+#include "scrnintstr.h"
+#include "windowstr.h"
+#include "scrnintstr.h"
+#include "exevents.h"
+
+#ifndef PROTOCOL_COMMON_H
+#define PROTOCOL_COMMON_H
+
+extern int BadDevice;
+
+/* Check default values in a reply */
+#define reply_check_defaults(rep, len, type) \
+    { \
+        g_assert((len) >= sz_x##type##Reply); \
+        g_assert((rep)->repType == X_Reply); \
+        g_assert((rep)->RepType == X_##type); \
+        g_assert((rep)->sequenceNumber == CLIENT_SEQUENCE); \
+        g_assert((rep)->length >= (sz_x##type##Reply - 32)/4); \
+    }
+
+/* initialise default values for request */
+#define request_init(req, type) \
+    { \
+        (req)->reqType = 128; /* doesn't matter */ \
+        (req)->ReqType = X_##type; \
+        (req)->length = (sz_x##type##Req >> 2); \
+    }
+
+
+/* Various defines used in the tests. Some tests may use different values
+ * than these defaults */
+/* default client index */
+#define CLIENT_INDEX            1
+/* default client mask for resources and windows */
+#define CLIENT_MASK             ((CLIENT_INDEX) << CLIENTOFFSET)
+/* default client sequence number for replies */
+#define CLIENT_SEQUENCE         0x100
+/* default root window id */
+#define ROOT_WINDOW_ID          0x10
+/* default client window id */
+#define CLIENT_WINDOW_ID        0x100001
+
+/* Various structs used throughout the tests */
+
+
+/* The default devices struct, contains one pointer + keyboard and the
+ * matching master devices. Initialize with init_devices() if needed. */
+struct devices {
+    DeviceIntPtr vcp;
+    DeviceIntPtr vck;
+    DeviceIntPtr mouse;
+    DeviceIntPtr kbd;
+
+    int num_devices;
+    int num_master_devices;
+} devices;
+
+/**
+ * The set of default devices available in all tests if necessary.
+ */
+extern struct devices devices;
+
+/**
+ * test-specific userdata, passed into the reply handler.
+ */
+extern void *userdata;
+/**
+ * The reply handler called from WriteToClient. Set this handler if you need
+ * to check the reply values.
+ */
+void (*reply_handler)(ClientPtr client, int len, char *data, void *userdata);
+
+/**
+ * Semi-initialized root window. initialized by init().
+ */
+extern WindowRec root;
+/**
+ * Semi-initialized top-level window. initialized by init().
+ */
+extern WindowRec window;
+
+/* various simple functions for quick setup */
+/**
+ * Initialize the above struct with default devices and return the struct.
+ * Usually not needed if you call ::init_simple.
+ */
+struct devices init_devices(void);
+/**
+ * Init a mostly zeroed out client with default values for index and mask.
+ */
+ClientRec init_client(int request_len, void *request_data);
+/**
+ * Init a mostly zeroed out window with the given window ID.
+ * Usually not needed if you call ::init_simple which sets up root and
+ * window.
+ */
+void init_window(WindowPtr window, WindowPtr parent, int id);
+/**
+ * Create a very simple setup that provides the minimum values for most
+ * tests, including a screen, the root and client window and the default
+ * device setup.
+ */
+void init_simple(void);
+
+/* Declarations for various overrides in the test files. */
+void __wrap_WriteToClient(ClientPtr client, int len, void *data);
+void __wrap_XISetEventMask(DeviceIntPtr dev, WindowPtr win, int len, unsigned char* mask);
+int __wrap_dixLookupWindow(WindowPtr *win, XID id, ClientPtr client, Mask access);
+int __real_dixLookupWindow(WindowPtr *win, XID id, ClientPtr client, Mask access);
+Bool __wrap_AddResource(XID id, RESTYPE type, pointer value);
+int __wrap_dixLookupClient(ClientPtr *c, XID id, ClientPtr client, Mask access);
+int __real_dixLookupClient(ClientPtr *c, XID id, ClientPtr client, Mask access);
+
+
+#endif /* PROTOCOL_COMMON_H */
+
commit 4b93413b2a490a74de2e27b37268332b609ac872
Author: Peter Hutterer <peter.hutterer at who-t.net>
Date:   Tue Jul 14 11:20:01 2009 +1000

    Add test subdir to base Makefile.am
    
    If unittests are enabled, make will build those as well - spotting potential
    build errors in the tests faster. Furthermore, this allows for the tests to
    be run from the top-level directory.
    This patch removes the "run make check to build the test suite" message
    since that'd pop up after every build now.
    
    If unittests are disabled, this change has no effect.
    
    Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/Makefile.am b/Makefile.am
index dea6fa4..4ee1e17 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -38,7 +38,8 @@ SUBDIRS = \
 	$(GLX_DIR) \
 	exa \
 	config \
-	hw
+	hw \
+	test
 
 aclocaldir = $(datadir)/aclocal
 aclocal_DATA = xorg-server.m4
diff --git a/test/Makefile.am b/test/Makefile.am
index dbad93b..c5fc4cd 100644
--- a/test/Makefile.am
+++ b/test/Makefile.am
@@ -33,7 +33,4 @@ CLEANFILES=libxservertest.c
 libxservertest.c:
 	touch $@
 
-all:
-	@echo "Run 'make check' to run the test suite"
-
 endif


More information about the xorg-commit mailing list