Finally, one last note on foreign values before moving on to actually
calling foreign functions. Sometimes you need to deal with C structs,
which requires interpreting each element of the struct according to the
its type, offset, and alignment. The (system foreign)
module has
some primitives to support this.
(use-modules (system foreign))
Return the size of type, in bytes.
type should be a valid C type, like int
.
Alternately type may be the symbol *
, in which
case the size of a pointer is returned. type may
also be a list of types, in which case the size of a
struct
with ABI-conventional packing is returned.
Return the alignment of type, in bytes.
type should be a valid C type, like int
.
Alternately type may be the symbol *
, in which
case the alignment of a pointer is returned. type may
also be a list of types, in which case the alignment of a
struct
with ABI-conventional packing is returned.
Guile also provides some convenience methods to pack and unpack foreign pointers wrapping C structs.
Create a foreign pointer to a C struct containing vals with types
types
.
vals and types
should be lists of the same length.
Parse a foreign pointer to a C struct, returning a list of values.
types
should be a list of C types.
For example, to create and parse the equivalent of a struct {
int64_t a; uint8_t b; }
:
(parse-c-struct (make-c-struct (list int64 uint8) (list 300 43)) (list int64 uint8)) ⇒ (300 43)
As yet, Guile only has convenience routines to support
conventionally-packed structs. But given the bytevector->pointer
and pointer->bytevector
routines, one can create and parse
tightly packed structs and unions by hand. See the code for
(system foreign)
for details.