# @ccall: returning a pointer to an array

**URL:** https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329
**Category:** General Usage
**Tags:** ccall
**Created:** [January 4, 2024, 5:48am UTC](https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329 "2024-01-04T05:48:18Z")
**Posts on this page:** 5
**Page:** 1

<div class="post-metadata">

### Author: ![rmfritz](https://avatars.discourse-cdn.com/v4/letter/r/b487fb/32.png) [@rmfritz](https://discourse.julialang.org/u/rmfritz)
#### Post date: [January 4, 2024, 5:48am UTC](https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329/1 "2024-01-04T05:48:18Z")

</div>

I am trying to wrap a C function that returns a pointer to an array of UInt8, and I can’t quite figure out how to pass that pointer in.

The C function signature is:

```
int tmMapPicture(uby8 **psp, int *xp, int *yp, …

```

A pointer to an UInt8 array is stored in \*psp, and pointers to integers are stored in xp and yp.

What I have written in Julia is:

```
x = y = 0
imarr = Ptr{Vector{Cuchar}}(C_NULL)
err = @ccall tmMapPicture(
    imarr::Ref{Ptr{Vector{Cuchar}}},
    x::Ref{Int}, y::Ref{Int}, …

```

And it doesn’t work. I can tell the function is getting called because it returns an error code if I give it a bad file, but when I give it a valid file, imarr, x, and y all come back zeros. I think I’m missing something obvious. Can anyone tell me what it is?

---

<div class="post-metadata">

### Author: ![torrance](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/torrance/32/38990_2.png) [@torrance](https://discourse.julialang.org/u/torrance)
#### Post date: [January 4, 2024, 11:23am UTC](https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329/2 "2024-01-04T11:23:38Z")

</div>

Assuming the C code is doing the memory allocation, I think (untested - but it’s something like this!) the way to do this is:

```julia
x = Ref{Cint}()
y = Ref{Cint}()
imarr = Ref{Ptr{Cuchar}}()
@ccall tmMapPicture(
    imarr::Ptr{Ptr{Cuchar}},
    x::Ptr{Cint}, y::Ptr{Cint}, ...
)::Mint

```

Note a few things:

- I’ve created `x` and `y` as references. You can only safely take a pointer to a heap allocated variable: e.g. a `Ref` or an `Array`.
- The type of imarr is not a reference to a _vector_, but just the `unsigned char*`.
- I’ve changed the types of x, y to `Cint`, which is presumably 32 bit on your system and not 64 bit like `Int` is.
- The `@ccall` will handle the conversation version from Ref to Ptr (and the same is true for Array to Ptr).

If you then want to access the pointer as if it were an array you would do:

```julia
arr = unsafe_wrap(Array, imarr[], dims)

```

By default, `unsafe_wrap()` will not own the memory and therefore won’t attempt to free the memory when it falls out of scope. If the C api you called allocated the memory, it should also provide a corresponding free api. If it doesn’t provide an API, you can l pass `own=true` to `unsafe_wrap()` and Julia will attempt to free the memory (technically, this requires compatible allocators by both Julia and the C api).

---

<div class="post-metadata">

### Author: ![rmfritz](https://avatars.discourse-cdn.com/v4/letter/r/b487fb/32.png) [@rmfritz](https://discourse.julialang.org/u/rmfritz)
#### Post date: [January 5, 2024, 1:22am UTC](https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329/3 "2024-01-05T01:22:03Z")

</div>

Thank you! I ended up with:

```
xp = Ref{Cint}() # cols
yp = Ref{Cint}() # rows
psp = Ref{Ptr{Cuchar}}()
err = @ccall tmMapPicture(
    psp::Ptr{Ptr{Cuchar}},
    xp::Ptr{Cint}, yp::Ptr{Cint}, …
[…]
imagepixels = unsafe_wrap(Array, psp[], Int.((3, xp[], yp[])))

# …code to convert to JuliaImages goes here…

Libc.free(psp[]) # I hope this is correct

```

And this seems to work, though I’m still uncertain of the order of the array dimensions. (Added: they were wrong; I’ve corrected them.) Also not sure if I have the `free()` correct, though the storage is allocated with `malloc()` in the loaded library – perhaps I ought to add a routine which calls `free()` to the library.

---

<div class="post-metadata">

### Author: ![vettert](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/vettert/32/30599_2.png) [@vettert](https://discourse.julialang.org/u/vettert)
#### Post date: [January 5, 2024, 3:40am UTC](https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329/4 "2024-01-05T03:40:54Z")

</div>

Have you checked the underlying library whether it has a way to free the memory? (What library is it?) Safer to use the specific and built in way to do it, rather than calling libc yourself.

---

<div class="post-metadata">

### Author: ![rmfritz](https://avatars.discourse-cdn.com/v4/letter/r/b487fb/32.png) [@rmfritz](https://discourse.julialang.org/u/rmfritz)
#### Post date: [January 5, 2024, 4:13am UTC](https://discourse.julialang.org/t/ccall-returning-a-pointer-to-an-array/108329/5 "2024-01-05T04:13:09Z")

</div>

The underlying library uses `malloc()`/`free()`, neither defined in the library. Is there reason to wrap `free()` in a function and add it to the library?
