From 99fc8542b7595c4080cab2d72cb82903c5fb24f7 Mon Sep 17 00:00:00 2001 From: Kaz Kylheku Date: Wed, 3 May 2017 20:58:12 -0700 Subject: ffi: fix semantics of ptr-out-d. Since the callee allocates the buffer for a ptr-out-d, the FFI mechanism should not also be allocating a buffer to receive the object. The buffer pointer will just be overwritten by the callee with its own dynamic pointer. We should pass a null pointer which the callee fills in (making a ptr-out-d not suitable as a by-value parameter). Initially, ptr-out-d was envisioned for return values only and for use in callbacks, which is why I neglected this aspect. * ffi.c (ffi_ptr_out_null_put): New static function. (ffi_type_compile): Use ffi_ptr_out_null_put for the ffi_ptr_out_d case, so caller places a null pointer, then frees the pointer that the callee places there. --- ffi.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/ffi.c b/ffi.c index 29d943be..8664ea64 100644 --- a/ffi.c +++ b/ffi.c @@ -780,6 +780,12 @@ static void ffi_ptr_in_put(struct txr_ffi_type *tft, val s, mem_t *dst, } } +static void ffi_ptr_out_null_put(struct txr_ffi_type *tft, val s, mem_t *dst, + val self) +{ + *coerce(mem_t **, dst) = 0; +} + static val ffi_struct_in(struct txr_ffi_type *tft, mem_t *src, val strct, val self) { @@ -1282,7 +1288,7 @@ val ffi_type_compile(val syntax) val target_type = ffi_type_compile(cadr(syntax)); return make_ffi_type_pointer(syntax, cptr_s, sizeof (mem_t *), &ffi_type_pointer, - ffi_ptr_out_put, ffi_ptr_d_get, + ffi_ptr_out_null_put, ffi_ptr_d_get, ffi_ptr_out_in, ffi_ptr_out_out, target_type); } else if (sym == ptr_s) { -- cgit v1.2.3