Filters getting disposed by System.gc before EOL

Previous to this commit Filters passed as parameters to the
BlockTableConfig are disposed before they should be disposed.

Further Smart pointer usage was corrected.

Java holds now the smart pointer to the FilterPolicy correctly
and cares about freeing underlying c++ structures.
main
fyrz 11 years ago
parent 7658bcc1e5
commit bafbc23baa
  1. 6
      java/org/rocksdb/Options.java
  2. 17
      java/org/rocksdb/test/FilterTest.java
  3. 16
      java/rocksjni/filter.cc
  4. 8
      java/rocksjni/portal.h
  5. 6
      java/rocksjni/table.cc

@ -1154,6 +1154,7 @@ public class Options extends RocksObject {
*/ */
public Options setMemTableConfig(MemTableConfig config) public Options setMemTableConfig(MemTableConfig config)
throws RocksDBException { throws RocksDBException {
memTableConfig_ = config;
setMemTableFactory(nativeHandle_, config.newMemTableFactoryHandle()); setMemTableFactory(nativeHandle_, config.newMemTableFactoryHandle());
return this; return this;
} }
@ -1168,6 +1169,7 @@ public class Options extends RocksObject {
* @throws RocksDBException * @throws RocksDBException
*/ */
public Options setRateLimiterConfig(RateLimiterConfig config) { public Options setRateLimiterConfig(RateLimiterConfig config) {
rateLimiterConfig_ = config;
setRateLimiter(nativeHandle_, config.newRateLimiterHandle()); setRateLimiter(nativeHandle_, config.newRateLimiterHandle());
return this; return this;
} }
@ -1191,6 +1193,7 @@ public class Options extends RocksObject {
* @return the reference of the current Options. * @return the reference of the current Options.
*/ */
public Options setTableFormatConfig(TableFormatConfig config) { public Options setTableFormatConfig(TableFormatConfig config) {
tableFormatConfig_ = config;
setTableFactory(nativeHandle_, config.newTableFactoryHandle()); setTableFactory(nativeHandle_, config.newTableFactoryHandle());
return this; return this;
} }
@ -2280,4 +2283,7 @@ public class Options extends RocksObject {
long cacheSize_; long cacheSize_;
int numShardBits_; int numShardBits_;
RocksEnv env_; RocksEnv env_;
MemTableConfig memTableConfig_;
TableFormatConfig tableFormatConfig_;
RateLimiterConfig rateLimiterConfig_;
} }

@ -13,19 +13,30 @@ public class FilterTest {
} }
public static void main(String[] args) { public static void main(String[] args) {
Options options = new Options(); Options options = new Options();
// test table config without filter // test table config
BlockBasedTableConfig blockConfig = new BlockBasedTableConfig(); BlockBasedTableConfig blockConfig = new BlockBasedTableConfig();
options.setTableFormatConfig(blockConfig); options.setTableFormatConfig(new BlockBasedTableConfig().
setFilter(new BloomFilter()));
options.dispose(); options.dispose();
System.gc();
System.runFinalization();
// new Bloom filter // new Bloom filter
options = new Options(); options = new Options();
blockConfig = new BlockBasedTableConfig(); blockConfig = new BlockBasedTableConfig();
blockConfig.setFilter(new BloomFilter()); blockConfig.setFilter(new BloomFilter());
options.setTableFormatConfig(blockConfig); options.setTableFormatConfig(blockConfig);
blockConfig.setFilter(new BloomFilter(10)); BloomFilter bloomFilter = new BloomFilter(10);
blockConfig.setFilter(bloomFilter);
options.setTableFormatConfig(blockConfig); options.setTableFormatConfig(blockConfig);
System.gc();
System.runFinalization();
blockConfig.setFilter(new BloomFilter(10, false)); blockConfig.setFilter(new BloomFilter(10, false));
options.setTableFormatConfig(blockConfig); options.setTableFormatConfig(blockConfig);
options.dispose();
options = null;
blockConfig = null;
System.gc();
System.runFinalization();
System.out.println("Filter test passed"); System.out.println("Filter test passed");
} }
} }

@ -24,9 +24,12 @@
void Java_org_rocksdb_BloomFilter_createNewBloomFilter( void Java_org_rocksdb_BloomFilter_createNewBloomFilter(
JNIEnv* env, jobject jobj, jint bits_per_key, JNIEnv* env, jobject jobj, jint bits_per_key,
jboolean use_block_base_builder) { jboolean use_block_base_builder) {
const rocksdb::FilterPolicy* fp = rocksdb::NewBloomFilterPolicy(bits_per_key, rocksdb::FilterPolicy* fp = const_cast<rocksdb::FilterPolicy *>(
use_block_base_builder); rocksdb::NewBloomFilterPolicy(bits_per_key, use_block_base_builder));
rocksdb::FilterJni::setHandle(env, jobj, fp); std::shared_ptr<rocksdb::FilterPolicy> *pFilterPolicy =
new std::shared_ptr<rocksdb::FilterPolicy>;
*pFilterPolicy = std::shared_ptr<rocksdb::FilterPolicy>(fp);
rocksdb::FilterJni::setHandle(env, jobj, pFilterPolicy);
} }
/* /*
@ -35,6 +38,9 @@ void Java_org_rocksdb_BloomFilter_createNewBloomFilter(
* Signature: (J)V * Signature: (J)V
*/ */
void Java_org_rocksdb_Filter_disposeInternal( void Java_org_rocksdb_Filter_disposeInternal(
JNIEnv* env, jobject jobj, jlong handle) { JNIEnv* env, jobject jobj, jlong jhandle) {
delete reinterpret_cast<rocksdb::FilterPolicy*>(handle);
std::shared_ptr<rocksdb::FilterPolicy> *handle =
reinterpret_cast<std::shared_ptr<rocksdb::FilterPolicy> *>(jhandle);
handle->reset();
} }

@ -313,14 +313,16 @@ class FilterJni {
} }
// Get the pointer to rocksdb::FilterPolicy. // Get the pointer to rocksdb::FilterPolicy.
static rocksdb::FilterPolicy* getHandle(JNIEnv* env, jobject jobj) { static std::shared_ptr<rocksdb::FilterPolicy>* getHandle(
return reinterpret_cast<rocksdb::FilterPolicy*>( JNIEnv* env, jobject jobj) {
return reinterpret_cast
<std::shared_ptr<rocksdb::FilterPolicy> *>(
env->GetLongField(jobj, getHandleFieldID(env))); env->GetLongField(jobj, getHandleFieldID(env)));
} }
// Pass the rocksdb::FilterPolicy pointer to the java side. // Pass the rocksdb::FilterPolicy pointer to the java side.
static void setHandle( static void setHandle(
JNIEnv* env, jobject jobj, const rocksdb::FilterPolicy* op) { JNIEnv* env, jobject jobj, std::shared_ptr<rocksdb::FilterPolicy>* op) {
env->SetLongField( env->SetLongField(
jobj, getHandleFieldID(env), jobj, getHandleFieldID(env),
reinterpret_cast<jlong>(op)); reinterpret_cast<jlong>(op));

@ -56,8 +56,10 @@ jlong Java_org_rocksdb_BlockBasedTableConfig_newTableFactoryHandle(
options.block_restart_interval = block_restart_interval; options.block_restart_interval = block_restart_interval;
options.whole_key_filtering = whole_key_filtering; options.whole_key_filtering = whole_key_filtering;
if (jfilterPolicy > 0) { if (jfilterPolicy > 0) {
options.filter_policy.reset( std::shared_ptr<rocksdb::FilterPolicy> *pFilterPolicy =
reinterpret_cast<rocksdb::FilterPolicy*>(jfilterPolicy)); reinterpret_cast<std::shared_ptr<rocksdb::FilterPolicy> *>(
jfilterPolicy);
options.filter_policy = *pFilterPolicy;
} }
options.cache_index_and_filter_blocks = cache_index_and_filter_blocks; options.cache_index_and_filter_blocks = cache_index_and_filter_blocks;
options.hash_index_allow_collision = hash_index_allow_collision; options.hash_index_allow_collision = hash_index_allow_collision;

Loading…
Cancel
Save