# Calling C function with pointer of C strings works once but not twice

**URL:** https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632
**Category:** New to Julia
**Tags:** question, ccall, strings
**Created:** [September 7, 2023, 9:48pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632 "2023-09-07T21:48:37Z")
**Posts on this page:** 12
**Page:** 1

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 7, 2023, 9:48pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/1 "2023-09-07T21:48:37Z")

</div>

Hi, I’ve written a wrapper to a C library ([GitHub - dforero0896/libpowspec: Library based on Cheng Zhao's powspec code](https://github.com/dforero0896/libpowspec)) in here [GitHub - dforero0896/Powspec.jl: Julia bindings to Cheng Zhao's powspec C code.](https://github.com/dforero0896/Powspec.jl) . While my initial tests worked, when actually using the tools in my daily research, I find that calling the same function twice with the same data does not work.  
Some details. I modified a C code into a library I could compile and then call externally. To do this I made a function that accepts argc and argv (which sounded really simple back then since I wouldn;t have to modify much of the internals of the code). Everything seems to work fine when calling a function (say `power_spectrum`) once, that is, line 90 in `src/box_periodic.jl` works and `auto_output` is properly defined. On the second call, the same variable is no longer properly defined, as calling the external library yields an error, complaining that the “command line argument” is not understood. The first time arround the command to be passed is `auto_output = "--auto=[test1.dat, test1.dat]"`, and the second, it is somehow turned into `auto_output = "--auto\0[test1.dat\0 test1.dat\0"`. Does someone have any idea about what is happening here?

Thanks in advance

---

<div class="post-metadata">

### Author: ![GunnarFarneback](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gunnarfarneback/32/1827_2.png) [@GunnarFarneback](https://discourse.julialang.org/u/GunnarFarneback)
#### Post date: [September 7, 2023, 10:29pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/2 "2023-09-07T22:29:54Z")

</div>

The command line parser is probably mutating the string you send to it, similar to what is happening here:

```julia
julia> x = "a=b"
"a=b"

julia> unsafe_store!(pointer(x), '\0', 2)
Ptr{UInt8} @0x00007fde495a0330

julia> x
"a\0b"

```

---

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 7, 2023, 11:11pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/3 "2023-09-07T23:11:25Z")

</div>

But I create the string inside the function call, I would expect changes that may have happened to it in the first call, wouldn’t matter afterwards. I mean, the string is defined as

```julia
auto_output = "--auto=[test1.dat, test1.dat]"
@show auto_output

```

and then the `@show` line shows something different each time, even before calling the C function.

---

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 7, 2023, 11:21pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/4 "2023-09-07T23:21:24Z")

</div>

Issue seems to be solved by changing

```julia
auto_output_ptr = Cstring(pointer(auto_output))`

```

to

```julia
auto_output_ptr = Cstring(pointer(deepcopy(auto_output)))

```

though I still don’t understand why.

---

<div class="post-metadata">

### Author: ![stevengj](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stevengj/32/71_2.png) [@stevengj](https://discourse.julialang.org/u/stevengj)
#### Post date: [September 8, 2023, 1:52am UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/5 "2023-09-08T01:52:11Z")

</div>

You have to make sure the string object is rooted, .eg. with `GC.@preserve`, so that it doesn’t get garbage collected before you are done with the pointer.

---

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 8, 2023, 11:20am UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/6 "2023-09-08T11:20:46Z")

</div>

But what would I need the same pointer for two different function calls if the string object is created inside each of them? My guess would have been that they are different objects completely independent from each other.

---

<div class="post-metadata">

### Author: ![GunnarFarneback](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gunnarfarneback/32/1827_2.png) [@GunnarFarneback](https://discourse.julialang.org/u/GunnarFarneback)
#### Post date: [September 8, 2023, 11:48am UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/7 "2023-09-08T11:48:35Z")

</div>

Strings are semantically immutable in Julia, so there is no reason to create new copies every time the function is run. You can see that it is at the same memory address in every call:

```julia
julia> function f()
           x = "abc"
           println(pointer(x))
           return x
       end
f (generic function with 1 method)

julia> f();
Ptr{UInt8} @0x00007f0862c0eb38

julia> f();
Ptr{UInt8} @0x00007f0862c0eb38

```

Now if someone gets behind the back of the compiler and modifies the memory storing the string anyway, e.g. with `unsafe_store!` (which is named unsafe for a reason) or a `ccall` (which always is unsafe), you will see that modification in future calls:

```julia
julia> function g()
           x = "abc"
           println(x)
           unsafe_store!(pointer(x), 'x', 1)
           return x
       end
g (generic function with 1 method)

julia> g()
abc
"xbc"

julia> g()
xbc
"xbc"

```

That’s why it helps to send a copy of the string in your `ccall`. The argument parser mutates that copy but the next time you call the function you make a fresh copy of the uncorrupted original string.

---

<div class="post-metadata">

### Author: ![stevengj](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stevengj/32/71_2.png) [@stevengj](https://discourse.julialang.org/u/stevengj)
#### Post date: [September 8, 2023, 12:16pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/8 "2023-09-08T12:16:23Z")

</div>

> [@GunnarFarneback](#):
>
> That’s why it helps to send a copy of the string in your `ccall`. The argument parser mutates that copy but the next time you call the function you make a fresh copy of the uncorrupted original string.

Since strings are supposed to be immutable in Julia, I wouldn’t pass a `String` to a function that mutates the contents, since you don’t know what that will break _even if you make a copy_. (e.g. there is no semantic requirement that `copy` or `deepcopy` actually copies immutable data AFAIK.) Safer to just **copy the data** into a `Vector{UInt8}`.

Unfortunately, `Vector{UInt8}(mystring)` is not enough here, because you want to (a) include the NUL terminator and (b) make sure that `mystring` does not have an embedded NUL. The latter is handled by `Base.unsafe_convert(Cstring, mystring)`, so what you can do is:

```julia
# get the NUL-terminated data from `s` as a `Vector{UInt8}` including the
# NUL terminator, while checking that `s` does not contain NUL.
cstring_vector(s::String) = GC.@preserve s begin
    p = Base.unsafe_convert(Cstring, s) # throws if s contains NUL
    copy(unsafe_wrap(Array, Ptr{UInt8}(p), sizeof(s)+1)) # copy the data + NUL
end

```

which gives:

```julia
julia> cstring_vector("foo")
4-element Vector{UInt8}:
 0x66
 0x6f
 0x6f
 0x00

julia> cstring_vector("fo\0o")
ERROR: ArgumentError: embedded NULs are not allowed in C strings: "fo\0o"

```

It might be nice if there were some function in Base to do this kind of copying more conveniently.

PS. And as I said before, passing around all of these raw pointers without rooting the underlying objects is just asking for segmentation faults if you get unlucky with garbage collection. You really need to read the documentation of [`GC.@preserve`](https://docs.julialang.org/en/v1/base/base/#Base.GC.@preserve).

PPS. `Cstring(pointer(mystring))` is unsafe, independent of rooting issues, because it doesn’t check whether `mystring` contains embedded NUL (`\0`) characters and hence can’t be treated as a NUL-terminated string. Use `Base.unsafe_convert(Cstring, mystring)` instead if you must do this.

---

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 8, 2023, 12:45pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/9 "2023-09-08T12:45:21Z")

</div>

I see, but does that mean that I should change the C library signature too? So far my c function receives a `char *argv[]` and that doesn’t seem to work with your proposed solution.

---

<div class="post-metadata">

### Author: ![stevengj](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stevengj/32/71_2.png) [@stevengj](https://discourse.julialang.org/u/stevengj)
#### Post date: [September 8, 2023, 2:03pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/10 "2023-09-08T14:03:04Z")

</div>

> [@dforero0896](#):
>
> I see, but does that mean that I should change the C library signature too?

No. A `Vector{UInt8}` produces the same kind of pointer as a `String`, because it has the same underlying data format.

---

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 8, 2023, 7:27pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/11 "2023-09-08T19:27:11Z")

</div>

I see, but then I should change the way I call it? I did

```julia
pk = GC.@preserve argv_vec ccall((:compute_pk, "$(ENV["LIBPOWSPEC_PATH"])/libpowspec_f.so"), Ptr{PK}, (Ref{CATA}, Cint, Cint, Ptr{Cint}, Cint, Ptr{Vector{Uint8}), cat, save_auto & save_cross, false, int_cache, argc, argv)

```

but the string read is not correct.

---

<div class="post-metadata">

### Author: ![dforero0896](https://avatars.discourse-cdn.com/v4/letter/d/e95f7d/32.png) [@dforero0896](https://discourse.julialang.org/u/dforero0896)
#### Post date: [September 8, 2023, 8:06pm UTC](https://discourse.julialang.org/t/calling-c-function-with-pointer-of-c-strings-works-once-but-not-twice/103632/12 "2023-09-08T20:06:14Z")

</div>

It works now. I still have some more issues with calling the C library but I am not sure if I should rather open a new thread. To summarize, I can now call the C function repeatedly and apparently without issues . However, a sort time after the code SegFaults at random points like a Julia pure function that never showed Segfaults earlier or at a `savefig` call. I suspect that the GC is trying to collect some memory that the C library has already freed, could that be a possibility?
