Wiki
Download
Manual
Eggs
API
Tests
Bugs
show
edit
history
You can edit this page using
wiki syntax
for markup.
Article contents:
[[tags: manual]] [[toc:]] == Accessing externally defined data For a list of the special forms that allow definition of Scheme procedures that access native C/C++ code, consult the documentation on the [[Module (chicken foreign)|(chicken foreign)]] module. The remainder of this chapter merely explains a few special cases. == Returning large objects or chunks of memory to Scheme When you call a C function which needs to return quantities of data, several issues arise: * the size of the nursery is limited, so {{C_alloc}} can cause stack overflow * if you malloc in C, and intend to leave it there, and directly access parts of that data from Scheme, you will need C accessor functions to pinpoint the parts you need and return them as Scheme objects; you will also need a finalizer if you intend for this data to be garbage-collected * building up lists or other complex Scheme structures from individual pairs, or putting non-immediate objects into vectors, is cumbersome in C So some would advise you to just return a pointer to Scheme, use memcpy or any other function(s) which you need to get the data into CHICKEN-managed memory and into the desired kind of data structure, then free the C data. For this example, we are trying to return an array of doubles into an {{f64vector}}; we can accomplish that by adding a specialized copy function to the C library being integrated: <enscript highlight=C> void CopyResults(double* vector) { memcpy(vector, bezierBuffer, totalOutputPoints * sizeof(double)); } // The original C function which takes an array of doubles, // does some sort of transmogrification, // retains a new malloc'd array of the results // and returns the count int GenerateResults(double* vector, int count) { ... } </enscript> and the "egg" which calls the C functions can be implemented like this: <enscript highlight=scheme> (module memcpy-demo (input->output) (import (chicken base) scheme (chicken foreign) srfi-4) (define CopyResults (foreign-lambda void "CopyResults" f64vector)) (define GenerateResults (foreign-lambda integer "GenerateResults" f64vector integer)) (define (input->output input) (let* ([size (GenerateResults input (f64vector-length input))] [vect (make-f64vector size)]) (printf "returned size ~a~%" size) (CopyResults vect) vect))) </enscript> The foreign-lambda takes care of the details in this case so that an f64vector allocated in the nursery can be treated as a plain old array of doubles in C (assuming your C compiler uses 64-bit values for double). Various eggs provide other examples, and some of them do it more efficiently too, but this method is relatively clean and compact. --- Previous: [[Interface to external functions and variables]] Next: [[Foreign type specifiers]]
Description of your changes:
I would like to authenticate
Authentication
Username:
Password:
Spam control
What do you get when you multiply 5 by 6?