Skip to content

Commit

Permalink
src: keep reference buffer alive longer (#55)
Browse files Browse the repository at this point in the history
* src: keep reference buffer alive longer

Keep a buffer written by WritePointer alive
until the finalizers for the buffer to which
the pointer has been run have been executed:

Refs: #54

Signed-off-by: Michael Dawson <mdawson@devrus.com>

* limit change to writePointer

Update to avoid changing behaviour for
_writePointer and limit change to writePointer
where objects were already being associated
with the buffer.

Signed-off-by: Michael Dawson <mdawson@devrus.com>

* remove _attach call in writePointer

remove _attach call in writePointer as
it is no longer needed since a stronger
version is done in the native code
when true is passed as the fourth parameter
  • Loading branch information
mhdawson committed Mar 17, 2021
1 parent b0809c2 commit be21678
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 2 deletions.
8 changes: 6 additions & 2 deletions lib/ref.js
Original file line number Diff line number Diff line change
Expand Up @@ -746,8 +746,12 @@ exports.writeObject = function writeObject (buf, offset, obj) {

exports.writePointer = function writePointer (buf, offset, ptr) {
debug('writing pointer to buffer', buf, offset, ptr);
exports._writePointer(buf, offset, ptr);
exports._attach(buf, ptr);
// Passing true as a fourth parameter does an a stronger
// version of attach which ensures ptr is only collected after
// the finalizer for buf has run. See
// https://github.com/node-ffi-napi/ref-napi/issues/54
// for why this is necessary
exports._writePointer(buf, offset, ptr, true);
};

/**
Expand Down
12 changes: 12 additions & 0 deletions src/binding.cc
Original file line number Diff line number Diff line change
Expand Up @@ -355,6 +355,18 @@ void WritePointer(const CallbackInfo& args) {
if (input.IsNull()) {
*reinterpret_cast<char**>(ptr) = nullptr;
} else {
if ((args.Length() == 4) && (args[3].As<Boolean>() == true)) {
// create a node-api reference and finalizer to ensure that
// the buffer whoes pointer is written can only be
// collected after the finalizers for the buffer
// to which the pointer was written have already run
Reference<Value>* ref = new Reference<Value>;
*ref = Persistent(args[2]);
args[0].As<Object>().AddFinalizer([](Env env, Reference<Value>* ref) {
delete ref;
}, ref);
}

char* input_ptr = GetBufferData(input);
*reinterpret_cast<char**>(ptr) = input_ptr;
}
Expand Down

0 comments on commit be21678

Please sign in to comment.