#15210·rocksdb

【BUG】In the SeekForGetImpl function of the block.cc file, the check for whether data_ is null is omitted. The function directly uses data_ for hash lookup and subsequent parsing, which poses a potential risk of null pointer for RocksDB-v6.26.1.

Author: wkxNiubiCreated Sep 14, 2026Updated Sep 14, 2026

Problem Description

This issue is caused by inconsistent state of DataBlockIter, resulting in a potential null pointer dereference. When the iterator has not been initialized or has been invalidated by calling Invalidate(), the member variable data_ may be nullptr. However, SeekForGet() only checks whether data_block_hash_index_ is empty, but does not check data_. If the hash index pointer is still non-null or has a residual value, it will enter SeekForGetImpl(). The function then directly executes: data_block_hash_index_->Lookup(data_, map_offset, target_user_key); Lookup() performs address operations on data_ and reads the hash bucket. When data_ is nullptr, this is undefined behavior and may cause the RocksDB process to crash.

How to reproduce

  1. Use kDataBlockBinaryAndHash to create a data block containing at least one record.
  2. Initialize DataBlockIter using Block::NewDataIterator() and ensure that data_block_hash_index_ is not empty.
  3. Call: iter.Invalidate(Status::OK()); At this point, data_ is set to nullptr, but data_block_hash_index_ has not been cleared.
  4. Construct a valid InternalKey, and then call: iter.SeekForGet(internal_key.Encode()); SeekForGet() will enter SeekForGetImpl() due to the remaining hash index pointers, and finally perform the hash bucket read using an empty data_.

Content of the code evidence

cpp
bool DataBlockIter::SeekForGetImpl(const Slice& target) {
  Slice target_user_key = ExtractUserKey(target);
  uint32_t map_offset = restarts_ + num_restarts_ * sizeof(uint32_t);
  uint8_t entry =
      data_block_hash_index_->Lookup(data_, map_offset, target_user_key);

  if (entry == kCollision) {
    // HashSeek not effective, falling back
    SeekImpl(target);
    return true;
  }