Skip to content
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

(C API) Segfault when calling rocksdb_slicetransform_destroy() after rocksdb_options_set_prefix_extractor() #1095

Closed
warrenfalk opened this issue Apr 26, 2016 · 2 comments

Comments

@warrenfalk
Copy link
Contributor

warrenfalk commented Apr 26, 2016

The code below will segfault.

The expectation is that a call to rocksdb_slicetransform_create_fixed_prefix() should be paired with a call to rocksdb_slicetransform_destroy().

However, once the rocksdb_slicetransform_t is associated with an rocksdb_options_t, it gets destroyed when the rocksdb_options_t is destroyed, and so if you call rocksdb_slicetransform_destroy() it segfaults.

This makes language bindings exceedingly clumsy as you have to keep track of whether the rocksdb_slicetransform_t has been associated with a rocksdb_options_t somewhere.

Is this desired behavior?

/*
 The code below segfaults.
 Lines marked (B) and (C) appear to be mutually exclusive.  Is this the desired behavior?
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <assert.h>
#include "rocksdb/c.h"
int main(int argc, char **argv) {
  rocksdb_slicetransform_t *prefix = rocksdb_slicetransform_create_fixed_prefix(8);  // <-- (A) Create Prefix Extractor
  rocksdb_options_t *options = rocksdb_options_create();
  rocksdb_options_set_create_if_missing(options, 1);
  rocksdb_options_set_prefix_extractor(options, prefix); // <-- (B) Set Prefix Extractor
  /* ... */
  rocksdb_options_destroy(options);
  rocksdb_slicetransform_destroy(prefix); // <-- (C) Destroy Prefix Extractor
  return 0;
}
@warrenfalk
Copy link
Contributor Author

The segfault also occurs with the bloom filter policies also, and possibly more. However it does not occur with block based table options. And here is what appears to be the difference:

The following seems to be OK:

void rocksdb_options_set_block_based_table_factory(
    rocksdb_options_t *opt,
    rocksdb_block_based_table_options_t* table_options) {
  if (table_options) {
    opt->rep.table_factory.reset(
        rocksdb::NewBlockBasedTableFactory(table_options->rep));
  }
}

The following eventually results in segfault:

void rocksdb_options_set_prefix_extractor(
    rocksdb_options_t* opt, rocksdb_slicetransform_t* prefix_extractor) {
  opt->rep.prefix_extractor.reset(prefix_extractor);
}

Is there any reason why the latter can't be made to work like the former?

warrenfalk added a commit to warrenfalk/rocksdb-sharp that referenced this issue Apr 26, 2016
…(rocksdb issue #1095 facebook/rocksdb#1095) will cause them to be doubly destroyed.  Better to leak than to segfault.
warrenfalk added a commit to warrenfalk/rocksdb-sharp that referenced this issue Apr 26, 2016
…(rocksdb issue #1095 facebook/rocksdb#1095) will cause them to be doubly destroyed.  Better to leak than to segfault.
@gfosco
Copy link
Contributor

gfosco commented Jan 10, 2018

Closing this via automation due to lack of activity. If discussion is still needed here, please re-open or create a new/updated issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants