[Pkg-javascript-commits] [node-leveldown] 01/02: backport memory leak fixes from 0.4.1 & 0.4.2
Andrew Kelley
andrewrk-guest at moszumanska.debian.org
Sun Jul 6 17:17:22 UTC 2014
This is an automated email from the git hooks/post-receive script.
andrewrk-guest pushed a commit to tag 0.2.3
in repository node-leveldown.
commit d6a6e1d9b23e937204317fd7a941a6fafc0f6093
Author: Rod Vagg <rod at vagg.org>
Date: Fri May 17 13:24:22 2013 +1000
backport memory leak fixes from 0.4.1 & 0.4.2
---
package.json | 2 +-
src/batch.cc | 36 +++++++++++++++---------------------
src/batch.h | 2 +-
src/database.cc | 27 +++++++++++++--------------
src/database.h | 19 +++++++++++++++++++
src/database_async.cc | 18 ++++++------------
src/database_async.h | 4 ++--
src/leveldown.h | 12 ++++++++++++
8 files changed, 69 insertions(+), 51 deletions(-)
diff --git a/package.json b/package.json
index 418075d..ea9ae96 100644
--- a/package.json
+++ b/package.json
@@ -25,7 +25,7 @@
, "rimraf" : "~2.1.4"
, "mkfiletree" : "~0.0.0"
, "readfiletree" : "~0.0.0"
- , "abstract-leveldown" : "git://github.com/rvagg/node-abstract-leveldown.git"
+ , "abstract-leveldown" : "~0.4.0"
}
, "repository" : {
"type" : "git"
diff --git a/src/batch.cc b/src/batch.cc
index 0436599..3f43e53 100644
--- a/src/batch.cc
+++ b/src/batch.cc
@@ -13,17 +13,11 @@ Batch::Batch (leveldown::Database* database, bool sync) : database(database) {
options = new leveldb::WriteOptions();
options->sync = sync;
batch = new leveldb::WriteBatch();
- references = new std::vector< v8::Persistent<v8::Value> >;
+ references = new std::vector<Reference>;
}
Batch::~Batch () {
- for (std::vector< v8::Persistent<v8::Value> >::iterator it = references->begin()
- ; it != references->end()
- ; ) {
- it->Dispose(LD_NODE_ISOLATE);
- it = references->erase(it);
- }
- delete references;
+ ClearReferences(references);
delete options;
delete batch;
}
@@ -108,14 +102,14 @@ v8::Handle<v8::Value> Batch::Put (const v8::Arguments& args) {
LD_STRING_OR_BUFFER_TO_SLICE(key, keyBuffer, key)
LD_STRING_OR_BUFFER_TO_SLICE(value, valueBuffer, value)
- if (node::Buffer::HasInstance(keyBuffer->ToObject()))
- batch->references->push_back(v8::Persistent<v8::Value>::New(
- LD_NODE_ISOLATE_PRE
- keyBuffer));
- if (node::Buffer::HasInstance(valueBuffer->ToObject()))
- batch->references->push_back(v8::Persistent<v8::Value>::New(
- LD_NODE_ISOLATE_PRE
- valueBuffer));
+ batch->references->push_back(Reference(
+ v8::Persistent<v8::Value>::New(LD_NODE_ISOLATE_PRE keyBuffer)
+ , key
+ ));
+ batch->references->push_back(Reference(
+ v8::Persistent<v8::Value>::New(LD_NODE_ISOLATE_PRE valueBuffer)
+ , value
+ ));
batch->batch->Put(key, value);
@@ -133,10 +127,10 @@ v8::Handle<v8::Value> Batch::Del (const v8::Arguments& args) {
v8::Local<v8::Value> keyBuffer = args[0];
LD_STRING_OR_BUFFER_TO_SLICE(key, keyBuffer, key)
- if (node::Buffer::HasInstance(keyBuffer->ToObject()))
- batch->references->push_back(v8::Persistent<v8::Value>::New(
- LD_NODE_ISOLATE_PRE
- keyBuffer));
+ batch->references->push_back(Reference(
+ v8::Persistent<v8::Value>::New(LD_NODE_ISOLATE_PRE keyBuffer)
+ , key
+ ));
batch->batch->Delete(key);
@@ -169,4 +163,4 @@ v8::Handle<v8::Value> Batch::Write (const v8::Arguments& args) {
return v8::Undefined();
}
-} // namespace leveldown
\ No newline at end of file
+} // namespace leveldown
diff --git a/src/batch.h b/src/batch.h
index 4655b05..1077670 100644
--- a/src/batch.h
+++ b/src/batch.h
@@ -26,7 +26,7 @@ private:
leveldown::Database* database;
leveldb::WriteOptions* options;
leveldb::WriteBatch* batch;
- std::vector< v8::Persistent<v8::Value> >* references;
+ std::vector<Reference>* references;
static v8::Persistent<v8::Function> constructor;
diff --git a/src/database.cc b/src/database.cc
index 0eacb15..9b64e00 100644
--- a/src/database.cc
+++ b/src/database.cc
@@ -411,8 +411,7 @@ v8::Handle<v8::Value> Database::Batch (const v8::Arguments& args) {
v8::Local<v8::Array> array = v8::Local<v8::Array>::Cast(args[0]);
- std::vector< v8::Persistent<v8::Value> >* references =
- new std::vector< v8::Persistent<v8::Value> >;
+ std::vector<Reference>* references = new std::vector<Reference>;
leveldb::WriteBatch* batch = new leveldb::WriteBatch();
for (unsigned int i = 0; i < array->Length(); i++) {
@@ -430,10 +429,10 @@ v8::Handle<v8::Value> Database::Batch (const v8::Arguments& args) {
LD_STRING_OR_BUFFER_TO_SLICE(key, keyBuffer, key)
batch->Delete(key);
- if (node::Buffer::HasInstance(keyBuffer->ToObject()))
- references->push_back(v8::Persistent<v8::Value>::New(
- LD_NODE_ISOLATE_PRE
- keyBuffer));
+ references->push_back(Reference(
+ v8::Persistent<v8::Value>::New(LD_NODE_ISOLATE_PRE keyBuffer)
+ , key
+ ));
} else if (obj->Get(str_type)->StrictEquals(str_put)) {
v8::Local<v8::Value> valueBuffer = obj->Get(str_value);
LD_CB_ERR_IF_NULL_OR_UNDEFINED(valueBuffer, value)
@@ -442,14 +441,14 @@ v8::Handle<v8::Value> Database::Batch (const v8::Arguments& args) {
LD_STRING_OR_BUFFER_TO_SLICE(value, valueBuffer, value)
batch->Put(key, value);
- if (node::Buffer::HasInstance(keyBuffer->ToObject()))
- references->push_back(v8::Persistent<v8::Value>::New(
- LD_NODE_ISOLATE_PRE
- keyBuffer));
- if (node::Buffer::HasInstance(valueBuffer->ToObject()))
- references->push_back(v8::Persistent<v8::Value>::New(
- LD_NODE_ISOLATE_PRE
- valueBuffer));
+ references->push_back(Reference(
+ v8::Persistent<v8::Value>::New(LD_NODE_ISOLATE_PRE keyBuffer)
+ , key
+ ));
+ references->push_back(Reference(
+ v8::Persistent<v8::Value>::New(LD_NODE_ISOLATE_PRE valueBuffer)
+ , value
+ ));
}
}
diff --git a/src/database.h b/src/database.h
index b2f2377..5a5a32a 100644
--- a/src/database.h
+++ b/src/database.h
@@ -7,6 +7,7 @@
#define LD_DATABASE_H
#include <map>
+#include <vector>
#include <node.h>
#include "leveldb/db.h"
@@ -31,6 +32,24 @@ struct AsyncDescriptor;
v8::Handle<v8::Value> LevelDOWN (const v8::Arguments& args);
+struct Reference {
+ v8::Persistent<v8::Value> ptr;
+ leveldb::Slice slice;
+ Reference(v8::Persistent<v8::Value> ptr, leveldb::Slice slice) :
+ ptr(ptr)
+ , slice(slice) { };
+};
+
+static inline void ClearReferences (std::vector<Reference>* references) {
+ for (std::vector<Reference>::iterator it = references->begin()
+ ; it != references->end()
+ ; ) {
+ DisposeStringOrBufferFromSlice(it->ptr, it->slice);
+ it = references->erase(it);
+ }
+ delete references;
+}
+
class Database : public node::ObjectWrap {
public:
static void Init ();
diff --git a/src/database_async.cc b/src/database_async.cc
index 2644f7c..ef24498 100644
--- a/src/database_async.cc
+++ b/src/database_async.cc
@@ -85,7 +85,7 @@ IOWorker::~IOWorker () {}
void IOWorker::WorkComplete () {
AsyncWorker::WorkComplete();
- keyPtr.Dispose(LD_NODE_ISOLATE);
+ DisposeStringOrBufferFromSlice(keyPtr, key);
}
/** READ WORKER **/
@@ -172,7 +172,7 @@ void WriteWorker::Execute () {
void WriteWorker::WorkComplete () {
IOWorker::WorkComplete();
- valuePtr.Dispose(LD_NODE_ISOLATE);
+ DisposeStringOrBufferFromSlice(valuePtr, value);
}
/** BATCH WORKER **/
@@ -181,7 +181,7 @@ BatchWorker::BatchWorker (
Database* database
, v8::Persistent<v8::Function> callback
, leveldb::WriteBatch* batch
- , std::vector< v8::Persistent<v8::Value> >* references
+ , std::vector<Reference>* references
, bool sync
) : AsyncWorker(database, callback)
, batch(batch)
@@ -192,13 +192,7 @@ BatchWorker::BatchWorker (
};
BatchWorker::~BatchWorker () {
- for (std::vector< v8::Persistent<v8::Value> >::iterator it = references->begin()
- ; it != references->end()
- ; ) {
- it->Dispose(LD_NODE_ISOLATE);
- it = references->erase(it);
- }
- delete references;
+ ClearReferences(references);
delete options;
}
@@ -229,8 +223,8 @@ void ApproximateSizeWorker::Execute () {
void ApproximateSizeWorker::WorkComplete() {
AsyncWorker::WorkComplete();
- startPtr.Dispose(LD_NODE_ISOLATE);
- endPtr.Dispose(LD_NODE_ISOLATE);
+ DisposeStringOrBufferFromSlice(startPtr, range.start);
+ DisposeStringOrBufferFromSlice(endPtr, range.limit);
}
void ApproximateSizeWorker::HandleOKCallback () {
diff --git a/src/database_async.h b/src/database_async.h
index 8ca9fdd..80dafff 100644
--- a/src/database_async.h
+++ b/src/database_async.h
@@ -131,7 +131,7 @@ public:
Database* database
, v8::Persistent<v8::Function> callback
, leveldb::WriteBatch* batch
- , std::vector< v8::Persistent<v8::Value> >* references
+ , std::vector<Reference>* references
, bool sync
);
@@ -141,7 +141,7 @@ public:
private:
leveldb::WriteOptions* options;
leveldb::WriteBatch* batch;
- std::vector< v8::Persistent<v8::Value> >* references;
+ std::vector<Reference>* references;
};
class ApproximateSizeWorker : public AsyncWorker {
diff --git a/src/leveldown.h b/src/leveldown.h
index 49fd2fe..67d0c80 100644
--- a/src/leveldown.h
+++ b/src/leveldown.h
@@ -7,6 +7,7 @@
#include <node.h>
#include <node_buffer.h>
+#include <leveldb/slice.h>
static inline char* FromV8String(v8::Local<v8::Value> from) {
size_t sz_;
@@ -79,6 +80,17 @@ static inline uint32_t UInt32OptionValue(
LD_RETURN_CALLBACK_OR_ERROR(callback, #name " cannot be `null` or `undefined`") \
}
+// NOTE: this MUST be called on objects created by
+// LD_STRING_OR_BUFFER_TO_SLICE
+static inline void DisposeStringOrBufferFromSlice(v8::Persistent<v8::Value> ptr
+ , leveldb::Slice slice) {
+
+ if (!node::Buffer::HasInstance(ptr))
+ delete slice.data();
+ ptr.Dispose(LD_NODE_ISOLATE);
+}
+
+// NOTE: must call DisposeStringOrBufferFromSlice() on objects created here
#define LD_STRING_OR_BUFFER_TO_SLICE(to, from, name) \
size_t to ## Sz_; \
char* to ## Ch_; \
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-javascript/node-leveldown.git
More information about the Pkg-javascript-commits
mailing list