On this page:
define-serializable-cstruct

5.4 Serializable C Struct Types

 (require ffi/serialize-cstruct)
  package: serialize-cstruct-lib

syntax

(define-serializable-cstruct _id ([field-id type-expr] ...)
                             property ...)
 
property = #:alignment alignment-expr
  | #:malloc-mode malloc-mode-expr
  | #:serialize-inplace
  | #:deserialize-inplace
  | #:property prop-expr val-expr
Like define-cstruct, but defines a serializable type. In addition to the bindings created by define-cstruct, make-id/mode is bound to a function that behaves like make-id but uses the mode or allocator specified via malloc-mode-expr.

Instances of the new type fulfill the serializable? predicate and can be used with serialize and deserialize. Serialization may fail if one of the fields contains an arbitrary pointer, an embedded non-serializable C struct, or a pointer to a non-serializable C struct. Array-types are supported as long as they don’t contain one of these types.

The malloc-mode-expr arguments control the memory allocation for this type during deserialization and make-id/mode. It can be one of the mode arguments to malloc, or a procedure
that allocates memory of the given size. The default is malloc with 'atomic.

When #:serialize-inplace is specified, the serialized representation shares memory with the C struct object. While being more efficient, especially for large objects, changes to the object after serialization may lead to changes in the serialized representation.

A #:deserialize-inplace option reuses the memory of the serialized representation, if possible. This option is more efficient for large objects, but it may fall back to allocation via malloc-mode-expr for cyclic structures. As the allocation mode of the serialized representation will be 'atomic by default or may be arbitrary if #:serialize-inplace is specified, inplace deserialisation should be used with caution whenever the object contains pointers.

When the C struct contains pointers, it is advisable to use a custom allocator. It should be based on a non-moving-memory allocation like 'raw, potentially with manual freeing to avoid memory leaks after garbage collection.