@nxtedition/rocksdb 7.1.20 → 7.1.21

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (262) hide show
  1. package/deps/rocksdb/rocksdb/CMakeLists.txt +13 -6
  2. package/deps/rocksdb/rocksdb/Makefile +1 -1
  3. package/deps/rocksdb/rocksdb/TARGETS +2 -0
  4. package/deps/rocksdb/rocksdb/cache/cache_reservation_manager_test.cc +1 -0
  5. package/deps/rocksdb/rocksdb/cache/cache_test.cc +4 -4
  6. package/deps/rocksdb/rocksdb/cache/clock_cache.cc +139 -161
  7. package/deps/rocksdb/rocksdb/cache/clock_cache.h +92 -82
  8. package/deps/rocksdb/rocksdb/cache/compressed_secondary_cache.cc +16 -3
  9. package/deps/rocksdb/rocksdb/cache/compressed_secondary_cache.h +9 -3
  10. package/deps/rocksdb/rocksdb/cache/compressed_secondary_cache_test.cc +73 -30
  11. package/deps/rocksdb/rocksdb/cache/fast_lru_cache.cc +25 -67
  12. package/deps/rocksdb/rocksdb/cache/fast_lru_cache.h +41 -40
  13. package/deps/rocksdb/rocksdb/cache/lru_cache.cc +109 -155
  14. package/deps/rocksdb/rocksdb/cache/lru_cache.h +127 -149
  15. package/deps/rocksdb/rocksdb/cache/lru_cache_test.cc +75 -80
  16. package/deps/rocksdb/rocksdb/cache/sharded_cache.cc +22 -172
  17. package/deps/rocksdb/rocksdb/cache/sharded_cache.h +272 -85
  18. package/deps/rocksdb/rocksdb/db/arena_wrapped_db_iter.cc +12 -4
  19. package/deps/rocksdb/rocksdb/db/blob/blob_counting_iterator_test.cc +1 -0
  20. package/deps/rocksdb/rocksdb/db/blob/blob_file_addition_test.cc +1 -0
  21. package/deps/rocksdb/rocksdb/db/blob/blob_file_builder_test.cc +1 -0
  22. package/deps/rocksdb/rocksdb/db/blob/blob_file_cache_test.cc +1 -0
  23. package/deps/rocksdb/rocksdb/db/blob/blob_file_garbage_test.cc +1 -0
  24. package/deps/rocksdb/rocksdb/db/blob/blob_file_reader_test.cc +1 -0
  25. package/deps/rocksdb/rocksdb/db/blob/blob_garbage_meter_test.cc +1 -0
  26. package/deps/rocksdb/rocksdb/db/blob/blob_source_test.cc +13 -4
  27. package/deps/rocksdb/rocksdb/db/builder.cc +1 -1
  28. package/deps/rocksdb/rocksdb/db/column_family.cc +15 -1
  29. package/deps/rocksdb/rocksdb/db/compact_files_test.cc +1 -0
  30. package/deps/rocksdb/rocksdb/db/compaction/clipping_iterator_test.cc +1 -0
  31. package/deps/rocksdb/rocksdb/db/compaction/compaction.cc +25 -7
  32. package/deps/rocksdb/rocksdb/db/compaction/compaction.h +10 -0
  33. package/deps/rocksdb/rocksdb/db/compaction/compaction_iterator.cc +22 -8
  34. package/deps/rocksdb/rocksdb/db/compaction/compaction_iterator.h +14 -5
  35. package/deps/rocksdb/rocksdb/db/compaction/compaction_iterator_test.cc +1 -0
  36. package/deps/rocksdb/rocksdb/db/compaction/compaction_job.cc +38 -12
  37. package/deps/rocksdb/rocksdb/db/compaction/compaction_job.h +9 -6
  38. package/deps/rocksdb/rocksdb/db/compaction/compaction_job_test.cc +408 -6
  39. package/deps/rocksdb/rocksdb/db/compaction/compaction_outputs.cc +244 -54
  40. package/deps/rocksdb/rocksdb/db/compaction/compaction_outputs.h +27 -6
  41. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker.cc +25 -30
  42. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_fifo.cc +87 -26
  43. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_level.cc +23 -4
  44. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_test.cc +61 -0
  45. package/deps/rocksdb/rocksdb/db/compaction/tiered_compaction_test.cc +294 -21
  46. package/deps/rocksdb/rocksdb/db/comparator_db_test.cc +1 -0
  47. package/deps/rocksdb/rocksdb/db/cuckoo_table_db_test.cc +1 -0
  48. package/deps/rocksdb/rocksdb/db/db_block_cache_test.cc +28 -10
  49. package/deps/rocksdb/rocksdb/db/db_bloom_filter_test.cc +4 -4
  50. package/deps/rocksdb/rocksdb/db/db_compaction_test.cc +272 -0
  51. package/deps/rocksdb/rocksdb/db/db_flush_test.cc +38 -0
  52. package/deps/rocksdb/rocksdb/db/db_impl/db_impl.cc +69 -25
  53. package/deps/rocksdb/rocksdb/db/db_impl/db_impl.h +7 -3
  54. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_compaction_flush.cc +29 -12
  55. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_debug.cc +0 -12
  56. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_files.cc +10 -4
  57. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_open.cc +35 -22
  58. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_secondary.cc +5 -1
  59. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_write.cc +40 -5
  60. package/deps/rocksdb/rocksdb/db/db_iter.cc +1 -0
  61. package/deps/rocksdb/rocksdb/db/db_iter_stress_test.cc +1 -0
  62. package/deps/rocksdb/rocksdb/db/db_iter_test.cc +1 -0
  63. package/deps/rocksdb/rocksdb/db/db_iterator_test.cc +22 -0
  64. package/deps/rocksdb/rocksdb/db/db_kv_checksum_test.cc +1 -0
  65. package/deps/rocksdb/rocksdb/db/db_logical_block_size_cache_test.cc +1 -0
  66. package/deps/rocksdb/rocksdb/db/db_range_del_test.cc +72 -5
  67. package/deps/rocksdb/rocksdb/db/db_tailing_iter_test.cc +60 -21
  68. package/deps/rocksdb/rocksdb/db/db_test.cc +170 -1
  69. package/deps/rocksdb/rocksdb/db/db_test2.cc +9 -3
  70. package/deps/rocksdb/rocksdb/db/db_test_util.cc +19 -0
  71. package/deps/rocksdb/rocksdb/db/db_test_util.h +32 -0
  72. package/deps/rocksdb/rocksdb/db/db_with_timestamp_basic_test.cc +444 -3
  73. package/deps/rocksdb/rocksdb/db/db_write_test.cc +8 -8
  74. package/deps/rocksdb/rocksdb/db/dbformat.cc +13 -0
  75. package/deps/rocksdb/rocksdb/db/dbformat.h +59 -4
  76. package/deps/rocksdb/rocksdb/db/dbformat_test.cc +1 -0
  77. package/deps/rocksdb/rocksdb/db/experimental.cc +3 -1
  78. package/deps/rocksdb/rocksdb/db/external_sst_file_ingestion_job.cc +24 -3
  79. package/deps/rocksdb/rocksdb/db/fault_injection_test.cc +1 -0
  80. package/deps/rocksdb/rocksdb/db/filename_test.cc +1 -0
  81. package/deps/rocksdb/rocksdb/db/flush_job.cc +4 -3
  82. package/deps/rocksdb/rocksdb/db/flush_job_test.cc +1 -0
  83. package/deps/rocksdb/rocksdb/db/forward_iterator.cc +85 -43
  84. package/deps/rocksdb/rocksdb/db/forward_iterator.h +3 -1
  85. package/deps/rocksdb/rocksdb/db/internal_stats.cc +33 -6
  86. package/deps/rocksdb/rocksdb/db/internal_stats.h +6 -0
  87. package/deps/rocksdb/rocksdb/db/listener_test.cc +1 -0
  88. package/deps/rocksdb/rocksdb/db/log_test.cc +1 -0
  89. package/deps/rocksdb/rocksdb/db/log_writer.cc +1 -1
  90. package/deps/rocksdb/rocksdb/db/log_writer.h +1 -1
  91. package/deps/rocksdb/rocksdb/db/manual_compaction_test.cc +1 -0
  92. package/deps/rocksdb/rocksdb/db/memtable.cc +158 -56
  93. package/deps/rocksdb/rocksdb/db/memtable.h +2 -0
  94. package/deps/rocksdb/rocksdb/db/memtable_list_test.cc +1 -0
  95. package/deps/rocksdb/rocksdb/db/merge_helper_test.cc +1 -0
  96. package/deps/rocksdb/rocksdb/db/options_file_test.cc +1 -0
  97. package/deps/rocksdb/rocksdb/db/perf_context_test.cc +1 -0
  98. package/deps/rocksdb/rocksdb/db/periodic_task_scheduler_test.cc +1 -0
  99. package/deps/rocksdb/rocksdb/db/plain_table_db_test.cc +1 -0
  100. package/deps/rocksdb/rocksdb/db/prefix_test.cc +1 -0
  101. package/deps/rocksdb/rocksdb/db/range_del_aggregator.cc +52 -9
  102. package/deps/rocksdb/rocksdb/db/range_del_aggregator.h +31 -2
  103. package/deps/rocksdb/rocksdb/db/range_del_aggregator_test.cc +1 -0
  104. package/deps/rocksdb/rocksdb/db/range_tombstone_fragmenter.cc +81 -42
  105. package/deps/rocksdb/rocksdb/db/range_tombstone_fragmenter.h +78 -12
  106. package/deps/rocksdb/rocksdb/db/range_tombstone_fragmenter_test.cc +1 -0
  107. package/deps/rocksdb/rocksdb/db/repair_test.cc +1 -0
  108. package/deps/rocksdb/rocksdb/db/seqno_time_test.cc +154 -27
  109. package/deps/rocksdb/rocksdb/db/seqno_to_time_mapping.cc +21 -4
  110. package/deps/rocksdb/rocksdb/db/seqno_to_time_mapping.h +4 -1
  111. package/deps/rocksdb/rocksdb/db/table_cache.cc +18 -6
  112. package/deps/rocksdb/rocksdb/db/table_properties_collector_test.cc +1 -0
  113. package/deps/rocksdb/rocksdb/db/version_builder_test.cc +1 -0
  114. package/deps/rocksdb/rocksdb/db/version_edit_test.cc +1 -0
  115. package/deps/rocksdb/rocksdb/db/version_set.cc +15 -7
  116. package/deps/rocksdb/rocksdb/db/version_set.h +2 -1
  117. package/deps/rocksdb/rocksdb/db/version_set_test.cc +1 -0
  118. package/deps/rocksdb/rocksdb/db/version_util.h +3 -1
  119. package/deps/rocksdb/rocksdb/db/wal_manager_test.cc +1 -0
  120. package/deps/rocksdb/rocksdb/db/wide/wide_column_serialization.cc +28 -9
  121. package/deps/rocksdb/rocksdb/db/wide/wide_column_serialization.h +21 -0
  122. package/deps/rocksdb/rocksdb/db/wide/wide_column_serialization_test.cc +30 -0
  123. package/deps/rocksdb/rocksdb/db/wide/wide_columns.cc +4 -0
  124. package/deps/rocksdb/rocksdb/db/write_batch.cc +30 -7
  125. package/deps/rocksdb/rocksdb/db/write_batch_internal.h +24 -13
  126. package/deps/rocksdb/rocksdb/db/write_batch_test.cc +5 -4
  127. package/deps/rocksdb/rocksdb/db/write_callback_test.cc +1 -0
  128. package/deps/rocksdb/rocksdb/db/write_controller_test.cc +1 -0
  129. package/deps/rocksdb/rocksdb/db_stress_tool/batched_ops_stress.cc +104 -60
  130. package/deps/rocksdb/rocksdb/db_stress_tool/cf_consistency_stress.cc +199 -108
  131. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_common.cc +39 -0
  132. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_common.h +8 -0
  133. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_driver.cc +3 -1
  134. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_gflags.cc +19 -0
  135. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_shared_state.h +26 -0
  136. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_test_base.cc +247 -118
  137. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_test_base.h +24 -4
  138. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_tool.cc +18 -0
  139. package/deps/rocksdb/rocksdb/db_stress_tool/expected_state.cc +129 -1
  140. package/deps/rocksdb/rocksdb/db_stress_tool/multi_ops_txns_stress.cc +22 -0
  141. package/deps/rocksdb/rocksdb/db_stress_tool/multi_ops_txns_stress.h +4 -0
  142. package/deps/rocksdb/rocksdb/db_stress_tool/no_batched_ops_stress.cc +312 -117
  143. package/deps/rocksdb/rocksdb/env/env_basic_test.cc +1 -0
  144. package/deps/rocksdb/rocksdb/env/fs_posix.cc +10 -2
  145. package/deps/rocksdb/rocksdb/env/io_posix_test.cc +1 -0
  146. package/deps/rocksdb/rocksdb/env/mock_env_test.cc +1 -0
  147. package/deps/rocksdb/rocksdb/file/delete_scheduler.cc +5 -1
  148. package/deps/rocksdb/rocksdb/file/delete_scheduler_test.cc +1 -0
  149. package/deps/rocksdb/rocksdb/file/prefetch_test.cc +1 -0
  150. package/deps/rocksdb/rocksdb/file/writable_file_writer.h +1 -1
  151. package/deps/rocksdb/rocksdb/include/rocksdb/advanced_options.h +49 -1
  152. package/deps/rocksdb/rocksdb/include/rocksdb/cache.h +44 -18
  153. package/deps/rocksdb/rocksdb/include/rocksdb/db.h +8 -7
  154. package/deps/rocksdb/rocksdb/include/rocksdb/file_system.h +6 -1
  155. package/deps/rocksdb/rocksdb/include/rocksdb/listener.h +3 -0
  156. package/deps/rocksdb/rocksdb/include/rocksdb/secondary_cache.h +17 -4
  157. package/deps/rocksdb/rocksdb/include/rocksdb/sst_file_reader.h +4 -0
  158. package/deps/rocksdb/rocksdb/include/rocksdb/sst_file_writer.h +7 -0
  159. package/deps/rocksdb/rocksdb/include/rocksdb/universal_compaction.h +1 -1
  160. package/deps/rocksdb/rocksdb/include/rocksdb/wide_columns.h +9 -0
  161. package/deps/rocksdb/rocksdb/include/rocksdb/write_batch.h +3 -6
  162. package/deps/rocksdb/rocksdb/logging/auto_roll_logger_test.cc +1 -0
  163. package/deps/rocksdb/rocksdb/logging/env_logger_test.cc +1 -0
  164. package/deps/rocksdb/rocksdb/logging/event_logger_test.cc +1 -0
  165. package/deps/rocksdb/rocksdb/memory/arena.cc +23 -88
  166. package/deps/rocksdb/rocksdb/memory/arena.h +25 -31
  167. package/deps/rocksdb/rocksdb/memory/arena_test.cc +61 -0
  168. package/deps/rocksdb/rocksdb/memory/memory_allocator_test.cc +1 -0
  169. package/deps/rocksdb/rocksdb/memtable/inlineskiplist_test.cc +1 -0
  170. package/deps/rocksdb/rocksdb/memtable/skiplist_test.cc +1 -0
  171. package/deps/rocksdb/rocksdb/memtable/write_buffer_manager_test.cc +1 -0
  172. package/deps/rocksdb/rocksdb/monitoring/histogram_test.cc +1 -0
  173. package/deps/rocksdb/rocksdb/monitoring/iostats_context_test.cc +1 -0
  174. package/deps/rocksdb/rocksdb/options/cf_options.cc +19 -0
  175. package/deps/rocksdb/rocksdb/options/cf_options.h +8 -0
  176. package/deps/rocksdb/rocksdb/options/configurable_test.cc +1 -0
  177. package/deps/rocksdb/rocksdb/options/options.cc +7 -0
  178. package/deps/rocksdb/rocksdb/options/options_helper.cc +6 -0
  179. package/deps/rocksdb/rocksdb/options/options_settable_test.cc +6 -0
  180. package/deps/rocksdb/rocksdb/options/options_test.cc +63 -40
  181. package/deps/rocksdb/rocksdb/port/mmap.cc +98 -0
  182. package/deps/rocksdb/rocksdb/port/mmap.h +70 -0
  183. package/deps/rocksdb/rocksdb/port/stack_trace.cc +7 -0
  184. package/deps/rocksdb/rocksdb/port/stack_trace.h +4 -1
  185. package/deps/rocksdb/rocksdb/port/win/port_win.h +2 -7
  186. package/deps/rocksdb/rocksdb/src.mk +1 -0
  187. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_factory.cc +7 -7
  188. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_reader.cc +3 -3
  189. package/deps/rocksdb/rocksdb/table/block_based/block_test.cc +1 -0
  190. package/deps/rocksdb/rocksdb/table/block_based/data_block_hash_index_test.cc +1 -0
  191. package/deps/rocksdb/rocksdb/table/block_based/full_filter_block_test.cc +1 -0
  192. package/deps/rocksdb/rocksdb/table/block_based/partitioned_filter_block_test.cc +1 -0
  193. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_builder_test.cc +1 -0
  194. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_reader_test.cc +1 -0
  195. package/deps/rocksdb/rocksdb/table/get_context.cc +19 -1
  196. package/deps/rocksdb/rocksdb/table/get_context.h +9 -0
  197. package/deps/rocksdb/rocksdb/table/merger_test.cc +1 -0
  198. package/deps/rocksdb/rocksdb/table/merging_iterator.cc +10 -11
  199. package/deps/rocksdb/rocksdb/table/mock_table.cc +37 -19
  200. package/deps/rocksdb/rocksdb/table/mock_table.h +5 -1
  201. package/deps/rocksdb/rocksdb/table/sst_file_reader.cc +6 -0
  202. package/deps/rocksdb/rocksdb/table/sst_file_reader_test.cc +33 -0
  203. package/deps/rocksdb/rocksdb/table/sst_file_writer.cc +45 -6
  204. package/deps/rocksdb/rocksdb/test_util/testharness.h +2 -0
  205. package/deps/rocksdb/rocksdb/tools/block_cache_analyzer/block_cache_trace_analyzer_test.cc +1 -0
  206. package/deps/rocksdb/rocksdb/tools/db_bench_tool.cc +5 -0
  207. package/deps/rocksdb/rocksdb/tools/db_bench_tool_test.cc +1 -0
  208. package/deps/rocksdb/rocksdb/tools/io_tracer_parser_test.cc +1 -0
  209. package/deps/rocksdb/rocksdb/tools/ldb_cmd_test.cc +36 -0
  210. package/deps/rocksdb/rocksdb/tools/reduce_levels_test.cc +1 -0
  211. package/deps/rocksdb/rocksdb/tools/trace_analyzer_test.cc +1 -0
  212. package/deps/rocksdb/rocksdb/trace_replay/block_cache_tracer_test.cc +1 -0
  213. package/deps/rocksdb/rocksdb/trace_replay/io_tracer_test.cc +1 -0
  214. package/deps/rocksdb/rocksdb/util/autovector_test.cc +1 -0
  215. package/deps/rocksdb/rocksdb/util/bloom_test.cc +1 -0
  216. package/deps/rocksdb/rocksdb/util/coding_test.cc +1 -0
  217. package/deps/rocksdb/rocksdb/util/crc32c_test.cc +1 -0
  218. package/deps/rocksdb/rocksdb/util/dynamic_bloom_test.cc +1 -0
  219. package/deps/rocksdb/rocksdb/util/file_reader_writer_test.cc +1 -0
  220. package/deps/rocksdb/rocksdb/util/filelock_test.cc +1 -0
  221. package/deps/rocksdb/rocksdb/util/gflags_compat.h +12 -7
  222. package/deps/rocksdb/rocksdb/util/hash_test.cc +1 -0
  223. package/deps/rocksdb/rocksdb/util/heap_test.cc +4 -2
  224. package/deps/rocksdb/rocksdb/util/random_test.cc +1 -0
  225. package/deps/rocksdb/rocksdb/util/rate_limiter_test.cc +1 -0
  226. package/deps/rocksdb/rocksdb/util/repeatable_thread_test.cc +1 -0
  227. package/deps/rocksdb/rocksdb/util/ribbon_test.cc +1 -0
  228. package/deps/rocksdb/rocksdb/util/slice_transform_test.cc +1 -0
  229. package/deps/rocksdb/rocksdb/util/thread_list_test.cc +1 -0
  230. package/deps/rocksdb/rocksdb/util/thread_local_test.cc +1 -0
  231. package/deps/rocksdb/rocksdb/util/timer_test.cc +1 -0
  232. package/deps/rocksdb/rocksdb/util/work_queue_test.cc +4 -0
  233. package/deps/rocksdb/rocksdb/utilities/agg_merge/agg_merge_test.cc +1 -0
  234. package/deps/rocksdb/rocksdb/utilities/backup/backup_engine.cc +13 -0
  235. package/deps/rocksdb/rocksdb/utilities/backup/backup_engine_test.cc +9 -3
  236. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_test.cc +1 -0
  237. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_format_test.cc +1 -0
  238. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_functional_test.cc +1 -0
  239. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_row_merge_test.cc +1 -0
  240. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_serialize_test.cc +1 -0
  241. package/deps/rocksdb/rocksdb/utilities/env_mirror_test.cc +1 -0
  242. package/deps/rocksdb/rocksdb/utilities/env_timed_test.cc +1 -0
  243. package/deps/rocksdb/rocksdb/utilities/fault_injection_secondary_cache.h +8 -0
  244. package/deps/rocksdb/rocksdb/utilities/memory/memory_test.cc +1 -0
  245. package/deps/rocksdb/rocksdb/utilities/object_registry_test.cc +1 -0
  246. package/deps/rocksdb/rocksdb/utilities/options/options_util_test.cc +1 -0
  247. package/deps/rocksdb/rocksdb/utilities/persistent_cache/hash_table_test.cc +1 -0
  248. package/deps/rocksdb/rocksdb/utilities/persistent_cache/persistent_cache_test.cc +1 -0
  249. package/deps/rocksdb/rocksdb/utilities/simulator_cache/cache_simulator_test.cc +1 -0
  250. package/deps/rocksdb/rocksdb/utilities/transactions/optimistic_transaction_test.cc +1 -0
  251. package/deps/rocksdb/rocksdb/utilities/transactions/timestamped_snapshot_test.cc +1 -0
  252. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_test.cc +1 -0
  253. package/deps/rocksdb/rocksdb/utilities/transactions/write_committed_transaction_ts_test.cc +1 -0
  254. package/deps/rocksdb/rocksdb/utilities/transactions/write_unprepared_transaction_test.cc +1 -0
  255. package/deps/rocksdb/rocksdb/utilities/ttl/ttl_test.cc +1 -0
  256. package/deps/rocksdb/rocksdb/utilities/util_merge_operators_test.cc +1 -0
  257. package/deps/rocksdb/rocksdb/utilities/write_batch_with_index/write_batch_with_index.cc +7 -0
  258. package/deps/rocksdb/rocksdb/utilities/write_batch_with_index/write_batch_with_index_test.cc +20 -0
  259. package/index.js +12 -4
  260. package/package.json +1 -1
  261. package/prebuilds/darwin-arm64/node.napi.node +0 -0
  262. package/prebuilds/linux-x64/node.napi.node +0 -0
@@ -76,7 +76,7 @@ MemTable::MemTable(const InternalKeyComparator& cmp,
76
76
  : comparator_(cmp),
77
77
  moptions_(ioptions, mutable_cf_options),
78
78
  refs_(0),
79
- kArenaBlockSize(OptimizeBlockSize(moptions_.arena_block_size)),
79
+ kArenaBlockSize(Arena::OptimizeBlockSize(moptions_.arena_block_size)),
80
80
  mem_tracker_(write_buffer_manager),
81
81
  arena_(moptions_.arena_block_size,
82
82
  (write_buffer_manager != nullptr &&
@@ -573,7 +573,7 @@ FragmentedRangeTombstoneIterator* MemTable::NewRangeTombstoneIteratorInternal(
573
573
  assert(IsFragmentedRangeTombstonesConstructed());
574
574
  return new FragmentedRangeTombstoneIterator(
575
575
  fragmented_range_tombstone_list_.get(), comparator_.comparator,
576
- read_seq);
576
+ read_seq, read_options.timestamp);
577
577
  }
578
578
 
579
579
  // takes current cache
@@ -596,8 +596,9 @@ FragmentedRangeTombstoneIterator* MemTable::NewRangeTombstoneIteratorInternal(
596
596
  cache->reader_mutex.unlock();
597
597
  }
598
598
 
599
- return new FragmentedRangeTombstoneIterator(cache, comparator_.comparator,
600
- read_seq);
599
+ auto* fragmented_iter = new FragmentedRangeTombstoneIterator(
600
+ cache, comparator_.comparator, read_seq, read_options.timestamp);
601
+ return fragmented_iter;
601
602
  }
602
603
 
603
604
  void MemTable::ConstructFragmentedRangeTombstones() {
@@ -946,6 +947,10 @@ static bool SaveValue(void* arg, const char* entry) {
946
947
  const Comparator* user_comparator =
947
948
  s->mem->GetInternalKeyComparator().user_comparator();
948
949
  size_t ts_sz = user_comparator->timestamp_size();
950
+ if (ts_sz && s->timestamp && max_covering_tombstone_seq > 0) {
951
+ // timestamp should already be set to range tombstone timestamp
952
+ assert(s->timestamp->size() == ts_sz);
953
+ }
949
954
  if (user_comparator->EqualWithoutTimestamp(user_key_slice,
950
955
  s->key->user_key())) {
951
956
  // Correct user key
@@ -960,10 +965,20 @@ static bool SaveValue(void* arg, const char* entry) {
960
965
 
961
966
  if (s->seq == kMaxSequenceNumber) {
962
967
  s->seq = seq;
968
+ if (s->seq > max_covering_tombstone_seq) {
969
+ if (ts_sz && s->timestamp != nullptr) {
970
+ // `timestamp` was set to range tombstone's timestamp before
971
+ // `SaveValue` is ever called. This key has a higher sequence number
972
+ // than range tombstone, and is the key with the highest seqno across
973
+ // all keys with this user_key, so we update timestamp here.
974
+ Slice ts = ExtractTimestampFromUserKey(user_key_slice, ts_sz);
975
+ s->timestamp->assign(ts.data(), ts_sz);
976
+ }
977
+ } else {
978
+ s->seq = max_covering_tombstone_seq;
979
+ }
963
980
  }
964
981
 
965
- s->seq = std::max(s->seq, max_covering_tombstone_seq);
966
-
967
982
  if (ts_sz > 0 && s->timestamp != nullptr) {
968
983
  if (!s->timestamp->empty()) {
969
984
  assert(ts_sz == s->timestamp->size());
@@ -978,82 +993,153 @@ static bool SaveValue(void* arg, const char* entry) {
978
993
  }
979
994
 
980
995
  if ((type == kTypeValue || type == kTypeMerge || type == kTypeBlobIndex ||
981
- type == kTypeWideColumnEntity) &&
996
+ type == kTypeWideColumnEntity || type == kTypeDeletion ||
997
+ type == kTypeSingleDeletion || type == kTypeDeletionWithTimestamp) &&
982
998
  max_covering_tombstone_seq > seq) {
983
999
  type = kTypeRangeDeletion;
984
1000
  }
985
1001
  switch (type) {
986
- case kTypeBlobIndex:
987
- case kTypeWideColumnEntity:
1002
+ case kTypeBlobIndex: {
1003
+ if (!s->do_merge) {
1004
+ *(s->status) = Status::NotSupported(
1005
+ "GetMergeOperands not supported by stacked BlobDB");
1006
+ *(s->found_final_value) = true;
1007
+ return false;
1008
+ }
1009
+
988
1010
  if (*(s->merge_in_progress)) {
989
- *(s->status) = Status::NotSupported("Merge operator not supported");
990
- } else if (!s->do_merge) {
991
- *(s->status) = Status::NotSupported("GetMergeOperands not supported");
992
- } else if (type == kTypeBlobIndex) {
993
- if (s->is_blob_index == nullptr) {
994
- ROCKS_LOG_ERROR(s->logger, "Encounter unexpected blob index.");
995
- *(s->status) = Status::NotSupported(
996
- "Encounter unsupported blob value. Please open DB with "
997
- "ROCKSDB_NAMESPACE::blob_db::BlobDB instead.");
998
- }
1011
+ *(s->status) = Status::NotSupported(
1012
+ "Merge operator not supported by stacked BlobDB");
1013
+ *(s->found_final_value) = true;
1014
+ return false;
999
1015
  }
1000
1016
 
1001
- if (!s->status->ok()) {
1017
+ if (s->is_blob_index == nullptr) {
1018
+ ROCKS_LOG_ERROR(s->logger, "Encountered unexpected blob index.");
1019
+ *(s->status) = Status::NotSupported(
1020
+ "Encountered unexpected blob index. Please open DB with "
1021
+ "ROCKSDB_NAMESPACE::blob_db::BlobDB.");
1002
1022
  *(s->found_final_value) = true;
1003
1023
  return false;
1004
1024
  }
1005
- FALLTHROUGH_INTENDED;
1025
+
1026
+ if (s->inplace_update_support) {
1027
+ s->mem->GetLock(s->key->user_key())->ReadLock();
1028
+ }
1029
+
1030
+ Slice v = GetLengthPrefixedSlice(key_ptr + key_length);
1031
+
1032
+ *(s->status) = Status::OK();
1033
+
1034
+ if (s->value) {
1035
+ s->value->assign(v.data(), v.size());
1036
+ } else if (s->columns) {
1037
+ s->columns->SetPlainValue(v);
1038
+ }
1039
+
1040
+ if (s->inplace_update_support) {
1041
+ s->mem->GetLock(s->key->user_key())->ReadUnlock();
1042
+ }
1043
+
1044
+ *(s->found_final_value) = true;
1045
+ *(s->is_blob_index) = true;
1046
+
1047
+ return false;
1048
+ }
1006
1049
  case kTypeValue: {
1007
1050
  if (s->inplace_update_support) {
1008
1051
  s->mem->GetLock(s->key->user_key())->ReadLock();
1009
1052
  }
1053
+
1010
1054
  Slice v = GetLengthPrefixedSlice(key_ptr + key_length);
1055
+
1011
1056
  *(s->status) = Status::OK();
1012
- if (*(s->merge_in_progress)) {
1013
- if (s->do_merge) {
1014
- if (s->value != nullptr) {
1015
- *(s->status) = MergeHelper::TimedFullMerge(
1016
- merge_operator, s->key->user_key(), &v,
1017
- merge_context->GetOperands(), s->value, s->logger,
1018
- s->statistics, s->clock, nullptr /* result_operand */, true);
1019
- }
1020
- } else {
1021
- // Preserve the value with the goal of returning it as part of
1022
- // raw merge operands to the user
1023
- merge_context->PushOperand(
1024
- v, s->inplace_update_support == false /* operand_pinned */);
1025
- }
1026
- } else if (!s->do_merge) {
1057
+
1058
+ if (!s->do_merge) {
1027
1059
  // Preserve the value with the goal of returning it as part of
1028
1060
  // raw merge operands to the user
1061
+
1029
1062
  merge_context->PushOperand(
1030
1063
  v, s->inplace_update_support == false /* operand_pinned */);
1031
- } else if (s->value) {
1032
- if (type != kTypeWideColumnEntity) {
1033
- assert(type == kTypeValue || type == kTypeBlobIndex);
1034
- s->value->assign(v.data(), v.size());
1035
- } else {
1036
- Slice value;
1037
- *(s->status) =
1038
- WideColumnSerialization::GetValueOfDefaultColumn(v, value);
1064
+ } else if (*(s->merge_in_progress)) {
1065
+ assert(s->do_merge);
1066
+
1067
+ if (s->value || s->columns) {
1068
+ std::string result;
1069
+ *(s->status) = MergeHelper::TimedFullMerge(
1070
+ merge_operator, s->key->user_key(), &v,
1071
+ merge_context->GetOperands(), &result, s->logger, s->statistics,
1072
+ s->clock, nullptr /* result_operand */, true);
1073
+
1039
1074
  if (s->status->ok()) {
1040
- s->value->assign(value.data(), value.size());
1075
+ if (s->value) {
1076
+ *(s->value) = std::move(result);
1077
+ } else {
1078
+ assert(s->columns);
1079
+ s->columns->SetPlainValue(result);
1080
+ }
1041
1081
  }
1042
1082
  }
1083
+ } else if (s->value) {
1084
+ s->value->assign(v.data(), v.size());
1043
1085
  } else if (s->columns) {
1044
- if (type != kTypeWideColumnEntity) {
1045
- s->columns->SetPlainValue(v);
1046
- } else {
1047
- *(s->status) = s->columns->SetWideColumnValue(v);
1086
+ s->columns->SetPlainValue(v);
1087
+ }
1088
+
1089
+ if (s->inplace_update_support) {
1090
+ s->mem->GetLock(s->key->user_key())->ReadUnlock();
1091
+ }
1092
+
1093
+ *(s->found_final_value) = true;
1094
+
1095
+ if (s->is_blob_index != nullptr) {
1096
+ *(s->is_blob_index) = false;
1097
+ }
1098
+
1099
+ return false;
1100
+ }
1101
+ case kTypeWideColumnEntity: {
1102
+ if (!s->do_merge) {
1103
+ *(s->status) = Status::NotSupported(
1104
+ "GetMergeOperands not supported for wide-column entities");
1105
+ *(s->found_final_value) = true;
1106
+ return false;
1107
+ }
1108
+
1109
+ if (*(s->merge_in_progress)) {
1110
+ *(s->status) = Status::NotSupported(
1111
+ "Merge not supported for wide-column entities");
1112
+ *(s->found_final_value) = true;
1113
+ return false;
1114
+ }
1115
+
1116
+ if (s->inplace_update_support) {
1117
+ s->mem->GetLock(s->key->user_key())->ReadLock();
1118
+ }
1119
+
1120
+ Slice v = GetLengthPrefixedSlice(key_ptr + key_length);
1121
+
1122
+ *(s->status) = Status::OK();
1123
+
1124
+ if (s->value) {
1125
+ Slice value_of_default;
1126
+ *(s->status) = WideColumnSerialization::GetValueOfDefaultColumn(
1127
+ v, value_of_default);
1128
+ if (s->status->ok()) {
1129
+ s->value->assign(value_of_default.data(), value_of_default.size());
1048
1130
  }
1131
+ } else if (s->columns) {
1132
+ *(s->status) = s->columns->SetWideColumnValue(v);
1049
1133
  }
1050
1134
 
1051
1135
  if (s->inplace_update_support) {
1052
1136
  s->mem->GetLock(s->key->user_key())->ReadUnlock();
1053
1137
  }
1138
+
1054
1139
  *(s->found_final_value) = true;
1140
+
1055
1141
  if (s->is_blob_index != nullptr) {
1056
- *(s->is_blob_index) = (type == kTypeBlobIndex);
1142
+ *(s->is_blob_index) = false;
1057
1143
  }
1058
1144
 
1059
1145
  return false;
@@ -1139,9 +1225,17 @@ bool MemTable::Get(const LookupKey& key, std::string* value,
1139
1225
  GetInternalKeySeqno(key.internal_key()),
1140
1226
  immutable_memtable));
1141
1227
  if (range_del_iter != nullptr) {
1142
- *max_covering_tombstone_seq =
1143
- std::max(*max_covering_tombstone_seq,
1144
- range_del_iter->MaxCoveringTombstoneSeqnum(key.user_key()));
1228
+ SequenceNumber covering_seq =
1229
+ range_del_iter->MaxCoveringTombstoneSeqnum(key.user_key());
1230
+ if (covering_seq > *max_covering_tombstone_seq) {
1231
+ *max_covering_tombstone_seq = covering_seq;
1232
+ if (timestamp) {
1233
+ // Will be overwritten in SaveValue() if there is a point key with
1234
+ // a higher seqno.
1235
+ timestamp->assign(range_del_iter->timestamp().data(),
1236
+ range_del_iter->timestamp().size());
1237
+ }
1238
+ }
1145
1239
  }
1146
1240
 
1147
1241
  bool found_final_value = false;
@@ -1272,9 +1366,17 @@ void MemTable::MultiGet(const ReadOptions& read_options, MultiGetRange* range,
1272
1366
  NewRangeTombstoneIteratorInternal(
1273
1367
  read_options, GetInternalKeySeqno(iter->lkey->internal_key()),
1274
1368
  immutable_memtable));
1275
- iter->max_covering_tombstone_seq = std::max(
1276
- iter->max_covering_tombstone_seq,
1277
- range_del_iter->MaxCoveringTombstoneSeqnum(iter->lkey->user_key()));
1369
+ SequenceNumber covering_seq =
1370
+ range_del_iter->MaxCoveringTombstoneSeqnum(iter->lkey->user_key());
1371
+ if (covering_seq > iter->max_covering_tombstone_seq) {
1372
+ iter->max_covering_tombstone_seq = covering_seq;
1373
+ if (iter->timestamp) {
1374
+ // Will be overwritten in SaveValue() if there is a point key with
1375
+ // a higher seqno.
1376
+ iter->timestamp->assign(range_del_iter->timestamp().data(),
1377
+ range_del_iter->timestamp().size());
1378
+ }
1379
+ }
1278
1380
  }
1279
1381
  SequenceNumber dummy_seq;
1280
1382
  GetFromTable(*(iter->lkey), iter->max_covering_tombstone_seq, true,
@@ -639,6 +639,8 @@ class MemTable {
639
639
  // Always returns non-null and assumes certain pre-checks (e.g.,
640
640
  // is_range_del_table_empty_) are done. This is only valid during the lifetime
641
641
  // of the underlying memtable.
642
+ // read_seq and read_options.timestamp will be used as the upper bound
643
+ // for range tombstones.
642
644
  FragmentedRangeTombstoneIterator* NewRangeTombstoneIteratorInternal(
643
645
  const ReadOptions& read_options, SequenceNumber read_seq,
644
646
  bool immutable_memtable);
@@ -1009,6 +1009,7 @@ TEST_F(MemTableListTest, AtomicFlusTest) {
1009
1009
  } // namespace ROCKSDB_NAMESPACE
1010
1010
 
1011
1011
  int main(int argc, char** argv) {
1012
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
1012
1013
  ::testing::InitGoogleTest(&argc, argv);
1013
1014
  return RUN_ALL_TESTS();
1014
1015
  }
@@ -291,6 +291,7 @@ TEST_F(MergeHelperTest, DontFilterMergeOperandsBeforeSnapshotTest) {
291
291
  } // namespace ROCKSDB_NAMESPACE
292
292
 
293
293
  int main(int argc, char** argv) {
294
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
294
295
  ::testing::InitGoogleTest(&argc, argv);
295
296
  return RUN_ALL_TESTS();
296
297
  }
@@ -102,6 +102,7 @@ TEST_F(OptionsFileTest, OptionsFileName) {
102
102
 
103
103
  int main(int argc, char** argv) {
104
104
  #if !(defined NDEBUG) || !defined(OS_WIN)
105
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
105
106
  ::testing::InitGoogleTest(&argc, argv);
106
107
  return RUN_ALL_TESTS();
107
108
  #else
@@ -959,6 +959,7 @@ TEST_F(PerfContextTest, CPUTimer) {
959
959
  } // namespace ROCKSDB_NAMESPACE
960
960
 
961
961
  int main(int argc, char** argv) {
962
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
962
963
  ::testing::InitGoogleTest(&argc, argv);
963
964
 
964
965
  for (int i = 1; i < argc; i++) {
@@ -224,6 +224,7 @@ TEST_F(PeriodicTaskSchedulerTest, MultiEnv) {
224
224
  } // namespace ROCKSDB_NAMESPACE
225
225
 
226
226
  int main(int argc, char** argv) {
227
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
227
228
  ::testing::InitGoogleTest(&argc, argv);
228
229
 
229
230
  return RUN_ALL_TESTS();
@@ -1352,6 +1352,7 @@ INSTANTIATE_TEST_CASE_P(PlainTableDBTest, PlainTableDBTest, ::testing::Bool());
1352
1352
  } // namespace ROCKSDB_NAMESPACE
1353
1353
 
1354
1354
  int main(int argc, char** argv) {
1355
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
1355
1356
  ::testing::InitGoogleTest(&argc, argv);
1356
1357
  return RUN_ALL_TESTS();
1357
1358
  }
@@ -890,6 +890,7 @@ TEST_F(PrefixTest, PrefixSeekModePrev3) {
890
890
  } // namespace ROCKSDB_NAMESPACE
891
891
 
892
892
  int main(int argc, char** argv) {
893
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
893
894
  ::testing::InitGoogleTest(&argc, argv);
894
895
  ParseCommandLineFlags(&argc, &argv, true);
895
896
  return RUN_ALL_TESTS();
@@ -85,7 +85,7 @@ bool TruncatedRangeDelIterator::Valid() const {
85
85
  icmp_->Compare(iter_->parsed_start_key(), *largest_) < 0);
86
86
  }
87
87
 
88
- // NOTE: target is a user key
88
+ // NOTE: target is a user key, with timestamp if enabled.
89
89
  void TruncatedRangeDelIterator::Seek(const Slice& target) {
90
90
  if (largest_ != nullptr &&
91
91
  icmp_->Compare(*largest_, ParsedInternalKey(target, kMaxSequenceNumber,
@@ -101,7 +101,7 @@ void TruncatedRangeDelIterator::Seek(const Slice& target) {
101
101
  iter_->Seek(target);
102
102
  }
103
103
 
104
- // NOTE: target is a user key
104
+ // NOTE: target is a user key, with timestamp if enabled.
105
105
  void TruncatedRangeDelIterator::SeekForPrev(const Slice& target) {
106
106
  if (smallest_ != nullptr &&
107
107
  icmp_->Compare(ParsedInternalKey(target, 0, kTypeRangeDeletion),
@@ -339,11 +339,22 @@ void CompactionRangeDelAggregator::AddTombstones(
339
339
  if (input_iter == nullptr || input_iter->empty()) {
340
340
  return;
341
341
  }
342
+ // This bounds output of CompactionRangeDelAggregator::NewIterator.
343
+ if (!trim_ts_.empty()) {
344
+ assert(icmp_->user_comparator()->timestamp_size() > 0);
345
+ input_iter->SetTimestampUpperBound(&trim_ts_);
346
+ }
347
+
342
348
  assert(input_iter->lower_bound() == 0);
343
349
  assert(input_iter->upper_bound() == kMaxSequenceNumber);
344
350
  parent_iters_.emplace_back(new TruncatedRangeDelIterator(
345
351
  std::move(input_iter), icmp_, smallest, largest));
346
352
 
353
+ Slice* ts_upper_bound = nullptr;
354
+ if (!ts_upper_bound_.empty()) {
355
+ assert(icmp_->user_comparator()->timestamp_size() > 0);
356
+ ts_upper_bound = &ts_upper_bound_;
357
+ }
347
358
  auto split_iters = parent_iters_.back()->SplitBySnapshot(*snapshots_);
348
359
  for (auto& split_iter : split_iters) {
349
360
  auto it = reps_.find(split_iter.first);
@@ -356,6 +367,16 @@ void CompactionRangeDelAggregator::AddTombstones(
356
367
  assert(inserted);
357
368
  }
358
369
  assert(it != reps_.end());
370
+ // ts_upper_bound is used to bound ShouldDelete() to only consider
371
+ // range tombstones under full_history_ts_low_ and trim_ts_. Keys covered by
372
+ // range tombstones that are above full_history_ts_low_ should not be
373
+ // dropped prematurely: user may read with a timestamp between the range
374
+ // tombstone and the covered key. Note that we cannot set timestamp
375
+ // upperbound on the original `input_iter` since `input_iter`s are later
376
+ // used in CompactionRangeDelAggregator::NewIterator to output range
377
+ // tombstones for persistence. We do not want to only persist range
378
+ // tombstones with timestamp lower than ts_upper_bound.
379
+ split_iter.second->SetTimestampUpperBound(ts_upper_bound);
359
380
  it->second.AddTombstones(std::move(split_iter.second));
360
381
  }
361
382
  }
@@ -371,6 +392,12 @@ bool CompactionRangeDelAggregator::ShouldDelete(const ParsedInternalKey& parsed,
371
392
 
372
393
  namespace {
373
394
 
395
+ // Produce a sorted (by start internal key) stream of range tombstones from
396
+ // `children`. lower_bound and upper_bound on user key can be
397
+ // optionally specified. Range tombstones that ends before lower_bound or starts
398
+ // after upper_bound are excluded.
399
+ // If user-defined timestamp is enabled, lower_bound and upper_bound should
400
+ // contain timestamp, but comparison is done ignoring timestamps.
374
401
  class TruncatedRangeDelMergingIter : public InternalIterator {
375
402
  public:
376
403
  TruncatedRangeDelMergingIter(
@@ -381,7 +408,8 @@ class TruncatedRangeDelMergingIter : public InternalIterator {
381
408
  lower_bound_(lower_bound),
382
409
  upper_bound_(upper_bound),
383
410
  upper_bound_inclusive_(upper_bound_inclusive),
384
- heap_(StartKeyMinComparator(icmp)) {
411
+ heap_(StartKeyMinComparator(icmp)),
412
+ ts_sz_(icmp_->user_comparator()->timestamp_size()) {
385
413
  for (auto& child : children) {
386
414
  if (child != nullptr) {
387
415
  assert(child->lower_bound() == 0);
@@ -422,15 +450,28 @@ class TruncatedRangeDelMergingIter : public InternalIterator {
422
450
 
423
451
  Slice key() const override {
424
452
  auto* top = heap_.top();
425
- cur_start_key_.Set(top->start_key().user_key, top->seq(),
426
- kTypeRangeDeletion);
453
+ if (ts_sz_) {
454
+ cur_start_key_.Set(top->start_key().user_key, top->seq(),
455
+ kTypeRangeDeletion, top->timestamp());
456
+ } else {
457
+ cur_start_key_.Set(top->start_key().user_key, top->seq(),
458
+ kTypeRangeDeletion);
459
+ }
460
+ assert(top->start_key().user_key.size() >= ts_sz_);
427
461
  return cur_start_key_.Encode();
428
462
  }
429
463
 
430
464
  Slice value() const override {
431
465
  auto* top = heap_.top();
432
- assert(top->end_key().sequence == kMaxSequenceNumber);
433
- return top->end_key().user_key;
466
+ if (!ts_sz_) {
467
+ return top->end_key().user_key;
468
+ }
469
+ assert(top->timestamp().size() == ts_sz_);
470
+ cur_end_key_.clear();
471
+ cur_end_key_.append(top->end_key().user_key.data(),
472
+ top->end_key().user_key.size() - ts_sz_);
473
+ cur_end_key_.append(top->timestamp().data(), ts_sz_);
474
+ return cur_end_key_;
434
475
  }
435
476
 
436
477
  // Unused InternalIterator methods
@@ -444,8 +485,8 @@ class TruncatedRangeDelMergingIter : public InternalIterator {
444
485
  if (upper_bound_ == nullptr) {
445
486
  return true;
446
487
  }
447
- int cmp = icmp_->user_comparator()->Compare(iter->start_key().user_key,
448
- *upper_bound_);
488
+ int cmp = icmp_->user_comparator()->CompareWithoutTimestamp(
489
+ iter->start_key().user_key, *upper_bound_);
449
490
  return upper_bound_inclusive_ ? cmp <= 0 : cmp < 0;
450
491
  }
451
492
 
@@ -457,6 +498,8 @@ class TruncatedRangeDelMergingIter : public InternalIterator {
457
498
  std::vector<TruncatedRangeDelIterator*> children_;
458
499
 
459
500
  mutable InternalKey cur_start_key_;
501
+ mutable std::string cur_end_key_;
502
+ size_t ts_sz_;
460
503
  };
461
504
 
462
505
  } // namespace
@@ -72,6 +72,13 @@ class TruncatedRangeDelIterator {
72
72
  }
73
73
 
74
74
  SequenceNumber seq() const { return iter_->seq(); }
75
+ Slice timestamp() const {
76
+ assert(icmp_->user_comparator()->timestamp_size());
77
+ return iter_->timestamp();
78
+ }
79
+ void SetTimestampUpperBound(const Slice* ts_upper_bound) {
80
+ iter_->SetTimestampUpperBound(ts_upper_bound);
81
+ }
75
82
 
76
83
  std::map<SequenceNumber, std::unique_ptr<TruncatedRangeDelIterator>>
77
84
  SplitBySnapshot(const std::vector<SequenceNumber>& snapshots);
@@ -332,6 +339,8 @@ class RangeDelAggregator {
332
339
  }
333
340
  }
334
341
 
342
+ // If user-defined timestamp is enabled, `start` and `end` are user keys
343
+ // with timestamp.
335
344
  bool IsRangeOverlapped(const Slice& start, const Slice& end);
336
345
 
337
346
  private:
@@ -395,8 +404,25 @@ class ReadRangeDelAggregator final : public RangeDelAggregator {
395
404
  class CompactionRangeDelAggregator : public RangeDelAggregator {
396
405
  public:
397
406
  CompactionRangeDelAggregator(const InternalKeyComparator* icmp,
398
- const std::vector<SequenceNumber>& snapshots)
399
- : RangeDelAggregator(icmp), snapshots_(&snapshots) {}
407
+ const std::vector<SequenceNumber>& snapshots,
408
+ const std::string* full_history_ts_low = nullptr,
409
+ const std::string* trim_ts = nullptr)
410
+ : RangeDelAggregator(icmp), snapshots_(&snapshots) {
411
+ if (full_history_ts_low) {
412
+ ts_upper_bound_ = *full_history_ts_low;
413
+ }
414
+ if (trim_ts) {
415
+ trim_ts_ = *trim_ts;
416
+ // Range tombstone newer than `trim_ts` or `full_history_ts_low` should
417
+ // not be considered in ShouldDelete().
418
+ if (ts_upper_bound_.empty()) {
419
+ ts_upper_bound_ = trim_ts_;
420
+ } else if (!trim_ts_.empty() && icmp->user_comparator()->CompareTimestamp(
421
+ trim_ts_, ts_upper_bound_) < 0) {
422
+ ts_upper_bound_ = trim_ts_;
423
+ }
424
+ }
425
+ }
400
426
  ~CompactionRangeDelAggregator() override {}
401
427
 
402
428
  void AddTombstones(
@@ -442,6 +468,9 @@ class CompactionRangeDelAggregator : public RangeDelAggregator {
442
468
  std::map<SequenceNumber, StripeRep> reps_;
443
469
 
444
470
  const std::vector<SequenceNumber>* snapshots_;
471
+ // min over full_history_ts_low and trim_ts_
472
+ Slice ts_upper_bound_{};
473
+ Slice trim_ts_{};
445
474
  };
446
475
 
447
476
  } // namespace ROCKSDB_NAMESPACE
@@ -709,6 +709,7 @@ TEST_F(RangeDelAggregatorTest,
709
709
  } // namespace ROCKSDB_NAMESPACE
710
710
 
711
711
  int main(int argc, char** argv) {
712
+ ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
712
713
  ::testing::InitGoogleTest(&argc, argv);
713
714
  return RUN_ALL_TESTS();
714
715
  }