I agree with this. The code Laurent is talking about is my x11 ffi bindings. Laurent, feel free to make this change and push to the repo. I'm not sure why I didn't use the super struct thing to begin with, maybe it didn't exist when I initially wrote the bindings.
https://github.com/kazzmir/x11-racket for anyone interested. On 10/26/2012 02:26 PM, Matthew Flatt wrote: > That seems like an ok solution. > > I would be tempted to write > > (define-cstruct _XEvent ([type _int])) > > (define-cstruct (_XAnyEvent _XEvent) ([serial _ulong] > ....)) > (define-cstruct (_XKeyEvent _XEvent) ([serial _ulong] > ....)) > .... > > Those declarations more directly fit the sub-structuring that is > implemented by the union in "Xlib.h", but it doesn't give you > `XAnyEvent-type', `XKeyEvent-type', etc., and the size of `_XEvent' > isn't the maximum of the variant sizes. > > At Fri, 26 Oct 2012 19:00:01 +0200, Laurent wrote: >> Oooohh, I think I understand now: the way it was is already sufficiently >> general. >> The writer of the initial code took a different direction. >> Instead of defining a union type, he changes the tag of the pointer >> depending on what kind of type he needs in the union: >> (cpointer-push-tag! e XAnyEvent-tag) >> (case (XAnyEvent-type e) >> ((KeyPress) (cpointer-push-tag! e XKeyPressedEvent-tag)) >> ((KeyRelease) (cpointer-push-tag! e XKeyReleasedEvent-tag)) >> .... >> >> It's pretty smart. Is it the right way to go in general, and should _unions >> be avoided? >> >> Laurent >> >> On Fri, Oct 26, 2012 at 6:39 PM, Laurent <laurent.ors...@gmail.com> wrote: >> >>> Hi, >>> >>> I am trying to convert an FFI cstruct definition into a union. >>> More exactly, the previous definition was : >>> (define-cstruct _XEvent >>> ((type EventType))) >>> >>> with EventType being defined elsewhere. >>> But this was an incomplete definition, and I now want to translate the >>> following C union: >>> typedef union _XEvent { >>> int type; /* must not be changed; first element */ >>> XAnyEvent xany; >>> XKeyEvent xkey; >>> // ... the rest for later >>> } XEvent; >>> >>> I searched the collects directory, but I see only a single and too simple >>> _union use, so I'm not sure how to use it. >>> I guessed the following: >>> (define _XEvent >>> (_union EventType ; type >>> _XAnyEvent ; xany >>> _XKeyEvent ; xkey >>> ; etc. >>> )) >>> (define (XEvent-type ev) (union-ref ev 0)) >>> (define (XEvent-xany ev) (union-ref ev 1)) >>> (define (XEvent-xkey ev) (union-ref ev 2)) >>> >>> However, now I don't use define-cstruct anymore (it would not work with >>> _union, would it?), so I don't have all the -tag, -pointer, etc. bindings, >>> which I need. >>> >>> What should I do ? >>> >>> Thanks, >>> Laurent >>> >>> >> ____________________ >> Racket Users list: >> http://lists.racket-lang.org/users > ____________________ > Racket Users list: > http://lists.racket-lang.org/users ____________________ Racket Users list: http://lists.racket-lang.org/users