[erlang-questions] NIF resources, environments and GC

Loïc Hoguin essen@REDACTED
Wed Dec 20 00:21:45 CET 2017


It works! And it ended up much simpler than I initially went for.

Worth noting that the destructor takes a while to be called if you are 
debugging using io:format.

Thanks a bunch!

On 12/19/2017 04:41 PM, Loïc Hoguin wrote:
> Thanks for the tip, I haven't tried that. I'll report back with the 
> results.
> 
> On 12/19/2017 04:33 PM, Sverker Eriksson wrote:
>> Two resource terms will compare equal (in OTP-20) iff they yield
>> the same pointer from enif_get_resource().
>>
>> So, isn't the solution to instead maintain a pointer to your resource
>> in the static variable. Call enif_make_resource(static_ptr) when you
>> need to return a resource term.
>>
>> And then clear that static pointer in the destructor.
>>
>> /Sverker
>>
>>
>> On tis, 2017-12-19 at 16:03 +0100, Loïc Hoguin wrote:
>>> Hello,
>>>
>>> I've got the following situation.
>>>
>>> I have a function SDL_CreateWindow that returns an SDL_Window* from
>>> which I create a resource with a destructor which is called when the
>>> resource variable gets GC'd. So far so good.
>>>
>>> I also have various other functions which may return the same
>>> SDL_Window* as the one that was created earlier. In this case I want
>>> to
>>> return the same resource so that it is possible to match or compare
>>> the
>>> resources on the latest Erlang versions so that users can confirm
>>> that
>>> yes, it's the same window. This is useful to know for example to
>>> know
>>> which window currently has focus.
>>>
>>> I therefore need to keep the ERL_NIF_TERM around along with
>>> SDL_Window*
>>> since recreating the term would lead to different references and
>>> comparisons failing. I've therefore proceded to use enif_make_copy
>>> to
>>> copy it to a static variable and I do enif_make_copy again when I
>>> need
>>> to return it.
>>>
>>> It works.
>>>
>>> Almost.
>>>
>>> The only issue with my approach is that the destructor for the
>>> SDL_Window* resource no longer gets called. Apparently enif_make_copy
>>> is
>>> the culprit. As soon as I copy the resource term to my private env,
>>> the
>>> destructor stops being called.
>>>
>>> Is there any way I can keep this resource term while still
>>> benefitting
>>> from the destructor being called when the variable is discarded?
>>> Basically I would like the private copy to not be reference counted.
>>> Any
>>> way to do this?
>>>
>>> Thanks,
>>>
>> _______________________________________________
>> erlang-questions mailing list
>> erlang-questions@REDACTED
>> http://erlang.org/mailman/listinfo/erlang-questions
>>
> 

-- 
Loïc Hoguin
https://ninenines.eu



More information about the erlang-questions mailing list