<div dir="auto"><div dir="auto">I would return a malloced pointer. After that, it depends on what you want to do with the Foo.</div><div dir="auto"><br></div><div dir="auto">If you just want to pass it to other C stuff and don't want to read its contents from Haskell, I would wrap it in an opaque ForeignPtr to be freed or make sure it gets freed with a `bracket`. Then there's no awkwardness with generating/updating a Storable instance.</div><div dir="auto"><br></div><div dir="auto">If you need the contents from Haskell, peek it and free it immediately. Haskell's alloca also allocates internally so it's not like it would be on the stack in any case.</div><div dir="auto"><br></div><div dir="auto">The important thing is that any bit of code that deals with raw pointers with no cleanup registered must have async exceptions masked, otherwise if one is thrown the memory will be leaked.<br><br><div class="gmail_quote" dir="auto"><div dir="ltr" class="gmail_attr">On Tue, Jun 16, 2020, 16:45 ☂Josh Chia (謝任中) <<a href="mailto:joshchia@gmail.com">joshchia@gmail.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir="ltr">Suppose I have the following C code:<div><br></div><div>typedef struct Foo {</div><div>    char* p1;  /* Some data on the heap. */</div><div>    size_t s1; /* Size of data. */</div><div>    char* p2;  /* More data on the heap. */</div><div>    size_t s2;</div><div>} Foo;</div><div><br></div><div>/* Allocates and writes two pieces of data on the heap and returns them in a Foo. */<br></div><div>Foo makeFoo(size_t x);</div><div><br></div><div>Based on my limited understanding of Haskell FFI according to the Haskell 2010 Language Report (<a href="https://www.haskell.org/onlinereport/haskell2010/haskellch8.html" target="_blank" rel="noreferrer">https://www.haskell.org/onlinereport/haskell2010/haskellch8.html</a>), it is not possible to have a ccall for makeFoo() because Foo is not a marshallable foreign result type. Is my understanding correct?</div><div><br></div><div>However, I believe I can have a ccall if I change makeFoo() to either of the following:</div><div>Foo* makeFoo(size_t x);</div><div>void makeFoo(Foo* out, size_t x);</div><div><br></div><div>The first involves the C code allocating a Foo and returning a pointer to it (so now there's one more pointer for the C code to deallocate later in another function). The second involves the C code writing a Foo value to a piece of memory allocated in Haskell (possibly using Foreign.Marshall.Alloc.alloca). Both signatures work because Foo* is marshallable but are clumsier to use than the original signature. Is there just no way to return a struct by value on the stack? Is there a cleaner way than the above two?</div><div><br></div><div>Josh</div></div>
_______________________________________________<br>
Haskell-Cafe mailing list<br>
To (un)subscribe, modify options or view archives go to:<br>
<a href="http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe" rel="noreferrer noreferrer" target="_blank">http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe</a><br>
Only members subscribed via the mailman list are allowed to post.</blockquote></div></div></div>