[Larceny-users] Passing bytevectors to C via the FFI

Lars T Hansen lth at acm.org
Sat Dec 15 16:26:23 EST 2007


Unless you're calling back into Scheme from C, letting the C code
retain a pointer into the bytevector, or Larceny has become
multithreaded (and one thread can cause GC while another is inside a
foreign call), you should be safe.

The Right Thing for the FFI is to provide pinning, but when I wrote
the code for the FFI (and the GC) originally I did not implement that,
and now and then I ended up writing wrappers that would malloc memory
and use copy-in/copy-out to transport data between Scheme and C.

--lars

On Dec 15, 2007 9:34 PM, Ray Racine <ray.racine at comcast.net> wrote:
> I just finished typing up the code below, and it works, but as I looked
> at it I'm worried it only works sometimes.
>
> The sig of the C function gethostname is
>
>  int gethostname(char *name, size_t len);
>
> It populates name with up to len chars of the hostname.  Below I use a
> boxed arg for name and pass a scheme heap allocated bytevector.
>
> I'm wondering if this is safe.  i,e, A GC won't move the bytevector or
> some other problem.  Or is a locally allocated heap object effectively
> pinned for the duration of the call?
>
> Q. When passing a char * buffer to a C function via the FFI is using a
> scheme allocated bytevector safe or should one be doing some kind of
> malloc call to allocate memory outside the auspices of the GC?
>
> Sorry if this is kind of obvious, my Scheme/C foo is not strong.
>
> Thanks,
>
> Ray
>
>
> (define c-gethostname (foreign-procedure "gethostname" '(boxed int)
> 'unsigned))
>
> (define get-hostname
>   (lambda ()
>     (define MAX-HOST 256)
>
>     (define null-offset
>       (lambda (bytes)
>         (let loop ((idx 0))
>           (if (fx=? (bytevector-u8-ref bytes idx) 0)
>               idx
>               (loop (fx+ idx 1))))))
>
>     (let ((buff (make-bytevector MAX-HOST 0)))
>       (let ((result (c-gethostname buff MAX-HOST)))
>         ;; man page says truncation is unspecified
>         (bytevector-u8-set! buff (fx- MAX-HOST 1) 0)
>         (substring (utf8->string buff) 0 (null-offset buff))))))
>
>
> _______________________________________________
> Larceny-users mailing list
> Larceny-users at lists.ccs.neu.edu
> https://lists.ccs.neu.edu/bin/listinfo/larceny-users
>



More information about the Larceny-users mailing list