"Fossies" - the Fresh Open Source Software Archive

Member "xorg-server-1.20.8/test/xi2/protocol-xiquerydevice.c" (29 Mar 2020, 11721 Bytes) of package /linux/misc/xorg-server-1.20.8.tar.bz2:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. See also the latest Fossies "Diffs" side-by-side code changes report for "protocol-xiquerydevice.c": 1.20.7_vs_1.20.8.

    1 /**
    2  * Copyright © 2009 Red Hat, Inc.
    3  *
    4  *  Permission is hereby granted, free of charge, to any person obtaining a
    5  *  copy of this software and associated documentation files (the "Software"),
    6  *  to deal in the Software without restriction, including without limitation
    7  *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
    8  *  and/or sell copies of the Software, and to permit persons to whom the
    9  *  Software is furnished to do so, subject to the following conditions:
   10  *
   11  *  The above copyright notice and this permission notice (including the next
   12  *  paragraph) shall be included in all copies or substantial portions of the
   13  *  Software.
   14  *
   15  *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
   16  *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
   17  *  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
   18  *  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
   19  *  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
   20  *  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
   21  *  DEALINGS IN THE SOFTWARE.
   22  */
   23 
   24 #ifdef HAVE_DIX_CONFIG_H
   25 #include <dix-config.h>
   26 #endif
   27 
   28 #include <stdint.h>
   29 #include <X11/X.h>
   30 #include <X11/Xproto.h>
   31 #include <X11/extensions/XI2proto.h>
   32 #include <X11/Xatom.h>
   33 #include "inputstr.h"
   34 #include "extinit.h"
   35 #include "exglobals.h"
   36 #include "scrnintstr.h"
   37 #include "xkbsrv.h"
   38 
   39 #include "xiquerydevice.h"
   40 
   41 #include "protocol-common.h"
   42 /*
   43  * Protocol testing for XIQueryDevice request and reply.
   44  *
   45  * Test approach:
   46  * Wrap WriteToClient to intercept server's reply. ProcXIQueryDevice returns
   47  * data in two batches, once for the request, once for the trailing data
   48  * with the device information.
   49  * Repeatedly test with varying deviceids and check against data in reply.
   50  */
   51 
   52 struct test_data {
   53     int which_device;
   54     int num_devices_in_reply;
   55 };
   56 
   57 extern ClientRec client_window;
   58 
   59 static void reply_XIQueryDevice_data(ClientPtr client, int len, char *data,
   60                                      void *closure);
   61 static void reply_XIQueryDevice(ClientPtr client, int len, char *data,
   62                                 void *closure);
   63 
   64 /* reply handling for the first bytes that constitute the reply */
   65 static void
   66 reply_XIQueryDevice(ClientPtr client, int len, char *data, void *userdata)
   67 {
   68     xXIQueryDeviceReply *rep = (xXIQueryDeviceReply *) data;
   69     struct test_data *querydata = (struct test_data *) userdata;
   70 
   71     if (client->swapped) {
   72         swapl(&rep->length);
   73         swaps(&rep->sequenceNumber);
   74         swaps(&rep->num_devices);
   75     }
   76 
   77     reply_check_defaults(rep, len, XIQueryDevice);
   78 
   79     if (querydata->which_device == XIAllDevices)
   80         assert(rep->num_devices == devices.num_devices);
   81     else if (querydata->which_device == XIAllMasterDevices)
   82         assert(rep->num_devices == devices.num_master_devices);
   83     else
   84         assert(rep->num_devices == 1);
   85 
   86     querydata->num_devices_in_reply = rep->num_devices;
   87     reply_handler = reply_XIQueryDevice_data;
   88 }
   89 
   90 /* reply handling for the trailing bytes that constitute the device info */
   91 static void
   92 reply_XIQueryDevice_data(ClientPtr client, int len, char *data, void *closure)
   93 {
   94     int i, j;
   95     struct test_data *querydata = (struct test_data *) closure;
   96 
   97     DeviceIntPtr dev;
   98     xXIDeviceInfo *info = (xXIDeviceInfo *) data;
   99     xXIAnyInfo *any;
  100 
  101     for (i = 0; i < querydata->num_devices_in_reply; i++) {
  102         if (client->swapped) {
  103             swaps(&info->deviceid);
  104             swaps(&info->attachment);
  105             swaps(&info->use);
  106             swaps(&info->num_classes);
  107             swaps(&info->name_len);
  108         }
  109 
  110         if (querydata->which_device > XIAllMasterDevices)
  111             assert(info->deviceid == querydata->which_device);
  112 
  113         assert(info->deviceid >= 2);    /* 0 and 1 is reserved */
  114 
  115         switch (info->deviceid) {
  116         case 2:                /* VCP */
  117             dev = devices.vcp;
  118             assert(info->use == XIMasterPointer);
  119             assert(info->attachment == devices.vck->id);
  120             assert(info->num_classes == 3);     /* 2 axes + button */
  121             break;
  122         case 3:                /* VCK */
  123             dev = devices.vck;
  124             assert(info->use == XIMasterKeyboard);
  125             assert(info->attachment == devices.vcp->id);
  126             assert(info->num_classes == 1);
  127             break;
  128         case 4:                /* mouse */
  129             dev = devices.mouse;
  130             assert(info->use == XISlavePointer);
  131             assert(info->attachment == devices.vcp->id);
  132             assert(info->num_classes == 7);     /* 4 axes + button + 2 scroll */
  133             break;
  134         case 5:                /* keyboard */
  135             dev = devices.kbd;
  136             assert(info->use == XISlaveKeyboard);
  137             assert(info->attachment == devices.vck->id);
  138             assert(info->num_classes == 1);
  139             break;
  140 
  141         default:
  142             /* We shouldn't get here */
  143             assert(0);
  144             break;
  145         }
  146         assert(info->enabled == dev->enabled);
  147         assert(info->name_len == strlen(dev->name));
  148         assert(strncmp((char *) &info[1], dev->name, info->name_len) == 0);
  149 
  150         any =
  151             (xXIAnyInfo *) ((char *) &info[1] + ((info->name_len + 3) / 4) * 4);
  152         for (j = 0; j < info->num_classes; j++) {
  153             if (client->swapped) {
  154                 swaps(&any->type);
  155                 swaps(&any->length);
  156                 swaps(&any->sourceid);
  157             }
  158 
  159             switch (info->deviceid) {
  160             case 3:            /* VCK and kbd have the same properties */
  161             case 5:
  162             {
  163                 int k;
  164                 xXIKeyInfo *ki = (xXIKeyInfo *) any;
  165                 XkbDescPtr xkb = devices.vck->key->xkbInfo->desc;
  166                 uint32_t *kc;
  167 
  168                 if (client->swapped)
  169                     swaps(&ki->num_keycodes);
  170 
  171                 assert(any->type == XIKeyClass);
  172                 assert(ki->num_keycodes ==
  173                        (xkb->max_key_code - xkb->min_key_code + 1));
  174                 assert(any->length == (2 + ki->num_keycodes));
  175 
  176                 kc = (uint32_t *) &ki[1];
  177                 for (k = 0; k < ki->num_keycodes; k++, kc++) {
  178                     if (client->swapped)
  179                         swapl(kc);
  180 
  181                     assert(*kc >= xkb->min_key_code);
  182                     assert(*kc <= xkb->max_key_code);
  183                 }
  184                 break;
  185             }
  186             case 4:
  187             {
  188                 assert(any->type == XIButtonClass ||
  189                        any->type == XIValuatorClass ||
  190                        any->type == XIScrollClass);
  191 
  192                 if (any->type == XIScrollClass) {
  193                     xXIScrollInfo *si = (xXIScrollInfo *) any;
  194 
  195                     if (client->swapped) {
  196                         swaps(&si->number);
  197                         swaps(&si->scroll_type);
  198                         swapl(&si->increment.integral);
  199                         swapl(&si->increment.frac);
  200                     }
  201                     assert(si->length == 6);
  202                     assert(si->number == 2 || si->number == 3);
  203                     if (si->number == 2) {
  204                         assert(si->scroll_type == XIScrollTypeVertical);
  205                         assert(!si->flags);
  206                     }
  207                     if (si->number == 3) {
  208                         assert(si->scroll_type == XIScrollTypeHorizontal);
  209                         assert(si->flags & XIScrollFlagPreferred);
  210                         assert(!(si->flags & ~XIScrollFlagPreferred));
  211                     }
  212 
  213                     assert(si->increment.integral == si->number);
  214                     /* protocol-common.c sets up increments of 2.4 and 3.5 */
  215                     assert(si->increment.frac > 0.3 * (1ULL << 32));
  216                     assert(si->increment.frac < 0.6 * (1ULL << 32));
  217                 }
  218 
  219             }
  220                 /* fall through */
  221             case 2:            /* VCP and mouse have the same properties except for scroll */
  222             {
  223                 if (info->deviceid == 2)        /* VCP */
  224                     assert(any->type == XIButtonClass ||
  225                            any->type == XIValuatorClass);
  226 
  227                 if (any->type == XIButtonClass) {
  228                     int l;
  229                     xXIButtonInfo *bi = (xXIButtonInfo *) any;
  230 
  231                     if (client->swapped)
  232                         swaps(&bi->num_buttons);
  233 
  234                     assert(bi->num_buttons == devices.vcp->button->numButtons);
  235 
  236                     l = 2 + bi->num_buttons +
  237                         bytes_to_int32(bits_to_bytes(bi->num_buttons));
  238                     assert(bi->length == l);
  239                 }
  240                 else if (any->type == XIValuatorClass) {
  241                     xXIValuatorInfo *vi = (xXIValuatorInfo *) any;
  242 
  243                     if (client->swapped) {
  244                         swaps(&vi->number);
  245                         swapl(&vi->label);
  246                         swapl(&vi->min.integral);
  247                         swapl(&vi->min.frac);
  248                         swapl(&vi->max.integral);
  249                         swapl(&vi->max.frac);
  250                         swapl(&vi->resolution);
  251                     }
  252 
  253                     assert(vi->length == 11);
  254                     assert(vi->number >= 0 && vi->number < 4);
  255                     if (info->deviceid == 2)    /* VCP */
  256                         assert(vi->number < 2);
  257 
  258                     assert(vi->mode == XIModeRelative);
  259                     /* device was set up as relative, so standard
  260                      * values here. */
  261                     assert(vi->min.integral == -1);
  262                     assert(vi->min.frac == 0);
  263                     assert(vi->max.integral == -1);
  264                     assert(vi->max.frac == 0);
  265                     assert(vi->resolution == 0);
  266                 }
  267             }
  268                 break;
  269             }
  270             any = (xXIAnyInfo *) (((char *) any) + any->length * 4);
  271         }
  272 
  273         info = (xXIDeviceInfo *) any;
  274     }
  275 }
  276 
  277 static void
  278 request_XIQueryDevice(struct test_data *querydata, int deviceid, int error)
  279 {
  280     int rc;
  281     ClientRec client;
  282     xXIQueryDeviceReq request;
  283 
  284     request_init(&request, XIQueryDevice);
  285     client = init_client(request.length, &request);
  286     reply_handler = reply_XIQueryDevice;
  287 
  288     querydata->which_device = deviceid;
  289 
  290     request.deviceid = deviceid;
  291     rc = ProcXIQueryDevice(&client);
  292     assert(rc == error);
  293 
  294     if (rc != Success)
  295         assert(client.errorValue == deviceid);
  296 
  297     reply_handler = reply_XIQueryDevice;
  298 
  299     client.swapped = TRUE;
  300     swaps(&request.length);
  301     swaps(&request.deviceid);
  302     rc = SProcXIQueryDevice(&client);
  303     assert(rc == error);
  304 
  305     if (rc != Success)
  306         assert(client.errorValue == deviceid);
  307 }
  308 
  309 static void
  310 test_XIQueryDevice(void)
  311 {
  312     int i;
  313     xXIQueryDeviceReq request;
  314     struct test_data data;
  315 
  316     reply_handler = reply_XIQueryDevice;
  317     global_userdata = &data;
  318     request_init(&request, XIQueryDevice);
  319 
  320     printf("Testing XIAllDevices.\n");
  321     request_XIQueryDevice(&data, XIAllDevices, Success);
  322     printf("Testing XIAllMasterDevices.\n");
  323     request_XIQueryDevice(&data, XIAllMasterDevices, Success);
  324 
  325     printf("Testing existing device ids.\n");
  326     for (i = 2; i < 6; i++)
  327         request_XIQueryDevice(&data, i, Success);
  328 
  329     printf("Testing non-existing device ids.\n");
  330     for (i = 6; i <= 0xFFFF; i++)
  331         request_XIQueryDevice(&data, i, BadDevice);
  332 
  333     reply_handler = NULL;
  334 
  335 }
  336 
  337 int
  338 protocol_xiquerydevice_test(void)
  339 {
  340     init_simple();
  341 
  342     test_XIQueryDevice();
  343 
  344     return 0;
  345 }