On Thu, Nov 26, 2009 at 11:45:39 +1000, Peter Hutterer wrote:

> @@ -117,10 +118,51 @@ XExtDisplayInfo *XextAddDisplay (
>       */
>      if (dpyinfo->codes) {
>       int i, j;
> +     int idx = dpyinfo->codes->first_event & 0x3f;
> +
> +
> +     /* Xlib extensions use compiled in event numbers. A new library
> +      * against an older server may thus expect a different (higher)
> +      * number of events than the server will send. We have no way of
> +      * knowing the number of events for an extension, the server won't
> +      * tell us.
> +      *
> +      * Depending on the extension initialization order, this smashes the
> +      * event_vec[type] for anything after the extension with the
> +      * different number of events.
> +      *
> +      * e.g. server with inputproto 1.3 expects 15 events, libXi with
> +      * inputproto 2.0 expects 17 events.
> +      * base code is 80, events [80,96] are handled by libXi. events [95,
> +      * 96] belong to the next extension already though.
> +      * This requires XI to be initialized after the extension occupying
> +      * the next range of event codes.
> +      *
> +      * To avoid this, we have a zeroed out array of extension handlers.
> +      * If an extension handler for an event type is already set, and the
> +      * previous event code (before base_code) is the same extension, we
> +      * have the nevents conflict. Unset all those handlers and allow
> +      * overwriting them with the new handlers.
> +         *
> +         * If a handler for a (base + n) event is already set, stop
> +         * registering this extension for the event codes.

there's some whitespace issues here...

> +      *
> +      * event_codes are subtracted by 64 since we don't need to worry
> +      * about core.
> +      */
> +
> +     if (idx && ext_handlers[idx - 1] == ext_handlers[idx]) {
> +         for (i = idx; i < idx + nevents; i++)
> +             if (ext_handlers[idx - 1] == ext_handlers[i])
> +                 ext_handlers[i] = 0;
> +     }

Shouldn't this loop actually look like:

for (i = idx; i < 64; i++)
    if (ext_handlers[idx - 1] == ext_handlers[i])
        ext_handlers[i] = 0;
    else
        break;

Otherwise if extension1 registers events base to base+10, then
extension2 comes and registers events base+5 to base+7, there'll still
be some wrong values for base+8 to base+10, and extension3 will leave
them alone.

>  
> -     for (i = 0, j = dpyinfo->codes->first_event; i < nevents; i++, j++) {
> +     for (i = 0, j = dpyinfo->codes->first_event; i < nevents; i++, j++, 
> idx++) {
> +         if (ext_handlers[idx]) /* don't smash the following extension */
> +             break;
>           XESetWireToEvent (dpy, j, hooks->wire_to_event);
>           XESetEventToWire (dpy, j, hooks->event_to_wire);
> +         ext_handlers[idx] = dpyinfo->codes->first_event & 0x3f;
>       }
>  
>          /* register extension for XGE */

Cheers,
Julien
_______________________________________________
xorg mailing list
[email protected]
http://lists.freedesktop.org/mailman/listinfo/xorg

Reply via email to