#define NEED_EVENTS
#define NEED_REPLIES
#ifdef HAVE_DIX_CONFIG_H
#include <dix-config.h>
#endif
#include "inputstr.h"
#include <X11/extensions/XI.h>
#include <X11/extensions/XIproto.h>
#include "exglobals.h"
#include "getdctl.h"
int
SProcXGetDeviceControl(ClientPtr client)
{
char n;
REQUEST(xGetDeviceControlReq);
swaps(&stuff->length, n);
REQUEST_SIZE_MATCH(xGetDeviceControlReq);
swaps(&stuff->control, n);
return (ProcXGetDeviceControl(client));
}
static void
CopySwapDeviceResolution(ClientPtr client, ValuatorClassPtr v, char *buf,
int length)
{
char n;
AxisInfoPtr a;
xDeviceResolutionState *r;
int i, *iptr;
r = (xDeviceResolutionState *) buf;
r->control = DEVICE_RESOLUTION;
r->length = length;
r->num_valuators = v->numAxes;
buf += sizeof(xDeviceResolutionState);
iptr = (int *)buf;
for (i = 0, a = v->axes; i < v->numAxes; i++, a++)
*iptr++ = a->resolution;
for (i = 0, a = v->axes; i < v->numAxes; i++, a++)
*iptr++ = a->min_resolution;
for (i = 0, a = v->axes; i < v->numAxes; i++, a++)
*iptr++ = a->max_resolution;
if (client->swapped) {
swaps(&r->control, n);
swaps(&r->length, n);
swapl(&r->num_valuators, n);
iptr = (int *)buf;
for (i = 0; i < (3 * v->numAxes); i++, iptr++) {
swapl(iptr, n);
}
}
}
static void CopySwapDeviceAbsCalib (ClientPtr client, AbsoluteClassPtr dts,
char *buf)
{
char n;
xDeviceAbsCalibState *calib = (xDeviceAbsCalibState *) buf;
calib->control = DEVICE_ABS_CALIB;
calib->length = sizeof(xDeviceAbsCalibState);
calib->min_x = dts->min_x;
calib->max_x = dts->max_x;
calib->min_y = dts->min_y;
calib->max_y = dts->max_y;
calib->flip_x = dts->flip_x;
calib->flip_y = dts->flip_y;
calib->rotation = dts->rotation;
calib->button_threshold = dts->button_threshold;
if (client->swapped) {
swaps(&calib->control, n);
swaps(&calib->length, n);
swapl(&calib->min_x, n);
swapl(&calib->max_x, n);
swapl(&calib->min_y, n);
swapl(&calib->max_y, n);
swapl(&calib->flip_x, n);
swapl(&calib->flip_y, n);
swapl(&calib->rotation, n);
swapl(&calib->button_threshold, n);
}
}
static void CopySwapDeviceAbsArea (ClientPtr client, AbsoluteClassPtr dts,
char *buf)
{
char n;
xDeviceAbsAreaState *area = (xDeviceAbsAreaState *) buf;
area->control = DEVICE_ABS_AREA;
area->length = sizeof(xDeviceAbsAreaState);
area->offset_x = dts->offset_x;
area->offset_y = dts->offset_y;
area->width = dts->width;
area->height = dts->height;
area->screen = dts->screen;
area->following = dts->following;
if (client->swapped) {
swaps(&area->control, n);
swaps(&area->length, n);
swapl(&area->offset_x, n);
swapl(&area->offset_y, n);
swapl(&area->width, n);
swapl(&area->height, n);
swapl(&area->screen, n);
swapl(&area->following, n);
}
}
static void CopySwapDeviceCore (ClientPtr client, DeviceIntPtr dev, char *buf)
{
char n;
xDeviceCoreState *c = (xDeviceCoreState *) buf;
c->control = DEVICE_CORE;
c->length = sizeof(xDeviceCoreState);
c->status = dev->coreEvents;
c->iscore = (dev == inputInfo.keyboard || dev == inputInfo.pointer);
if (client->swapped) {
swaps(&c->control, n);
swaps(&c->length, n);
swaps(&c->status, n);
}
}
static void CopySwapDeviceEnable (ClientPtr client, DeviceIntPtr dev, char *buf)
{
char n;
xDeviceEnableState *e = (xDeviceEnableState *) buf;
e->control = DEVICE_ENABLE;
e->length = sizeof(xDeviceEnableState);
e->enable = dev->enabled;
if (client->swapped) {
swaps(&e->control, n);
swaps(&e->length, n);
swaps(&e->enable, n);
}
}
void
SRepXGetDeviceControl(ClientPtr client, int size, xGetDeviceControlReply * rep)
{
char n;
swaps(&rep->sequenceNumber, n);
swapl(&rep->length, n);
WriteToClient(client, size, (char *)rep);
}
int
ProcXGetDeviceControl(ClientPtr client)
{
int rc, total_length = 0;
char *buf, *savbuf;
DeviceIntPtr dev;
xGetDeviceControlReply rep;
REQUEST(xGetDeviceControlReq);
REQUEST_SIZE_MATCH(xGetDeviceControlReq);
rc = dixLookupDevice(&dev, stuff->deviceid, client, DixGetAttrAccess);
if (rc != Success)
return rc;
rep.repType = X_Reply;
rep.RepType = X_GetDeviceControl;
rep.length = 0;
rep.sequenceNumber = client->sequence;
switch (stuff->control) {
case DEVICE_RESOLUTION:
if (!dev->valuator)
return BadMatch;
total_length = sizeof(xDeviceResolutionState) +
(3 * sizeof(int) * dev->valuator->numAxes);
break;
case DEVICE_ABS_CALIB:
if (!dev->absolute)
return BadMatch;
total_length = sizeof(xDeviceAbsCalibState);
break;
case DEVICE_ABS_AREA:
if (!dev->absolute)
return BadMatch;
total_length = sizeof(xDeviceAbsAreaState);
break;
case DEVICE_CORE:
total_length = sizeof(xDeviceCoreState);
break;
case DEVICE_ENABLE:
total_length = sizeof(xDeviceEnableState);
break;
default:
return BadValue;
}
buf = (char *)xalloc(total_length);
if (!buf)
return BadAlloc;
savbuf = buf;
switch (stuff->control) {
case DEVICE_RESOLUTION:
CopySwapDeviceResolution(client, dev->valuator, buf, total_length);
break;
case DEVICE_ABS_CALIB:
CopySwapDeviceAbsCalib(client, dev->absolute, buf);
break;
case DEVICE_ABS_AREA:
CopySwapDeviceAbsArea(client, dev->absolute, buf);
break;
case DEVICE_CORE:
CopySwapDeviceCore(client, dev, buf);
break;
case DEVICE_ENABLE:
CopySwapDeviceEnable(client, dev, buf);
break;
default:
break;
}
rep.length = (total_length + 3) >> 2;
WriteReplyToClient(client, sizeof(xGetDeviceControlReply), &rep);
WriteToClient(client, total_length, savbuf);
xfree(savbuf);
return Success;
}