-
Notifications
You must be signed in to change notification settings - Fork 6.2k
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
Extend Java RocksDB iterators to support indirect Byte Buffers #9222
Extend Java RocksDB iterators to support indirect Byte Buffers #9222
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM :-)
Thanks @alanpaxton
jint jkey_len) { | ||
auto* it = reinterpret_cast<ROCKSDB_NAMESPACE::Iterator*>(handle); | ||
ROCKSDB_NAMESPACE::Slice key_slice = it->key(); | ||
jsize copy_size = std::min(static_cast<uint32_t>(key_slice.size()), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
define var actual_size=key_slice.size()
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've done auto slice_size = key_slice.size();
? (actual suggests to me the presence of non-actual).
jkey, jkey_off, copy_size, | ||
const_cast<jbyte*>(reinterpret_cast<const jbyte*>(key_slice.data()))); | ||
|
||
return static_cast<jsize>(key_slice.size()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
can use actual_size here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
slice_size
jint jvalue_off, jint jvalue_len) { | ||
auto* it = reinterpret_cast<ROCKSDB_NAMESPACE::Iterator*>(handle); | ||
ROCKSDB_NAMESPACE::Slice value_slice = it->value(); | ||
jsize copy_size = std::min(static_cast<uint32_t>(value_slice.size()), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ditto
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ditto
public int value(ByteBuffer value) { | ||
assert (isOwningHandle() && value.isDirect()); | ||
int result = valueDirect0(nativeHandle_, value, value.position(), value.remaining()); | ||
public int value(final ByteBuffer value) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
do we plan to support more methods in the future? RocksDB.get/put/delete
and WriteBatch.put/delete
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@javeme Yes, but that will be done in separate PRs
@jay-zhuang @mrambacher Can we get some review/merge here please? |
auto* it = reinterpret_cast<ROCKSDB_NAMESPACE::Iterator*>(handle); | ||
it->Seek(target_slice); | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we do something either through templates or otherwise to reduce the code duplication here? Essentially the same code is in multiple places.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've done some helper-based stuff.
java/rocksjni/iterator.cc
Outdated
void Java_org_rocksdb_RocksIterator_seekByteArray0( | ||
JNIEnv* env, jobject /*jobj*/, jlong handle, jbyteArray jtarget, | ||
jint jtarget_off, jint jtarget_len) { | ||
const std::unique_ptr<char[]> target(new char[jtarget_len]); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I want to understand if this is correct. Memory is being allocated here and freed at the end of this method. But it is also being passed to GetByteArrayRegion. Some comments here would help those (like me) who are less familiar with the JNIEnv understand what is going on.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
GetByteArrayRegion is a copy from the Java object into a C++ buffer (in this case the char[] contents). These are being used as the slice key to the seek. I know you need to look up what GetByteArrayRegion does to grok this, but I think an accompanying comment would turn into an overly verbose half-wrong explanation of GetByteArrayRegion and I think the right thing is to let the code speak for itself, at the cost of a bit of reading time. I'm willing to be argued out of this position.
e90a6a3
to
48ab703
Compare
a9cc7ae
to
c59f2eb
Compare
I've gone through and done what I hope answers your concerns @Javame @mrambacher . I think it would be good for this to get into Rocks 7 if you can give it the once over. |
@jay-zhuang Can we get this merged for Rocks 7 please? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM. Thanks @alanpaxton
Rework tests to be TDD for key(), value() Implement JNI for key() for indirect Left to do - tests for seek(), implement value(), and seek()
And associated test now passes. SstFileReaderIterator and WBWIRocksIterator stubbed.
Tests for WBWI. A bit of improvement to the WBWI tests.
Same pattern of implementing a native byte[] method with offsets.
seek0()/seekForPrev0(), methods using GetByteArrayElements now share a helper with seekByteArray0()/seekByteArrayForPrev0().
6e19562
to
58234c5
Compare
Thanks for making this change, really looking forward to this! I ran some quick benchmarks using indirect ByteBuffers in our iterator-heavy app and it was a significant performance boost. |
@jay-zhuang has imported this pull request. If you are a Meta employee, you can view this diff on Phabricator. |
Extend Java RocksDB iterators to support indirect byte buffers, to add to the existing support for direct byte buffers.
Code to distinguish direct/indirect buffers is switched in Java, and a 2nd separate JNI call implemented to support indirect
buffers. Indirect support passes contained buffers using byte[]
There are some Java subclasses of iterator (WBWIIterator, SstFileReaderIterator) which also now have parallel JNI support functions implemented, along with direct/indirect switches in Java methods.
Closes #6282