# Pass struct with mutable array field to ccall?

**URL:** <https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576>\
**Category:** New to Julia\
**Tags:** ccall\
**Created:** [July 20, 2019, 6:07am UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576 "2019-07-20T06:07:30Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![tuckermcclure](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tuckermcclure/32/1187_2.png) [@tuckermcclure](https://discourse.julialang.org/u/tuckermcclure)\
**Post date:** [July 20, 2019, 6:07am UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/1 "2019-07-20T06:07:31Z")

</div>

I need to call a C interface that has a struct argument like so:

```nohighlight
typedef struct {
    double a[2];
} MyStruct;

```

I know I can could use the following Julia type to represent my data and pass that to `ccall`:

```julia
mutable struct MyJStruct
    a::NTuple{2, Float64}
end

x = MyJStruct((1., 2.))
ccall(f, Nothing, (MyJStruct,), x)

```

However, the `MyJStruct` type wouldn’t be useful to me in Julia. I frequently need to edit the values in the array in the type, which of course I can’t do when it’s represented as a Tuple. I can’t find a way to get a mutable type to work there.

Does the type of thing passed to `ccall` have to be a bits type and immutable? If so, is there some other way to do what I’m trying to do, like derive an immutable bits type from my mutable one?

Obviously, this is a tiny example, and my real type has many fields that are arrays of known length, hence I despair of having to create parallel types by hand or something like that.

---

<div class="post-metadata">

**Author:** ![tkoolen](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tkoolen/32/1603_2.png) [@tkoolen](https://discourse.julialang.org/u/tkoolen)\
**Post date:** [July 20, 2019, 1:23pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/2 "2019-07-20T13:23:41Z")

</div>

Maybe you could use a `StaticArrays.MVector{2, Float64}`?

---

<div class="post-metadata">

**Author:** ![tuckermcclure](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tuckermcclure/32/1187_2.png) [@tuckermcclure](https://discourse.julialang.org/u/tuckermcclure)\
**Post date:** [July 20, 2019, 4:31pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/3 "2019-07-20T16:31:52Z")

</div>

Hi Twan, and thanks. I tried an `MVector`, and that didn’t work. I filled it with data, but over on the C side, all I saw was a bunch of 0s. When I use an `SVector`, it works (the data is carried over to C correclty), but of course that’s not mutable and so still isn’t useful here. I confirmed that the type is a bits type when using an SVector, but not when using an MVector (I don’t know the internals of StaticArrays except that it uses tuples).

---

<div class="post-metadata">

**Author:** ![yuyichao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yuyichao/32/20_2.png) [@yuyichao](https://discourse.julialang.org/u/yuyichao)\
**Post date:** [July 20, 2019, 6:07pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/4 "2019-07-20T18:07:20Z")

</div>

No it won’t work with any mutable types. You should be able to mutate that field just fine with an immutable type though. Unless you need concurrent access of different array element svector should work.

---

<div class="post-metadata">

**Author:** ![tuckermcclure](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tuckermcclure/32/1187_2.png) [@tuckermcclure](https://discourse.julialang.org/u/tuckermcclure)\
**Post date:** [July 20, 2019, 6:16pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/5 "2019-07-20T18:16:44Z")

</div>

Thanks @yuyichao. An `SVector` in fact gets the data over to C correctly, but it fundamentally fails my use case: I need to be able to edit fields and indices of these types in Julia and then send them over to C. Am I supposed to have a mutable type that I use in Julia, then a parallel type that’s immutable but equivalent (e.g., SVector in the immutable version instead of array or MVector in the mutable one) and then have a conversion from the mutable type to the immutable one so that I can send the data over to C? And then, after the `ccall`, a conversion back from immutable to mutable so I can continue using things in Julia? This feels excessive.

Is there any other way I can “just gather my bits together to send them over”?

---

<div class="post-metadata">

**Author:** ![yuyichao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yuyichao/32/20_2.png) [@yuyichao](https://discourse.julialang.org/u/yuyichao)\
**Post date:** [July 20, 2019, 6:28pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/6 "2019-07-20T18:28:27Z")

</div>

No there’s no failure at all and you don’t need two types. Again, you just mutate the field and not the object stored in the field, same way you reassign a variable that hold a immutable object. Please read the document of svector for the helper functions that allow you to construct an object with one of the elements changed.

---

<div class="post-metadata">

**Author:** ![tuckermcclure](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tuckermcclure/32/1187_2.png) [@tuckermcclure](https://discourse.julialang.org/u/tuckermcclure)\
**Post date:** [July 20, 2019, 7:01pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/7 "2019-07-20T19:01:58Z")

</div>

Thanks again, @yuyichao. I read more into the StaticArrays doc. If I understand you correctly, you mean to use an `SVector` for the field along with `setindex` (no exclamation) for the “mutation”:

```julia
using StaticArrays

mutable struct MyJStruct
    a::SVector{2, Float64}
end

# Create our type.
x = MyJStruct([1., 2.])

# This would fail.
# x.a[1] = 3.

# This works as long as my struct type is mutable.
x.a = setindex(x.a, 3., 1)

display(x.a[1])
display(isbits(x))

```

In this way, I’m changing the index of the thing that I care about. Here `MyJStruct` would have to be mutable too, and it’s not a bits type. Is this what you’re suggesting?

That seems to conflict with what you were saying above, that I’ll need all immutables. It does, however, still seem to send this data over to C the right way.

---

<div class="post-metadata">

**Author:** ![yuyichao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yuyichao/32/20_2.png) [@yuyichao](https://discourse.julialang.org/u/yuyichao)\
**Post date:** [July 20, 2019, 10:01pm UTC](https://discourse.julialang.org/t/pass-struct-with-mutable-array-field-to-ccall/26576/8 "2019-07-20T22:01:55Z")

</div>

Yes the type with that mutable field needs to be mutable and I don’t think I’ve said anything about it above since you’ve got that part fine in the first post.
