home *** CD-ROM | disk | FTP | other *** search
- /*
- * parse.c - Parse event specifications (see Xt manual, appendix B)
- *
- * George Ferguson, ferguson@cs.rochester.edu, 1 Jun 1990.
- *
- * $Id: parse.c,v 1.4 90/08/15 11:32:19 ferguson Exp $
- *
- */
-
- #include <stdio.h>
- #include <ctype.h>
- #include <string.h>
- #include <X11/Xlib.h>
- #include <X11/keysym.h>
- #include "parse.h"
- extern Display *display;
- extern Window root;
-
- /*
- * Functions defined
- */
- char *parseEventList();
- void freeEventList();
- static char *parseEvent(),*parseMods(),*parseType(),*parseDetail();
- static unsigned int lookup();
- static void parseError();
-
- #define SKIPWHITE(S) while (isspace(*(S))) (S) += 1
-
- /*
- * Text to value mappings
- */
- typedef struct {
- char *name;
- unsigned int value;
- } NameValue;
-
- static NameValue booleans[] = {
- {"True", True},
- {"False", False},
- {"On", True},
- {"Off", False},
- {NULL, 0},
- };
-
- static NameValue modifiers[] = {
- {"None", None},
- {"Shift", ShiftMask},
- {"Lock", LockMask},
- {"Ctrl", ControlMask},
- {"Mod1", Mod1Mask},
- {"Mod2", Mod2Mask},
- {"Mod3", Mod3Mask},
- {"Mod4", Mod4Mask},
- {"Mod5", Mod5Mask},
- {"Meta", XK_Meta_L},
- {"m", XK_Meta_L},
- {"h", XK_Hyper_L},
- {"su", XK_Super_L},
- {"a", XK_Alt_L},
- {"Hyper", XK_Hyper_L},
- {"Super", XK_Super_L},
- {"Alt", XK_Alt_L},
- {"Button1", Button1Mask},
- {"Button2", Button2Mask},
- {"Button3", Button3Mask},
- {"Button4", Button4Mask},
- {"Button5", Button5Mask},
- {"Any", AnyModifier},
- {"c", ControlMask},
- {"s", ShiftMask},
- {"l", LockMask},
- {NULL, 0},
- };
-
- static NameValue buttonNames[] = {
- {"Button1", Button1},
- {"Button2", Button2},
- {"Button3", Button3},
- {"Button4", Button4},
- {"Button5", Button5},
- {NULL, 0},
- };
-
- static NameValue motionDetails[] = {
- {"Normal", NotifyNormal},
- {"Hint", NotifyHint},
- {NULL, 0},
- };
-
- static NameValue notifyModes[] = {
- {"Normal", NotifyNormal},
- {"Grab", NotifyGrab},
- {"Ungrab", NotifyUngrab},
- {"WhileGrabbed", NotifyWhileGrabbed},
- {NULL, 0},
- };
-
- static NameValue notifyDetails[] = {
- {"Ancestor", NotifyAncestor},
- {"Virtual", NotifyVirtual},
- {"Inferior", NotifyInferior},
- {"Nonlinear", NotifyNonlinear},
- {"NonlinearVirtual",NotifyNonlinearVirtual},
- {"Pointer", NotifyPointer},
- {"PointerRoot", NotifyPointerRoot},
- {"DetailNone", NotifyDetailNone},
- {NULL, 0},
- };
-
- static NameValue circulateDetails[] = {
- {"PlaceOnTop", PlaceOnTop},
- {"OnTop", PlaceOnTop},
- {"PlaceOnBottom", PlaceOnBottom},
- {"OnBottom", PlaceOnBottom},
- {NULL, 0},
- };
-
- static NameValue mappingDetails[] = {
- {"Modifier", MappingModifier},
- {"Keyboard", MappingKeyboard},
- {"Pointer", MappingPointer},
- {NULL, 0},
- };
-
- static NameValue visibilityDetails[] = {
- {"Unobscured", VisibilityUnobscured},
- {"PartiallyObscured",VisibilityPartiallyObscured},
- {"FullyObscured", VisibilityFullyObscured},
- {NULL, 0},
- };
-
- static NameValue propertyDetails[] = {
- {"NewValue", PropertyNewValue},
- {"Delete", PropertyDelete},
- {NULL, 0},
- };
-
- typedef struct {
- char *name;
- unsigned int value;
- unsigned int mods;
- unsigned int detail;
- } NameValueModsDetail;
-
- static NameValueModsDetail types[] = {
- {"KeyPress", KeyPress, 0, 0},
- {"Key", KeyPress, 0, 0},
- {"KeyDown", KeyPress, 0, 0},
- {"Ctrl", KeyPress, ControlMask, 0},
- {"Shift", KeyPress, ShiftMask, 0},
- {"Meta", KeyPress, 0, 0},
- {"KeyUp", KeyRelease, 0, 0},
- {"KeyRelease", KeyRelease, 0, 0},
- {"ButtonPress", ButtonPress, 0, 0},
- {"BtnDown", ButtonPress, 0, 0},
- {"Btn1Down", ButtonPress, 0, Button1},
- {"Btn2Down", ButtonPress, 0, Button2},
- {"Btn3Down", ButtonPress, 0, Button3},
- {"Btn4Down", ButtonPress, 0, Button4},
- {"Btn5Down", ButtonPress, 0, Button5},
- {"ButtonRelease", ButtonRelease, 0, 0},
- {"BtnUp", ButtonRelease, 0, 0},
- {"Btn1Up", ButtonRelease, 0, Button1},
- {"Btn2Up", ButtonRelease, 0, Button2},
- {"Btn3Up", ButtonRelease, 0, Button3},
- {"Btn4Up", ButtonRelease, 0, Button4},
- {"Btn5Up", ButtonRelease, 0, Button5},
- {"MotionNotify", MotionNotify, 0, 0},
- {"PtrMoved", MotionNotify, 0, 0},
- {"Motion", MotionNotify, 0, 0},
- {"MouseMoved", MotionNotify, 0, 0},
- {"BtnMotion", MotionNotify, 0, 0},
- {"Btn1Motion", MotionNotify, Button1Mask, 0},
- {"Btn2Motion", MotionNotify, Button2Mask, 0},
- {"Btn3Motion", MotionNotify, Button3Mask, 0},
- {"Btn4Motion", MotionNotify, Button4Mask, 0},
- {"Btn5Motion", MotionNotify, Button5Mask, 0},
- {"EnterNotify", EnterNotify, 0, 0},
- {"Enter", EnterNotify, 0, 0},
- {"EnterWindow", EnterNotify, 0, 0},
- {"LeaveNotify", LeaveNotify, 0, 0},
- {"LeaveWindow", LeaveNotify, 0, 0},
- {"Leave", LeaveNotify, 0, 0},
- {"FocusIn", FocusIn, 0, 0},
- {"FocusOut", FocusOut, 0, 0},
- {"KeymapNotify", KeymapNotify, 0, 0},
- {"Keymap", KeymapNotify, 0, 0},
- {"Expose", Expose, 0, 0},
- {"GraphicsExpose", GraphicsExpose, 0, 0},
- {"GrExp", GraphicsExpose, 0, 0},
- {"NoExpose", NoExpose, 0, 0},
- {"NoExp", NoExpose, 0, 0},
- {"VisibilityNotify", VisibilityNotify, 0, 0},
- {"Visible", VisibilityNotify, 0, 0},
- {"CreateNotify", CreateNotify, 0, 0},
- {"Create", CreateNotify, 0, 0},
- {"DestroyNotify", DestroyNotify, 0, 0},
- {"Destroy", DestroyNotify, 0, 0},
- {"UnmapNotify", UnmapNotify, 0, 0},
- {"Unmap", UnmapNotify, 0, 0},
- {"MapNotify", MapNotify, 0, 0},
- {"Map", MapNotify, 0, 0},
- {"MapRequest", MapRequest, 0, 0},
- {"MapReq", MapRequest, 0, 0},
- {"ReparentNotify", ReparentNotify, 0, 0},
- {"Reparent", ReparentNotify, 0, 0},
- {"ConfigureNotify", ConfigureNotify, 0, 0},
- {"Configure", ConfigureNotify, 0, 0},
- {"ConfigureRequest", ConfigureRequest, 0, 0},
- {"ConfigureReq", ConfigureRequest, 0, 0},
- {"GravityNotify", GravityNotify, 0, 0},
- {"Grav", GravityNotify, 0, 0},
- {"ResizeRequest", ResizeRequest, 0, 0},
- {"ResReq", ResizeRequest, 0, 0},
- {"CirculateNotify", CirculateNotify, 0, 0},
- {"Circ", CirculateNotify, 0, 0},
- {"CirculateRequest", CirculateRequest, 0, 0},
- {"CircReq", CirculateRequest, 0, 0},
- {"PropertyNotify", PropertyNotify, 0, 0},
- {"Prop", PropertyNotify, 0, 0},
- {"SelectionClear", SelectionClear, 0, 0},
- {"SelClr", SelectionClear, 0, 0},
- {"SelectionRequest", SelectionRequest, 0, 0},
- {"SelReq", SelectionRequest, 0, 0},
- {"SelectionNotify", SelectionNotify, 0, 0},
- {"Select", SelectionNotify, 0, 0},
- {"ColormapNotify", ColormapNotify, 0, 0},
- {"Clrmap", ColormapNotify, 0, 0},
- {"ClientMessage", ClientMessage, 0, 0},
- {"Message", ClientMessage, 0, 0},
- {"MappingNotify", MappingNotify, 0, 0},
- {"Mapping", MappingNotify, 0, 0},
- {NULL, 0, 0, 0}
- };
-
- /* - - - - - - - - */
-
- static unsigned int
- lookup(table,name)
- NameValue *table;
- char *name;
- {
- while (table->name != NULL && strcasecmp(name,table->name) != 0)
- table += 1;
- return(table->value);
- }
-
- char *
- parseEventList(str,evp)
- char *str;
- EventListPtr *evp;
- {
- EventListPtr ev,end;
-
- *evp == NULL;
- while (*str) {
- str = parseEvent(str,&ev);
- if (ev != NULL)
- if (*evp == NULL)
- end = *evp = ev;
- else
- end = end->next = ev; /* wow! */
- else
- return(str);
- if (*str && *str != ',') {
- parseError("',' expected",str);
- return(str);
- } else if (*str)
- str += 1; /* skip comma */
- }
- return(str);
- }
-
- static char *
- parseEvent(str,evp)
- char *str;
- EventListPtr *evp;
- {
- unsigned int mods;
- int type,count;
- unsigned int detail;
-
- str = parseMods(str,&mods);
- SKIPWHITE(str);
- if (*str != '<') {
- parseError("'<' expected",str);
- return(str);
- } else
- str += 1;
- str = parseType(str,&type,&mods,&detail);
- if (*str != '>') {
- parseError("'>' expected",str);
- return(str);
- } else
- str += 1;
- SKIPWHITE(str);
- count = 1; /* default */
- if (*str == '(') {
- str += 1;
- count = (int)strtol(str,&str,0);
- if (count == 0) {
- parseError("count expected",str);
- return(str);
- }
- if (*str != ')') {
- parseError("')' expected",str);
- return(str);
- } else
- str += 1;
- }
- SKIPWHITE(str);
- *evp = (EventListElem *)malloc(sizeof(EventListElem));
- (*evp)->count = count;
- (*evp)->next = NULL;
- str = parseDetail(str,&((*evp)->event),type,mods,detail);
- return(str);
- }
-
- static char *
- parseMods(str,modsp)
- char *str;
- unsigned int *modsp;
- {
- char modstr[32];
- int i;
- unsigned int m;
-
- *modsp = (unsigned int)0;
- while (*str && *str != '<') {
- SKIPWHITE(str);
- i = 0;
- while (isalnum(*str) && i < 30)
- modstr[i++] = *str++;
- if (i == 31)
- parseError("modifier name too long",str);
- modstr[i] = '\0';
- if ((m=lookup(modifiers,modstr)) == 0)
- parseError("unknown modifier",modstr);
- else
- *modsp |= m;
- }
- return(str);
- }
-
- static char *
- parseType(str,typep,modsp,detailp)
- char *str;
- int *typep;
- unsigned int *modsp,*detailp;
- {
- char typestr[32];
- int i;
-
- i = 0;
- while (isalnum(*str) && i < 30)
- typestr[i++] = *str++;
- if (i == 31)
- parseError("event type too long",str);
- typestr[i] = '\0';
- for (i=0; types[i].name!=NULL && strcasecmp(types[i].name,typestr)!=0; i++);
- if (types[i].name == NULL) {
- parseError("unknown event type",typestr);
- *typep = 0;
- } else {
- *typep = types[i].value;
- *detailp = types[i].detail;
- *modsp |= types[i].mods;
- }
- return(str);
- }
-
- static char *
- parseDetail(str,xevp,type,mods,detail)
- char *str;
- XEvent *xevp;
- int type;
- unsigned int mods,detail;
- {
- char detailstr[256];
- int i;
-
- i = 0;
- while (*str && !(i > 0 && *str == ',') && i < 255)
- detailstr[i++] = *str++;
- if (i == 255)
- parseError("detail too long (truncated)",str);
- detailstr[i] = '\0';
- xevp->type = type;
- switch (type) {
- case KeyPress:
- case KeyRelease: {
- XKeyEvent *xkevp = (XKeyEvent *)xevp;
- KeyCode k;
- char *s = strchr(detailstr,' ');
- if (s != NULL)
- *s++ = '\0';
- k = XKeysymToKeycode(display,XStringToKeysym(detailstr));
- if (detail != 0 && k != 0) {
- parseError("key detail conflict",detailstr);
- xkevp->type = -1;
- break;
- } else if (detail == 0)
- xkevp->keycode = k;
- else
- xkevp->keycode = detail;
- if (s != NULL) {
- xkevp->x = (int)strtol(s,&s,0);
- xkevp->y = (int)strtol(s,&s,0);
- xkevp->x_root = (int)strtol(s,&s,0);
- xkevp->y_root = (int)strtol(s,&s,0);
- }
- xkevp->state = mods;
- xkevp->root = root;
- xkevp->same_screen = True;
- break;
- }
- case ButtonPress:
- case ButtonRelease: {
- XButtonEvent *xbevp = (XButtonEvent *)xevp;
- unsigned b = lookup(buttonNames,detailstr);
- if (*detailstr && b == 0) {
- parseError("bad button detail",detailstr);
- xbevp->type = -1;
- break;
- }
- if (detail != 0 && b != 0) {
- parseError("button detail conflict",detailstr);
- xbevp->button = 0;
- } else if (detail == 0)
- xbevp->button = b;
- else
- xbevp->button = detail;
- xbevp->state = mods;
- xbevp->root = root;
- xbevp->same_screen = True;
- break;
- }
- case MotionNotify: {
- XMotionEvent *xmevp = (XMotionEvent *)xevp;
- xmevp->is_hint = lookup(motionDetails,detailstr);
- if (*detailstr && xmevp->is_hint == 0) {
- parseError("bad motion detail",detailstr);
- xmevp->type = -1;
- }
- xmevp->state = mods;
- xmevp->root = root;
- xmevp->same_screen = True;
- break;
- }
- case EnterNotify:
- case LeaveNotify: {
- XCrossingEvent *xcevp = (XCrossingEvent *)xevp;
- char *s = strchr(detailstr,' ');
- if (s != NULL)
- *s++ = '\0';
- xcevp->mode = lookup(notifyModes,detailstr);
- if (s != NULL)
- xcevp->detail = lookup(notifyDetails,s);
- xcevp->state = mods;
- xcevp->root = root;
- xcevp->same_screen = True;
- break;
- }
- case FocusIn:
- case FocusOut: {
- XFocusChangeEvent *xfcevp = (XFocusChangeEvent *)xevp;
- char *s = strchr(detailstr,' ');
- if (s != NULL)
- *s++ = '\0';
- xfcevp->mode = lookup(notifyModes,detailstr);
- if (s != NULL)
- xfcevp->detail = lookup(notifyDetails,s);
- if (*detailstr && xfcevp->mode == 0 && xfcevp->detail == 0) {
- parseError("bad focus mode or detail",detailstr);
- xfcevp->type = -1;
- }
- break;
- }
- case KeymapNotify: {
- XKeymapEvent *xkevp = (XKeymapEvent *)xevp;
- int i;
- char *s = detailstr;
- for (i=0; i < 32; i++)
- xkevp->key_vector[i] = (char)strtol(s,&s,0);
- break;
- }
- case Expose: {
- XExposeEvent *xeevp = (XExposeEvent *)xevp;
- char *s = detailstr;
- xeevp->x = (int)strtol(s,&s,0);
- xeevp->y = (int)strtol(s,&s,0);
- xeevp->width = (int)strtol(s,&s,0);
- xeevp->height = (int)strtol(s,&s,0);
- xeevp->count = (int)strtol(s,&s,0);
- break;
- }
- case GraphicsExpose: {
- XGraphicsExposeEvent *xgevp = (XGraphicsExposeEvent *)xevp;
- char *s = detailstr;
- xgevp->x = (int)strtol(s,&s,0);
- xgevp->y = (int)strtol(s,&s,0);
- xgevp->width = (int)strtol(s,&s,0);
- xgevp->height = (int)strtol(s,&s,0);
- xgevp->count = (int)strtol(s,&s,0);
- xgevp->major_code = (int)strtol(s,&s,0);
- xgevp->minor_code = (int)strtol(s,&s,0);
- break;
- }
- case NoExpose: {
- XNoExposeEvent *xnevp = (XNoExposeEvent *)xevp;
- char *s = detailstr;
- xnevp->major_code = (int)strtol(s,&s,0);
- xnevp->minor_code = (int)strtol(s,&s,0);
- break;
- }
- case CirculateNotify:
- case CirculateRequest: {
- XCirculateEvent *xcevp = (XCirculateEvent *)xevp;
- if ((xcevp->place=lookup(circulateDetails,detailstr)) == 99) {
- parseError("bad circulate detail",detailstr);
- xcevp->type = -1;
- }
- break;
- }
- case ConfigureNotify:
- case ConfigureRequest: {
- XConfigureEvent *xcevp = (XConfigureEvent *)xevp;
- char *s = detailstr;
- xcevp->x = (int)strtol(s,&s,0);
- xcevp->y = (int)strtol(s,&s,0);
- xcevp->width = (int)strtol(s,&s,0);
- xcevp->height = (int)strtol(s,&s,0);
- xcevp->border_width = (int)strtol(s,&s,0);
- xcevp->above = (Window)strtol(s,&s,0);
- SKIPWHITE(s);
- xcevp->override_redirect=lookup(booleans,s);
- break;
- }
- case CreateNotify: {
- XCreateWindowEvent *xcevp = (XCreateWindowEvent *)xevp;
- char *s = detailstr;
- xcevp->x = (int)strtol(s,&s,0);
- xcevp->y = (int)strtol(s,&s,0);
- xcevp->width = (int)strtol(s,&s,0);
- xcevp->height = (int)strtol(s,&s,0);
- xcevp->border_width = (int)strtol(s,&s,0);
- SKIPWHITE(s);
- xcevp->override_redirect=lookup(booleans,s);
- break;
- }
- case DestroyNotify: {
- XDestroyWindowEvent *xdevp = (XDestroyWindowEvent *)xevp;
- xdevp->window = (Window)strtol(detailstr,NULL,0);
- break;
- }
- case GravityNotify: {
- XGravityEvent *xgevp = (XGravityEvent *)xevp;
- char *s = detailstr;
- xgevp->x = (int)strtol(s,&s,0);
- xgevp->y = (int)strtol(s,&s,0);
- break;
- }
- case MapNotify:
- case MapRequest: {
- XMapEvent *xmevp = (XMapEvent *)xevp;
- xmevp->override_redirect = lookup(booleans,detailstr);
- break;
- }
- case MappingNotify: {
- XMappingEvent *xmevp = (XMappingEvent *)xevp;
- char *s=strchr(detailstr,' ');
- if (s != NULL)
- *s++ = '\0';
- if ((xmevp->request=lookup(mappingDetails,detailstr)) == 0) {
- parseError("bad mapping detail",detailstr);
- xmevp->type = -1;
- }
- if (xmevp->request == MappingKeyboard && s != NULL) {
- SKIPWHITE(s);
- xmevp->first_keycode = (int)strtol(s,&s,0);
- xmevp->count = (int)strtol(s,&s,0);
- }
- break;
- }
- case ReparentNotify: {
- XReparentEvent *xrevp = (XReparentEvent *)xevp;
- char *s = strchr(detailstr,' ');
- if (s != NULL)
- *s++ = '\0';
- xrevp->parent = (Window)strtol(detailstr,NULL,0);
- if (s != NULL) {
- SKIPWHITE(s);
- xrevp->x = (int)strtol(s,&s,0);
- xrevp->y = (int)strtol(s,&s,0);
- SKIPWHITE(s);
- xrevp->override_redirect = lookup(booleans,s);
- }
- break;
- }
- case UnmapNotify: {
- XUnmapEvent *xuevp = (XUnmapEvent *)xevp;
- xuevp->from_configure = lookup(booleans,detailstr);
- break;
- }
- case VisibilityNotify: {
- XVisibilityEvent *xvevp = (XVisibilityEvent *)xevp;
- xvevp->state = lookup(visibilityDetails,detailstr);
- break;
- }
- case ResizeRequest: {
- XResizeRequestEvent *xrevp = (XResizeRequestEvent *)xevp;
- char *s = detailstr;
- xrevp->width = (int)strtol(s,&s,0);
- xrevp->height = (int)strtol(s,&s,0);
- break;
- }
- case ColormapNotify:
- parseError("can't handle ColormapNotify events","");
- xevp->type = -1;
- break;
- case ClientMessage: {
- XClientMessageEvent *xcevp = (XClientMessageEvent *)xevp;
- char *s = strchr(detailstr,' ');
- int i;
- if (*detailstr == '\0') {
- parseError("missing atom for client message","");
- xcevp->type = -1;
- break;
- }
- if (s != NULL)
- *s++ = '\0';
- xcevp->message_type = XInternAtom(display,detailstr,True);
- if (s != NULL) {
- SKIPWHITE(s);
- if (*s == 'b') {
- xcevp->format = 8;
- SKIPWHITE(s);
- for (i=0; i < 20; i++)
- xcevp->data.b[i] = (char)strtol(s,&s,0);
- } else if (*s == 'c') {
- xcevp->format = 8;
- SKIPWHITE(s);
- for (i=0; i < 20; i++)
- xcevp->data.b[i] = *s++;
- } else if (*s == 's') {
- xcevp->format = 16;
- SKIPWHITE(s);
- for (i=0; i < 10; i++)
- xcevp->data.s[i] = (short)strtol(s,&s,0);
- } else if (*s == 'l') {
- xcevp->format = 32;
- SKIPWHITE(s);
- for (i=0; i < 5; i++)
- xcevp->data.l[i] = strtol(s,&s,0);
- }
- }
- }
- case PropertyNotify: {
- XPropertyEvent *xpevp = (XPropertyEvent *)xevp;
- char *s = strchr(detailstr,' ');
- if (*detailstr == '\0') {
- parseError("missing atom for property notify","");
- xpevp->type = -1;
- break;
- }
- if (s != NULL)
- *s++ = '\0';
- xpevp->atom = XInternAtom(display,detailstr,True);
- if (s != NULL) {
- SKIPWHITE(s);
- xpevp->state = lookup(propertyDetails,s);
- }
- xpevp->time = CurrentTime;
- break;
- }
- case SelectionClear: {
- XSelectionClearEvent *xsevp = (XSelectionClearEvent *)xevp;
- if (*detailstr == '\0') {
- parseError("missing atom for selection clear","");
- xsevp->type = -1;
- break;
- }
- xsevp->selection = XInternAtom(display,detailstr,True);
- xsevp->time = CurrentTime;
- break;
- }
- /* Note SelectionRequest and Selection are identical except the
- event types have different structures (and different errors). */
- case SelectionRequest: {
- XSelectionRequestEvent *xsevp = (XSelectionRequestEvent *)xevp;
- char *s1 = detailstr;
- char *s2,*s3;
- if (*s1 == '\0') {
- parseError("missing atom for selection request (selection)","");
- xsevp->type = -1;
- break;
- }
- if ((s2=strchr(s1,' ')) == NULL) {
- parseError("missing atom for selection request (target)","");
- xsevp->type = -1;
- break;
- }
- *s2++ = '\0';
- SKIPWHITE(s2);
- if ((s3=strchr(s2,' ')) == NULL) {
- parseError("missing atom for selection request (property)","");
- xsevp->type = -1;
- break;
- }
- *s3++ = '\0';
- SKIPWHITE(s3);
- xsevp->selection = XInternAtom(display,s1,True);
- xsevp->target = XInternAtom(display,s2,True);
- if (*s3 == '\0' || strcasecmp(s3,"None") == 0)
- xsevp->property = None;
- else
- xsevp->property = XInternAtom(display,s3,True);
- xsevp->time = CurrentTime;
- }
- case SelectionNotify: {
- XSelectionEvent *xsevp = (XSelectionEvent *)xevp;
- char *s1 = detailstr;
- char *s2,*s3;
- if (*s1 == '\0') {
- parseError("missing atom for selection notify (selection)","");
- xsevp->type = -1;
- break;
- }
- if ((s2=strchr(s1,' ')) == NULL) {
- parseError("missing atom for selection notify (target)","");
- xsevp->type = -1;
- break;
- }
- *s2++ = '\0';
- SKIPWHITE(s2);
- if ((s3=strchr(s2,' ')) == NULL) {
- parseError("missing atom for selection notify (property)","");
- xsevp->type = -1;
- break;
- }
- *s3++ = '\0';
- SKIPWHITE(s3);
- xsevp->selection = XInternAtom(display,s1,True);
- xsevp->target = XInternAtom(display,s2,True);
- if (*s3 == '\0' || strcasecmp(s3,"None") == 0)
- xsevp->property = None;
- else
- xsevp->property = XInternAtom(display,s3,True);
- xsevp->time = CurrentTime;
- }
- default:
- parseError("don't understand event type\n","");
- xevp->type = -1;
- }
- return(str);
- }
-
- static void
- parseError(s1,s2)
- char *s1,*s2;
- {
- if (*s2 == '\0')
- fprintf(stderr,"xse: %s\n",s1);
- else
- fprintf(stderr,"xse: %s: \"%s\"\n",s1,s2);
- }
-
- void
- freeEventList(p)
- EventListPtr p;
- {
- EventListPtr q;
-
- while (p != NULL) {
- q = p;
- p = p->next;
- free(q);
- }
- }
-