New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Implement callback returning type :string #770
Conversation
Callbacks returning a :string type were not supported so far. It was possible to define such a callback, but the value returned was NULL in any case. This implementation follows the semantics for passing :string parameters to functions as implemented in Call.c. That means in particular usage of StringValueCStr(), so that no zero bytes are allowed in the string. Special care has to be taken regarding lifetime of the returned text pointer. The C pointer to the string is only valid until the next GC triggering function is called, unless the String object is hold in Ruby outside of the callback block. Even when the object is stored outside of the Ruby block, the text pointer can move when GC.compact is called. So :string returning callbacks can safely be used only, when the referenced text is processed immediately by the calling C function. Resolves ffi#751
b6372af
to
32df97e
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is good, and if C calls a Ruby callback and expects a char*
I would indeed expect in most causes the C side uses it immediately (it's not something the C side allocated, so the C side must anyway not rely on it to be alive forever).
@eregon How long is a |
@larskanis It's similar to what you described above, as soon as the Ruby String is no longer referenced then the native The |
Actually, the current semantics on TruffleRuby are different than I thought (they're not using This is documented here: https://github.com/oracle/graal/blob/master/truffle/docs/NFI.md#string |
Closing this in favor of #782 . The validity of the @eregon Thank you for investigating the Truffleruby conversion of strings! I also inspected the Truffleruby's FFI code a bit, but wasn't sure about how and when the memory is freed. |
Callbacks returning a
:string
type were not supported so far. It was possible to define such a callback, but the value returned wasNULL
in any case. This implementation follows the semantics for passing:string
parameters to functions as implemented inCall.c
. That means in particular usage ofStringValueCStr()
, so that no zero bytes are allowed in the string.Special care has to be taken regarding lifetime of the returned text pointer. The C pointer to the string is only valid until the next GC triggering function is called, unless the String object is hold in Ruby outside of the callback block. Even when the object is stored outside of the Ruby block, the text pointer can move when GC.compact is called. So
:string
returning callbacks can safely be used only, when the referenced text is processed immediately by the calling C function.Return type
:string
is already implemented in TruffleRuby, but fails in JRuby and raises aResolves #751
@eregon, @headius What do you think about this addition? Should we add
:string
returning callbacks in JRuby or deny them on all implementations?