Xi: add versioning support.
Remember the version the client sent to us, so we can adjust our replies accordingly. This requires the client to use the {major|minor}Version fields in the GetExtensionVersion request. However, they were padding before, so we must assume they are garbage if nbytes is non-zero. If nbytes is zero, the client is probably a new client and we can handle it correctly.
This commit is contained in:
parent
e251c9e75a
commit
b304b0a65c
|
@ -31,6 +31,7 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||||
#ifdef HAVE_DIX_CONFIG_H
|
#ifdef HAVE_DIX_CONFIG_H
|
||||||
#include <dix-config.h>
|
#include <dix-config.h>
|
||||||
#endif
|
#endif
|
||||||
|
#include "privates.h"
|
||||||
|
|
||||||
#ifndef EXGLOBALS_H
|
#ifndef EXGLOBALS_H
|
||||||
#define EXGLOBALS_H 1
|
#define EXGLOBALS_H 1
|
||||||
|
@ -75,4 +76,5 @@ extern int DeviceLeaveNotify;
|
||||||
|
|
||||||
extern int RT_INPUTCLIENT;
|
extern int RT_INPUTCLIENT;
|
||||||
|
|
||||||
|
extern DevPrivateKey XIClientPrivateKey;
|
||||||
#endif /* EXGLOBALS_H */
|
#endif /* EXGLOBALS_H */
|
||||||
|
|
39
Xi/extinit.c
39
Xi/extinit.c
|
@ -72,6 +72,7 @@ SOFTWARE.
|
||||||
#include "exglobals.h"
|
#include "exglobals.h"
|
||||||
#include "swaprep.h"
|
#include "swaprep.h"
|
||||||
#include "registry.h"
|
#include "registry.h"
|
||||||
|
#include "privates.h"
|
||||||
|
|
||||||
/* modules local to Xi */
|
/* modules local to Xi */
|
||||||
#include "allowev.h"
|
#include "allowev.h"
|
||||||
|
@ -324,19 +325,42 @@ int RT_INPUTCLIENT;
|
||||||
|
|
||||||
extern XExtensionVersion AllExtensionVersions[];
|
extern XExtensionVersion AllExtensionVersions[];
|
||||||
|
|
||||||
|
|
||||||
Mask PropagateMask[MAX_DEVICES];
|
Mask PropagateMask[MAX_DEVICES];
|
||||||
|
|
||||||
|
/*****************************************************************
|
||||||
|
*
|
||||||
|
* Versioning support
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
DevPrivateKey XIClientPrivateKey = &XIClientPrivateKey;
|
||||||
|
|
||||||
|
static XExtensionVersion thisversion = { XI_Present,
|
||||||
|
XI_2_Major,
|
||||||
|
XI_2_Minor
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/*****************************************************************
|
/*****************************************************************
|
||||||
*
|
*
|
||||||
* Declarations of local routines.
|
* Declarations of local routines.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static XExtensionVersion thisversion = { XI_Present,
|
static void
|
||||||
XI_2_Major,
|
XIClientCallback(CallbackListPtr *list,
|
||||||
XI_2_Minor
|
pointer closure,
|
||||||
};
|
pointer data)
|
||||||
|
{
|
||||||
|
NewClientInfoRec *clientinfo = (NewClientInfoRec*)data;
|
||||||
|
ClientPtr pClient = clientinfo->client;
|
||||||
|
XIClientPtr pXIClient;
|
||||||
|
|
||||||
|
pXIClient = dixLookupPrivate(&pClient->devPrivates, XIClientPrivateKey);
|
||||||
|
pXIClient->major_version = 0;
|
||||||
|
pXIClient->minor_version = 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*************************************************************************
|
/*************************************************************************
|
||||||
*
|
*
|
||||||
|
@ -1080,6 +1104,7 @@ XIGEEventFill(xGenericEvent* ev, DeviceIntPtr pDev,
|
||||||
*
|
*
|
||||||
* This extension has several events and errors.
|
* This extension has several events and errors.
|
||||||
*
|
*
|
||||||
|
* XI is mandatory nowadays, so if we fail to init XI, we die.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -1087,6 +1112,12 @@ XInputExtensionInit(void)
|
||||||
{
|
{
|
||||||
ExtensionEntry *extEntry;
|
ExtensionEntry *extEntry;
|
||||||
|
|
||||||
|
if (!dixRequestPrivate(XIClientPrivateKey, sizeof(XIClientRec)))
|
||||||
|
FatalError("Cannot request private for XI.\n");
|
||||||
|
|
||||||
|
if (!AddCallback(&ClientStateCallback, XIClientCallback, 0))
|
||||||
|
FatalError("Failed to add callback to XI.\n");
|
||||||
|
|
||||||
extEntry = AddExtension(INAME, IEVENTS, IERRORS, ProcIDispatch,
|
extEntry = AddExtension(INAME, IEVENTS, IERRORS, ProcIDispatch,
|
||||||
SProcIDispatch, IResetProc, StandardMinorOpcode);
|
SProcIDispatch, IResetProc, StandardMinorOpcode);
|
||||||
if (extEntry) {
|
if (extEntry) {
|
||||||
|
|
17
Xi/getvers.c
17
Xi/getvers.c
|
@ -59,6 +59,7 @@ SOFTWARE.
|
||||||
#include "inputstr.h" /* DeviceIntPtr */
|
#include "inputstr.h" /* DeviceIntPtr */
|
||||||
#include <X11/extensions/XI.h>
|
#include <X11/extensions/XI.h>
|
||||||
#include <X11/extensions/XIproto.h>
|
#include <X11/extensions/XIproto.h>
|
||||||
|
#include "exevents.h"
|
||||||
#include "exglobals.h"
|
#include "exglobals.h"
|
||||||
|
|
||||||
#include "getvers.h"
|
#include "getvers.h"
|
||||||
|
@ -93,6 +94,7 @@ int
|
||||||
ProcXGetExtensionVersion(ClientPtr client)
|
ProcXGetExtensionVersion(ClientPtr client)
|
||||||
{
|
{
|
||||||
xGetExtensionVersionReply rep;
|
xGetExtensionVersionReply rep;
|
||||||
|
XIClientPtr pXIClient;
|
||||||
|
|
||||||
REQUEST(xGetExtensionVersionReq);
|
REQUEST(xGetExtensionVersionReq);
|
||||||
REQUEST_AT_LEAST_SIZE(xGetExtensionVersionReq);
|
REQUEST_AT_LEAST_SIZE(xGetExtensionVersionReq);
|
||||||
|
@ -101,6 +103,21 @@ ProcXGetExtensionVersion(ClientPtr client)
|
||||||
stuff->nbytes + 3) >> 2)
|
stuff->nbytes + 3) >> 2)
|
||||||
return BadLength;
|
return BadLength;
|
||||||
|
|
||||||
|
pXIClient = dixLookupPrivate(&client->devPrivates, XIClientPrivateKey);
|
||||||
|
|
||||||
|
/* GetExtensionVersionReq before XI 2 didn't supply the client's
|
||||||
|
* major/minor. So we don't actually have a clue what they support.
|
||||||
|
* {major|minor}Version was added as part of XI, so if they are set, we
|
||||||
|
* know we can trust it. In this case the client must set nbytes to 0
|
||||||
|
* though, otherwise we have to assume that the version are padding
|
||||||
|
* garbage.
|
||||||
|
*/
|
||||||
|
if (!stuff->nbytes) /* Client using XQueryInputVersion(). */
|
||||||
|
{
|
||||||
|
pXIClient->major_version = stuff->majorVersion;
|
||||||
|
pXIClient->minor_version = stuff->minorVersion;
|
||||||
|
} /* else version unknown, leave it at 0.0 */
|
||||||
|
|
||||||
rep.repType = X_Reply;
|
rep.repType = X_Reply;
|
||||||
rep.RepType = X_GetExtensionVersion;
|
rep.RepType = X_GetExtensionVersion;
|
||||||
rep.length = 0;
|
rep.length = 0;
|
||||||
|
|
|
@ -32,6 +32,15 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
|
||||||
#include <X11/extensions/XIproto.h>
|
#include <X11/extensions/XIproto.h>
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Attached to the devPrivates of each client. Specifies the version number as
|
||||||
|
* supported by the client.
|
||||||
|
*/
|
||||||
|
typedef struct _XIClientRec {
|
||||||
|
int major_version;
|
||||||
|
int minor_version;
|
||||||
|
} XIClientRec, *XIClientPtr;
|
||||||
|
|
||||||
extern void RegisterOtherDevice (
|
extern void RegisterOtherDevice (
|
||||||
DeviceIntPtr /* device */);
|
DeviceIntPtr /* device */);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue