@nxtedition/rocksdb 5.2.21 → 5.2.28

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 (923) hide show
  1. package/binding.cc +510 -967
  2. package/binding.gyp +78 -72
  3. package/chained-batch.js +1 -2
  4. package/deps/rocksdb/build_version.cc +70 -4
  5. package/deps/rocksdb/rocksdb/CMakeLists.txt +281 -149
  6. package/deps/rocksdb/rocksdb/Makefile +459 -469
  7. package/deps/rocksdb/rocksdb/TARGETS +5244 -1500
  8. package/deps/rocksdb/rocksdb/cache/cache.cc +12 -3
  9. package/deps/rocksdb/rocksdb/cache/cache_bench.cc +7 -368
  10. package/deps/rocksdb/rocksdb/cache/cache_bench_tool.cc +924 -0
  11. package/deps/rocksdb/rocksdb/cache/cache_entry_roles.cc +128 -0
  12. package/deps/rocksdb/rocksdb/cache/cache_entry_roles.h +103 -0
  13. package/deps/rocksdb/rocksdb/cache/cache_entry_stats.h +183 -0
  14. package/deps/rocksdb/rocksdb/cache/cache_helpers.h +11 -0
  15. package/deps/rocksdb/rocksdb/cache/cache_key.cc +344 -0
  16. package/deps/rocksdb/rocksdb/cache/cache_key.h +132 -0
  17. package/deps/rocksdb/rocksdb/cache/cache_reservation_manager.cc +183 -0
  18. package/deps/rocksdb/rocksdb/cache/cache_reservation_manager.h +288 -0
  19. package/deps/rocksdb/rocksdb/cache/cache_reservation_manager_test.cc +468 -0
  20. package/deps/rocksdb/rocksdb/cache/cache_test.cc +85 -8
  21. package/deps/rocksdb/rocksdb/cache/clock_cache.cc +121 -51
  22. package/deps/rocksdb/rocksdb/cache/compressed_secondary_cache.cc +171 -0
  23. package/deps/rocksdb/rocksdb/cache/compressed_secondary_cache.h +86 -0
  24. package/deps/rocksdb/rocksdb/cache/compressed_secondary_cache_test.cc +607 -0
  25. package/deps/rocksdb/rocksdb/cache/lru_cache.cc +381 -154
  26. package/deps/rocksdb/rocksdb/cache/lru_cache.h +176 -33
  27. package/deps/rocksdb/rocksdb/cache/lru_cache_test.cc +1659 -3
  28. package/deps/rocksdb/rocksdb/cache/sharded_cache.cc +94 -23
  29. package/deps/rocksdb/rocksdb/cache/sharded_cache.h +49 -28
  30. package/deps/rocksdb/rocksdb/cmake/modules/CxxFlags.cmake +7 -0
  31. package/deps/rocksdb/rocksdb/cmake/modules/FindJeMalloc.cmake +29 -0
  32. package/deps/rocksdb/rocksdb/cmake/modules/FindNUMA.cmake +29 -0
  33. package/deps/rocksdb/rocksdb/cmake/modules/FindSnappy.cmake +29 -0
  34. package/deps/rocksdb/rocksdb/cmake/modules/FindTBB.cmake +33 -0
  35. package/deps/rocksdb/rocksdb/cmake/modules/Findgflags.cmake +29 -0
  36. package/deps/rocksdb/rocksdb/cmake/modules/Findlz4.cmake +29 -0
  37. package/deps/rocksdb/rocksdb/cmake/modules/Finduring.cmake +26 -0
  38. package/deps/rocksdb/rocksdb/cmake/modules/Findzstd.cmake +29 -0
  39. package/deps/rocksdb/rocksdb/cmake/modules/ReadVersion.cmake +10 -0
  40. package/deps/rocksdb/rocksdb/crash_test.mk +93 -0
  41. package/deps/rocksdb/rocksdb/db/arena_wrapped_db_iter.cc +54 -31
  42. package/deps/rocksdb/rocksdb/db/arena_wrapped_db_iter.h +10 -6
  43. package/deps/rocksdb/rocksdb/db/blob/blob_counting_iterator.h +146 -0
  44. package/deps/rocksdb/rocksdb/db/blob/blob_counting_iterator_test.cc +326 -0
  45. package/deps/rocksdb/rocksdb/db/blob/blob_fetcher.cc +34 -0
  46. package/deps/rocksdb/rocksdb/db/blob/blob_fetcher.h +37 -0
  47. package/deps/rocksdb/rocksdb/db/blob/blob_file_addition.cc +4 -2
  48. package/deps/rocksdb/rocksdb/db/blob/blob_file_addition_test.cc +8 -4
  49. package/deps/rocksdb/rocksdb/db/blob/blob_file_builder.cc +99 -40
  50. package/deps/rocksdb/rocksdb/db/blob/blob_file_builder.h +20 -8
  51. package/deps/rocksdb/rocksdb/db/blob/blob_file_builder_test.cc +95 -83
  52. package/deps/rocksdb/rocksdb/db/blob/blob_file_cache.cc +13 -10
  53. package/deps/rocksdb/rocksdb/db/blob/blob_file_cache.h +7 -4
  54. package/deps/rocksdb/rocksdb/db/blob/blob_file_cache_test.cc +37 -37
  55. package/deps/rocksdb/rocksdb/db/blob/blob_file_completion_callback.h +101 -0
  56. package/deps/rocksdb/rocksdb/db/blob/blob_file_meta.cc +8 -1
  57. package/deps/rocksdb/rocksdb/db/blob/blob_file_meta.h +6 -0
  58. package/deps/rocksdb/rocksdb/db/blob/blob_file_reader.cc +209 -44
  59. package/deps/rocksdb/rocksdb/db/blob/blob_file_reader.h +37 -11
  60. package/deps/rocksdb/rocksdb/db/blob/blob_file_reader_test.cc +382 -179
  61. package/deps/rocksdb/rocksdb/db/blob/blob_garbage_meter.cc +100 -0
  62. package/deps/rocksdb/rocksdb/db/blob/blob_garbage_meter.h +102 -0
  63. package/deps/rocksdb/rocksdb/db/blob/blob_garbage_meter_test.cc +196 -0
  64. package/deps/rocksdb/rocksdb/db/blob/blob_index.h +3 -0
  65. package/deps/rocksdb/rocksdb/db/blob/blob_log_format.h +2 -1
  66. package/deps/rocksdb/rocksdb/db/blob/blob_log_sequential_reader.cc +7 -5
  67. package/deps/rocksdb/rocksdb/db/blob/blob_log_sequential_reader.h +10 -3
  68. package/deps/rocksdb/rocksdb/db/blob/blob_log_writer.cc +12 -8
  69. package/deps/rocksdb/rocksdb/db/blob/blob_log_writer.h +5 -5
  70. package/deps/rocksdb/rocksdb/db/blob/db_blob_basic_test.cc +772 -9
  71. package/deps/rocksdb/rocksdb/db/blob/db_blob_compaction_test.cc +730 -0
  72. package/deps/rocksdb/rocksdb/db/blob/db_blob_corruption_test.cc +82 -0
  73. package/deps/rocksdb/rocksdb/db/blob/db_blob_index_test.cc +155 -17
  74. package/deps/rocksdb/rocksdb/db/blob/prefetch_buffer_collection.cc +21 -0
  75. package/deps/rocksdb/rocksdb/db/blob/prefetch_buffer_collection.h +38 -0
  76. package/deps/rocksdb/rocksdb/db/builder.cc +137 -89
  77. package/deps/rocksdb/rocksdb/db/builder.h +16 -37
  78. package/deps/rocksdb/rocksdb/db/c.cc +413 -208
  79. package/deps/rocksdb/rocksdb/db/c_test.c +227 -138
  80. package/deps/rocksdb/rocksdb/db/column_family.cc +118 -103
  81. package/deps/rocksdb/rocksdb/db/column_family.h +86 -44
  82. package/deps/rocksdb/rocksdb/db/column_family_test.cc +38 -24
  83. package/deps/rocksdb/rocksdb/db/compact_files_test.cc +81 -0
  84. package/deps/rocksdb/rocksdb/db/compaction/clipping_iterator.h +275 -0
  85. package/deps/rocksdb/rocksdb/db/compaction/clipping_iterator_test.cc +258 -0
  86. package/deps/rocksdb/rocksdb/db/compaction/compaction.cc +81 -28
  87. package/deps/rocksdb/rocksdb/db/compaction/compaction.h +43 -12
  88. package/deps/rocksdb/rocksdb/db/compaction/compaction_iteration_stats.h +12 -0
  89. package/deps/rocksdb/rocksdb/db/compaction/compaction_iterator.cc +406 -215
  90. package/deps/rocksdb/rocksdb/db/compaction/compaction_iterator.h +147 -50
  91. package/deps/rocksdb/rocksdb/db/compaction/compaction_iterator_test.cc +167 -61
  92. package/deps/rocksdb/rocksdb/db/compaction/compaction_job.cc +1321 -156
  93. package/deps/rocksdb/rocksdb/db/compaction/compaction_job.h +197 -28
  94. package/deps/rocksdb/rocksdb/db/compaction/compaction_job_stats_test.cc +2 -3
  95. package/deps/rocksdb/rocksdb/db/compaction/compaction_job_test.cc +246 -43
  96. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker.cc +65 -26
  97. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker.h +7 -7
  98. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_fifo.cc +122 -9
  99. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_fifo.h +8 -2
  100. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_level.cc +18 -6
  101. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_level.h +1 -1
  102. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_test.cc +536 -44
  103. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_universal.cc +311 -30
  104. package/deps/rocksdb/rocksdb/db/compaction/compaction_picker_universal.h +1 -1
  105. package/deps/rocksdb/rocksdb/db/compaction/compaction_service_test.cc +849 -0
  106. package/deps/rocksdb/rocksdb/db/compaction/file_pri.h +92 -0
  107. package/deps/rocksdb/rocksdb/db/compaction/sst_partitioner.cc +46 -0
  108. package/deps/rocksdb/rocksdb/db/comparator_db_test.cc +1 -1
  109. package/deps/rocksdb/rocksdb/db/convenience.cc +6 -3
  110. package/deps/rocksdb/rocksdb/db/corruption_test.cc +383 -28
  111. package/deps/rocksdb/rocksdb/db/cuckoo_table_db_test.cc +7 -2
  112. package/deps/rocksdb/rocksdb/db/db_basic_test.cc +154 -45
  113. package/deps/rocksdb/rocksdb/db/db_block_cache_test.cc +1095 -33
  114. package/deps/rocksdb/rocksdb/db/db_bloom_filter_test.cc +1249 -203
  115. package/deps/rocksdb/rocksdb/db/db_compaction_filter_test.cc +135 -9
  116. package/deps/rocksdb/rocksdb/db/db_compaction_test.cc +1348 -166
  117. package/deps/rocksdb/rocksdb/db/db_dynamic_level_test.cc +3 -5
  118. package/deps/rocksdb/rocksdb/db/db_encryption_test.cc +1 -1
  119. package/deps/rocksdb/rocksdb/db/db_filesnapshot.cc +312 -45
  120. package/deps/rocksdb/rocksdb/db/db_flush_test.cc +1734 -48
  121. package/deps/rocksdb/rocksdb/db/{compacted_db_impl.cc → db_impl/compacted_db_impl.cc} +24 -7
  122. package/deps/rocksdb/rocksdb/db/{compacted_db_impl.h → db_impl/compacted_db_impl.h} +1 -1
  123. package/deps/rocksdb/rocksdb/db/db_impl/db_impl.cc +644 -333
  124. package/deps/rocksdb/rocksdb/db/db_impl/db_impl.h +365 -92
  125. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_compaction_flush.cc +578 -210
  126. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_debug.cc +38 -16
  127. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_experimental.cc +17 -10
  128. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_files.cc +75 -74
  129. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_open.cc +450 -183
  130. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_readonly.cc +42 -9
  131. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_secondary.cc +232 -15
  132. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_secondary.h +42 -4
  133. package/deps/rocksdb/rocksdb/db/db_impl/db_impl_write.cc +297 -100
  134. package/deps/rocksdb/rocksdb/db/db_info_dumper.cc +16 -15
  135. package/deps/rocksdb/rocksdb/db/db_inplace_update_test.cc +31 -1
  136. package/deps/rocksdb/rocksdb/db/db_io_failure_test.cc +6 -5
  137. package/deps/rocksdb/rocksdb/db/db_iter.cc +218 -153
  138. package/deps/rocksdb/rocksdb/db/db_iter.h +14 -12
  139. package/deps/rocksdb/rocksdb/db/db_iter_stress_test.cc +1 -1
  140. package/deps/rocksdb/rocksdb/db/db_iter_test.cc +84 -160
  141. package/deps/rocksdb/rocksdb/db/db_iterator_test.cc +47 -6
  142. package/deps/rocksdb/rocksdb/db/db_kv_checksum_test.cc +204 -0
  143. package/deps/rocksdb/rocksdb/db/db_log_iter_test.cc +21 -13
  144. package/deps/rocksdb/rocksdb/db/db_logical_block_size_cache_test.cc +17 -10
  145. package/deps/rocksdb/rocksdb/db/db_memtable_test.cc +38 -24
  146. package/deps/rocksdb/rocksdb/db/db_merge_operand_test.cc +184 -19
  147. package/deps/rocksdb/rocksdb/db/db_merge_operator_test.cc +1 -1
  148. package/deps/rocksdb/rocksdb/db/db_options_test.cc +183 -3
  149. package/deps/rocksdb/rocksdb/db/db_properties_test.cc +409 -9
  150. package/deps/rocksdb/rocksdb/db/db_range_del_test.cc +92 -23
  151. package/deps/rocksdb/rocksdb/db/db_rate_limiter_test.cc +446 -0
  152. package/deps/rocksdb/rocksdb/db/{db_impl/db_secondary_test.cc → db_secondary_test.cc} +363 -35
  153. package/deps/rocksdb/rocksdb/db/db_sst_test.cc +520 -15
  154. package/deps/rocksdb/rocksdb/db/db_statistics_test.cc +50 -1
  155. package/deps/rocksdb/rocksdb/db/db_table_properties_test.cc +139 -4
  156. package/deps/rocksdb/rocksdb/db/db_tailing_iter_test.cc +1 -1
  157. package/deps/rocksdb/rocksdb/db/db_test.cc +669 -359
  158. package/deps/rocksdb/rocksdb/db/db_test2.cc +2110 -304
  159. package/deps/rocksdb/rocksdb/db/db_test_util.cc +76 -43
  160. package/deps/rocksdb/rocksdb/db/db_test_util.h +231 -103
  161. package/deps/rocksdb/rocksdb/db/db_universal_compaction_test.cc +19 -11
  162. package/deps/rocksdb/rocksdb/db/db_wal_test.cc +490 -71
  163. package/deps/rocksdb/rocksdb/db/db_with_timestamp_basic_test.cc +980 -349
  164. package/deps/rocksdb/rocksdb/db/db_with_timestamp_compaction_test.cc +11 -12
  165. package/deps/rocksdb/rocksdb/db/db_write_buffer_manager_test.cc +793 -0
  166. package/deps/rocksdb/rocksdb/db/db_write_test.cc +2 -1
  167. package/deps/rocksdb/rocksdb/db/dbformat.cc +4 -12
  168. package/deps/rocksdb/rocksdb/db/dbformat.h +28 -18
  169. package/deps/rocksdb/rocksdb/db/dbformat_test.cc +3 -0
  170. package/deps/rocksdb/rocksdb/db/deletefile_test.cc +50 -15
  171. package/deps/rocksdb/rocksdb/db/error_handler.cc +127 -41
  172. package/deps/rocksdb/rocksdb/db/error_handler.h +12 -5
  173. package/deps/rocksdb/rocksdb/db/error_handler_fs_test.cc +524 -255
  174. package/deps/rocksdb/rocksdb/db/event_helpers.cc +136 -11
  175. package/deps/rocksdb/rocksdb/db/event_helpers.h +27 -2
  176. package/deps/rocksdb/rocksdb/db/experimental.cc +100 -0
  177. package/deps/rocksdb/rocksdb/db/external_sst_file_basic_test.cc +307 -4
  178. package/deps/rocksdb/rocksdb/db/external_sst_file_ingestion_job.cc +137 -60
  179. package/deps/rocksdb/rocksdb/db/external_sst_file_ingestion_job.h +12 -8
  180. package/deps/rocksdb/rocksdb/db/external_sst_file_test.cc +86 -55
  181. package/deps/rocksdb/rocksdb/db/fault_injection_test.cc +86 -5
  182. package/deps/rocksdb/rocksdb/db/filename_test.cc +63 -0
  183. package/deps/rocksdb/rocksdb/db/flush_job.cc +619 -64
  184. package/deps/rocksdb/rocksdb/db/flush_job.h +30 -7
  185. package/deps/rocksdb/rocksdb/db/flush_job_test.cc +33 -16
  186. package/deps/rocksdb/rocksdb/db/flush_scheduler.h +2 -1
  187. package/deps/rocksdb/rocksdb/db/forward_iterator.cc +18 -17
  188. package/deps/rocksdb/rocksdb/db/forward_iterator.h +5 -4
  189. package/deps/rocksdb/rocksdb/db/forward_iterator_bench.cc +0 -1
  190. package/deps/rocksdb/rocksdb/db/history_trimming_iterator.h +91 -0
  191. package/deps/rocksdb/rocksdb/db/import_column_family_job.cc +25 -14
  192. package/deps/rocksdb/rocksdb/db/import_column_family_job.h +6 -5
  193. package/deps/rocksdb/rocksdb/db/import_column_family_test.cc +1 -1
  194. package/deps/rocksdb/rocksdb/db/internal_stats.cc +471 -50
  195. package/deps/rocksdb/rocksdb/db/internal_stats.h +129 -25
  196. package/deps/rocksdb/rocksdb/db/job_context.h +22 -9
  197. package/deps/rocksdb/rocksdb/db/kv_checksum.h +394 -0
  198. package/deps/rocksdb/rocksdb/db/listener_test.cc +518 -41
  199. package/deps/rocksdb/rocksdb/db/log_format.h +4 -1
  200. package/deps/rocksdb/rocksdb/db/log_reader.cc +129 -6
  201. package/deps/rocksdb/rocksdb/db/log_reader.h +17 -1
  202. package/deps/rocksdb/rocksdb/db/log_test.cc +161 -11
  203. package/deps/rocksdb/rocksdb/db/log_writer.cc +92 -13
  204. package/deps/rocksdb/rocksdb/db/log_writer.h +18 -5
  205. package/deps/rocksdb/rocksdb/db/logs_with_prep_tracker.h +1 -1
  206. package/deps/rocksdb/rocksdb/db/lookup_key.h +0 -1
  207. package/deps/rocksdb/rocksdb/db/malloc_stats.cc +2 -2
  208. package/deps/rocksdb/rocksdb/db/manual_compaction_test.cc +21 -8
  209. package/deps/rocksdb/rocksdb/db/memtable.cc +144 -54
  210. package/deps/rocksdb/rocksdb/db/memtable.h +72 -15
  211. package/deps/rocksdb/rocksdb/db/memtable_list.cc +95 -47
  212. package/deps/rocksdb/rocksdb/db/memtable_list.h +33 -13
  213. package/deps/rocksdb/rocksdb/db/memtable_list_test.cc +61 -31
  214. package/deps/rocksdb/rocksdb/db/merge_context.h +20 -8
  215. package/deps/rocksdb/rocksdb/db/merge_helper.cc +54 -11
  216. package/deps/rocksdb/rocksdb/db/merge_helper.h +17 -6
  217. package/deps/rocksdb/rocksdb/db/merge_helper_test.cc +13 -7
  218. package/deps/rocksdb/rocksdb/db/merge_test.cc +40 -19
  219. package/deps/rocksdb/rocksdb/db/obsolete_files_test.cc +14 -25
  220. package/deps/rocksdb/rocksdb/db/output_validator.cc +3 -0
  221. package/deps/rocksdb/rocksdb/db/output_validator.h +5 -4
  222. package/deps/rocksdb/rocksdb/db/perf_context_test.cc +32 -28
  223. package/deps/rocksdb/rocksdb/db/periodic_work_scheduler.cc +43 -29
  224. package/deps/rocksdb/rocksdb/db/periodic_work_scheduler.h +9 -7
  225. package/deps/rocksdb/rocksdb/db/periodic_work_scheduler_test.cc +21 -16
  226. package/deps/rocksdb/rocksdb/db/pinned_iterators_manager.h +1 -1
  227. package/deps/rocksdb/rocksdb/db/plain_table_db_test.cc +29 -36
  228. package/deps/rocksdb/rocksdb/db/pre_release_callback.h +1 -2
  229. package/deps/rocksdb/rocksdb/db/prefix_test.cc +4 -4
  230. package/deps/rocksdb/rocksdb/db/range_del_aggregator.h +2 -2
  231. package/deps/rocksdb/rocksdb/db/range_del_aggregator_bench.cc +11 -11
  232. package/deps/rocksdb/rocksdb/db/range_del_aggregator_test.cc +3 -2
  233. package/deps/rocksdb/rocksdb/db/range_tombstone_fragmenter.cc +14 -8
  234. package/deps/rocksdb/rocksdb/db/range_tombstone_fragmenter.h +17 -0
  235. package/deps/rocksdb/rocksdb/db/range_tombstone_fragmenter_test.cc +4 -2
  236. package/deps/rocksdb/rocksdb/db/read_callback.h +1 -0
  237. package/deps/rocksdb/rocksdb/db/repair.cc +87 -58
  238. package/deps/rocksdb/rocksdb/db/repair_test.cc +35 -5
  239. package/deps/rocksdb/rocksdb/db/snapshot_impl.h +2 -1
  240. package/deps/rocksdb/rocksdb/db/table_cache.cc +95 -69
  241. package/deps/rocksdb/rocksdb/db/table_cache.h +63 -53
  242. package/deps/rocksdb/rocksdb/db/table_properties_collector.cc +4 -4
  243. package/deps/rocksdb/rocksdb/db/table_properties_collector.h +78 -10
  244. package/deps/rocksdb/rocksdb/db/table_properties_collector_test.cc +28 -33
  245. package/deps/rocksdb/rocksdb/db/transaction_log_impl.cc +30 -51
  246. package/deps/rocksdb/rocksdb/db/transaction_log_impl.h +12 -8
  247. package/deps/rocksdb/rocksdb/db/version_builder.cc +564 -341
  248. package/deps/rocksdb/rocksdb/db/version_builder.h +8 -8
  249. package/deps/rocksdb/rocksdb/db/version_builder_test.cc +327 -155
  250. package/deps/rocksdb/rocksdb/db/version_edit.cc +89 -27
  251. package/deps/rocksdb/rocksdb/db/version_edit.h +42 -17
  252. package/deps/rocksdb/rocksdb/db/version_edit_handler.cc +324 -43
  253. package/deps/rocksdb/rocksdb/db/version_edit_handler.h +79 -22
  254. package/deps/rocksdb/rocksdb/db/version_edit_test.cc +165 -20
  255. package/deps/rocksdb/rocksdb/db/version_set.cc +935 -1034
  256. package/deps/rocksdb/rocksdb/db/version_set.h +183 -122
  257. package/deps/rocksdb/rocksdb/db/version_set_test.cc +556 -138
  258. package/deps/rocksdb/rocksdb/db/version_util.h +68 -0
  259. package/deps/rocksdb/rocksdb/db/wal_manager.cc +23 -21
  260. package/deps/rocksdb/rocksdb/db/wal_manager.h +5 -2
  261. package/deps/rocksdb/rocksdb/db/wal_manager_test.cc +30 -27
  262. package/deps/rocksdb/rocksdb/db/write_batch.cc +704 -209
  263. package/deps/rocksdb/rocksdb/db/write_batch_internal.h +135 -2
  264. package/deps/rocksdb/rocksdb/db/write_batch_test.cc +209 -5
  265. package/deps/rocksdb/rocksdb/db/write_callback_test.cc +2 -0
  266. package/deps/rocksdb/rocksdb/db/write_controller.cc +47 -54
  267. package/deps/rocksdb/rocksdb/db/write_controller.h +12 -9
  268. package/deps/rocksdb/rocksdb/db/write_controller_test.cc +215 -103
  269. package/deps/rocksdb/rocksdb/db/write_thread.cc +11 -0
  270. package/deps/rocksdb/rocksdb/db/write_thread.h +14 -8
  271. package/deps/rocksdb/rocksdb/db_stress_tool/CMakeLists.txt +7 -4
  272. package/deps/rocksdb/rocksdb/db_stress_tool/batched_ops_stress.cc +10 -3
  273. package/deps/rocksdb/rocksdb/db_stress_tool/cf_consistency_stress.cc +6 -0
  274. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress.cc +1 -1
  275. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_common.cc +19 -2
  276. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_common.h +78 -25
  277. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_compaction_filter.h +13 -2
  278. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_driver.cc +29 -12
  279. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_env_wrapper.h +5 -1
  280. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_gflags.cc +199 -32
  281. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_listener.cc +188 -0
  282. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_listener.h +59 -10
  283. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_shared_state.h +77 -109
  284. package/deps/rocksdb/rocksdb/{third-party/folly/folly/synchronization/WaitOptions.cpp → db_stress_tool/db_stress_stat.cc} +9 -4
  285. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_stat.h +7 -6
  286. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_table_properties_collector.h +1 -0
  287. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_test_base.cc +699 -143
  288. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_test_base.h +20 -2
  289. package/deps/rocksdb/rocksdb/db_stress_tool/db_stress_tool.cc +49 -39
  290. package/deps/rocksdb/rocksdb/db_stress_tool/expected_state.cc +631 -0
  291. package/deps/rocksdb/rocksdb/db_stress_tool/expected_state.h +287 -0
  292. package/deps/rocksdb/rocksdb/db_stress_tool/multi_ops_txns_stress.cc +1565 -0
  293. package/deps/rocksdb/rocksdb/db_stress_tool/multi_ops_txns_stress.h +374 -0
  294. package/deps/rocksdb/rocksdb/db_stress_tool/no_batched_ops_stress.cc +149 -18
  295. package/deps/rocksdb/rocksdb/env/composite_env.cc +464 -0
  296. package/deps/rocksdb/rocksdb/env/composite_env_wrapper.h +98 -646
  297. package/deps/rocksdb/rocksdb/env/emulated_clock.h +114 -0
  298. package/deps/rocksdb/rocksdb/env/env.cc +632 -42
  299. package/deps/rocksdb/rocksdb/env/env_basic_test.cc +84 -36
  300. package/deps/rocksdb/rocksdb/env/env_chroot.cc +88 -286
  301. package/deps/rocksdb/rocksdb/env/env_chroot.h +34 -1
  302. package/deps/rocksdb/rocksdb/env/env_encryption.cc +469 -277
  303. package/deps/rocksdb/rocksdb/env/env_encryption_ctr.h +9 -30
  304. package/deps/rocksdb/rocksdb/env/env_posix.cc +110 -119
  305. package/deps/rocksdb/rocksdb/env/env_test.cc +1128 -39
  306. package/deps/rocksdb/rocksdb/env/file_system.cc +147 -8
  307. package/deps/rocksdb/rocksdb/env/file_system_tracer.cc +207 -136
  308. package/deps/rocksdb/rocksdb/env/file_system_tracer.h +86 -54
  309. package/deps/rocksdb/rocksdb/env/fs_posix.cc +192 -64
  310. package/deps/rocksdb/rocksdb/env/fs_readonly.h +107 -0
  311. package/deps/rocksdb/rocksdb/env/fs_remap.cc +339 -0
  312. package/deps/rocksdb/rocksdb/env/fs_remap.h +139 -0
  313. package/deps/rocksdb/rocksdb/env/io_posix.cc +245 -41
  314. package/deps/rocksdb/rocksdb/env/io_posix.h +66 -1
  315. package/deps/rocksdb/rocksdb/env/mock_env.cc +147 -149
  316. package/deps/rocksdb/rocksdb/env/mock_env.h +113 -11
  317. package/deps/rocksdb/rocksdb/env/mock_env_test.cc +2 -4
  318. package/deps/rocksdb/rocksdb/env/unique_id_gen.cc +164 -0
  319. package/deps/rocksdb/rocksdb/env/unique_id_gen.h +71 -0
  320. package/deps/rocksdb/rocksdb/file/delete_scheduler.cc +9 -5
  321. package/deps/rocksdb/rocksdb/file/delete_scheduler.h +6 -4
  322. package/deps/rocksdb/rocksdb/file/delete_scheduler_test.cc +19 -12
  323. package/deps/rocksdb/rocksdb/file/file_prefetch_buffer.cc +459 -70
  324. package/deps/rocksdb/rocksdb/file/file_prefetch_buffer.h +205 -28
  325. package/deps/rocksdb/rocksdb/file/file_util.cc +39 -28
  326. package/deps/rocksdb/rocksdb/file/file_util.h +18 -27
  327. package/deps/rocksdb/rocksdb/file/filename.cc +59 -22
  328. package/deps/rocksdb/rocksdb/file/filename.h +13 -8
  329. package/deps/rocksdb/rocksdb/file/line_file_reader.cc +68 -0
  330. package/deps/rocksdb/rocksdb/file/line_file_reader.h +59 -0
  331. package/deps/rocksdb/rocksdb/file/prefetch_test.cc +1130 -6
  332. package/deps/rocksdb/rocksdb/file/random_access_file_reader.cc +220 -36
  333. package/deps/rocksdb/rocksdb/file/random_access_file_reader.h +69 -17
  334. package/deps/rocksdb/rocksdb/file/random_access_file_reader_test.cc +13 -12
  335. package/deps/rocksdb/rocksdb/file/read_write_util.cc +3 -38
  336. package/deps/rocksdb/rocksdb/file/read_write_util.h +0 -4
  337. package/deps/rocksdb/rocksdb/file/readahead_file_info.h +33 -0
  338. package/deps/rocksdb/rocksdb/file/sequence_file_reader.cc +57 -9
  339. package/deps/rocksdb/rocksdb/file/sequence_file_reader.h +58 -6
  340. package/deps/rocksdb/rocksdb/file/sst_file_manager_impl.cc +29 -54
  341. package/deps/rocksdb/rocksdb/file/sst_file_manager_impl.h +22 -29
  342. package/deps/rocksdb/rocksdb/file/writable_file_writer.cc +424 -50
  343. package/deps/rocksdb/rocksdb/file/writable_file_writer.h +66 -19
  344. package/deps/rocksdb/rocksdb/include/rocksdb/advanced_options.h +157 -66
  345. package/deps/rocksdb/rocksdb/include/rocksdb/c.h +224 -121
  346. package/deps/rocksdb/rocksdb/include/rocksdb/cache.h +333 -30
  347. package/deps/rocksdb/rocksdb/include/rocksdb/cache_bench_tool.h +14 -0
  348. package/deps/rocksdb/rocksdb/include/rocksdb/cleanable.h +1 -1
  349. package/deps/rocksdb/rocksdb/include/rocksdb/compaction_filter.h +90 -50
  350. package/deps/rocksdb/rocksdb/include/rocksdb/compaction_job_stats.h +13 -5
  351. package/deps/rocksdb/rocksdb/include/rocksdb/comparator.h +20 -4
  352. package/deps/rocksdb/rocksdb/include/rocksdb/concurrent_task_limiter.h +8 -3
  353. package/deps/rocksdb/rocksdb/include/rocksdb/configurable.h +53 -12
  354. package/deps/rocksdb/rocksdb/include/rocksdb/convenience.h +31 -6
  355. package/deps/rocksdb/rocksdb/include/rocksdb/customizable.h +102 -7
  356. package/deps/rocksdb/rocksdb/include/rocksdb/data_structure.h +51 -0
  357. package/deps/rocksdb/rocksdb/include/rocksdb/db.h +370 -262
  358. package/deps/rocksdb/rocksdb/include/rocksdb/env.h +286 -87
  359. package/deps/rocksdb/rocksdb/include/rocksdb/env_encryption.h +124 -64
  360. package/deps/rocksdb/rocksdb/include/rocksdb/experimental.h +27 -0
  361. package/deps/rocksdb/rocksdb/include/rocksdb/file_checksum.h +21 -4
  362. package/deps/rocksdb/rocksdb/include/rocksdb/file_system.h +384 -41
  363. package/deps/rocksdb/rocksdb/include/rocksdb/filter_policy.h +111 -143
  364. package/deps/rocksdb/rocksdb/include/rocksdb/flush_block_policy.h +20 -6
  365. package/deps/rocksdb/rocksdb/include/rocksdb/functor_wrapper.h +56 -0
  366. package/deps/rocksdb/rocksdb/include/rocksdb/io_status.h +15 -33
  367. package/deps/rocksdb/rocksdb/include/rocksdb/iostats_context.h +37 -1
  368. package/deps/rocksdb/rocksdb/include/rocksdb/iterator.h +1 -3
  369. package/deps/rocksdb/rocksdb/include/rocksdb/listener.h +314 -26
  370. package/deps/rocksdb/rocksdb/include/rocksdb/memory_allocator.h +11 -7
  371. package/deps/rocksdb/rocksdb/include/rocksdb/memtablerep.h +50 -15
  372. package/deps/rocksdb/rocksdb/include/rocksdb/merge_operator.h +10 -3
  373. package/deps/rocksdb/rocksdb/include/rocksdb/metadata.h +186 -96
  374. package/deps/rocksdb/rocksdb/include/rocksdb/options.h +373 -103
  375. package/deps/rocksdb/rocksdb/include/rocksdb/perf_context.h +13 -3
  376. package/deps/rocksdb/rocksdb/include/rocksdb/persistent_cache.h +2 -2
  377. package/deps/rocksdb/rocksdb/include/rocksdb/rate_limiter.h +37 -7
  378. package/deps/rocksdb/rocksdb/include/rocksdb/rocksdb_namespace.h +6 -0
  379. package/deps/rocksdb/rocksdb/include/rocksdb/secondary_cache.h +87 -0
  380. package/deps/rocksdb/rocksdb/include/rocksdb/slice.h +5 -12
  381. package/deps/rocksdb/rocksdb/include/rocksdb/slice_transform.h +59 -30
  382. package/deps/rocksdb/rocksdb/include/rocksdb/sst_file_manager.h +11 -11
  383. package/deps/rocksdb/rocksdb/include/rocksdb/sst_file_writer.h +22 -0
  384. package/deps/rocksdb/rocksdb/include/rocksdb/sst_partitioner.h +17 -10
  385. package/deps/rocksdb/rocksdb/include/rocksdb/statistics.h +121 -41
  386. package/deps/rocksdb/rocksdb/include/rocksdb/stats_history.h +1 -0
  387. package/deps/rocksdb/rocksdb/include/rocksdb/status.h +114 -136
  388. package/deps/rocksdb/rocksdb/include/rocksdb/system_clock.h +116 -0
  389. package/deps/rocksdb/rocksdb/include/rocksdb/table.h +160 -18
  390. package/deps/rocksdb/rocksdb/include/rocksdb/table_properties.h +57 -15
  391. package/deps/rocksdb/rocksdb/include/rocksdb/thread_status.h +3 -1
  392. package/deps/rocksdb/rocksdb/include/rocksdb/trace_reader_writer.h +10 -6
  393. package/deps/rocksdb/rocksdb/include/rocksdb/trace_record.h +247 -0
  394. package/deps/rocksdb/rocksdb/include/rocksdb/trace_record_result.h +187 -0
  395. package/deps/rocksdb/rocksdb/include/rocksdb/transaction_log.h +1 -1
  396. package/deps/rocksdb/rocksdb/include/rocksdb/types.h +14 -24
  397. package/deps/rocksdb/rocksdb/include/rocksdb/unique_id.h +46 -0
  398. package/deps/rocksdb/rocksdb/include/rocksdb/universal_compaction.h +14 -4
  399. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/agg_merge.h +138 -0
  400. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/backup_engine.h +631 -0
  401. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/cache_dump_load.h +142 -0
  402. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/checkpoint.h +12 -9
  403. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/customizable_util.h +368 -0
  404. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/ldb_cmd.h +24 -0
  405. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/ldb_cmd_execute_result.h +4 -0
  406. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/object_registry.h +418 -63
  407. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/options_type.h +143 -73
  408. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/options_util.h +2 -2
  409. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/replayer.h +87 -0
  410. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/sim_cache.h +2 -2
  411. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/stackable_db.h +43 -5
  412. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/table_properties_collectors.h +18 -23
  413. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/transaction.h +26 -0
  414. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/transaction_db.h +32 -6
  415. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/transaction_db_mutex.h +1 -2
  416. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/write_batch_with_index.h +20 -1
  417. package/deps/rocksdb/rocksdb/include/rocksdb/version.h +30 -3
  418. package/deps/rocksdb/rocksdb/include/rocksdb/wal_filter.h +11 -2
  419. package/deps/rocksdb/rocksdb/include/rocksdb/write_batch.h +89 -11
  420. package/deps/rocksdb/rocksdb/include/rocksdb/write_batch_base.h +11 -0
  421. package/deps/rocksdb/rocksdb/include/rocksdb/write_buffer_manager.h +108 -38
  422. package/deps/rocksdb/rocksdb/logging/auto_roll_logger.cc +40 -23
  423. package/deps/rocksdb/rocksdb/logging/auto_roll_logger.h +12 -5
  424. package/deps/rocksdb/rocksdb/logging/auto_roll_logger_test.cc +100 -49
  425. package/deps/rocksdb/rocksdb/logging/env_logger.h +7 -5
  426. package/deps/rocksdb/rocksdb/logging/env_logger_test.cc +0 -1
  427. package/deps/rocksdb/rocksdb/logging/posix_logger.h +3 -9
  428. package/deps/rocksdb/rocksdb/memory/arena.cc +3 -1
  429. package/deps/rocksdb/rocksdb/memory/arena.h +1 -1
  430. package/deps/rocksdb/rocksdb/memory/jemalloc_nodump_allocator.cc +171 -106
  431. package/deps/rocksdb/rocksdb/memory/jemalloc_nodump_allocator.h +31 -15
  432. package/deps/rocksdb/rocksdb/memory/memkind_kmem_allocator.cc +15 -4
  433. package/deps/rocksdb/rocksdb/memory/memkind_kmem_allocator.h +24 -8
  434. package/deps/rocksdb/rocksdb/memory/memory_allocator.cc +91 -0
  435. package/deps/rocksdb/rocksdb/memory/memory_allocator_test.cc +239 -0
  436. package/deps/rocksdb/rocksdb/memory/memory_usage.h +14 -1
  437. package/deps/rocksdb/rocksdb/memtable/hash_linklist_rep.cc +72 -9
  438. package/deps/rocksdb/rocksdb/memtable/hash_skiplist_rep.cc +52 -6
  439. package/deps/rocksdb/rocksdb/memtable/inlineskiplist.h +53 -0
  440. package/deps/rocksdb/rocksdb/memtable/inlineskiplist_test.cc +5 -5
  441. package/deps/rocksdb/rocksdb/memtable/memtablerep_bench.cc +17 -5
  442. package/deps/rocksdb/rocksdb/memtable/skiplist_test.cc +1 -1
  443. package/deps/rocksdb/rocksdb/memtable/skiplistrep.cc +87 -0
  444. package/deps/rocksdb/rocksdb/memtable/vectorrep.cc +20 -10
  445. package/deps/rocksdb/rocksdb/memtable/write_buffer_manager.cc +148 -94
  446. package/deps/rocksdb/rocksdb/memtable/write_buffer_manager_test.cc +160 -62
  447. package/deps/rocksdb/rocksdb/microbench/CMakeLists.txt +17 -0
  448. package/deps/rocksdb/rocksdb/microbench/db_basic_bench.cc +1360 -0
  449. package/deps/rocksdb/rocksdb/microbench/ribbon_bench.cc +153 -0
  450. package/deps/rocksdb/rocksdb/monitoring/histogram.cc +8 -15
  451. package/deps/rocksdb/rocksdb/monitoring/histogram.h +0 -1
  452. package/deps/rocksdb/rocksdb/monitoring/histogram_test.cc +18 -16
  453. package/deps/rocksdb/rocksdb/monitoring/histogram_windowing.cc +9 -7
  454. package/deps/rocksdb/rocksdb/monitoring/histogram_windowing.h +5 -3
  455. package/deps/rocksdb/rocksdb/monitoring/instrumented_mutex.cc +7 -5
  456. package/deps/rocksdb/rocksdb/monitoring/instrumented_mutex.h +37 -12
  457. package/deps/rocksdb/rocksdb/monitoring/iostats_context.cc +26 -6
  458. package/deps/rocksdb/rocksdb/monitoring/iostats_context_imp.h +6 -10
  459. package/deps/rocksdb/rocksdb/monitoring/perf_context.cc +14 -13
  460. package/deps/rocksdb/rocksdb/monitoring/perf_context_imp.h +19 -20
  461. package/deps/rocksdb/rocksdb/monitoring/perf_step_timer.h +18 -18
  462. package/deps/rocksdb/rocksdb/monitoring/statistics.cc +84 -2
  463. package/deps/rocksdb/rocksdb/monitoring/statistics.h +6 -0
  464. package/deps/rocksdb/rocksdb/monitoring/statistics_test.cc +47 -2
  465. package/deps/rocksdb/rocksdb/monitoring/stats_history_test.cc +67 -54
  466. package/deps/rocksdb/rocksdb/monitoring/thread_status_updater.cc +4 -1
  467. package/deps/rocksdb/rocksdb/monitoring/thread_status_util.cc +2 -1
  468. package/deps/rocksdb/rocksdb/monitoring/thread_status_util_debug.cc +2 -2
  469. package/deps/rocksdb/rocksdb/options/cf_options.cc +280 -212
  470. package/deps/rocksdb/rocksdb/options/cf_options.h +51 -57
  471. package/deps/rocksdb/rocksdb/options/configurable.cc +242 -138
  472. package/deps/rocksdb/rocksdb/options/configurable_helper.h +4 -68
  473. package/deps/rocksdb/rocksdb/options/configurable_test.cc +144 -21
  474. package/deps/rocksdb/rocksdb/options/configurable_test.h +2 -3
  475. package/deps/rocksdb/rocksdb/options/customizable.cc +67 -7
  476. package/deps/rocksdb/rocksdb/options/customizable_test.cc +1773 -151
  477. package/deps/rocksdb/rocksdb/options/db_options.cc +275 -47
  478. package/deps/rocksdb/rocksdb/options/db_options.h +36 -7
  479. package/deps/rocksdb/rocksdb/options/options.cc +49 -17
  480. package/deps/rocksdb/rocksdb/options/options_helper.cc +369 -352
  481. package/deps/rocksdb/rocksdb/options/options_helper.h +23 -23
  482. package/deps/rocksdb/rocksdb/options/options_parser.cc +18 -13
  483. package/deps/rocksdb/rocksdb/options/options_settable_test.cc +67 -54
  484. package/deps/rocksdb/rocksdb/options/options_test.cc +1162 -187
  485. package/deps/rocksdb/rocksdb/port/jemalloc_helper.h +1 -1
  486. package/deps/rocksdb/rocksdb/port/lang.h +52 -0
  487. package/deps/rocksdb/rocksdb/port/port_example.h +1 -1
  488. package/deps/rocksdb/rocksdb/port/port_posix.cc +31 -2
  489. package/deps/rocksdb/rocksdb/port/port_posix.h +20 -2
  490. package/deps/rocksdb/rocksdb/port/stack_trace.cc +20 -4
  491. package/deps/rocksdb/rocksdb/port/sys_time.h +2 -2
  492. package/deps/rocksdb/rocksdb/port/win/env_default.cc +7 -7
  493. package/deps/rocksdb/rocksdb/port/win/env_win.cc +44 -74
  494. package/deps/rocksdb/rocksdb/port/win/env_win.h +25 -23
  495. package/deps/rocksdb/rocksdb/port/win/io_win.cc +32 -34
  496. package/deps/rocksdb/rocksdb/port/win/io_win.h +12 -6
  497. package/deps/rocksdb/rocksdb/port/win/port_win.cc +55 -35
  498. package/deps/rocksdb/rocksdb/port/win/port_win.h +22 -5
  499. package/deps/rocksdb/rocksdb/port/win/win_logger.cc +3 -3
  500. package/deps/rocksdb/rocksdb/port/win/win_logger.h +3 -5
  501. package/deps/rocksdb/rocksdb/port/win/win_thread.cc +7 -1
  502. package/deps/rocksdb/rocksdb/port/win/win_thread.h +12 -17
  503. package/deps/rocksdb/rocksdb/python.mk +9 -0
  504. package/deps/rocksdb/rocksdb/src.mk +82 -34
  505. package/deps/rocksdb/rocksdb/table/adaptive/adaptive_table_factory.cc +3 -4
  506. package/deps/rocksdb/rocksdb/table/adaptive/adaptive_table_factory.h +1 -1
  507. package/deps/rocksdb/rocksdb/table/block_based/block.cc +158 -80
  508. package/deps/rocksdb/rocksdb/table/block_based/block.h +64 -36
  509. package/deps/rocksdb/rocksdb/table/block_based/block_based_filter_block.cc +23 -14
  510. package/deps/rocksdb/rocksdb/table/block_based/block_based_filter_block.h +13 -5
  511. package/deps/rocksdb/rocksdb/table/block_based/block_based_filter_block_test.cc +3 -218
  512. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_builder.cc +603 -328
  513. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_builder.h +28 -22
  514. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_factory.cc +220 -82
  515. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_factory.h +8 -2
  516. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_iterator.cc +3 -4
  517. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_iterator.h +28 -4
  518. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_reader.cc +598 -492
  519. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_reader.h +151 -96
  520. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_reader_impl.h +31 -58
  521. package/deps/rocksdb/rocksdb/table/block_based/block_based_table_reader_test.cc +330 -92
  522. package/deps/rocksdb/rocksdb/table/block_based/block_builder.cc +50 -19
  523. package/deps/rocksdb/rocksdb/table/block_based/block_builder.h +23 -0
  524. package/deps/rocksdb/rocksdb/table/block_based/block_like_traits.h +226 -0
  525. package/deps/rocksdb/rocksdb/table/block_based/block_prefetcher.cc +56 -22
  526. package/deps/rocksdb/rocksdb/table/block_based/block_prefetcher.h +42 -4
  527. package/deps/rocksdb/rocksdb/table/block_based/block_test.cc +5 -2
  528. package/deps/rocksdb/rocksdb/table/block_based/block_type.h +2 -0
  529. package/deps/rocksdb/rocksdb/table/block_based/cachable_entry.h +34 -20
  530. package/deps/rocksdb/rocksdb/table/block_based/data_block_hash_index_test.cc +9 -10
  531. package/deps/rocksdb/rocksdb/table/block_based/filter_block.h +26 -3
  532. package/deps/rocksdb/rocksdb/table/block_based/filter_block_reader_common.cc +2 -1
  533. package/deps/rocksdb/rocksdb/table/block_based/filter_policy.cc +844 -202
  534. package/deps/rocksdb/rocksdb/table/block_based/filter_policy_internal.h +281 -81
  535. package/deps/rocksdb/rocksdb/table/block_based/flush_block_policy.cc +62 -2
  536. package/deps/rocksdb/rocksdb/table/block_based/flush_block_policy.h +2 -3
  537. package/deps/rocksdb/rocksdb/table/block_based/full_filter_block.cc +28 -7
  538. package/deps/rocksdb/rocksdb/table/block_based/full_filter_block.h +22 -6
  539. package/deps/rocksdb/rocksdb/table/block_based/full_filter_block_test.cc +28 -26
  540. package/deps/rocksdb/rocksdb/table/block_based/hash_index_reader.cc +1 -1
  541. package/deps/rocksdb/rocksdb/table/block_based/index_builder.cc +1 -2
  542. package/deps/rocksdb/rocksdb/table/block_based/index_reader_common.cc +2 -1
  543. package/deps/rocksdb/rocksdb/table/block_based/mock_block_based_table.h +11 -4
  544. package/deps/rocksdb/rocksdb/table/block_based/parsed_full_filter_block.cc +2 -1
  545. package/deps/rocksdb/rocksdb/table/block_based/parsed_full_filter_block.h +2 -0
  546. package/deps/rocksdb/rocksdb/table/block_based/partitioned_filter_block.cc +68 -26
  547. package/deps/rocksdb/rocksdb/table/block_based/partitioned_filter_block.h +44 -9
  548. package/deps/rocksdb/rocksdb/table/block_based/partitioned_filter_block_test.cc +12 -10
  549. package/deps/rocksdb/rocksdb/table/block_based/partitioned_index_iterator.cc +3 -4
  550. package/deps/rocksdb/rocksdb/table/block_based/partitioned_index_iterator.h +23 -4
  551. package/deps/rocksdb/rocksdb/table/block_based/partitioned_index_reader.cc +44 -19
  552. package/deps/rocksdb/rocksdb/table/block_based/partitioned_index_reader.h +5 -1
  553. package/deps/rocksdb/rocksdb/table/block_based/reader_common.cc +16 -28
  554. package/deps/rocksdb/rocksdb/table/block_based/uncompression_dict_reader.cc +7 -4
  555. package/deps/rocksdb/rocksdb/table/block_based/uncompression_dict_reader.h +2 -2
  556. package/deps/rocksdb/rocksdb/table/block_fetcher.cc +77 -57
  557. package/deps/rocksdb/rocksdb/table/block_fetcher.h +23 -12
  558. package/deps/rocksdb/rocksdb/table/block_fetcher_test.cc +43 -56
  559. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_builder.cc +8 -8
  560. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_builder.h +2 -1
  561. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_builder_test.cc +52 -70
  562. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_factory.cc +5 -8
  563. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_factory.h +1 -1
  564. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_reader.cc +17 -11
  565. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_reader.h +2 -3
  566. package/deps/rocksdb/rocksdb/table/cuckoo/cuckoo_table_reader_test.cc +42 -51
  567. package/deps/rocksdb/rocksdb/table/format.cc +258 -104
  568. package/deps/rocksdb/rocksdb/table/format.h +120 -109
  569. package/deps/rocksdb/rocksdb/table/get_context.cc +97 -65
  570. package/deps/rocksdb/rocksdb/table/get_context.h +19 -12
  571. package/deps/rocksdb/rocksdb/table/internal_iterator.h +14 -0
  572. package/deps/rocksdb/rocksdb/table/iterator_wrapper.h +8 -0
  573. package/deps/rocksdb/rocksdb/table/merger_test.cc +3 -2
  574. package/deps/rocksdb/rocksdb/table/merging_iterator.cc +11 -21
  575. package/deps/rocksdb/rocksdb/table/merging_iterator.h +3 -3
  576. package/deps/rocksdb/rocksdb/table/meta_blocks.cc +176 -171
  577. package/deps/rocksdb/rocksdb/table/meta_blocks.h +47 -33
  578. package/deps/rocksdb/rocksdb/table/mock_table.cc +7 -9
  579. package/deps/rocksdb/rocksdb/table/mock_table.h +3 -2
  580. package/deps/rocksdb/rocksdb/table/multiget_context.h +15 -8
  581. package/deps/rocksdb/rocksdb/table/persistent_cache_helper.cc +22 -29
  582. package/deps/rocksdb/rocksdb/table/persistent_cache_options.h +6 -3
  583. package/deps/rocksdb/rocksdb/table/plain/plain_table_bloom.h +5 -8
  584. package/deps/rocksdb/rocksdb/table/plain/plain_table_builder.cc +29 -26
  585. package/deps/rocksdb/rocksdb/table/plain/plain_table_builder.h +12 -16
  586. package/deps/rocksdb/rocksdb/table/plain/plain_table_factory.cc +145 -69
  587. package/deps/rocksdb/rocksdb/table/plain/plain_table_factory.h +1 -1
  588. package/deps/rocksdb/rocksdb/table/plain/plain_table_index.cc +7 -6
  589. package/deps/rocksdb/rocksdb/table/plain/plain_table_index.h +3 -4
  590. package/deps/rocksdb/rocksdb/table/plain/plain_table_key_coding.cc +3 -1
  591. package/deps/rocksdb/rocksdb/table/plain/plain_table_key_coding.h +1 -1
  592. package/deps/rocksdb/rocksdb/table/plain/plain_table_reader.cc +13 -18
  593. package/deps/rocksdb/rocksdb/table/plain/plain_table_reader.h +4 -9
  594. package/deps/rocksdb/rocksdb/table/sst_file_dumper.cc +55 -37
  595. package/deps/rocksdb/rocksdb/table/sst_file_dumper.h +10 -5
  596. package/deps/rocksdb/rocksdb/table/sst_file_reader.cc +11 -8
  597. package/deps/rocksdb/rocksdb/table/sst_file_reader_test.cc +222 -16
  598. package/deps/rocksdb/rocksdb/table/sst_file_writer.cc +106 -58
  599. package/deps/rocksdb/rocksdb/table/sst_file_writer_collectors.h +6 -5
  600. package/deps/rocksdb/rocksdb/table/table_builder.h +68 -44
  601. package/deps/rocksdb/rocksdb/table/table_factory.cc +37 -10
  602. package/deps/rocksdb/rocksdb/table/table_properties.cc +109 -54
  603. package/deps/rocksdb/rocksdb/table/table_properties_internal.h +4 -20
  604. package/deps/rocksdb/rocksdb/table/table_reader_bench.cc +33 -32
  605. package/deps/rocksdb/rocksdb/table/table_reader_caller.h +2 -0
  606. package/deps/rocksdb/rocksdb/table/table_test.cc +989 -326
  607. package/deps/rocksdb/rocksdb/table/two_level_iterator.cc +4 -0
  608. package/deps/rocksdb/rocksdb/table/unique_id.cc +166 -0
  609. package/deps/rocksdb/rocksdb/table/unique_id_impl.h +59 -0
  610. package/deps/rocksdb/rocksdb/test_util/mock_time_env.cc +1 -1
  611. package/deps/rocksdb/rocksdb/test_util/mock_time_env.h +13 -10
  612. package/deps/rocksdb/rocksdb/test_util/sync_point.cc +1 -2
  613. package/deps/rocksdb/rocksdb/test_util/sync_point.h +35 -16
  614. package/deps/rocksdb/rocksdb/test_util/sync_point_impl.cc +32 -10
  615. package/deps/rocksdb/rocksdb/test_util/sync_point_impl.h +31 -4
  616. package/deps/rocksdb/rocksdb/test_util/testharness.cc +53 -1
  617. package/deps/rocksdb/rocksdb/test_util/testharness.h +67 -3
  618. package/deps/rocksdb/rocksdb/test_util/testutil.cc +236 -66
  619. package/deps/rocksdb/rocksdb/test_util/testutil.h +63 -100
  620. package/deps/rocksdb/rocksdb/test_util/transaction_test_util.cc +12 -1
  621. package/deps/rocksdb/rocksdb/tools/blob_dump.cc +2 -2
  622. package/deps/rocksdb/rocksdb/tools/block_cache_analyzer/block_cache_trace_analyzer.cc +6 -3
  623. package/deps/rocksdb/rocksdb/tools/block_cache_analyzer/block_cache_trace_analyzer.h +1 -0
  624. package/deps/rocksdb/rocksdb/tools/block_cache_analyzer/block_cache_trace_analyzer_test.cc +9 -3
  625. package/deps/rocksdb/rocksdb/tools/db_bench.cc +1 -1
  626. package/deps/rocksdb/rocksdb/tools/db_bench_tool.cc +1420 -611
  627. package/deps/rocksdb/rocksdb/tools/db_bench_tool_test.cc +11 -8
  628. package/deps/rocksdb/rocksdb/tools/db_repl_stress.cc +11 -1
  629. package/deps/rocksdb/rocksdb/tools/io_tracer_parser_test.cc +4 -2
  630. package/deps/rocksdb/rocksdb/tools/io_tracer_parser_tool.cc +46 -22
  631. package/deps/rocksdb/rocksdb/tools/ldb_cmd.cc +655 -179
  632. package/deps/rocksdb/rocksdb/tools/ldb_cmd_impl.h +58 -6
  633. package/deps/rocksdb/rocksdb/tools/ldb_cmd_test.cc +472 -29
  634. package/deps/rocksdb/rocksdb/tools/ldb_tool.cc +23 -2
  635. package/deps/rocksdb/rocksdb/tools/reduce_levels_test.cc +2 -2
  636. package/deps/rocksdb/rocksdb/tools/simulated_hybrid_file_system.cc +246 -0
  637. package/deps/rocksdb/rocksdb/tools/simulated_hybrid_file_system.h +126 -0
  638. package/deps/rocksdb/rocksdb/tools/sst_dump_test.cc +83 -29
  639. package/deps/rocksdb/rocksdb/tools/sst_dump_tool.cc +38 -17
  640. package/deps/rocksdb/rocksdb/tools/trace_analyzer_test.cc +191 -55
  641. package/deps/rocksdb/rocksdb/tools/trace_analyzer_tool.cc +219 -296
  642. package/deps/rocksdb/rocksdb/tools/trace_analyzer_tool.h +87 -53
  643. package/deps/rocksdb/rocksdb/tools/write_stress.cc +8 -7
  644. package/deps/rocksdb/rocksdb/trace_replay/block_cache_tracer.cc +6 -5
  645. package/deps/rocksdb/rocksdb/trace_replay/block_cache_tracer.h +5 -4
  646. package/deps/rocksdb/rocksdb/trace_replay/block_cache_tracer_test.cc +14 -9
  647. package/deps/rocksdb/rocksdb/trace_replay/io_tracer.cc +134 -60
  648. package/deps/rocksdb/rocksdb/trace_replay/io_tracer.h +49 -38
  649. package/deps/rocksdb/rocksdb/trace_replay/io_tracer_test.cc +152 -15
  650. package/deps/rocksdb/rocksdb/trace_replay/trace_record.cc +206 -0
  651. package/deps/rocksdb/rocksdb/trace_replay/trace_record_handler.cc +190 -0
  652. package/deps/rocksdb/rocksdb/trace_replay/trace_record_handler.h +46 -0
  653. package/deps/rocksdb/rocksdb/trace_replay/trace_record_result.cc +146 -0
  654. package/deps/rocksdb/rocksdb/trace_replay/trace_replay.cc +475 -344
  655. package/deps/rocksdb/rocksdb/trace_replay/trace_replay.h +83 -95
  656. package/deps/rocksdb/rocksdb/util/autovector.h +38 -18
  657. package/deps/rocksdb/rocksdb/util/autovector_test.cc +1 -1
  658. package/deps/rocksdb/rocksdb/util/bloom_impl.h +4 -0
  659. package/deps/rocksdb/rocksdb/util/bloom_test.cc +276 -94
  660. package/deps/rocksdb/rocksdb/util/build_version.cc.in +81 -4
  661. package/deps/rocksdb/rocksdb/util/cast_util.h +22 -0
  662. package/deps/rocksdb/rocksdb/util/channel.h +2 -0
  663. package/deps/rocksdb/rocksdb/util/coding.h +1 -33
  664. package/deps/rocksdb/rocksdb/util/compaction_job_stats_impl.cc +8 -0
  665. package/deps/rocksdb/rocksdb/util/comparator.cc +163 -3
  666. package/deps/rocksdb/rocksdb/util/compression.cc +122 -0
  667. package/deps/rocksdb/rocksdb/util/compression.h +212 -7
  668. package/deps/rocksdb/rocksdb/util/compression_context_cache.cc +1 -3
  669. package/deps/rocksdb/rocksdb/util/crc32c.cc +165 -2
  670. package/deps/rocksdb/rocksdb/util/crc32c.h +6 -0
  671. package/deps/rocksdb/rocksdb/util/crc32c_arm64.cc +14 -0
  672. package/deps/rocksdb/rocksdb/util/crc32c_ppc.h +3 -0
  673. package/deps/rocksdb/rocksdb/util/crc32c_test.cc +47 -0
  674. package/deps/rocksdb/rocksdb/util/defer.h +30 -1
  675. package/deps/rocksdb/rocksdb/util/defer_test.cc +11 -0
  676. package/deps/rocksdb/rocksdb/util/duplicate_detector.h +3 -1
  677. package/deps/rocksdb/rocksdb/util/dynamic_bloom.h +3 -3
  678. package/deps/rocksdb/rocksdb/util/dynamic_bloom_test.cc +5 -4
  679. package/deps/rocksdb/rocksdb/util/fastrange.h +2 -0
  680. package/deps/rocksdb/rocksdb/util/file_checksum_helper.cc +36 -0
  681. package/deps/rocksdb/rocksdb/util/file_checksum_helper.h +3 -1
  682. package/deps/rocksdb/rocksdb/util/file_reader_writer_test.cc +512 -52
  683. package/deps/rocksdb/rocksdb/util/filter_bench.cc +65 -10
  684. package/deps/rocksdb/rocksdb/util/gflags_compat.h +6 -1
  685. package/deps/rocksdb/rocksdb/util/hash.cc +121 -3
  686. package/deps/rocksdb/rocksdb/util/hash.h +31 -1
  687. package/deps/rocksdb/rocksdb/util/hash128.h +26 -0
  688. package/deps/rocksdb/rocksdb/util/hash_containers.h +51 -0
  689. package/deps/rocksdb/rocksdb/util/hash_test.cc +194 -2
  690. package/deps/rocksdb/rocksdb/util/heap.h +6 -1
  691. package/deps/rocksdb/rocksdb/util/kv_map.h +1 -1
  692. package/deps/rocksdb/rocksdb/util/log_write_bench.cc +8 -6
  693. package/deps/rocksdb/rocksdb/util/math.h +74 -7
  694. package/deps/rocksdb/rocksdb/util/math128.h +13 -1
  695. package/deps/rocksdb/rocksdb/util/murmurhash.h +3 -3
  696. package/deps/rocksdb/rocksdb/util/random.cc +9 -0
  697. package/deps/rocksdb/rocksdb/util/random.h +6 -0
  698. package/deps/rocksdb/rocksdb/util/rate_limiter.cc +298 -144
  699. package/deps/rocksdb/rocksdb/util/rate_limiter.h +68 -19
  700. package/deps/rocksdb/rocksdb/util/rate_limiter_test.cc +335 -23
  701. package/deps/rocksdb/rocksdb/util/repeatable_thread.h +10 -12
  702. package/deps/rocksdb/rocksdb/util/repeatable_thread_test.cc +18 -15
  703. package/deps/rocksdb/rocksdb/util/ribbon_alg.h +98 -74
  704. package/deps/rocksdb/rocksdb/util/ribbon_config.cc +506 -0
  705. package/deps/rocksdb/rocksdb/util/ribbon_config.h +182 -0
  706. package/deps/rocksdb/rocksdb/util/ribbon_impl.h +154 -79
  707. package/deps/rocksdb/rocksdb/util/ribbon_test.cc +742 -365
  708. package/deps/rocksdb/rocksdb/util/set_comparator.h +2 -0
  709. package/deps/rocksdb/rocksdb/util/slice.cc +198 -35
  710. package/deps/rocksdb/rocksdb/util/slice_test.cc +30 -1
  711. package/deps/rocksdb/rocksdb/util/status.cc +32 -29
  712. package/deps/rocksdb/rocksdb/util/stop_watch.h +18 -18
  713. package/deps/rocksdb/rocksdb/util/string_util.cc +85 -6
  714. package/deps/rocksdb/rocksdb/util/string_util.h +47 -2
  715. package/deps/rocksdb/rocksdb/util/thread_guard.h +41 -0
  716. package/deps/rocksdb/rocksdb/util/thread_local.h +2 -2
  717. package/deps/rocksdb/rocksdb/util/thread_local_test.cc +22 -24
  718. package/deps/rocksdb/rocksdb/util/threadpool_imp.cc +7 -6
  719. package/deps/rocksdb/rocksdb/util/timer.h +55 -46
  720. package/deps/rocksdb/rocksdb/util/timer_test.cc +50 -48
  721. package/deps/rocksdb/rocksdb/util/user_comparator_wrapper.h +4 -0
  722. package/deps/rocksdb/rocksdb/util/vector_iterator.h +31 -15
  723. package/deps/rocksdb/rocksdb/util/work_queue.h +2 -0
  724. package/deps/rocksdb/rocksdb/util/xxhash.cc +35 -1144
  725. package/deps/rocksdb/rocksdb/util/xxhash.h +5117 -373
  726. package/deps/rocksdb/rocksdb/util/xxph3.h +1762 -0
  727. package/deps/rocksdb/rocksdb/utilities/agg_merge/agg_merge.cc +238 -0
  728. package/deps/rocksdb/rocksdb/utilities/agg_merge/agg_merge.h +49 -0
  729. package/deps/rocksdb/rocksdb/utilities/agg_merge/agg_merge_test.cc +134 -0
  730. package/deps/rocksdb/rocksdb/utilities/agg_merge/test_agg_merge.cc +104 -0
  731. package/deps/rocksdb/rocksdb/utilities/agg_merge/test_agg_merge.h +47 -0
  732. package/deps/rocksdb/rocksdb/utilities/backup/backup_engine.cc +3164 -0
  733. package/deps/rocksdb/rocksdb/utilities/backup/backup_engine_impl.h +29 -0
  734. package/deps/rocksdb/rocksdb/utilities/{backupable/backupable_db_test.cc → backup/backup_engine_test.cc} +1679 -485
  735. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_compaction_filter.cc +6 -4
  736. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_compaction_filter.h +14 -9
  737. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db.cc +2 -0
  738. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db.h +1 -0
  739. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_gc_stats.h +4 -0
  740. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_impl.cc +37 -27
  741. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_impl.h +8 -4
  742. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_impl_filesnapshot.cc +1 -1
  743. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_iterator.h +13 -10
  744. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_listener.h +5 -0
  745. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_db_test.cc +44 -25
  746. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_dump_tool.cc +3 -4
  747. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_file.cc +27 -19
  748. package/deps/rocksdb/rocksdb/utilities/blob_db/blob_file.h +4 -2
  749. package/deps/rocksdb/rocksdb/utilities/cache_dump_load.cc +69 -0
  750. package/deps/rocksdb/rocksdb/utilities/cache_dump_load_impl.cc +489 -0
  751. package/deps/rocksdb/rocksdb/utilities/cache_dump_load_impl.h +366 -0
  752. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_compaction_filter.cc +67 -4
  753. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_compaction_filter.h +21 -6
  754. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_functional_test.cc +107 -7
  755. package/deps/rocksdb/rocksdb/utilities/cassandra/cassandra_options.h +43 -0
  756. package/deps/rocksdb/rocksdb/utilities/cassandra/format.h +1 -1
  757. package/deps/rocksdb/rocksdb/utilities/cassandra/merge_operator.cc +24 -8
  758. package/deps/rocksdb/rocksdb/utilities/cassandra/merge_operator.h +7 -7
  759. package/deps/rocksdb/rocksdb/utilities/cassandra/serialize.h +5 -0
  760. package/deps/rocksdb/rocksdb/utilities/checkpoint/checkpoint_impl.cc +99 -218
  761. package/deps/rocksdb/rocksdb/utilities/checkpoint/checkpoint_impl.h +8 -24
  762. package/deps/rocksdb/rocksdb/utilities/checkpoint/checkpoint_test.cc +114 -1
  763. package/deps/rocksdb/rocksdb/utilities/compaction_filters/layered_compaction_filter_base.h +6 -2
  764. package/deps/rocksdb/rocksdb/utilities/compaction_filters/remove_emptyvalue_compactionfilter.cc +0 -4
  765. package/deps/rocksdb/rocksdb/utilities/compaction_filters/remove_emptyvalue_compactionfilter.h +7 -6
  766. package/deps/rocksdb/rocksdb/utilities/compaction_filters.cc +56 -0
  767. package/deps/rocksdb/rocksdb/utilities/convenience/info_log_finder.cc +2 -2
  768. package/deps/rocksdb/rocksdb/utilities/counted_fs.cc +355 -0
  769. package/deps/rocksdb/rocksdb/utilities/counted_fs.h +152 -0
  770. package/deps/rocksdb/rocksdb/utilities/env_mirror.cc +13 -0
  771. package/deps/rocksdb/rocksdb/utilities/env_timed.cc +164 -122
  772. package/deps/rocksdb/rocksdb/utilities/env_timed.h +97 -0
  773. package/deps/rocksdb/rocksdb/utilities/fault_injection_env.cc +75 -17
  774. package/deps/rocksdb/rocksdb/utilities/fault_injection_env.h +19 -3
  775. package/deps/rocksdb/rocksdb/utilities/fault_injection_fs.cc +539 -126
  776. package/deps/rocksdb/rocksdb/utilities/fault_injection_fs.h +162 -17
  777. package/deps/rocksdb/rocksdb/utilities/fault_injection_secondary_cache.cc +110 -0
  778. package/deps/rocksdb/rocksdb/utilities/fault_injection_secondary_cache.h +94 -0
  779. package/deps/rocksdb/rocksdb/utilities/memory/memory_test.cc +5 -2
  780. package/deps/rocksdb/rocksdb/utilities/memory_allocators.h +104 -0
  781. package/deps/rocksdb/rocksdb/utilities/merge_operators/bytesxor.h +5 -3
  782. package/deps/rocksdb/rocksdb/utilities/merge_operators/max.cc +4 -1
  783. package/deps/rocksdb/rocksdb/utilities/merge_operators/put.cc +11 -3
  784. package/deps/rocksdb/rocksdb/utilities/merge_operators/sortlist.cc +0 -2
  785. package/deps/rocksdb/rocksdb/utilities/merge_operators/sortlist.h +5 -1
  786. package/deps/rocksdb/rocksdb/utilities/merge_operators/string_append/stringappend.cc +29 -10
  787. package/deps/rocksdb/rocksdb/utilities/merge_operators/string_append/stringappend.h +6 -3
  788. package/deps/rocksdb/rocksdb/utilities/merge_operators/string_append/stringappend2.cc +29 -14
  789. package/deps/rocksdb/rocksdb/utilities/merge_operators/string_append/stringappend2.h +6 -3
  790. package/deps/rocksdb/rocksdb/utilities/merge_operators/string_append/stringappend_test.cc +71 -18
  791. package/deps/rocksdb/rocksdb/utilities/merge_operators/uint64add.cc +15 -9
  792. package/deps/rocksdb/rocksdb/utilities/merge_operators.cc +120 -0
  793. package/deps/rocksdb/rocksdb/utilities/merge_operators.h +3 -23
  794. package/deps/rocksdb/rocksdb/utilities/object_registry.cc +267 -42
  795. package/deps/rocksdb/rocksdb/utilities/object_registry_test.cc +702 -76
  796. package/deps/rocksdb/rocksdb/utilities/option_change_migration/option_change_migration.cc +1 -1
  797. package/deps/rocksdb/rocksdb/utilities/option_change_migration/option_change_migration_test.cc +26 -5
  798. package/deps/rocksdb/rocksdb/utilities/options/options_util.cc +1 -1
  799. package/deps/rocksdb/rocksdb/utilities/options/options_util_test.cc +124 -1
  800. package/deps/rocksdb/rocksdb/utilities/persistent_cache/block_cache_tier.cc +2 -3
  801. package/deps/rocksdb/rocksdb/utilities/persistent_cache/block_cache_tier.h +8 -9
  802. package/deps/rocksdb/rocksdb/utilities/persistent_cache/block_cache_tier_file.cc +15 -13
  803. package/deps/rocksdb/rocksdb/utilities/persistent_cache/block_cache_tier_file.h +1 -1
  804. package/deps/rocksdb/rocksdb/utilities/persistent_cache/block_cache_tier_metadata.h +4 -4
  805. package/deps/rocksdb/rocksdb/utilities/persistent_cache/hash_table_evictable.h +2 -2
  806. package/deps/rocksdb/rocksdb/utilities/persistent_cache/persistent_cache_bench.cc +8 -9
  807. package/deps/rocksdb/rocksdb/utilities/persistent_cache/persistent_cache_test.cc +1 -1
  808. package/deps/rocksdb/rocksdb/utilities/persistent_cache/persistent_cache_tier.h +6 -3
  809. package/deps/rocksdb/rocksdb/utilities/persistent_cache/volatile_tier_impl.h +2 -2
  810. package/deps/rocksdb/rocksdb/utilities/simulator_cache/cache_simulator.cc +3 -0
  811. package/deps/rocksdb/rocksdb/utilities/simulator_cache/cache_simulator_test.cc +2 -0
  812. package/deps/rocksdb/rocksdb/utilities/simulator_cache/sim_cache.cc +43 -35
  813. package/deps/rocksdb/rocksdb/utilities/simulator_cache/sim_cache_test.cc +20 -18
  814. package/deps/rocksdb/rocksdb/utilities/table_properties_collectors/compact_on_deletion_collector.cc +107 -2
  815. package/deps/rocksdb/rocksdb/utilities/trace/file_trace_reader_writer.cc +23 -15
  816. package/deps/rocksdb/rocksdb/utilities/trace/file_trace_reader_writer.h +2 -2
  817. package/deps/rocksdb/rocksdb/utilities/trace/replayer_impl.cc +316 -0
  818. package/deps/rocksdb/rocksdb/utilities/trace/replayer_impl.h +86 -0
  819. package/deps/rocksdb/rocksdb/utilities/transactions/lock/point/point_lock_manager.cc +4 -5
  820. package/deps/rocksdb/rocksdb/utilities/transactions/lock/point/point_lock_manager.h +4 -3
  821. package/deps/rocksdb/rocksdb/utilities/transactions/lock/point/point_lock_manager_test.h +1 -1
  822. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_locking_test.cc +119 -3
  823. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/lib/locktree/locktree.cc +20 -3
  824. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/lib/locktree/locktree.h +20 -0
  825. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/lib/portability/toku_external_pthread.h +3 -2
  826. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/lib/portability/toku_time.h +4 -0
  827. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/range_tree_lock_manager.cc +38 -14
  828. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/range_tree_lock_manager.h +17 -10
  829. package/deps/rocksdb/rocksdb/utilities/transactions/optimistic_transaction_db_impl.h +1 -0
  830. package/deps/rocksdb/rocksdb/utilities/transactions/optimistic_transaction_test.cc +1 -2
  831. package/deps/rocksdb/rocksdb/utilities/transactions/pessimistic_transaction.cc +423 -34
  832. package/deps/rocksdb/rocksdb/utilities/transactions/pessimistic_transaction.h +82 -2
  833. package/deps/rocksdb/rocksdb/utilities/transactions/pessimistic_transaction_db.cc +72 -40
  834. package/deps/rocksdb/rocksdb/utilities/transactions/pessimistic_transaction_db.h +32 -1
  835. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_base.cc +13 -5
  836. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_base.h +7 -3
  837. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_test.cc +207 -43
  838. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_test.h +50 -7
  839. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_util.cc +28 -10
  840. package/deps/rocksdb/rocksdb/utilities/transactions/transaction_util.h +11 -6
  841. package/deps/rocksdb/rocksdb/utilities/transactions/write_committed_transaction_ts_test.cc +516 -0
  842. package/deps/rocksdb/rocksdb/utilities/transactions/write_prepared_transaction_test.cc +506 -15
  843. package/deps/rocksdb/rocksdb/utilities/transactions/write_prepared_txn.cc +27 -13
  844. package/deps/rocksdb/rocksdb/utilities/transactions/write_prepared_txn_db.cc +14 -14
  845. package/deps/rocksdb/rocksdb/utilities/transactions/write_prepared_txn_db.h +3 -0
  846. package/deps/rocksdb/rocksdb/utilities/transactions/write_unprepared_transaction_test.cc +2 -2
  847. package/deps/rocksdb/rocksdb/utilities/transactions/write_unprepared_txn.cc +14 -5
  848. package/deps/rocksdb/rocksdb/utilities/ttl/db_ttl_impl.cc +305 -27
  849. package/deps/rocksdb/rocksdb/utilities/ttl/db_ttl_impl.h +55 -159
  850. package/deps/rocksdb/rocksdb/utilities/ttl/ttl_test.cc +209 -2
  851. package/deps/rocksdb/rocksdb/utilities/wal_filter.cc +23 -0
  852. package/deps/rocksdb/rocksdb/utilities/write_batch_with_index/write_batch_with_index.cc +157 -88
  853. package/deps/rocksdb/rocksdb/utilities/write_batch_with_index/write_batch_with_index_internal.cc +501 -114
  854. package/deps/rocksdb/rocksdb/utilities/write_batch_with_index/write_batch_with_index_internal.h +91 -316
  855. package/deps/rocksdb/rocksdb/utilities/write_batch_with_index/write_batch_with_index_test.cc +1212 -672
  856. package/deps/rocksdb/rocksdb.gyp +425 -446
  857. package/index.js +5 -87
  858. package/package-lock.json +23687 -0
  859. package/package.json +8 -9
  860. package/prebuilds/darwin-arm64/node.napi.node +0 -0
  861. package/prebuilds/darwin-x64/node.napi.node +0 -0
  862. package/prebuilds/{darwin-x64+arm64 → linux-x64}/node.napi.node +0 -0
  863. package/deps/rocksdb/rocksdb/README.md +0 -32
  864. package/deps/rocksdb/rocksdb/env/env_hdfs.cc +0 -648
  865. package/deps/rocksdb/rocksdb/hdfs/README +0 -23
  866. package/deps/rocksdb/rocksdb/hdfs/env_hdfs.h +0 -386
  867. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/backupable_db.h +0 -535
  868. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/env_librados.h +0 -175
  869. package/deps/rocksdb/rocksdb/include/rocksdb/utilities/utility_db.h +0 -34
  870. package/deps/rocksdb/rocksdb/memory/memkind_kmem_allocator_test.cc +0 -102
  871. package/deps/rocksdb/rocksdb/memtable/hash_linklist_rep.h +0 -49
  872. package/deps/rocksdb/rocksdb/memtable/hash_skiplist_rep.h +0 -44
  873. package/deps/rocksdb/rocksdb/options/customizable_helper.h +0 -216
  874. package/deps/rocksdb/rocksdb/port/README +0 -10
  875. package/deps/rocksdb/rocksdb/third-party/folly/folly/CPortability.h +0 -27
  876. package/deps/rocksdb/rocksdb/third-party/folly/folly/ConstexprMath.h +0 -45
  877. package/deps/rocksdb/rocksdb/third-party/folly/folly/Indestructible.h +0 -166
  878. package/deps/rocksdb/rocksdb/third-party/folly/folly/Optional.h +0 -570
  879. package/deps/rocksdb/rocksdb/third-party/folly/folly/Portability.h +0 -92
  880. package/deps/rocksdb/rocksdb/third-party/folly/folly/ScopeGuard.h +0 -54
  881. package/deps/rocksdb/rocksdb/third-party/folly/folly/Traits.h +0 -152
  882. package/deps/rocksdb/rocksdb/third-party/folly/folly/Unit.h +0 -59
  883. package/deps/rocksdb/rocksdb/third-party/folly/folly/Utility.h +0 -141
  884. package/deps/rocksdb/rocksdb/third-party/folly/folly/chrono/Hardware.h +0 -33
  885. package/deps/rocksdb/rocksdb/third-party/folly/folly/container/Array.h +0 -74
  886. package/deps/rocksdb/rocksdb/third-party/folly/folly/detail/Futex-inl.h +0 -117
  887. package/deps/rocksdb/rocksdb/third-party/folly/folly/detail/Futex.cpp +0 -263
  888. package/deps/rocksdb/rocksdb/third-party/folly/folly/detail/Futex.h +0 -96
  889. package/deps/rocksdb/rocksdb/third-party/folly/folly/functional/Invoke.h +0 -40
  890. package/deps/rocksdb/rocksdb/third-party/folly/folly/hash/Hash.h +0 -29
  891. package/deps/rocksdb/rocksdb/third-party/folly/folly/lang/Align.h +0 -144
  892. package/deps/rocksdb/rocksdb/third-party/folly/folly/lang/Bits.h +0 -30
  893. package/deps/rocksdb/rocksdb/third-party/folly/folly/lang/Launder.h +0 -51
  894. package/deps/rocksdb/rocksdb/third-party/folly/folly/portability/Asm.h +0 -28
  895. package/deps/rocksdb/rocksdb/third-party/folly/folly/portability/SysSyscall.h +0 -10
  896. package/deps/rocksdb/rocksdb/third-party/folly/folly/portability/SysTypes.h +0 -26
  897. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/AtomicNotification-inl.h +0 -138
  898. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/AtomicNotification.cpp +0 -23
  899. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/AtomicNotification.h +0 -57
  900. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/AtomicUtil-inl.h +0 -260
  901. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/AtomicUtil.h +0 -52
  902. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/Baton.h +0 -328
  903. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/DistributedMutex-inl.h +0 -1703
  904. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/DistributedMutex.cpp +0 -16
  905. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/DistributedMutex.h +0 -304
  906. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/DistributedMutexSpecializations.h +0 -39
  907. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/ParkingLot.cpp +0 -26
  908. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/ParkingLot.h +0 -318
  909. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/WaitOptions.h +0 -57
  910. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/detail/InlineFunctionRef.h +0 -219
  911. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/detail/ProxyLockable-inl.h +0 -207
  912. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/detail/ProxyLockable.h +0 -164
  913. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/detail/Sleeper.h +0 -57
  914. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/detail/Spin.h +0 -77
  915. package/deps/rocksdb/rocksdb/third-party/folly/folly/synchronization/test/DistributedMutexTest.cpp +0 -1145
  916. package/deps/rocksdb/rocksdb/util/build_version.h +0 -15
  917. package/deps/rocksdb/rocksdb/util/xxh3p.h +0 -1392
  918. package/deps/rocksdb/rocksdb/utilities/backupable/backupable_db.cc +0 -2354
  919. package/deps/rocksdb/rocksdb/utilities/env_librados.cc +0 -1497
  920. package/deps/rocksdb/rocksdb/utilities/env_librados_test.cc +0 -1146
  921. package/deps/rocksdb/rocksdb/utilities/transactions/lock/range/range_tree/lib/README +0 -13
  922. package/deps/snappy/snappy-1.1.7/README.md +0 -149
  923. package/prebuilds/linux-x64/node.napi.glibc.node +0 -0
@@ -6,17 +6,25 @@
6
6
  // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
7
7
  // Use of this source code is governed by a BSD-style license that can be
8
8
  // found in the LICENSE file. See the AUTHORS file for names of contributors.
9
+
9
10
  #include <atomic>
10
11
  #include <cstdlib>
11
12
  #include <functional>
13
+ #include <memory>
12
14
 
13
15
  #include "db/db_test_util.h"
14
16
  #include "db/read_callback.h"
15
17
  #include "options/options_helper.h"
16
18
  #include "port/port.h"
17
19
  #include "port/stack_trace.h"
20
+ #include "rocksdb/experimental.h"
21
+ #include "rocksdb/iostats_context.h"
18
22
  #include "rocksdb/persistent_cache.h"
23
+ #include "rocksdb/trace_record.h"
24
+ #include "rocksdb/trace_record_result.h"
25
+ #include "rocksdb/utilities/replayer.h"
19
26
  #include "rocksdb/wal_filter.h"
27
+ #include "test_util/testutil.h"
20
28
  #include "util/random.h"
21
29
  #include "utilities/fault_injection_env.h"
22
30
 
@@ -24,7 +32,19 @@ namespace ROCKSDB_NAMESPACE {
24
32
 
25
33
  class DBTest2 : public DBTestBase {
26
34
  public:
27
- DBTest2() : DBTestBase("/db_test2", /*env_do_fsync=*/true) {}
35
+ DBTest2() : DBTestBase("db_test2", /*env_do_fsync=*/true) {}
36
+
37
+ protected:
38
+ #ifndef ROCKSDB_LITE
39
+ uint64_t GetSstSizeHelper(Temperature temperature) {
40
+ std::string prop;
41
+ EXPECT_TRUE(
42
+ dbfull()->GetProperty(DB::Properties::kLiveSstFilesSizeAtTemperature +
43
+ ToString(static_cast<uint8_t>(temperature)),
44
+ &prop));
45
+ return static_cast<uint64_t>(std::atoi(prop.c_str()));
46
+ }
47
+ #endif // ROCKSDB_LITE
28
48
  };
29
49
 
30
50
  #ifndef ROCKSDB_LITE
@@ -90,7 +110,7 @@ class TestReadOnlyWithCompressedCache
90
110
  public testing::WithParamInterface<std::tuple<int, bool>> {
91
111
  public:
92
112
  TestReadOnlyWithCompressedCache()
93
- : DBTestBase("/test_readonly_with_compressed_cache",
113
+ : DBTestBase("test_readonly_with_compressed_cache",
94
114
  /*env_do_fsync=*/true) {
95
115
  max_open_files_ = std::get<0>(GetParam());
96
116
  use_mmap_ = std::get<1>(GetParam());
@@ -154,8 +174,14 @@ class PartitionedIndexTestListener : public EventListener {
154
174
  };
155
175
 
156
176
  TEST_F(DBTest2, PartitionedIndexUserToInternalKey) {
177
+ const int kValueSize = 10500;
178
+ const int kNumEntriesPerFile = 1000;
179
+ const int kNumFiles = 3;
180
+ const int kNumDistinctKeys = 30;
181
+
157
182
  BlockBasedTableOptions table_options;
158
183
  Options options = CurrentOptions();
184
+ options.disable_auto_compactions = true;
159
185
  table_options.index_type = BlockBasedTableOptions::kTwoLevelIndexSearch;
160
186
  PartitionedIndexTestListener* listener = new PartitionedIndexTestListener();
161
187
  options.table_factory.reset(NewBlockBasedTableFactory(table_options));
@@ -164,14 +190,15 @@ TEST_F(DBTest2, PartitionedIndexUserToInternalKey) {
164
190
  Reopen(options);
165
191
  Random rnd(301);
166
192
 
167
- for (int i = 0; i < 3000; i++) {
168
- int j = i % 30;
169
- std::string value = rnd.RandomString(10500);
170
- ASSERT_OK(Put("keykey_" + std::to_string(j), value));
171
- snapshots.push_back(db_->GetSnapshot());
193
+ for (int i = 0; i < kNumFiles; i++) {
194
+ for (int j = 0; j < kNumEntriesPerFile; j++) {
195
+ int key_id = (i * kNumEntriesPerFile + j) % kNumDistinctKeys;
196
+ std::string value = rnd.RandomString(kValueSize);
197
+ ASSERT_OK(Put("keykey_" + std::to_string(key_id), value));
198
+ snapshots.push_back(db_->GetSnapshot());
199
+ }
200
+ ASSERT_OK(Flush());
172
201
  }
173
- ASSERT_OK(Flush());
174
- dbfull()->TEST_WaitForFlushMemTable();
175
202
 
176
203
  for (auto s : snapshots) {
177
204
  db_->ReleaseSnapshot(s);
@@ -185,7 +212,7 @@ class PrefixFullBloomWithReverseComparator
185
212
  public ::testing::WithParamInterface<bool> {
186
213
  public:
187
214
  PrefixFullBloomWithReverseComparator()
188
- : DBTestBase("/prefix_bloom_reverse", /*env_do_fsync=*/true) {}
215
+ : DBTestBase("prefix_bloom_reverse", /*env_do_fsync=*/true) {}
189
216
  void SetUp() override { if_cache_filter_ = GetParam(); }
190
217
  bool if_cache_filter_;
191
218
  };
@@ -211,7 +238,7 @@ TEST_P(PrefixFullBloomWithReverseComparator,
211
238
  ASSERT_OK(dbfull()->Put(WriteOptions(), "bar234", "foo2"));
212
239
  ASSERT_OK(dbfull()->Put(WriteOptions(), "foo123", "foo3"));
213
240
 
214
- dbfull()->Flush(FlushOptions());
241
+ ASSERT_OK(dbfull()->Flush(FlushOptions()));
215
242
 
216
243
  if (bbto.block_cache) {
217
244
  bbto.block_cache->EraseUnRefEntries();
@@ -243,18 +270,20 @@ INSTANTIATE_TEST_CASE_P(PrefixFullBloomWithReverseComparator,
243
270
  PrefixFullBloomWithReverseComparator, testing::Bool());
244
271
 
245
272
  TEST_F(DBTest2, IteratorPropertyVersionNumber) {
246
- Put("", "");
273
+ ASSERT_OK(Put("", ""));
247
274
  Iterator* iter1 = db_->NewIterator(ReadOptions());
275
+ ASSERT_OK(iter1->status());
248
276
  std::string prop_value;
249
277
  ASSERT_OK(
250
278
  iter1->GetProperty("rocksdb.iterator.super-version-number", &prop_value));
251
279
  uint64_t version_number1 =
252
280
  static_cast<uint64_t>(std::atoi(prop_value.c_str()));
253
281
 
254
- Put("", "");
255
- Flush();
282
+ ASSERT_OK(Put("", ""));
283
+ ASSERT_OK(Flush());
256
284
 
257
285
  Iterator* iter2 = db_->NewIterator(ReadOptions());
286
+ ASSERT_OK(iter2->status());
258
287
  ASSERT_OK(
259
288
  iter2->GetProperty("rocksdb.iterator.super-version-number", &prop_value));
260
289
  uint64_t version_number2 =
@@ -262,9 +291,10 @@ TEST_F(DBTest2, IteratorPropertyVersionNumber) {
262
291
 
263
292
  ASSERT_GT(version_number2, version_number1);
264
293
 
265
- Put("", "");
294
+ ASSERT_OK(Put("", ""));
266
295
 
267
296
  Iterator* iter3 = db_->NewIterator(ReadOptions());
297
+ ASSERT_OK(iter3->status());
268
298
  ASSERT_OK(
269
299
  iter3->GetProperty("rocksdb.iterator.super-version-number", &prop_value));
270
300
  uint64_t version_number3 =
@@ -294,8 +324,8 @@ TEST_F(DBTest2, CacheIndexAndFilterWithDBRestart) {
294
324
  options.table_factory.reset(NewBlockBasedTableFactory(table_options));
295
325
  CreateAndReopenWithCF({"pikachu"}, options);
296
326
 
297
- Put(1, "a", "begin");
298
- Put(1, "z", "end");
327
+ ASSERT_OK(Put(1, "a", "begin"));
328
+ ASSERT_OK(Put(1, "z", "end"));
299
329
  ASSERT_OK(Flush(1));
300
330
  TryReopenWithColumnFamilies({"default", "pikachu"}, options);
301
331
 
@@ -311,10 +341,10 @@ TEST_F(DBTest2, MaxSuccessiveMergesChangeWithDBRecovery) {
311
341
  options.merge_operator = MergeOperators::CreatePutOperator();
312
342
  options.disable_auto_compactions = true;
313
343
  DestroyAndReopen(options);
314
- Put("poi", "Finch");
315
- db_->Merge(WriteOptions(), "poi", "Reese");
316
- db_->Merge(WriteOptions(), "poi", "Shaw");
317
- db_->Merge(WriteOptions(), "poi", "Root");
344
+ ASSERT_OK(Put("poi", "Finch"));
345
+ ASSERT_OK(db_->Merge(WriteOptions(), "poi", "Reese"));
346
+ ASSERT_OK(db_->Merge(WriteOptions(), "poi", "Shaw"));
347
+ ASSERT_OK(db_->Merge(WriteOptions(), "poi", "Root"));
318
348
  options.max_successive_merges = 2;
319
349
  Reopen(options);
320
350
  }
@@ -325,7 +355,7 @@ class DBTestSharedWriteBufferAcrossCFs
325
355
  public testing::WithParamInterface<std::tuple<bool, bool>> {
326
356
  public:
327
357
  DBTestSharedWriteBufferAcrossCFs()
328
- : DBTestBase("/db_test_shared_write_buffer", /*env_do_fsync=*/true) {}
358
+ : DBTestBase("db_test_shared_write_buffer", /*env_do_fsync=*/true) {}
329
359
  void SetUp() override {
330
360
  use_old_interface_ = std::get<0>(GetParam());
331
361
  cost_cache_ = std::get<1>(GetParam());
@@ -337,6 +367,10 @@ class DBTestSharedWriteBufferAcrossCFs
337
367
  TEST_P(DBTestSharedWriteBufferAcrossCFs, SharedWriteBufferAcrossCFs) {
338
368
  Options options = CurrentOptions();
339
369
  options.arena_block_size = 4096;
370
+ auto flush_listener = std::make_shared<FlushCounterListener>();
371
+ options.listeners.push_back(flush_listener);
372
+ // Don't trip the listener at shutdown.
373
+ options.avoid_flush_during_shutdown = true;
340
374
 
341
375
  // Avoid undeterministic value by malloc_usable_size();
342
376
  // Force arena block size to 1
@@ -372,14 +406,18 @@ TEST_P(DBTestSharedWriteBufferAcrossCFs, SharedWriteBufferAcrossCFs) {
372
406
  wo.disableWAL = true;
373
407
 
374
408
  std::function<void()> wait_flush = [&]() {
375
- dbfull()->TEST_WaitForFlushMemTable(handles_[0]);
376
- dbfull()->TEST_WaitForFlushMemTable(handles_[1]);
377
- dbfull()->TEST_WaitForFlushMemTable(handles_[2]);
378
- dbfull()->TEST_WaitForFlushMemTable(handles_[3]);
409
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[0]));
410
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[1]));
411
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[2]));
412
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[3]));
413
+ // Ensure background work is fully finished including listener callbacks
414
+ // before accessing listener state.
415
+ ASSERT_OK(dbfull()->TEST_WaitForBackgroundWork());
379
416
  };
380
417
 
381
418
  // Create some data and flush "default" and "nikitich" so that they
382
419
  // are newer CFs created.
420
+ flush_listener->expected_flush_reason = FlushReason::kManualFlush;
383
421
  ASSERT_OK(Put(3, Key(1), DummyString(1), wo));
384
422
  Flush(3);
385
423
  ASSERT_OK(Put(3, Key(1), DummyString(1), wo));
@@ -390,6 +428,7 @@ TEST_P(DBTestSharedWriteBufferAcrossCFs, SharedWriteBufferAcrossCFs) {
390
428
  ASSERT_EQ(GetNumberOfSstFilesForColumnFamily(db_, "nikitich"),
391
429
  static_cast<uint64_t>(1));
392
430
 
431
+ flush_listener->expected_flush_reason = FlushReason::kWriteBufferManager;
393
432
  ASSERT_OK(Put(3, Key(1), DummyString(30000), wo));
394
433
  if (cost_cache_) {
395
434
  ASSERT_GE(cache->GetUsage(), 256 * 1024);
@@ -514,6 +553,10 @@ TEST_F(DBTest2, SharedWriteBufferLimitAcrossDB) {
514
553
  std::string dbname2 = test::PerThreadDBPath("db_shared_wb_db2");
515
554
  Options options = CurrentOptions();
516
555
  options.arena_block_size = 4096;
556
+ auto flush_listener = std::make_shared<FlushCounterListener>();
557
+ options.listeners.push_back(flush_listener);
558
+ // Don't trip the listener at shutdown.
559
+ options.avoid_flush_during_shutdown = true;
517
560
  // Avoid undeterministic value by malloc_usable_size();
518
561
  // Force arena block size to 1
519
562
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
@@ -544,13 +587,19 @@ TEST_F(DBTest2, SharedWriteBufferLimitAcrossDB) {
544
587
  wo.disableWAL = true;
545
588
 
546
589
  std::function<void()> wait_flush = [&]() {
547
- dbfull()->TEST_WaitForFlushMemTable(handles_[0]);
548
- dbfull()->TEST_WaitForFlushMemTable(handles_[1]);
549
- dbfull()->TEST_WaitForFlushMemTable(handles_[2]);
550
- static_cast<DBImpl*>(db2)->TEST_WaitForFlushMemTable();
590
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[0]));
591
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[1]));
592
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[2]));
593
+ ASSERT_OK(static_cast<DBImpl*>(db2)->TEST_WaitForFlushMemTable());
594
+ // Ensure background work is fully finished including listener callbacks
595
+ // before accessing listener state.
596
+ ASSERT_OK(dbfull()->TEST_WaitForBackgroundWork());
597
+ ASSERT_OK(
598
+ static_cast_with_check<DBImpl>(db2)->TEST_WaitForBackgroundWork());
551
599
  };
552
600
 
553
601
  // Trigger a flush on cf2
602
+ flush_listener->expected_flush_reason = FlushReason::kWriteBufferManager;
554
603
  ASSERT_OK(Put(2, Key(1), DummyString(70000), wo));
555
604
  wait_flush();
556
605
  ASSERT_OK(Put(0, Key(1), DummyString(20000), wo));
@@ -562,7 +611,7 @@ TEST_F(DBTest2, SharedWriteBufferLimitAcrossDB) {
562
611
 
563
612
  ASSERT_OK(Put(2, Key(1), DummyString(1), wo));
564
613
  wait_flush();
565
- static_cast<DBImpl*>(db2)->TEST_WaitForFlushMemTable();
614
+ ASSERT_OK(static_cast<DBImpl*>(db2)->TEST_WaitForFlushMemTable());
566
615
  {
567
616
  ASSERT_EQ(GetNumberOfSstFilesForColumnFamily(db_, "default") +
568
617
  GetNumberOfSstFilesForColumnFamily(db_, "cf1") +
@@ -593,7 +642,7 @@ TEST_F(DBTest2, SharedWriteBufferLimitAcrossDB) {
593
642
  wait_flush();
594
643
  ASSERT_OK(db2->Put(wo, Key(1), DummyString(1)));
595
644
  wait_flush();
596
- static_cast<DBImpl*>(db2)->TEST_WaitForFlushMemTable();
645
+ ASSERT_OK(static_cast<DBImpl*>(db2)->TEST_WaitForFlushMemTable());
597
646
  {
598
647
  ASSERT_EQ(GetNumberOfSstFilesForColumnFamily(db_, "default"),
599
648
  static_cast<uint64_t>(1));
@@ -717,9 +766,9 @@ TEST_F(DBTest2, WalFilterTest) {
717
766
  for (size_t i = 0; i < batch_keys.size(); i++) {
718
767
  WriteBatch batch;
719
768
  for (size_t j = 0; j < batch_keys[i].size(); j++) {
720
- batch.Put(handles_[0], batch_keys[i][j], DummyString(1024));
769
+ ASSERT_OK(batch.Put(handles_[0], batch_keys[i][j], DummyString(1024)));
721
770
  }
722
- dbfull()->Write(WriteOptions(), &batch);
771
+ ASSERT_OK(dbfull()->Write(WriteOptions(), &batch));
723
772
  }
724
773
 
725
774
  WalFilter::WalProcessingOption wal_processing_option =
@@ -738,14 +787,14 @@ TEST_F(DBTest2, WalFilterTest) {
738
787
  TryReopenWithColumnFamilies({ "default", "pikachu" }, options);
739
788
  if (wal_processing_option ==
740
789
  WalFilter::WalProcessingOption::kCorruptedRecord) {
741
- assert(!status.ok());
790
+ ASSERT_NOK(status);
742
791
  // In case of corruption we can turn off paranoid_checks to reopen
743
792
  // databse
744
793
  options.paranoid_checks = false;
745
794
  ReopenWithColumnFamilies({ "default", "pikachu" }, options);
746
795
  }
747
796
  else {
748
- assert(status.ok());
797
+ ASSERT_OK(status);
749
798
  }
750
799
 
751
800
  // Compute which keys we expect to be found
@@ -802,7 +851,7 @@ TEST_F(DBTest2, WalFilterTest) {
802
851
  break;
803
852
  }
804
853
  default:
805
- assert(false); // unhandled case
854
+ FAIL(); // unhandled case
806
855
  }
807
856
 
808
857
  bool checked_after_reopen = false;
@@ -845,7 +894,7 @@ TEST_F(DBTest2, WalFilterTestWithChangeBatch) {
845
894
  num_keys_added_(0) {}
846
895
  void Put(const Slice& key, const Slice& value) override {
847
896
  if (num_keys_added_ < num_keys_to_add_in_new_batch_) {
848
- new_write_batch_->Put(key, value);
897
+ ASSERT_OK(new_write_batch_->Put(key, value));
849
898
  ++num_keys_added_;
850
899
  }
851
900
  }
@@ -872,8 +921,12 @@ TEST_F(DBTest2, WalFilterTestWithChangeBatch) {
872
921
  bool* batch_changed) const override {
873
922
  if (current_record_index_ >= change_records_from_index_) {
874
923
  ChangeBatchHandler handler(new_batch, num_keys_to_add_in_new_batch_);
875
- batch.Iterate(&handler);
876
- *batch_changed = true;
924
+ Status s = batch.Iterate(&handler);
925
+ if (s.ok()) {
926
+ *batch_changed = true;
927
+ } else {
928
+ assert(false);
929
+ }
877
930
  }
878
931
 
879
932
  // Filter is passed as a const object for RocksDB to not modify the
@@ -905,9 +958,9 @@ TEST_F(DBTest2, WalFilterTestWithChangeBatch) {
905
958
  for (size_t i = 0; i < batch_keys.size(); i++) {
906
959
  WriteBatch batch;
907
960
  for (size_t j = 0; j < batch_keys[i].size(); j++) {
908
- batch.Put(handles_[0], batch_keys[i][j], DummyString(1024));
961
+ ASSERT_OK(batch.Put(handles_[0], batch_keys[i][j], DummyString(1024)));
909
962
  }
910
- dbfull()->Write(WriteOptions(), &batch);
963
+ ASSERT_OK(dbfull()->Write(WriteOptions(), &batch));
911
964
  }
912
965
 
913
966
  // Create a test filter that would apply wal_processing_option at the first
@@ -966,8 +1019,12 @@ TEST_F(DBTest2, WalFilterTestWithChangeBatchExtraKeys) {
966
1019
  WalProcessingOption LogRecord(const WriteBatch& batch, WriteBatch* new_batch,
967
1020
  bool* batch_changed) const override {
968
1021
  *new_batch = batch;
969
- new_batch->Put("key_extra", "value_extra");
970
- *batch_changed = true;
1022
+ Status s = new_batch->Put("key_extra", "value_extra");
1023
+ if (s.ok()) {
1024
+ *batch_changed = true;
1025
+ } else {
1026
+ assert(false);
1027
+ }
971
1028
  return WalProcessingOption::kContinueProcessing;
972
1029
  }
973
1030
 
@@ -993,9 +1050,9 @@ TEST_F(DBTest2, WalFilterTestWithChangeBatchExtraKeys) {
993
1050
  for (size_t i = 0; i < batch_keys.size(); i++) {
994
1051
  WriteBatch batch;
995
1052
  for (size_t j = 0; j < batch_keys[i].size(); j++) {
996
- batch.Put(handles_[0], batch_keys[i][j], DummyString(1024));
1053
+ ASSERT_OK(batch.Put(handles_[0], batch_keys[i][j], DummyString(1024)));
997
1054
  }
998
- dbfull()->Write(WriteOptions(), &batch);
1055
+ ASSERT_OK(dbfull()->Write(WriteOptions(), &batch));
999
1056
  }
1000
1057
 
1001
1058
  // Create a test filter that would add extra keys
@@ -1078,7 +1135,11 @@ TEST_F(DBTest2, WalFilterTestWithColumnFamilies) {
1078
1135
  }
1079
1136
  } handler(log_number, cf_log_number_map_, cf_wal_keys_);
1080
1137
 
1081
- batch.Iterate(&handler);
1138
+ Status s = batch.Iterate(&handler);
1139
+ if (!s.ok()) {
1140
+ // TODO(AR) is this ok?
1141
+ return WalProcessingOption::kCorruptedRecord;
1142
+ }
1082
1143
 
1083
1144
  return WalProcessingOption::kContinueProcessing;
1084
1145
  }
@@ -1113,14 +1174,16 @@ TEST_F(DBTest2, WalFilterTestWithColumnFamilies) {
1113
1174
  for (size_t i = 0; i < batch_keys_pre_flush.size(); i++) {
1114
1175
  WriteBatch batch;
1115
1176
  for (size_t j = 0; j < batch_keys_pre_flush[i].size(); j++) {
1116
- batch.Put(handles_[0], batch_keys_pre_flush[i][j], DummyString(1024));
1117
- batch.Put(handles_[1], batch_keys_pre_flush[i][j], DummyString(1024));
1177
+ ASSERT_OK(batch.Put(handles_[0], batch_keys_pre_flush[i][j],
1178
+ DummyString(1024)));
1179
+ ASSERT_OK(batch.Put(handles_[1], batch_keys_pre_flush[i][j],
1180
+ DummyString(1024)));
1118
1181
  }
1119
- dbfull()->Write(WriteOptions(), &batch);
1182
+ ASSERT_OK(dbfull()->Write(WriteOptions(), &batch));
1120
1183
  }
1121
1184
 
1122
1185
  //Flush default column-family
1123
- db_->Flush(FlushOptions(), handles_[0]);
1186
+ ASSERT_OK(db_->Flush(FlushOptions(), handles_[0]));
1124
1187
 
1125
1188
  // Do some more writes
1126
1189
  std::vector<std::vector<std::string>> batch_keys_post_flush(3);
@@ -1136,10 +1199,12 @@ TEST_F(DBTest2, WalFilterTestWithColumnFamilies) {
1136
1199
  for (size_t i = 0; i < batch_keys_post_flush.size(); i++) {
1137
1200
  WriteBatch batch;
1138
1201
  for (size_t j = 0; j < batch_keys_post_flush[i].size(); j++) {
1139
- batch.Put(handles_[0], batch_keys_post_flush[i][j], DummyString(1024));
1140
- batch.Put(handles_[1], batch_keys_post_flush[i][j], DummyString(1024));
1202
+ ASSERT_OK(batch.Put(handles_[0], batch_keys_post_flush[i][j],
1203
+ DummyString(1024)));
1204
+ ASSERT_OK(batch.Put(handles_[1], batch_keys_post_flush[i][j],
1205
+ DummyString(1024)));
1141
1206
  }
1142
- dbfull()->Write(WriteOptions(), &batch);
1207
+ ASSERT_OK(dbfull()->Write(WriteOptions(), &batch));
1143
1208
  }
1144
1209
 
1145
1210
  // On Recovery we should only find the second batch applicable to default CF
@@ -1166,10 +1231,10 @@ TEST_F(DBTest2, WalFilterTestWithColumnFamilies) {
1166
1231
  for (size_t j = 0; j < batch_keys_post_flush[i].size(); j++) {
1167
1232
  Slice key_from_the_log(keys_cf[index++]);
1168
1233
  Slice batch_key(batch_keys_post_flush[i][j]);
1169
- ASSERT_TRUE(key_from_the_log.compare(batch_key) == 0);
1234
+ ASSERT_EQ(key_from_the_log.compare(batch_key), 0);
1170
1235
  }
1171
1236
  }
1172
- ASSERT_TRUE(index == keys_cf.size());
1237
+ ASSERT_EQ(index, keys_cf.size());
1173
1238
 
1174
1239
  index = 0;
1175
1240
  keys_cf = cf_wal_keys[name_id_map["pikachu"]];
@@ -1178,7 +1243,7 @@ TEST_F(DBTest2, WalFilterTestWithColumnFamilies) {
1178
1243
  for (size_t j = 0; j < batch_keys_pre_flush[i].size(); j++) {
1179
1244
  Slice key_from_the_log(keys_cf[index++]);
1180
1245
  Slice batch_key(batch_keys_pre_flush[i][j]);
1181
- ASSERT_TRUE(key_from_the_log.compare(batch_key) == 0);
1246
+ ASSERT_EQ(key_from_the_log.compare(batch_key), 0);
1182
1247
  }
1183
1248
  }
1184
1249
 
@@ -1186,10 +1251,10 @@ TEST_F(DBTest2, WalFilterTestWithColumnFamilies) {
1186
1251
  for (size_t j = 0; j < batch_keys_post_flush[i].size(); j++) {
1187
1252
  Slice key_from_the_log(keys_cf[index++]);
1188
1253
  Slice batch_key(batch_keys_post_flush[i][j]);
1189
- ASSERT_TRUE(key_from_the_log.compare(batch_key) == 0);
1254
+ ASSERT_EQ(key_from_the_log.compare(batch_key), 0);
1190
1255
  }
1191
1256
  }
1192
- ASSERT_TRUE(index == keys_cf.size());
1257
+ ASSERT_EQ(index, keys_cf.size());
1193
1258
  }
1194
1259
 
1195
1260
  TEST_F(DBTest2, PresetCompressionDict) {
@@ -1209,7 +1274,7 @@ TEST_F(DBTest2, PresetCompressionDict) {
1209
1274
  options.disable_auto_compactions = true;
1210
1275
  options.level0_file_num_compaction_trigger = kNumL0Files;
1211
1276
  options.memtable_factory.reset(
1212
- new SpecialSkipListFactory(kL0FileBytes / kBlockSizeBytes));
1277
+ test::NewSpecialSkipListFactory(kL0FileBytes / kBlockSizeBytes));
1213
1278
  options.num_levels = 2;
1214
1279
  options.target_file_size_base = kL0FileBytes;
1215
1280
  options.target_file_size_multiplier = 2;
@@ -1286,11 +1351,11 @@ TEST_F(DBTest2, PresetCompressionDict) {
1286
1351
  ASSERT_OK(Put(1, Key(static_cast<int>(key_num)),
1287
1352
  seq_datas[(key_num / 10) % 10]));
1288
1353
  }
1289
- dbfull()->TEST_WaitForFlushMemTable(handles_[1]);
1354
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable(handles_[1]));
1290
1355
  ASSERT_EQ(j + 1, NumTableFilesAtLevel(0, 1));
1291
1356
  }
1292
- dbfull()->TEST_CompactRange(0, nullptr, nullptr, handles_[1],
1293
- true /* disallow_trivial_move */);
1357
+ ASSERT_OK(dbfull()->TEST_CompactRange(0, nullptr, nullptr, handles_[1],
1358
+ true /* disallow_trivial_move */));
1294
1359
  ASSERT_EQ(0, NumTableFilesAtLevel(0, 1));
1295
1360
  ASSERT_GT(NumTableFilesAtLevel(1, 1), 0);
1296
1361
 
@@ -1394,7 +1459,7 @@ class PresetCompressionDictTest
1394
1459
  public testing::WithParamInterface<std::tuple<CompressionType, bool>> {
1395
1460
  public:
1396
1461
  PresetCompressionDictTest()
1397
- : DBTestBase("/db_test2", false /* env_do_fsync */),
1462
+ : DBTestBase("db_test2", false /* env_do_fsync */),
1398
1463
  compression_type_(std::get<0>(GetParam())),
1399
1464
  bottommost_(std::get<1>(GetParam())) {}
1400
1465
 
@@ -1410,67 +1475,94 @@ INSTANTIATE_TEST_CASE_P(
1410
1475
 
1411
1476
  TEST_P(PresetCompressionDictTest, Flush) {
1412
1477
  // Verifies that dictionary is generated and written during flush only when
1413
- // `ColumnFamilyOptions::compression` enables dictionary.
1478
+ // `ColumnFamilyOptions::compression` enables dictionary. Also verifies the
1479
+ // size of the dictionary is within expectations according to the limit on
1480
+ // buffering set by `CompressionOptions::max_dict_buffer_bytes`.
1414
1481
  const size_t kValueLen = 256;
1415
1482
  const size_t kKeysPerFile = 1 << 10;
1416
- const size_t kDictLen = 4 << 10;
1483
+ const size_t kDictLen = 16 << 10;
1484
+ const size_t kBlockLen = 4 << 10;
1417
1485
 
1418
1486
  Options options = CurrentOptions();
1419
1487
  if (bottommost_) {
1420
1488
  options.bottommost_compression = compression_type_;
1421
1489
  options.bottommost_compression_opts.enabled = true;
1422
1490
  options.bottommost_compression_opts.max_dict_bytes = kDictLen;
1491
+ options.bottommost_compression_opts.max_dict_buffer_bytes = kBlockLen;
1423
1492
  } else {
1424
1493
  options.compression = compression_type_;
1425
1494
  options.compression_opts.max_dict_bytes = kDictLen;
1495
+ options.compression_opts.max_dict_buffer_bytes = kBlockLen;
1426
1496
  }
1427
- options.memtable_factory.reset(new SpecialSkipListFactory(kKeysPerFile));
1497
+ options.memtable_factory.reset(test::NewSpecialSkipListFactory(kKeysPerFile));
1428
1498
  options.statistics = CreateDBStatistics();
1429
1499
  BlockBasedTableOptions bbto;
1500
+ bbto.block_size = kBlockLen;
1430
1501
  bbto.cache_index_and_filter_blocks = true;
1431
1502
  options.table_factory.reset(NewBlockBasedTableFactory(bbto));
1432
1503
  Reopen(options);
1433
1504
 
1434
- uint64_t prev_compression_dict_misses =
1435
- TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_MISS);
1436
1505
  Random rnd(301);
1437
1506
  for (size_t i = 0; i <= kKeysPerFile; ++i) {
1438
1507
  ASSERT_OK(Put(Key(static_cast<int>(i)), rnd.RandomString(kValueLen)));
1439
1508
  }
1440
1509
  ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable());
1441
1510
 
1442
- // If there's a compression dictionary, it should have been loaded when the
1443
- // flush finished, incurring a cache miss.
1444
- uint64_t expected_compression_dict_misses;
1511
+ // We can use `BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT` to detect whether a
1512
+ // compression dictionary exists since dictionaries would be preloaded when
1513
+ // the flush finishes.
1445
1514
  if (bottommost_) {
1446
- expected_compression_dict_misses = prev_compression_dict_misses;
1515
+ // Flush is never considered bottommost. This should change in the future
1516
+ // since flushed files may have nothing underneath them, like the one in
1517
+ // this test case.
1518
+ ASSERT_EQ(
1519
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1520
+ 0);
1447
1521
  } else {
1448
- expected_compression_dict_misses = prev_compression_dict_misses + 1;
1522
+ ASSERT_GT(
1523
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1524
+ 0);
1525
+ // TODO(ajkr): fix the below assertion to work with ZSTD. The expectation on
1526
+ // number of bytes needs to be adjusted in case the cached block is in
1527
+ // ZSTD's digested dictionary format.
1528
+ if (compression_type_ != kZSTD &&
1529
+ compression_type_ != kZSTDNotFinalCompression) {
1530
+ // Although we limited buffering to `kBlockLen`, there may be up to two
1531
+ // blocks of data included in the dictionary since we only check limit
1532
+ // after each block is built.
1533
+ ASSERT_LE(TestGetTickerCount(options,
1534
+ BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1535
+ 2 * kBlockLen);
1536
+ }
1449
1537
  }
1450
- ASSERT_EQ(expected_compression_dict_misses,
1451
- TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_MISS));
1452
1538
  }
1453
1539
 
1454
1540
  TEST_P(PresetCompressionDictTest, CompactNonBottommost) {
1455
1541
  // Verifies that dictionary is generated and written during compaction to
1456
1542
  // non-bottommost level only when `ColumnFamilyOptions::compression` enables
1457
- // dictionary.
1543
+ // dictionary. Also verifies the size of the dictionary is within expectations
1544
+ // according to the limit on buffering set by
1545
+ // `CompressionOptions::max_dict_buffer_bytes`.
1458
1546
  const size_t kValueLen = 256;
1459
1547
  const size_t kKeysPerFile = 1 << 10;
1460
- const size_t kDictLen = 4 << 10;
1548
+ const size_t kDictLen = 16 << 10;
1549
+ const size_t kBlockLen = 4 << 10;
1461
1550
 
1462
1551
  Options options = CurrentOptions();
1463
1552
  if (bottommost_) {
1464
1553
  options.bottommost_compression = compression_type_;
1465
1554
  options.bottommost_compression_opts.enabled = true;
1466
1555
  options.bottommost_compression_opts.max_dict_bytes = kDictLen;
1556
+ options.bottommost_compression_opts.max_dict_buffer_bytes = kBlockLen;
1467
1557
  } else {
1468
1558
  options.compression = compression_type_;
1469
1559
  options.compression_opts.max_dict_bytes = kDictLen;
1560
+ options.compression_opts.max_dict_buffer_bytes = kBlockLen;
1470
1561
  }
1471
1562
  options.disable_auto_compactions = true;
1472
1563
  options.statistics = CreateDBStatistics();
1473
1564
  BlockBasedTableOptions bbto;
1565
+ bbto.block_size = kBlockLen;
1474
1566
  bbto.cache_index_and_filter_blocks = true;
1475
1567
  options.table_factory.reset(NewBlockBasedTableFactory(bbto));
1476
1568
  Reopen(options);
@@ -1492,8 +1584,8 @@ TEST_P(PresetCompressionDictTest, CompactNonBottommost) {
1492
1584
  ASSERT_EQ("2,0,1", FilesPerLevel(0));
1493
1585
  #endif // ROCKSDB_LITE
1494
1586
 
1495
- uint64_t prev_compression_dict_misses =
1496
- TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_MISS);
1587
+ uint64_t prev_compression_dict_bytes_inserted =
1588
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT);
1497
1589
  // This L0->L1 compaction merges the two L0 files into L1. The produced L1
1498
1590
  // file is not bottommost due to the existing L2 file covering the same key-
1499
1591
  // range.
@@ -1501,38 +1593,58 @@ TEST_P(PresetCompressionDictTest, CompactNonBottommost) {
1501
1593
  #ifndef ROCKSDB_LITE
1502
1594
  ASSERT_EQ("0,1,1", FilesPerLevel(0));
1503
1595
  #endif // ROCKSDB_LITE
1504
- // If there's a compression dictionary, it should have been loaded when the
1505
- // compaction finished, incurring a cache miss.
1506
- uint64_t expected_compression_dict_misses;
1596
+ // We can use `BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT` to detect whether a
1597
+ // compression dictionary exists since dictionaries would be preloaded when
1598
+ // the compaction finishes.
1507
1599
  if (bottommost_) {
1508
- expected_compression_dict_misses = prev_compression_dict_misses;
1600
+ ASSERT_EQ(
1601
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1602
+ prev_compression_dict_bytes_inserted);
1509
1603
  } else {
1510
- expected_compression_dict_misses = prev_compression_dict_misses + 1;
1604
+ ASSERT_GT(
1605
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1606
+ prev_compression_dict_bytes_inserted);
1607
+ // TODO(ajkr): fix the below assertion to work with ZSTD. The expectation on
1608
+ // number of bytes needs to be adjusted in case the cached block is in
1609
+ // ZSTD's digested dictionary format.
1610
+ if (compression_type_ != kZSTD &&
1611
+ compression_type_ != kZSTDNotFinalCompression) {
1612
+ // Although we limited buffering to `kBlockLen`, there may be up to two
1613
+ // blocks of data included in the dictionary since we only check limit
1614
+ // after each block is built.
1615
+ ASSERT_LE(TestGetTickerCount(options,
1616
+ BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1617
+ prev_compression_dict_bytes_inserted + 2 * kBlockLen);
1618
+ }
1511
1619
  }
1512
- ASSERT_EQ(expected_compression_dict_misses,
1513
- TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_MISS));
1514
1620
  }
1515
1621
 
1516
1622
  TEST_P(PresetCompressionDictTest, CompactBottommost) {
1517
1623
  // Verifies that dictionary is generated and written during compaction to
1518
1624
  // non-bottommost level only when either `ColumnFamilyOptions::compression` or
1519
- // `ColumnFamilyOptions::bottommost_compression` enables dictionary.
1625
+ // `ColumnFamilyOptions::bottommost_compression` enables dictionary. Also
1626
+ // verifies the size of the dictionary is within expectations according to the
1627
+ // limit on buffering set by `CompressionOptions::max_dict_buffer_bytes`.
1520
1628
  const size_t kValueLen = 256;
1521
1629
  const size_t kKeysPerFile = 1 << 10;
1522
- const size_t kDictLen = 4 << 10;
1630
+ const size_t kDictLen = 16 << 10;
1631
+ const size_t kBlockLen = 4 << 10;
1523
1632
 
1524
1633
  Options options = CurrentOptions();
1525
1634
  if (bottommost_) {
1526
1635
  options.bottommost_compression = compression_type_;
1527
1636
  options.bottommost_compression_opts.enabled = true;
1528
1637
  options.bottommost_compression_opts.max_dict_bytes = kDictLen;
1638
+ options.bottommost_compression_opts.max_dict_buffer_bytes = kBlockLen;
1529
1639
  } else {
1530
1640
  options.compression = compression_type_;
1531
1641
  options.compression_opts.max_dict_bytes = kDictLen;
1642
+ options.compression_opts.max_dict_buffer_bytes = kBlockLen;
1532
1643
  }
1533
1644
  options.disable_auto_compactions = true;
1534
1645
  options.statistics = CreateDBStatistics();
1535
1646
  BlockBasedTableOptions bbto;
1647
+ bbto.block_size = kBlockLen;
1536
1648
  bbto.cache_index_and_filter_blocks = true;
1537
1649
  options.table_factory.reset(NewBlockBasedTableFactory(bbto));
1538
1650
  Reopen(options);
@@ -1548,17 +1660,28 @@ TEST_P(PresetCompressionDictTest, CompactBottommost) {
1548
1660
  ASSERT_EQ("2", FilesPerLevel(0));
1549
1661
  #endif // ROCKSDB_LITE
1550
1662
 
1551
- uint64_t prev_compression_dict_misses =
1552
- TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_MISS);
1663
+ uint64_t prev_compression_dict_bytes_inserted =
1664
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT);
1553
1665
  CompactRangeOptions cro;
1554
1666
  ASSERT_OK(db_->CompactRange(cro, nullptr, nullptr));
1555
1667
  #ifndef ROCKSDB_LITE
1556
1668
  ASSERT_EQ("0,1", FilesPerLevel(0));
1557
1669
  #endif // ROCKSDB_LITE
1558
- // If there's a compression dictionary, it should have been loaded when the
1559
- // compaction finished, incurring a cache miss.
1560
- ASSERT_EQ(prev_compression_dict_misses + 1,
1561
- TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_MISS));
1670
+ ASSERT_GT(
1671
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1672
+ prev_compression_dict_bytes_inserted);
1673
+ // TODO(ajkr): fix the below assertion to work with ZSTD. The expectation on
1674
+ // number of bytes needs to be adjusted in case the cached block is in ZSTD's
1675
+ // digested dictionary format.
1676
+ if (compression_type_ != kZSTD &&
1677
+ compression_type_ != kZSTDNotFinalCompression) {
1678
+ // Although we limited buffering to `kBlockLen`, there may be up to two
1679
+ // blocks of data included in the dictionary since we only check limit after
1680
+ // each block is built.
1681
+ ASSERT_LE(
1682
+ TestGetTickerCount(options, BLOCK_CACHE_COMPRESSION_DICT_BYTES_INSERT),
1683
+ prev_compression_dict_bytes_inserted + 2 * kBlockLen);
1684
+ }
1562
1685
  }
1563
1686
 
1564
1687
  class CompactionCompressionListener : public EventListener {
@@ -1571,9 +1694,9 @@ class CompactionCompressionListener : public EventListener {
1571
1694
  int bottommost_level = 0;
1572
1695
  for (int level = 0; level < db->NumberLevels(); level++) {
1573
1696
  std::string files_at_level;
1574
- ASSERT_TRUE(
1575
- db->GetProperty("rocksdb.num-files-at-level" + NumberToString(level),
1576
- &files_at_level));
1697
+ ASSERT_TRUE(db->GetProperty(
1698
+ "rocksdb.num-files-at-level" + ROCKSDB_NAMESPACE::ToString(level),
1699
+ &files_at_level));
1577
1700
  if (files_at_level != "0") {
1578
1701
  bottommost_level = level;
1579
1702
  }
@@ -1802,7 +1925,7 @@ TEST_F(DBTest2, CompressionOptions) {
1802
1925
  ASSERT_OK(Put(key, value));
1803
1926
  }
1804
1927
  ASSERT_OK(Flush());
1805
- dbfull()->TEST_WaitForCompact();
1928
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
1806
1929
  }
1807
1930
 
1808
1931
  // Make sure that we wrote enough to check all 7 levels
@@ -1817,6 +1940,7 @@ TEST_F(DBTest2, CompressionOptions) {
1817
1940
  ASSERT_EQ(key_value_written[key], value);
1818
1941
  key_value_written.erase(key);
1819
1942
  }
1943
+ ASSERT_OK(db_iter->status());
1820
1944
  ASSERT_EQ(0, key_value_written.size());
1821
1945
  }
1822
1946
  }
@@ -1898,7 +2022,7 @@ TEST_F(DBTest2, CompactionStall) {
1898
2022
  // Hold NotifyOnCompactionCompleted in the unlock mutex section
1899
2023
  TEST_SYNC_POINT("DBTest2::CompactionStall:3");
1900
2024
 
1901
- dbfull()->TEST_WaitForCompact();
2025
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
1902
2026
  ASSERT_LT(NumTableFilesAtLevel(0),
1903
2027
  options.level0_file_num_compaction_trigger);
1904
2028
  ASSERT_GT(listener->compacted_files_cnt_.load(),
@@ -1919,8 +2043,8 @@ TEST_F(DBTest2, FirstSnapshotTest) {
1919
2043
  // This snapshot will have sequence number 0 what is expected behaviour.
1920
2044
  const Snapshot* s1 = db_->GetSnapshot();
1921
2045
 
1922
- Put(1, "k1", std::string(100000, 'x')); // Fill memtable
1923
- Put(1, "k2", std::string(100000, 'y')); // Trigger flush
2046
+ ASSERT_OK(Put(1, "k1", std::string(100000, 'x'))); // Fill memtable
2047
+ ASSERT_OK(Put(1, "k2", std::string(100000, 'y'))); // Trigger flush
1924
2048
 
1925
2049
  db_->ReleaseSnapshot(s1);
1926
2050
  }
@@ -1933,17 +2057,17 @@ TEST_F(DBTest2, DuplicateSnapshot) {
1933
2057
  DBImpl* dbi = static_cast_with_check<DBImpl>(db_);
1934
2058
  SequenceNumber oldest_ww_snap, first_ww_snap;
1935
2059
 
1936
- Put("k", "v"); // inc seq
2060
+ ASSERT_OK(Put("k", "v")); // inc seq
1937
2061
  snapshots.push_back(db_->GetSnapshot());
1938
2062
  snapshots.push_back(db_->GetSnapshot());
1939
- Put("k", "v"); // inc seq
2063
+ ASSERT_OK(Put("k", "v")); // inc seq
1940
2064
  snapshots.push_back(db_->GetSnapshot());
1941
2065
  snapshots.push_back(dbi->GetSnapshotForWriteConflictBoundary());
1942
2066
  first_ww_snap = snapshots.back()->GetSequenceNumber();
1943
- Put("k", "v"); // inc seq
2067
+ ASSERT_OK(Put("k", "v")); // inc seq
1944
2068
  snapshots.push_back(dbi->GetSnapshotForWriteConflictBoundary());
1945
2069
  snapshots.push_back(db_->GetSnapshot());
1946
- Put("k", "v"); // inc seq
2070
+ ASSERT_OK(Put("k", "v")); // inc seq
1947
2071
  snapshots.push_back(db_->GetSnapshot());
1948
2072
 
1949
2073
  {
@@ -1964,7 +2088,7 @@ class PinL0IndexAndFilterBlocksTest
1964
2088
  public testing::WithParamInterface<std::tuple<bool, bool>> {
1965
2089
  public:
1966
2090
  PinL0IndexAndFilterBlocksTest()
1967
- : DBTestBase("/db_pin_l0_index_bloom_test", /*env_do_fsync=*/true) {}
2091
+ : DBTestBase("db_pin_l0_index_bloom_test", /*env_do_fsync=*/true) {}
1968
2092
  void SetUp() override {
1969
2093
  infinite_max_files_ = std::get<0>(GetParam());
1970
2094
  disallow_preload_ = std::get<1>(GetParam());
@@ -1983,19 +2107,19 @@ class PinL0IndexAndFilterBlocksTest
1983
2107
  options->table_factory.reset(NewBlockBasedTableFactory(table_options));
1984
2108
  CreateAndReopenWithCF({"pikachu"}, *options);
1985
2109
 
1986
- Put(1, "a", "begin");
1987
- Put(1, "z", "end");
2110
+ ASSERT_OK(Put(1, "a", "begin"));
2111
+ ASSERT_OK(Put(1, "z", "end"));
1988
2112
  ASSERT_OK(Flush(1));
1989
2113
  // move this table to L1
1990
- dbfull()->TEST_CompactRange(0, nullptr, nullptr, handles_[1]);
2114
+ ASSERT_OK(dbfull()->TEST_CompactRange(0, nullptr, nullptr, handles_[1]));
1991
2115
 
1992
2116
  // reset block cache
1993
2117
  table_options.block_cache = NewLRUCache(64 * 1024);
1994
2118
  options->table_factory.reset(NewBlockBasedTableFactory(table_options));
1995
2119
  TryReopenWithColumnFamilies({"default", "pikachu"}, *options);
1996
2120
  // create new table at L0
1997
- Put(1, "a2", "begin2");
1998
- Put(1, "z2", "end2");
2121
+ ASSERT_OK(Put(1, "a2", "begin2"));
2122
+ ASSERT_OK(Put(1, "z2", "end2"));
1999
2123
  ASSERT_OK(Flush(1));
2000
2124
 
2001
2125
  if (close_afterwards) {
@@ -2039,7 +2163,7 @@ TEST_P(PinL0IndexAndFilterBlocksTest,
2039
2163
 
2040
2164
  std::string value;
2041
2165
  // Miss and hit count should remain the same, they're all pinned.
2042
- db_->KeyMayExist(ReadOptions(), handles_[1], "key", &value);
2166
+ ASSERT_TRUE(db_->KeyMayExist(ReadOptions(), handles_[1], "key", &value));
2043
2167
  ASSERT_EQ(1, TestGetTickerCount(options, BLOCK_CACHE_FILTER_MISS));
2044
2168
  ASSERT_EQ(0, TestGetTickerCount(options, BLOCK_CACHE_FILTER_HIT));
2045
2169
  ASSERT_EQ(1, TestGetTickerCount(options, BLOCK_CACHE_INDEX_MISS));
@@ -2167,7 +2291,7 @@ TEST_P(PinL0IndexAndFilterBlocksTest, DisablePrefetchingNonL0IndexAndFilter) {
2167
2291
  // cache read for both of index and filter. If prefetch doesn't explicitly
2168
2292
  // happen, it will happen when verifying the file.
2169
2293
  Compact(1, "a", "zzzzz");
2170
- dbfull()->TEST_WaitForCompact();
2294
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
2171
2295
 
2172
2296
  if (!disallow_preload_) {
2173
2297
  ASSERT_EQ(fm + 3, TestGetTickerCount(options, BLOCK_CACHE_FILTER_MISS));
@@ -2205,8 +2329,8 @@ INSTANTIATE_TEST_CASE_P(PinL0IndexAndFilterBlocksTest,
2205
2329
  #ifndef ROCKSDB_LITE
2206
2330
  TEST_F(DBTest2, MaxCompactionBytesTest) {
2207
2331
  Options options = CurrentOptions();
2208
- options.memtable_factory.reset(
2209
- new SpecialSkipListFactory(DBTestBase::kNumKeysByGenerateNewRandomFile));
2332
+ options.memtable_factory.reset(test::NewSpecialSkipListFactory(
2333
+ DBTestBase::kNumKeysByGenerateNewRandomFile));
2210
2334
  options.compaction_style = kCompactionStyleLevel;
2211
2335
  options.write_buffer_size = 200 << 10;
2212
2336
  options.arena_block_size = 4 << 10;
@@ -2238,10 +2362,10 @@ TEST_F(DBTest2, MaxCompactionBytesTest) {
2238
2362
  GenerateNewRandomFile(&rnd);
2239
2363
  // Add three more small files that overlap with the previous file
2240
2364
  for (int i = 0; i < 3; i++) {
2241
- Put("a", "z");
2365
+ ASSERT_OK(Put("a", "z"));
2242
2366
  ASSERT_OK(Flush());
2243
2367
  }
2244
- dbfull()->TEST_WaitForCompact();
2368
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
2245
2369
 
2246
2370
  // Output files to L1 are cut to three pieces, according to
2247
2371
  // options.max_compaction_bytes
@@ -2402,6 +2526,7 @@ TEST_F(DBTest2, TestPerfContextIterCpuTime) {
2402
2526
  ASSERT_EQ(0, get_perf_context()->iter_next_cpu_nanos);
2403
2527
  iter->Prev();
2404
2528
  ASSERT_TRUE(iter->Valid());
2529
+ ASSERT_OK(iter->status());
2405
2530
  ASSERT_EQ("v0", iter->value().ToString());
2406
2531
  ASSERT_EQ(0, get_perf_context()->iter_prev_cpu_nanos);
2407
2532
  ASSERT_EQ(0, env_->now_cpu_count_.load());
@@ -2438,6 +2563,7 @@ TEST_F(DBTest2, TestPerfContextIterCpuTime) {
2438
2563
  ASSERT_LT(get_perf_context()->iter_next_cpu_nanos, kDummyAddonNanos);
2439
2564
  iter->Prev();
2440
2565
  ASSERT_TRUE(iter->Valid());
2566
+ ASSERT_OK(iter->status());
2441
2567
  ASSERT_EQ("v0", iter->value().ToString());
2442
2568
  ASSERT_GT(get_perf_context()->iter_prev_cpu_nanos, 0);
2443
2569
  ASSERT_LT(get_perf_context()->iter_prev_cpu_nanos, kDummyAddonNanos);
@@ -2635,6 +2761,7 @@ TEST_F(DBTest2, ReadAmpBitmap) {
2635
2761
  for (iter->SeekToFirst(); iter->Valid(); iter->Next()) {
2636
2762
  ASSERT_EQ(iter->value().ToString(), Get(iter->key().ToString()));
2637
2763
  }
2764
+ ASSERT_OK(iter->status());
2638
2765
  delete iter;
2639
2766
 
2640
2767
  // Read amp is on average 100% since we read all what we loaded in memory
@@ -2709,7 +2836,6 @@ TEST_F(DBTest2, ReadAmpBitmapLiveInCacheAfterDBClose) {
2709
2836
  Close();
2710
2837
  Reopen(options);
2711
2838
 
2712
- uint64_t total_useful_bytes = 0;
2713
2839
  std::set<int> read_keys;
2714
2840
  std::string value;
2715
2841
  // Iter1: Read half the DB, Read even keys
@@ -2720,8 +2846,6 @@ TEST_F(DBTest2, ReadAmpBitmapLiveInCacheAfterDBClose) {
2720
2846
 
2721
2847
  if (read_keys.find(i) == read_keys.end()) {
2722
2848
  auto internal_key = InternalKey(key, 0, ValueType::kTypeValue);
2723
- total_useful_bytes +=
2724
- GetEncodedEntrySize(internal_key.size(), value.size());
2725
2849
  read_keys.insert(i);
2726
2850
  }
2727
2851
  }
@@ -2748,8 +2872,6 @@ TEST_F(DBTest2, ReadAmpBitmapLiveInCacheAfterDBClose) {
2748
2872
 
2749
2873
  if (read_keys.find(i) == read_keys.end()) {
2750
2874
  auto internal_key = InternalKey(key, 0, ValueType::kTypeValue);
2751
- total_useful_bytes +=
2752
- GetEncodedEntrySize(internal_key.size(), value.size());
2753
2875
  read_keys.insert(i);
2754
2876
  }
2755
2877
  }
@@ -2954,10 +3076,12 @@ TEST_F(DBTest2, PausingManualCompaction1) {
2954
3076
  }
2955
3077
 
2956
3078
  // OK, now trigger a manual compaction
2957
- dbfull()->CompactRange(CompactRangeOptions(), nullptr, nullptr);
3079
+ ASSERT_TRUE(dbfull()
3080
+ ->CompactRange(CompactRangeOptions(), nullptr, nullptr)
3081
+ .IsManualCompactionPaused());
2958
3082
 
2959
3083
  // Wait for compactions to get scheduled and stopped
2960
- dbfull()->TEST_WaitForCompact(true);
3084
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
2961
3085
 
2962
3086
  // Get file names after compaction is stopped
2963
3087
  files_meta.clear();
@@ -2972,10 +3096,12 @@ TEST_F(DBTest2, PausingManualCompaction1) {
2972
3096
 
2973
3097
  manual_compactions_paused = 0;
2974
3098
  // Now make sure CompactFiles also not run
2975
- dbfull()->CompactFiles(ROCKSDB_NAMESPACE::CompactionOptions(),
2976
- files_before_compact, 0);
3099
+ ASSERT_TRUE(dbfull()
3100
+ ->CompactFiles(ROCKSDB_NAMESPACE::CompactionOptions(),
3101
+ files_before_compact, 0)
3102
+ .IsManualCompactionPaused());
2977
3103
  // Wait for manual compaction to get scheduled and finish
2978
- dbfull()->TEST_WaitForCompact(true);
3104
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
2979
3105
 
2980
3106
  files_meta.clear();
2981
3107
  files_after_compact.clear();
@@ -3028,7 +3154,7 @@ TEST_F(DBTest2, PausingManualCompaction3) {
3028
3154
  for (int k = 0; k < 1000; k++) {
3029
3155
  ASSERT_OK(Put(Key(k + j * 1000), rnd.RandomString(50)));
3030
3156
  }
3031
- Flush();
3157
+ ASSERT_OK(Flush());
3032
3158
  }
3033
3159
 
3034
3160
  for (int l = 1; l < options.num_levels - i; l++) {
@@ -3049,8 +3175,10 @@ TEST_F(DBTest2, PausingManualCompaction3) {
3049
3175
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3050
3176
 
3051
3177
  dbfull()->DisableManualCompaction();
3052
- dbfull()->CompactRange(compact_options, nullptr, nullptr);
3053
- dbfull()->TEST_WaitForCompact(true);
3178
+ ASSERT_TRUE(dbfull()
3179
+ ->CompactRange(compact_options, nullptr, nullptr)
3180
+ .IsManualCompactionPaused());
3181
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3054
3182
  // As manual compaction disabled, not even reach sync point
3055
3183
  ASSERT_EQ(run_manual_compactions, 0);
3056
3184
  #ifndef ROCKSDB_LITE
@@ -3060,8 +3188,8 @@ TEST_F(DBTest2, PausingManualCompaction3) {
3060
3188
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3061
3189
  "CompactionJob::Run():PausingManualCompaction:1");
3062
3190
  dbfull()->EnableManualCompaction();
3063
- dbfull()->CompactRange(compact_options, nullptr, nullptr);
3064
- dbfull()->TEST_WaitForCompact(true);
3191
+ ASSERT_OK(dbfull()->CompactRange(compact_options, nullptr, nullptr));
3192
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3065
3193
  #ifndef ROCKSDB_LITE
3066
3194
  ASSERT_EQ("0,0,0,0,0,0,2", FilesPerLevel());
3067
3195
  #endif // !ROCKSDB_LITE
@@ -3082,7 +3210,7 @@ TEST_F(DBTest2, PausingManualCompaction4) {
3082
3210
  for (int k = 0; k < 1000; k++) {
3083
3211
  ASSERT_OK(Put(Key(k + j * 1000), rnd.RandomString(50)));
3084
3212
  }
3085
- Flush();
3213
+ ASSERT_OK(Flush());
3086
3214
  }
3087
3215
 
3088
3216
  for (int l = 1; l < options.num_levels - i; l++) {
@@ -3106,8 +3234,10 @@ TEST_F(DBTest2, PausingManualCompaction4) {
3106
3234
  });
3107
3235
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3108
3236
 
3109
- dbfull()->CompactRange(compact_options, nullptr, nullptr);
3110
- dbfull()->TEST_WaitForCompact(true);
3237
+ ASSERT_TRUE(dbfull()
3238
+ ->CompactRange(compact_options, nullptr, nullptr)
3239
+ .IsManualCompactionPaused());
3240
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3111
3241
  ASSERT_EQ(run_manual_compactions, 1);
3112
3242
  #ifndef ROCKSDB_LITE
3113
3243
  ASSERT_EQ("2,3,4,5,6,7,8", FilesPerLevel());
@@ -3116,8 +3246,188 @@ TEST_F(DBTest2, PausingManualCompaction4) {
3116
3246
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3117
3247
  "CompactionJob::Run():PausingManualCompaction:2");
3118
3248
  dbfull()->EnableManualCompaction();
3119
- dbfull()->CompactRange(compact_options, nullptr, nullptr);
3120
- dbfull()->TEST_WaitForCompact(true);
3249
+ ASSERT_OK(dbfull()->CompactRange(compact_options, nullptr, nullptr));
3250
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3251
+ #ifndef ROCKSDB_LITE
3252
+ ASSERT_EQ("0,0,0,0,0,0,2", FilesPerLevel());
3253
+ #endif // !ROCKSDB_LITE
3254
+
3255
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3256
+ }
3257
+
3258
+ TEST_F(DBTest2, CancelManualCompaction1) {
3259
+ CompactRangeOptions compact_options;
3260
+ auto canceledPtr =
3261
+ std::unique_ptr<std::atomic<bool>>(new std::atomic<bool>{true});
3262
+ compact_options.canceled = canceledPtr.get();
3263
+
3264
+ Options options = CurrentOptions();
3265
+ options.disable_auto_compactions = true;
3266
+ options.num_levels = 7;
3267
+
3268
+ Random rnd(301);
3269
+ auto generate_files = [&]() {
3270
+ for (int i = 0; i < options.num_levels; i++) {
3271
+ for (int j = 0; j < options.num_levels - i + 1; j++) {
3272
+ for (int k = 0; k < 1000; k++) {
3273
+ ASSERT_OK(Put(Key(k + j * 1000), rnd.RandomString(50)));
3274
+ }
3275
+ ASSERT_OK(Flush());
3276
+ }
3277
+
3278
+ for (int l = 1; l < options.num_levels - i; l++) {
3279
+ MoveFilesToLevel(l);
3280
+ }
3281
+ }
3282
+ };
3283
+
3284
+ DestroyAndReopen(options);
3285
+ generate_files();
3286
+ #ifndef ROCKSDB_LITE
3287
+ ASSERT_EQ("2,3,4,5,6,7,8", FilesPerLevel());
3288
+ #endif // !ROCKSDB_LITE
3289
+
3290
+ int run_manual_compactions = 0;
3291
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3292
+ "CompactionJob::Run():PausingManualCompaction:1",
3293
+ [&](void* /*arg*/) { run_manual_compactions++; });
3294
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3295
+
3296
+ // Setup a callback to disable compactions after a couple of levels are
3297
+ // compacted
3298
+ int compactions_run = 0;
3299
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3300
+ "DBImpl::RunManualCompaction()::1",
3301
+ [&](void* /*arg*/) { ++compactions_run; });
3302
+
3303
+ ASSERT_TRUE(dbfull()
3304
+ ->CompactRange(compact_options, nullptr, nullptr)
3305
+ .IsManualCompactionPaused());
3306
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3307
+
3308
+ // Since compactions are disabled, we shouldn't start compacting.
3309
+ // E.g. we should call the compaction function exactly one time.
3310
+ ASSERT_EQ(compactions_run, 0);
3311
+ ASSERT_EQ(run_manual_compactions, 0);
3312
+ #ifndef ROCKSDB_LITE
3313
+ ASSERT_EQ("2,3,4,5,6,7,8", FilesPerLevel());
3314
+ #endif // !ROCKSDB_LITE
3315
+
3316
+ compactions_run = 0;
3317
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3318
+ "DBImpl::RunManualCompaction()::1");
3319
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3320
+ "DBImpl::RunManualCompaction()::1", [&](void* /*arg*/) {
3321
+ ++compactions_run;
3322
+ // After 3 compactions disable
3323
+ if (compactions_run == 3) {
3324
+ compact_options.canceled->store(true, std::memory_order_release);
3325
+ }
3326
+ });
3327
+
3328
+ compact_options.canceled->store(false, std::memory_order_release);
3329
+ ASSERT_TRUE(dbfull()
3330
+ ->CompactRange(compact_options, nullptr, nullptr)
3331
+ .IsManualCompactionPaused());
3332
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3333
+
3334
+ ASSERT_EQ(compactions_run, 3);
3335
+
3336
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3337
+ "DBImpl::RunManualCompaction()::1");
3338
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3339
+ "CompactionJob::Run():PausingManualCompaction:1");
3340
+
3341
+ // Compactions should work again if we re-enable them..
3342
+ compact_options.canceled->store(false, std::memory_order_relaxed);
3343
+ ASSERT_OK(dbfull()->CompactRange(compact_options, nullptr, nullptr));
3344
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3345
+ #ifndef ROCKSDB_LITE
3346
+ ASSERT_EQ("0,0,0,0,0,0,2", FilesPerLevel());
3347
+ #endif // !ROCKSDB_LITE
3348
+
3349
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3350
+ }
3351
+
3352
+ TEST_F(DBTest2, CancelManualCompaction2) {
3353
+ CompactRangeOptions compact_options;
3354
+ auto canceledPtr =
3355
+ std::unique_ptr<std::atomic<bool>>(new std::atomic<bool>{true});
3356
+ compact_options.canceled = canceledPtr.get();
3357
+ compact_options.max_subcompactions = 1;
3358
+
3359
+ Options options = CurrentOptions();
3360
+ options.disable_auto_compactions = true;
3361
+ options.num_levels = 7;
3362
+
3363
+ Random rnd(301);
3364
+ auto generate_files = [&]() {
3365
+ for (int i = 0; i < options.num_levels; i++) {
3366
+ for (int j = 0; j < options.num_levels - i + 1; j++) {
3367
+ for (int k = 0; k < 1000; k++) {
3368
+ ASSERT_OK(Put(Key(k + j * 1000), rnd.RandomString(50)));
3369
+ }
3370
+ ASSERT_OK(Flush());
3371
+ }
3372
+
3373
+ for (int l = 1; l < options.num_levels - i; l++) {
3374
+ MoveFilesToLevel(l);
3375
+ }
3376
+ }
3377
+ };
3378
+
3379
+ DestroyAndReopen(options);
3380
+ generate_files();
3381
+ #ifndef ROCKSDB_LITE
3382
+ ASSERT_EQ("2,3,4,5,6,7,8", FilesPerLevel());
3383
+ #endif // !ROCKSDB_LITE
3384
+
3385
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3386
+
3387
+ int compactions_run = 0;
3388
+ std::atomic<int> kv_compactions{0};
3389
+ int compactions_stopped_at = 0;
3390
+ int kv_compactions_stopped_at = 0;
3391
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3392
+ "DBImpl::RunManualCompaction()::1", [&](void* /*arg*/) {
3393
+ ++compactions_run;
3394
+ // After 3 compactions disable
3395
+ });
3396
+
3397
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3398
+ "CompactionIterator:ProcessKV", [&](void* /*arg*/) {
3399
+ int kv_compactions_run =
3400
+ kv_compactions.fetch_add(1, std::memory_order_release);
3401
+ if (kv_compactions_run == 5) {
3402
+ compact_options.canceled->store(true, std::memory_order_release);
3403
+ kv_compactions_stopped_at = kv_compactions_run;
3404
+ compactions_stopped_at = compactions_run;
3405
+ }
3406
+ });
3407
+
3408
+ compact_options.canceled->store(false, std::memory_order_release);
3409
+ ASSERT_TRUE(dbfull()
3410
+ ->CompactRange(compact_options, nullptr, nullptr)
3411
+ .IsManualCompactionPaused());
3412
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3413
+
3414
+ // NOTE: as we set compact_options.max_subcompacitons = 1, and store true to
3415
+ // the canceled variable from the single compacting thread (via callback),
3416
+ // this value is deterministically kv_compactions_stopped_at + 1.
3417
+ ASSERT_EQ(kv_compactions, kv_compactions_stopped_at + 1);
3418
+ ASSERT_EQ(compactions_run, compactions_stopped_at);
3419
+
3420
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3421
+ "CompactionIterator::ProcessKV");
3422
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3423
+ "DBImpl::RunManualCompaction()::1");
3424
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3425
+ "CompactionJob::Run():PausingManualCompaction:1");
3426
+
3427
+ // Compactions should work again if we re-enable them..
3428
+ compact_options.canceled->store(false, std::memory_order_relaxed);
3429
+ ASSERT_OK(dbfull()->CompactRange(compact_options, nullptr, nullptr));
3430
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3121
3431
  #ifndef ROCKSDB_LITE
3122
3432
  ASSERT_EQ("0,0,0,0,0,0,2", FilesPerLevel());
3123
3433
  #endif // !ROCKSDB_LITE
@@ -3125,6 +3435,180 @@ TEST_F(DBTest2, PausingManualCompaction4) {
3125
3435
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3126
3436
  }
3127
3437
 
3438
+ class CancelCompactionListener : public EventListener {
3439
+ public:
3440
+ CancelCompactionListener()
3441
+ : num_compaction_started_(0), num_compaction_ended_(0) {}
3442
+
3443
+ void OnCompactionBegin(DB* /*db*/, const CompactionJobInfo& ci) override {
3444
+ ASSERT_EQ(ci.cf_name, "default");
3445
+ ASSERT_EQ(ci.base_input_level, 0);
3446
+ num_compaction_started_++;
3447
+ }
3448
+
3449
+ void OnCompactionCompleted(DB* /*db*/, const CompactionJobInfo& ci) override {
3450
+ ASSERT_EQ(ci.cf_name, "default");
3451
+ ASSERT_EQ(ci.base_input_level, 0);
3452
+ ASSERT_EQ(ci.status.code(), code_);
3453
+ ASSERT_EQ(ci.status.subcode(), subcode_);
3454
+ num_compaction_ended_++;
3455
+ }
3456
+
3457
+ std::atomic<size_t> num_compaction_started_;
3458
+ std::atomic<size_t> num_compaction_ended_;
3459
+ Status::Code code_;
3460
+ Status::SubCode subcode_;
3461
+ };
3462
+
3463
+ TEST_F(DBTest2, CancelManualCompactionWithListener) {
3464
+ CompactRangeOptions compact_options;
3465
+ auto canceledPtr =
3466
+ std::unique_ptr<std::atomic<bool>>(new std::atomic<bool>{true});
3467
+ compact_options.canceled = canceledPtr.get();
3468
+ compact_options.max_subcompactions = 1;
3469
+
3470
+ Options options = CurrentOptions();
3471
+ options.disable_auto_compactions = true;
3472
+ CancelCompactionListener* listener = new CancelCompactionListener();
3473
+ options.listeners.emplace_back(listener);
3474
+
3475
+ DestroyAndReopen(options);
3476
+
3477
+ Random rnd(301);
3478
+ for (int i = 0; i < 10; i++) {
3479
+ for (int j = 0; j < 10; j++) {
3480
+ ASSERT_OK(Put(Key(i + j * 10), rnd.RandomString(50)));
3481
+ }
3482
+ ASSERT_OK(Flush());
3483
+ }
3484
+
3485
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3486
+
3487
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3488
+ "CompactionIterator:ProcessKV", [&](void* /*arg*/) {
3489
+ compact_options.canceled->store(true, std::memory_order_release);
3490
+ });
3491
+
3492
+ int running_compaction = 0;
3493
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3494
+ "CompactionJob::FinishCompactionOutputFile1",
3495
+ [&](void* /*arg*/) { running_compaction++; });
3496
+
3497
+ // Case I: 1 Notify begin compaction, 2 DisableManualCompaction, 3 Compaction
3498
+ // not run, 4 Notify compaction end.
3499
+ listener->code_ = Status::kIncomplete;
3500
+ listener->subcode_ = Status::SubCode::kManualCompactionPaused;
3501
+
3502
+ compact_options.canceled->store(false, std::memory_order_release);
3503
+ ASSERT_TRUE(dbfull()
3504
+ ->CompactRange(compact_options, nullptr, nullptr)
3505
+ .IsManualCompactionPaused());
3506
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3507
+
3508
+ ASSERT_GT(listener->num_compaction_started_, 0);
3509
+ ASSERT_EQ(listener->num_compaction_started_, listener->num_compaction_ended_);
3510
+ ASSERT_EQ(running_compaction, 0);
3511
+
3512
+ listener->num_compaction_started_ = 0;
3513
+ listener->num_compaction_ended_ = 0;
3514
+
3515
+ // Case II: 1 DisableManualCompaction, 2 Notify begin compaction (return
3516
+ // without notifying), 3 Notify compaction end (return without notifying).
3517
+ ASSERT_TRUE(dbfull()
3518
+ ->CompactRange(compact_options, nullptr, nullptr)
3519
+ .IsManualCompactionPaused());
3520
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3521
+
3522
+ ASSERT_EQ(listener->num_compaction_started_, 0);
3523
+ ASSERT_EQ(listener->num_compaction_started_, listener->num_compaction_ended_);
3524
+ ASSERT_EQ(running_compaction, 0);
3525
+
3526
+ // Case III: 1 Notify begin compaction, 2 Compaction in between
3527
+ // 3. DisableManualCompaction, , 4 Notify compaction end.
3528
+ // compact_options.canceled->store(false, std::memory_order_release);
3529
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearCallBack(
3530
+ "CompactionIterator:ProcessKV");
3531
+
3532
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3533
+ "CompactionJob::Run:BeforeVerify", [&](void* /*arg*/) {
3534
+ compact_options.canceled->store(true, std::memory_order_release);
3535
+ });
3536
+
3537
+ listener->code_ = Status::kOk;
3538
+ listener->subcode_ = Status::SubCode::kNone;
3539
+
3540
+ compact_options.canceled->store(false, std::memory_order_release);
3541
+ ASSERT_OK(dbfull()->CompactRange(compact_options, nullptr, nullptr));
3542
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
3543
+
3544
+ ASSERT_GT(listener->num_compaction_started_, 0);
3545
+ ASSERT_EQ(listener->num_compaction_started_, listener->num_compaction_ended_);
3546
+
3547
+ // Compaction job will succeed.
3548
+ ASSERT_GT(running_compaction, 0);
3549
+
3550
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearAllCallBacks();
3551
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3552
+ }
3553
+
3554
+ TEST_F(DBTest2, CompactionOnBottomPriorityWithListener) {
3555
+ int num_levels = 3;
3556
+ const int kNumFilesTrigger = 4;
3557
+
3558
+ Options options = CurrentOptions();
3559
+ env_->SetBackgroundThreads(0, Env::Priority::HIGH);
3560
+ env_->SetBackgroundThreads(0, Env::Priority::LOW);
3561
+ env_->SetBackgroundThreads(1, Env::Priority::BOTTOM);
3562
+ options.env = env_;
3563
+ options.compaction_style = kCompactionStyleUniversal;
3564
+ options.num_levels = num_levels;
3565
+ options.write_buffer_size = 100 << 10; // 100KB
3566
+ options.target_file_size_base = 32 << 10; // 32KB
3567
+ options.level0_file_num_compaction_trigger = kNumFilesTrigger;
3568
+ // Trigger compaction if size amplification exceeds 110%
3569
+ options.compaction_options_universal.max_size_amplification_percent = 110;
3570
+
3571
+ CancelCompactionListener* listener = new CancelCompactionListener();
3572
+ options.listeners.emplace_back(listener);
3573
+
3574
+ DestroyAndReopen(options);
3575
+
3576
+ int num_bottom_thread_compaction_scheduled = 0;
3577
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3578
+
3579
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3580
+ "DBImpl::BackgroundCompaction:ForwardToBottomPriPool",
3581
+ [&](void* /*arg*/) { num_bottom_thread_compaction_scheduled++; });
3582
+
3583
+ int num_compaction_jobs = 0;
3584
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->SetCallBack(
3585
+ "CompactionJob::Run():End",
3586
+ [&](void* /*arg*/) { num_compaction_jobs++; });
3587
+
3588
+ listener->code_ = Status::kOk;
3589
+ listener->subcode_ = Status::SubCode::kNone;
3590
+
3591
+ Random rnd(301);
3592
+ for (int i = 0; i < 1; ++i) {
3593
+ for (int num = 0; num < kNumFilesTrigger; num++) {
3594
+ int key_idx = 0;
3595
+ GenerateNewFile(&rnd, &key_idx, true /* no_wait */);
3596
+ // use no_wait above because that one waits for flush and compaction. We
3597
+ // don't want to wait for compaction because the full compaction is
3598
+ // intentionally blocked while more files are flushed.
3599
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable());
3600
+ }
3601
+ }
3602
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
3603
+ ASSERT_GT(num_bottom_thread_compaction_scheduled, 0);
3604
+ ASSERT_EQ(num_compaction_jobs, 1);
3605
+ ASSERT_GT(listener->num_compaction_started_, 0);
3606
+ ASSERT_EQ(listener->num_compaction_started_, listener->num_compaction_ended_);
3607
+
3608
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearAllCallBacks();
3609
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3610
+ }
3611
+
3128
3612
  TEST_F(DBTest2, OptimizeForPointLookup) {
3129
3613
  Options options = CurrentOptions();
3130
3614
  Close();
@@ -3133,7 +3617,7 @@ TEST_F(DBTest2, OptimizeForPointLookup) {
3133
3617
 
3134
3618
  ASSERT_OK(Put("foo", "v1"));
3135
3619
  ASSERT_EQ("v1", Get("foo"));
3136
- Flush();
3620
+ ASSERT_OK(Flush());
3137
3621
  ASSERT_EQ("v1", Get("foo"));
3138
3622
  }
3139
3623
 
@@ -3159,7 +3643,7 @@ TEST_F(DBTest2, OptimizeForSmallDB) {
3159
3643
  ASSERT_NE(0, cache->GetUsage());
3160
3644
 
3161
3645
  ASSERT_EQ("v1", Get("foo"));
3162
- Flush();
3646
+ ASSERT_OK(Flush());
3163
3647
 
3164
3648
  size_t prev_size = cache->GetUsage();
3165
3649
  // Remember block cache size, so that we can find that
@@ -3186,17 +3670,19 @@ TEST_F(DBTest2, IterRaceFlush1) {
3186
3670
  ROCKSDB_NAMESPACE::port::Thread t1([&] {
3187
3671
  TEST_SYNC_POINT("DBTest2::IterRaceFlush:1");
3188
3672
  ASSERT_OK(Put("foo", "v2"));
3189
- Flush();
3673
+ ASSERT_OK(Flush());
3190
3674
  TEST_SYNC_POINT("DBTest2::IterRaceFlush:2");
3191
3675
  });
3192
3676
 
3193
- // iterator is created after the first Put(), so it should see either
3194
- // "v1" or "v2".
3677
+ // iterator is created after the first Put(), and its snapshot sequence is
3678
+ // assigned after second Put(), so it must see v2.
3195
3679
  {
3196
3680
  std::unique_ptr<Iterator> it(db_->NewIterator(ReadOptions()));
3197
3681
  it->Seek("foo");
3198
3682
  ASSERT_TRUE(it->Valid());
3683
+ ASSERT_OK(it->status());
3199
3684
  ASSERT_EQ("foo", it->key().ToString());
3685
+ ASSERT_EQ("v2", it->value().ToString());
3200
3686
  }
3201
3687
 
3202
3688
  t1.join();
@@ -3215,17 +3701,19 @@ TEST_F(DBTest2, IterRaceFlush2) {
3215
3701
  ROCKSDB_NAMESPACE::port::Thread t1([&] {
3216
3702
  TEST_SYNC_POINT("DBTest2::IterRaceFlush2:1");
3217
3703
  ASSERT_OK(Put("foo", "v2"));
3218
- Flush();
3704
+ ASSERT_OK(Flush());
3219
3705
  TEST_SYNC_POINT("DBTest2::IterRaceFlush2:2");
3220
3706
  });
3221
3707
 
3222
- // iterator is created after the first Put(), so it should see either
3223
- // "v1" or "v2".
3708
+ // iterator is created after the first Put(), and its snapshot sequence is
3709
+ // assigned before second Put(), thus it must see v1.
3224
3710
  {
3225
3711
  std::unique_ptr<Iterator> it(db_->NewIterator(ReadOptions()));
3226
3712
  it->Seek("foo");
3227
3713
  ASSERT_TRUE(it->Valid());
3714
+ ASSERT_OK(it->status());
3228
3715
  ASSERT_EQ("foo", it->key().ToString());
3716
+ ASSERT_EQ("v1", it->value().ToString());
3229
3717
  }
3230
3718
 
3231
3719
  t1.join();
@@ -3244,18 +3732,21 @@ TEST_F(DBTest2, IterRefreshRaceFlush) {
3244
3732
  ROCKSDB_NAMESPACE::port::Thread t1([&] {
3245
3733
  TEST_SYNC_POINT("DBTest2::IterRefreshRaceFlush:1");
3246
3734
  ASSERT_OK(Put("foo", "v2"));
3247
- Flush();
3735
+ ASSERT_OK(Flush());
3248
3736
  TEST_SYNC_POINT("DBTest2::IterRefreshRaceFlush:2");
3249
3737
  });
3250
3738
 
3251
- // iterator is created after the first Put(), so it should see either
3252
- // "v1" or "v2".
3739
+ // iterator is refreshed after the first Put(), and its sequence number is
3740
+ // assigned after second Put(), thus it must see v2.
3253
3741
  {
3254
3742
  std::unique_ptr<Iterator> it(db_->NewIterator(ReadOptions()));
3255
- it->Refresh();
3743
+ ASSERT_OK(it->status());
3744
+ ASSERT_OK(it->Refresh());
3256
3745
  it->Seek("foo");
3257
3746
  ASSERT_TRUE(it->Valid());
3747
+ ASSERT_OK(it->status());
3258
3748
  ASSERT_EQ("foo", it->key().ToString());
3749
+ ASSERT_EQ("v2", it->value().ToString());
3259
3750
  }
3260
3751
 
3261
3752
  t1.join();
@@ -3274,7 +3765,7 @@ TEST_F(DBTest2, GetRaceFlush1) {
3274
3765
  ROCKSDB_NAMESPACE::port::Thread t1([&] {
3275
3766
  TEST_SYNC_POINT("DBTest2::GetRaceFlush:1");
3276
3767
  ASSERT_OK(Put("foo", "v2"));
3277
- Flush();
3768
+ ASSERT_OK(Flush());
3278
3769
  TEST_SYNC_POINT("DBTest2::GetRaceFlush:2");
3279
3770
  });
3280
3771
 
@@ -3297,7 +3788,7 @@ TEST_F(DBTest2, GetRaceFlush2) {
3297
3788
  port::Thread t1([&] {
3298
3789
  TEST_SYNC_POINT("DBTest2::GetRaceFlush:1");
3299
3790
  ASSERT_OK(Put("foo", "v2"));
3300
- Flush();
3791
+ ASSERT_OK(Flush());
3301
3792
  TEST_SYNC_POINT("DBTest2::GetRaceFlush:2");
3302
3793
  });
3303
3794
 
@@ -3370,6 +3861,7 @@ TEST_F(DBTest2, MemtableOnlyIterator) {
3370
3861
  ASSERT_EQ("second", value);
3371
3862
  // nothing should be returned using memtable-only iterator after flushing.
3372
3863
  it = db_->NewIterator(ropt, handles_[1]);
3864
+ ASSERT_OK(it->status());
3373
3865
  count = 0;
3374
3866
  for (it->SeekToFirst(); it->Valid(); it->Next()) {
3375
3867
  ASSERT_TRUE(it->Valid());
@@ -3377,11 +3869,13 @@ TEST_F(DBTest2, MemtableOnlyIterator) {
3377
3869
  }
3378
3870
  ASSERT_TRUE(!it->Valid());
3379
3871
  ASSERT_EQ(0, count);
3872
+ ASSERT_OK(it->status());
3380
3873
  delete it;
3381
3874
 
3382
3875
  // Add a key to memtable
3383
3876
  ASSERT_OK(Put(1, "foobar", "third"));
3384
3877
  it = db_->NewIterator(ropt, handles_[1]);
3878
+ ASSERT_OK(it->status());
3385
3879
  count = 0;
3386
3880
  for (it->SeekToFirst(); it->Valid(); it->Next()) {
3387
3881
  ASSERT_TRUE(it->Valid());
@@ -3391,6 +3885,7 @@ TEST_F(DBTest2, MemtableOnlyIterator) {
3391
3885
  }
3392
3886
  ASSERT_TRUE(!it->Valid());
3393
3887
  ASSERT_EQ(1, count);
3888
+ ASSERT_OK(it->status());
3394
3889
  delete it;
3395
3890
  }
3396
3891
 
@@ -3419,28 +3914,28 @@ TEST_F(DBTest2, LowPriWrite) {
3419
3914
  WriteOptions wo;
3420
3915
  for (int i = 0; i < 6; i++) {
3421
3916
  wo.low_pri = false;
3422
- Put("", "", wo);
3917
+ ASSERT_OK(Put("", "", wo));
3423
3918
  wo.low_pri = true;
3424
- Put("", "", wo);
3425
- Flush();
3919
+ ASSERT_OK(Put("", "", wo));
3920
+ ASSERT_OK(Flush());
3426
3921
  }
3427
3922
  ASSERT_EQ(0, rate_limit_count.load());
3428
3923
  wo.low_pri = true;
3429
- Put("", "", wo);
3924
+ ASSERT_OK(Put("", "", wo));
3430
3925
  ASSERT_EQ(1, rate_limit_count.load());
3431
3926
  wo.low_pri = false;
3432
- Put("", "", wo);
3927
+ ASSERT_OK(Put("", "", wo));
3433
3928
  ASSERT_EQ(1, rate_limit_count.load());
3434
3929
 
3435
3930
  TEST_SYNC_POINT("DBTest.LowPriWrite:0");
3436
3931
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3437
3932
 
3438
- dbfull()->TEST_WaitForCompact();
3933
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
3439
3934
  wo.low_pri = true;
3440
- Put("", "", wo);
3935
+ ASSERT_OK(Put("", "", wo));
3441
3936
  ASSERT_EQ(1, rate_limit_count.load());
3442
3937
  wo.low_pri = false;
3443
- Put("", "", wo);
3938
+ ASSERT_OK(Put("", "", wo));
3444
3939
  ASSERT_EQ(1, rate_limit_count.load());
3445
3940
  }
3446
3941
 
@@ -3451,65 +3946,74 @@ TEST_F(DBTest2, RateLimitedCompactionReads) {
3451
3946
  const int kBytesPerKey = 1024;
3452
3947
  const int kNumL0Files = 4;
3453
3948
 
3454
- for (auto use_direct_io : {false, true}) {
3455
- if (use_direct_io && !IsDirectIOSupported()) {
3456
- continue;
3457
- }
3458
- Options options = CurrentOptions();
3459
- options.compression = kNoCompression;
3460
- options.level0_file_num_compaction_trigger = kNumL0Files;
3461
- options.memtable_factory.reset(new SpecialSkipListFactory(kNumKeysPerFile));
3462
- options.new_table_reader_for_compaction_inputs = true;
3463
- // takes roughly one second, split into 100 x 10ms intervals. Each interval
3464
- // permits 5.12KB, which is smaller than the block size, so this test
3465
- // exercises the code for chunking reads.
3466
- options.rate_limiter.reset(NewGenericRateLimiter(
3467
- static_cast<int64_t>(kNumL0Files * kNumKeysPerFile *
3468
- kBytesPerKey) /* rate_bytes_per_sec */,
3469
- 10 * 1000 /* refill_period_us */, 10 /* fairness */,
3470
- RateLimiter::Mode::kReadsOnly));
3471
- options.use_direct_reads = options.use_direct_io_for_flush_and_compaction =
3472
- use_direct_io;
3473
- BlockBasedTableOptions bbto;
3474
- bbto.block_size = 16384;
3475
- bbto.no_block_cache = true;
3476
- options.table_factory.reset(NewBlockBasedTableFactory(bbto));
3477
- DestroyAndReopen(options);
3949
+ for (int compaction_readahead_size : {0, 32 << 10}) {
3950
+ for (auto use_direct_io : {false, true}) {
3951
+ if (use_direct_io && !IsDirectIOSupported()) {
3952
+ continue;
3953
+ }
3954
+ Options options = CurrentOptions();
3955
+ options.compaction_readahead_size = compaction_readahead_size;
3956
+ options.compression = kNoCompression;
3957
+ options.level0_file_num_compaction_trigger = kNumL0Files;
3958
+ options.memtable_factory.reset(
3959
+ test::NewSpecialSkipListFactory(kNumKeysPerFile));
3960
+ // takes roughly one second, split into 100 x 10ms intervals. Each
3961
+ // interval permits 5.12KB, which is smaller than the block size, so this
3962
+ // test exercises the code for chunking reads.
3963
+ options.rate_limiter.reset(NewGenericRateLimiter(
3964
+ static_cast<int64_t>(kNumL0Files * kNumKeysPerFile *
3965
+ kBytesPerKey) /* rate_bytes_per_sec */,
3966
+ 10 * 1000 /* refill_period_us */, 10 /* fairness */,
3967
+ RateLimiter::Mode::kReadsOnly));
3968
+ options.use_direct_reads =
3969
+ options.use_direct_io_for_flush_and_compaction = use_direct_io;
3970
+ BlockBasedTableOptions bbto;
3971
+ bbto.block_size = 16384;
3972
+ bbto.no_block_cache = true;
3973
+ options.table_factory.reset(NewBlockBasedTableFactory(bbto));
3974
+ DestroyAndReopen(options);
3478
3975
 
3479
- for (int i = 0; i < kNumL0Files; ++i) {
3480
- for (int j = 0; j <= kNumKeysPerFile; ++j) {
3481
- ASSERT_OK(Put(Key(j), DummyString(kBytesPerKey)));
3976
+ for (int i = 0; i < kNumL0Files; ++i) {
3977
+ for (int j = 0; j <= kNumKeysPerFile; ++j) {
3978
+ ASSERT_OK(Put(Key(j), DummyString(kBytesPerKey)));
3979
+ }
3980
+ ASSERT_OK(dbfull()->TEST_WaitForFlushMemTable());
3981
+ if (i + 1 < kNumL0Files) {
3982
+ ASSERT_EQ(i + 1, NumTableFilesAtLevel(0));
3983
+ }
3984
+ }
3985
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
3986
+ ASSERT_EQ(0, NumTableFilesAtLevel(0));
3987
+
3988
+ // should be slightly above 512KB due to non-data blocks read. Arbitrarily
3989
+ // chose 1MB as the upper bound on the total bytes read.
3990
+ size_t rate_limited_bytes =
3991
+ options.rate_limiter->GetTotalBytesThrough(Env::IO_TOTAL);
3992
+ // There must be no charges at non-`IO_LOW` priorities.
3993
+ ASSERT_EQ(rate_limited_bytes,
3994
+ static_cast<size_t>(
3995
+ options.rate_limiter->GetTotalBytesThrough(Env::IO_LOW)));
3996
+ // Include the explicit prefetch of the footer in direct I/O case.
3997
+ size_t direct_io_extra = use_direct_io ? 512 * 1024 : 0;
3998
+ ASSERT_GE(
3999
+ rate_limited_bytes,
4000
+ static_cast<size_t>(kNumKeysPerFile * kBytesPerKey * kNumL0Files));
4001
+ ASSERT_LT(
4002
+ rate_limited_bytes,
4003
+ static_cast<size_t>(2 * kNumKeysPerFile * kBytesPerKey * kNumL0Files +
4004
+ direct_io_extra));
4005
+
4006
+ Iterator* iter = db_->NewIterator(ReadOptions());
4007
+ ASSERT_OK(iter->status());
4008
+ for (iter->SeekToFirst(); iter->Valid(); iter->Next()) {
4009
+ ASSERT_EQ(iter->value().ToString(), DummyString(kBytesPerKey));
3482
4010
  }
3483
- dbfull()->TEST_WaitForFlushMemTable();
3484
- ASSERT_EQ(i + 1, NumTableFilesAtLevel(0));
4011
+ delete iter;
4012
+ // bytes read for user iterator shouldn't count against the rate limit.
4013
+ ASSERT_EQ(rate_limited_bytes,
4014
+ static_cast<size_t>(
4015
+ options.rate_limiter->GetTotalBytesThrough(Env::IO_LOW)));
3485
4016
  }
3486
- dbfull()->TEST_WaitForCompact();
3487
- ASSERT_EQ(0, NumTableFilesAtLevel(0));
3488
-
3489
- ASSERT_EQ(0, options.rate_limiter->GetTotalBytesThrough(Env::IO_HIGH));
3490
- // should be slightly above 512KB due to non-data blocks read. Arbitrarily
3491
- // chose 1MB as the upper bound on the total bytes read.
3492
- size_t rate_limited_bytes =
3493
- options.rate_limiter->GetTotalBytesThrough(Env::IO_LOW);
3494
- // Include the explicit prefetch of the footer in direct I/O case.
3495
- size_t direct_io_extra = use_direct_io ? 512 * 1024 : 0;
3496
- ASSERT_GE(
3497
- rate_limited_bytes,
3498
- static_cast<size_t>(kNumKeysPerFile * kBytesPerKey * kNumL0Files));
3499
- ASSERT_LT(
3500
- rate_limited_bytes,
3501
- static_cast<size_t>(2 * kNumKeysPerFile * kBytesPerKey * kNumL0Files +
3502
- direct_io_extra));
3503
-
3504
- Iterator* iter = db_->NewIterator(ReadOptions());
3505
- for (iter->SeekToFirst(); iter->Valid(); iter->Next()) {
3506
- ASSERT_EQ(iter->value().ToString(), DummyString(kBytesPerKey));
3507
- }
3508
- delete iter;
3509
- // bytes read for user iterator shouldn't count against the rate limit.
3510
- ASSERT_EQ(rate_limited_bytes,
3511
- static_cast<size_t>(
3512
- options.rate_limiter->GetTotalBytesThrough(Env::IO_LOW)));
3513
4017
  }
3514
4018
  }
3515
4019
  #endif // ROCKSDB_LITE
@@ -3522,8 +4026,8 @@ TEST_F(DBTest2, ReduceLevel) {
3522
4026
  options.disable_auto_compactions = true;
3523
4027
  options.num_levels = 7;
3524
4028
  Reopen(options);
3525
- Put("foo", "bar");
3526
- Flush();
4029
+ ASSERT_OK(Put("foo", "bar"));
4030
+ ASSERT_OK(Flush());
3527
4031
  MoveFilesToLevel(6);
3528
4032
  #ifndef ROCKSDB_LITE
3529
4033
  ASSERT_EQ("0,0,0,0,0,0,1", FilesPerLevel());
@@ -3531,7 +4035,7 @@ TEST_F(DBTest2, ReduceLevel) {
3531
4035
  CompactRangeOptions compact_options;
3532
4036
  compact_options.change_level = true;
3533
4037
  compact_options.target_level = 1;
3534
- dbfull()->CompactRange(compact_options, nullptr, nullptr);
4038
+ ASSERT_OK(dbfull()->CompactRange(compact_options, nullptr, nullptr));
3535
4039
  #ifndef ROCKSDB_LITE
3536
4040
  ASSERT_EQ("0,1", FilesPerLevel());
3537
4041
  #endif // !ROCKSDB_LITE
@@ -3560,35 +4064,35 @@ TEST_F(DBTest2, ReadCallbackTest) {
3560
4064
  // the DB instead of assuming what seq the DB used.
3561
4065
  int i = 1;
3562
4066
  for (; i < 10; i++) {
3563
- Put(key, value + std::to_string(i));
4067
+ ASSERT_OK(Put(key, value + std::to_string(i)));
3564
4068
  // Take a snapshot to avoid the value being removed during compaction
3565
4069
  auto snapshot = dbfull()->GetSnapshot();
3566
4070
  snapshots.push_back(snapshot);
3567
4071
  }
3568
- Flush();
4072
+ ASSERT_OK(Flush());
3569
4073
  for (; i < 20; i++) {
3570
- Put(key, value + std::to_string(i));
4074
+ ASSERT_OK(Put(key, value + std::to_string(i)));
3571
4075
  // Take a snapshot to avoid the value being removed during compaction
3572
4076
  auto snapshot = dbfull()->GetSnapshot();
3573
4077
  snapshots.push_back(snapshot);
3574
4078
  }
3575
- Flush();
4079
+ ASSERT_OK(Flush());
3576
4080
  MoveFilesToLevel(6);
3577
4081
  #ifndef ROCKSDB_LITE
3578
4082
  ASSERT_EQ("0,0,0,0,0,0,2", FilesPerLevel());
3579
4083
  #endif // !ROCKSDB_LITE
3580
4084
  for (; i < 30; i++) {
3581
- Put(key, value + std::to_string(i));
4085
+ ASSERT_OK(Put(key, value + std::to_string(i)));
3582
4086
  auto snapshot = dbfull()->GetSnapshot();
3583
4087
  snapshots.push_back(snapshot);
3584
4088
  }
3585
- Flush();
4089
+ ASSERT_OK(Flush());
3586
4090
  #ifndef ROCKSDB_LITE
3587
4091
  ASSERT_EQ("1,0,0,0,0,0,2", FilesPerLevel());
3588
4092
  #endif // !ROCKSDB_LITE
3589
4093
  // And also add some values to the memtable
3590
4094
  for (; i < 40; i++) {
3591
- Put(key, value + std::to_string(i));
4095
+ ASSERT_OK(Put(key, value + std::to_string(i)));
3592
4096
  auto snapshot = dbfull()->GetSnapshot();
3593
4097
  snapshots.push_back(snapshot);
3594
4098
  }
@@ -3661,21 +4165,21 @@ TEST_F(DBTest2, LiveFilesOmitObsoleteFiles) {
3661
4165
  [&](void* /*arg*/) { env_->SleepForMicroseconds(1000000); });
3662
4166
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
3663
4167
 
3664
- Put("key", "val");
4168
+ ASSERT_OK(Put("key", "val"));
3665
4169
  FlushOptions flush_opts;
3666
4170
  flush_opts.wait = false;
3667
4171
  db_->Flush(flush_opts);
3668
4172
  TEST_SYNC_POINT("DBTest2::LiveFilesOmitObsoleteFiles:FlushTriggered");
3669
4173
 
3670
- db_->DisableFileDeletions();
4174
+ ASSERT_OK(db_->DisableFileDeletions());
3671
4175
  VectorLogPtr log_files;
3672
- db_->GetSortedWalFiles(log_files);
4176
+ ASSERT_OK(db_->GetSortedWalFiles(log_files));
3673
4177
  TEST_SYNC_POINT("DBTest2::LiveFilesOmitObsoleteFiles:LiveFilesCaptured");
3674
4178
  for (const auto& log_file : log_files) {
3675
4179
  ASSERT_OK(env_->FileExists(LogFileName(dbname_, log_file->LogNumber())));
3676
4180
  }
3677
4181
 
3678
- db_->EnableFileDeletions();
4182
+ ASSERT_OK(db_->EnableFileDeletions());
3679
4183
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
3680
4184
  }
3681
4185
 
@@ -3751,6 +4255,118 @@ TEST_F(DBTest2, TestNumPread) {
3751
4255
  ASSERT_EQ(0, env_->random_file_open_counter_.load());
3752
4256
  }
3753
4257
 
4258
+ class TraceExecutionResultHandler : public TraceRecordResult::Handler {
4259
+ public:
4260
+ TraceExecutionResultHandler() {}
4261
+ ~TraceExecutionResultHandler() override {}
4262
+
4263
+ virtual Status Handle(const StatusOnlyTraceExecutionResult& result) override {
4264
+ if (result.GetStartTimestamp() > result.GetEndTimestamp()) {
4265
+ return Status::InvalidArgument("Invalid timestamps.");
4266
+ }
4267
+ result.GetStatus().PermitUncheckedError();
4268
+ switch (result.GetTraceType()) {
4269
+ case kTraceWrite: {
4270
+ total_latency_ += result.GetLatency();
4271
+ cnt_++;
4272
+ writes_++;
4273
+ break;
4274
+ }
4275
+ default:
4276
+ return Status::Corruption("Type mismatch.");
4277
+ }
4278
+ return Status::OK();
4279
+ }
4280
+
4281
+ virtual Status Handle(
4282
+ const SingleValueTraceExecutionResult& result) override {
4283
+ if (result.GetStartTimestamp() > result.GetEndTimestamp()) {
4284
+ return Status::InvalidArgument("Invalid timestamps.");
4285
+ }
4286
+ result.GetStatus().PermitUncheckedError();
4287
+ switch (result.GetTraceType()) {
4288
+ case kTraceGet: {
4289
+ total_latency_ += result.GetLatency();
4290
+ cnt_++;
4291
+ gets_++;
4292
+ break;
4293
+ }
4294
+ default:
4295
+ return Status::Corruption("Type mismatch.");
4296
+ }
4297
+ return Status::OK();
4298
+ }
4299
+
4300
+ virtual Status Handle(
4301
+ const MultiValuesTraceExecutionResult& result) override {
4302
+ if (result.GetStartTimestamp() > result.GetEndTimestamp()) {
4303
+ return Status::InvalidArgument("Invalid timestamps.");
4304
+ }
4305
+ for (const Status& s : result.GetMultiStatus()) {
4306
+ s.PermitUncheckedError();
4307
+ }
4308
+ switch (result.GetTraceType()) {
4309
+ case kTraceMultiGet: {
4310
+ total_latency_ += result.GetLatency();
4311
+ cnt_++;
4312
+ multigets_++;
4313
+ break;
4314
+ }
4315
+ default:
4316
+ return Status::Corruption("Type mismatch.");
4317
+ }
4318
+ return Status::OK();
4319
+ }
4320
+
4321
+ virtual Status Handle(const IteratorTraceExecutionResult& result) override {
4322
+ if (result.GetStartTimestamp() > result.GetEndTimestamp()) {
4323
+ return Status::InvalidArgument("Invalid timestamps.");
4324
+ }
4325
+ result.GetStatus().PermitUncheckedError();
4326
+ switch (result.GetTraceType()) {
4327
+ case kTraceIteratorSeek:
4328
+ case kTraceIteratorSeekForPrev: {
4329
+ total_latency_ += result.GetLatency();
4330
+ cnt_++;
4331
+ seeks_++;
4332
+ break;
4333
+ }
4334
+ default:
4335
+ return Status::Corruption("Type mismatch.");
4336
+ }
4337
+ return Status::OK();
4338
+ }
4339
+
4340
+ void Reset() {
4341
+ total_latency_ = 0;
4342
+ cnt_ = 0;
4343
+ writes_ = 0;
4344
+ gets_ = 0;
4345
+ seeks_ = 0;
4346
+ multigets_ = 0;
4347
+ }
4348
+
4349
+ double GetAvgLatency() const {
4350
+ return cnt_ == 0 ? 0.0 : 1.0 * total_latency_ / cnt_;
4351
+ }
4352
+
4353
+ int GetNumWrites() const { return writes_; }
4354
+
4355
+ int GetNumGets() const { return gets_; }
4356
+
4357
+ int GetNumIterSeeks() const { return seeks_; }
4358
+
4359
+ int GetNumMultiGets() const { return multigets_; }
4360
+
4361
+ private:
4362
+ std::atomic<uint64_t> total_latency_{0};
4363
+ std::atomic<uint32_t> cnt_{0};
4364
+ std::atomic<int> writes_{0};
4365
+ std::atomic<int> gets_{0};
4366
+ std::atomic<int> seeks_{0};
4367
+ std::atomic<int> multigets_{0};
4368
+ };
4369
+
3754
4370
  TEST_F(DBTest2, TraceAndReplay) {
3755
4371
  Options options = CurrentOptions();
3756
4372
  options.merge_operator = MergeOperators::CreatePutOperator();
@@ -3769,6 +4385,170 @@ TEST_F(DBTest2, TraceAndReplay) {
3769
4385
  ASSERT_OK(NewFileTraceWriter(env_, env_opts, trace_filename, &trace_writer));
3770
4386
  ASSERT_OK(db_->StartTrace(trace_opts, std::move(trace_writer)));
3771
4387
 
4388
+ // 5 Writes
4389
+ ASSERT_OK(Put(0, "a", "1"));
4390
+ ASSERT_OK(Merge(0, "b", "2"));
4391
+ ASSERT_OK(Delete(0, "c"));
4392
+ ASSERT_OK(SingleDelete(0, "d"));
4393
+ ASSERT_OK(db_->DeleteRange(wo, dbfull()->DefaultColumnFamily(), "e", "f"));
4394
+
4395
+ // 6th Write
4396
+ WriteBatch batch;
4397
+ ASSERT_OK(batch.Put("f", "11"));
4398
+ ASSERT_OK(batch.Merge("g", "12"));
4399
+ ASSERT_OK(batch.Delete("h"));
4400
+ ASSERT_OK(batch.SingleDelete("i"));
4401
+ ASSERT_OK(batch.DeleteRange("j", "k"));
4402
+ ASSERT_OK(db_->Write(wo, &batch));
4403
+
4404
+ // 2 Seek(ForPrev)s
4405
+ single_iter = db_->NewIterator(ro);
4406
+ single_iter->Seek("f"); // Seek 1
4407
+ single_iter->SeekForPrev("g");
4408
+ ASSERT_OK(single_iter->status());
4409
+ delete single_iter;
4410
+
4411
+ // 2 Gets
4412
+ ASSERT_EQ("1", Get(0, "a"));
4413
+ ASSERT_EQ("12", Get(0, "g"));
4414
+
4415
+ // 7th and 8th Write, 3rd Get
4416
+ ASSERT_OK(Put(1, "foo", "bar"));
4417
+ ASSERT_OK(Put(1, "rocksdb", "rocks"));
4418
+ ASSERT_EQ("NOT_FOUND", Get(1, "leveldb"));
4419
+
4420
+ // Total Write x 8, Get x 3, Seek x 2.
4421
+ ASSERT_OK(db_->EndTrace());
4422
+ // These should not get into the trace file as it is after EndTrace.
4423
+ ASSERT_OK(Put("hello", "world"));
4424
+ ASSERT_OK(Merge("foo", "bar"));
4425
+
4426
+ // Open another db, replay, and verify the data
4427
+ std::string value;
4428
+ std::string dbname2 = test::PerThreadDBPath(env_, "/db_replay");
4429
+ ASSERT_OK(DestroyDB(dbname2, options));
4430
+
4431
+ // Using a different name than db2, to pacify infer's use-after-lifetime
4432
+ // warnings (http://fbinfer.com).
4433
+ DB* db2_init = nullptr;
4434
+ options.create_if_missing = true;
4435
+ ASSERT_OK(DB::Open(options, dbname2, &db2_init));
4436
+ ColumnFamilyHandle* cf;
4437
+ ASSERT_OK(
4438
+ db2_init->CreateColumnFamily(ColumnFamilyOptions(), "pikachu", &cf));
4439
+ delete cf;
4440
+ delete db2_init;
4441
+
4442
+ DB* db2 = nullptr;
4443
+ std::vector<ColumnFamilyDescriptor> column_families;
4444
+ ColumnFamilyOptions cf_options;
4445
+ cf_options.merge_operator = MergeOperators::CreatePutOperator();
4446
+ column_families.push_back(ColumnFamilyDescriptor("default", cf_options));
4447
+ column_families.push_back(
4448
+ ColumnFamilyDescriptor("pikachu", ColumnFamilyOptions()));
4449
+ std::vector<ColumnFamilyHandle*> handles;
4450
+ DBOptions db_opts;
4451
+ db_opts.env = env_;
4452
+ ASSERT_OK(DB::Open(db_opts, dbname2, column_families, &handles, &db2));
4453
+
4454
+ env_->SleepForMicroseconds(100);
4455
+ // Verify that the keys don't already exist
4456
+ ASSERT_TRUE(db2->Get(ro, handles[0], "a", &value).IsNotFound());
4457
+ ASSERT_TRUE(db2->Get(ro, handles[0], "g", &value).IsNotFound());
4458
+
4459
+ std::unique_ptr<TraceReader> trace_reader;
4460
+ ASSERT_OK(NewFileTraceReader(env_, env_opts, trace_filename, &trace_reader));
4461
+ std::unique_ptr<Replayer> replayer;
4462
+ ASSERT_OK(
4463
+ db2->NewDefaultReplayer(handles, std::move(trace_reader), &replayer));
4464
+
4465
+ TraceExecutionResultHandler res_handler;
4466
+ std::function<void(Status, std::unique_ptr<TraceRecordResult> &&)> res_cb =
4467
+ [&res_handler](Status exec_s, std::unique_ptr<TraceRecordResult>&& res) {
4468
+ ASSERT_TRUE(exec_s.ok() || exec_s.IsNotSupported());
4469
+ if (res != nullptr) {
4470
+ ASSERT_OK(res->Accept(&res_handler));
4471
+ res.reset();
4472
+ }
4473
+ };
4474
+
4475
+ // Unprepared replay should fail with Status::Incomplete()
4476
+ ASSERT_TRUE(replayer->Replay(ReplayOptions(), nullptr).IsIncomplete());
4477
+ ASSERT_OK(replayer->Prepare());
4478
+ // Ok to repeatedly Prepare().
4479
+ ASSERT_OK(replayer->Prepare());
4480
+ // Replay using 1 thread, 1x speed.
4481
+ ASSERT_OK(replayer->Replay(ReplayOptions(1, 1.0), res_cb));
4482
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4483
+ ASSERT_EQ(res_handler.GetNumWrites(), 8);
4484
+ ASSERT_EQ(res_handler.GetNumGets(), 3);
4485
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 2);
4486
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4487
+ res_handler.Reset();
4488
+
4489
+ ASSERT_OK(db2->Get(ro, handles[0], "a", &value));
4490
+ ASSERT_EQ("1", value);
4491
+ ASSERT_OK(db2->Get(ro, handles[0], "g", &value));
4492
+ ASSERT_EQ("12", value);
4493
+ ASSERT_TRUE(db2->Get(ro, handles[0], "hello", &value).IsNotFound());
4494
+ ASSERT_TRUE(db2->Get(ro, handles[0], "world", &value).IsNotFound());
4495
+
4496
+ ASSERT_OK(db2->Get(ro, handles[1], "foo", &value));
4497
+ ASSERT_EQ("bar", value);
4498
+ ASSERT_OK(db2->Get(ro, handles[1], "rocksdb", &value));
4499
+ ASSERT_EQ("rocks", value);
4500
+
4501
+ // Re-replay should fail with Status::Incomplete() if Prepare() was not
4502
+ // called. Currently we don't distinguish between unprepared and trace end.
4503
+ ASSERT_TRUE(replayer->Replay(ReplayOptions(), nullptr).IsIncomplete());
4504
+
4505
+ // Re-replay using 2 threads, 2x speed.
4506
+ ASSERT_OK(replayer->Prepare());
4507
+ ASSERT_OK(replayer->Replay(ReplayOptions(2, 2.0), res_cb));
4508
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4509
+ ASSERT_EQ(res_handler.GetNumWrites(), 8);
4510
+ ASSERT_EQ(res_handler.GetNumGets(), 3);
4511
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 2);
4512
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4513
+ res_handler.Reset();
4514
+
4515
+ // Re-replay using 2 threads, 1/2 speed.
4516
+ ASSERT_OK(replayer->Prepare());
4517
+ ASSERT_OK(replayer->Replay(ReplayOptions(2, 0.5), res_cb));
4518
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4519
+ ASSERT_EQ(res_handler.GetNumWrites(), 8);
4520
+ ASSERT_EQ(res_handler.GetNumGets(), 3);
4521
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 2);
4522
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4523
+ res_handler.Reset();
4524
+
4525
+ replayer.reset();
4526
+
4527
+ for (auto handle : handles) {
4528
+ delete handle;
4529
+ }
4530
+ delete db2;
4531
+ ASSERT_OK(DestroyDB(dbname2, options));
4532
+ }
4533
+
4534
+ TEST_F(DBTest2, TraceAndManualReplay) {
4535
+ Options options = CurrentOptions();
4536
+ options.merge_operator = MergeOperators::CreatePutOperator();
4537
+ ReadOptions ro;
4538
+ WriteOptions wo;
4539
+ TraceOptions trace_opts;
4540
+ EnvOptions env_opts;
4541
+ CreateAndReopenWithCF({"pikachu"}, options);
4542
+ Random rnd(301);
4543
+ Iterator* single_iter = nullptr;
4544
+
4545
+ ASSERT_TRUE(db_->EndTrace().IsIOError());
4546
+
4547
+ std::string trace_filename = dbname_ + "/rocksdb.trace";
4548
+ std::unique_ptr<TraceWriter> trace_writer;
4549
+ ASSERT_OK(NewFileTraceWriter(env_, env_opts, trace_filename, &trace_writer));
4550
+ ASSERT_OK(db_->StartTrace(trace_opts, std::move(trace_writer)));
4551
+
3772
4552
  ASSERT_OK(Put(0, "a", "1"));
3773
4553
  ASSERT_OK(Merge(0, "b", "2"));
3774
4554
  ASSERT_OK(Delete(0, "c"));
@@ -3786,6 +4566,37 @@ TEST_F(DBTest2, TraceAndReplay) {
3786
4566
  single_iter = db_->NewIterator(ro);
3787
4567
  single_iter->Seek("f");
3788
4568
  single_iter->SeekForPrev("g");
4569
+ ASSERT_OK(single_iter->status());
4570
+ delete single_iter;
4571
+
4572
+ // Write some sequenced keys for testing lower/upper bounds of iterator.
4573
+ batch.Clear();
4574
+ ASSERT_OK(batch.Put("iter-0", "iter-0"));
4575
+ ASSERT_OK(batch.Put("iter-1", "iter-1"));
4576
+ ASSERT_OK(batch.Put("iter-2", "iter-2"));
4577
+ ASSERT_OK(batch.Put("iter-3", "iter-3"));
4578
+ ASSERT_OK(batch.Put("iter-4", "iter-4"));
4579
+ ASSERT_OK(db_->Write(wo, &batch));
4580
+
4581
+ ReadOptions bounded_ro = ro;
4582
+ Slice lower_bound("iter-1");
4583
+ Slice upper_bound("iter-3");
4584
+ bounded_ro.iterate_lower_bound = &lower_bound;
4585
+ bounded_ro.iterate_upper_bound = &upper_bound;
4586
+ single_iter = db_->NewIterator(bounded_ro);
4587
+ single_iter->Seek("iter-0");
4588
+ ASSERT_EQ(single_iter->key().ToString(), "iter-1");
4589
+ single_iter->Seek("iter-2");
4590
+ ASSERT_EQ(single_iter->key().ToString(), "iter-2");
4591
+ single_iter->Seek("iter-4");
4592
+ ASSERT_FALSE(single_iter->Valid());
4593
+ single_iter->SeekForPrev("iter-0");
4594
+ ASSERT_FALSE(single_iter->Valid());
4595
+ single_iter->SeekForPrev("iter-2");
4596
+ ASSERT_EQ(single_iter->key().ToString(), "iter-2");
4597
+ single_iter->SeekForPrev("iter-4");
4598
+ ASSERT_EQ(single_iter->key().ToString(), "iter-2");
4599
+ ASSERT_OK(single_iter->status());
3789
4600
  delete single_iter;
3790
4601
 
3791
4602
  ASSERT_EQ("1", Get(0, "a"));
@@ -3795,10 +4606,14 @@ TEST_F(DBTest2, TraceAndReplay) {
3795
4606
  ASSERT_OK(Put(1, "rocksdb", "rocks"));
3796
4607
  ASSERT_EQ("NOT_FOUND", Get(1, "leveldb"));
3797
4608
 
4609
+ // Same as TraceAndReplay, Write x 8, Get x 3, Seek x 2.
4610
+ // Plus 1 WriteBatch for iterator with lower/upper bounds, and 6
4611
+ // Seek(ForPrev)s.
4612
+ // Total Write x 9, Get x 3, Seek x 8
3798
4613
  ASSERT_OK(db_->EndTrace());
3799
4614
  // These should not get into the trace file as it is after EndTrace.
3800
- Put("hello", "world");
3801
- Merge("foo", "bar");
4615
+ ASSERT_OK(Put("hello", "world"));
4616
+ ASSERT_OK(Merge("foo", "bar"));
3802
4617
 
3803
4618
  // Open another db, replay, and verify the data
3804
4619
  std::string value;
@@ -3835,8 +4650,76 @@ TEST_F(DBTest2, TraceAndReplay) {
3835
4650
 
3836
4651
  std::unique_ptr<TraceReader> trace_reader;
3837
4652
  ASSERT_OK(NewFileTraceReader(env_, env_opts, trace_filename, &trace_reader));
3838
- Replayer replayer(db2, handles_, std::move(trace_reader));
3839
- ASSERT_OK(replayer.Replay());
4653
+ std::unique_ptr<Replayer> replayer;
4654
+ ASSERT_OK(
4655
+ db2->NewDefaultReplayer(handles, std::move(trace_reader), &replayer));
4656
+
4657
+ TraceExecutionResultHandler res_handler;
4658
+
4659
+ // Manual replay for 2 times. The 2nd checks if the replay can restart.
4660
+ std::unique_ptr<TraceRecord> record;
4661
+ std::unique_ptr<TraceRecordResult> result;
4662
+ for (int i = 0; i < 2; i++) {
4663
+ // Next should fail if unprepared.
4664
+ ASSERT_TRUE(replayer->Next(nullptr).IsIncomplete());
4665
+ ASSERT_OK(replayer->Prepare());
4666
+ Status s = Status::OK();
4667
+ // Looping until trace end.
4668
+ while (s.ok()) {
4669
+ s = replayer->Next(&record);
4670
+ // Skip unsupported operations.
4671
+ if (s.IsNotSupported()) {
4672
+ continue;
4673
+ }
4674
+ if (s.ok()) {
4675
+ ASSERT_OK(replayer->Execute(record, &result));
4676
+ if (result != nullptr) {
4677
+ ASSERT_OK(result->Accept(&res_handler));
4678
+ if (record->GetTraceType() == kTraceIteratorSeek ||
4679
+ record->GetTraceType() == kTraceIteratorSeekForPrev) {
4680
+ IteratorSeekQueryTraceRecord* iter_rec =
4681
+ dynamic_cast<IteratorSeekQueryTraceRecord*>(record.get());
4682
+ IteratorTraceExecutionResult* iter_res =
4683
+ dynamic_cast<IteratorTraceExecutionResult*>(result.get());
4684
+ // Check if lower/upper bounds are correctly saved and decoded.
4685
+ std::string lower_str = iter_rec->GetLowerBound().ToString();
4686
+ std::string upper_str = iter_rec->GetUpperBound().ToString();
4687
+ std::string iter_key = iter_res->GetKey().ToString();
4688
+ std::string iter_value = iter_res->GetValue().ToString();
4689
+ if (!lower_str.empty() && !upper_str.empty()) {
4690
+ ASSERT_EQ(lower_str, "iter-1");
4691
+ ASSERT_EQ(upper_str, "iter-3");
4692
+ if (iter_res->GetValid()) {
4693
+ // If iterator is valid, then lower_bound <= key < upper_bound.
4694
+ ASSERT_GE(iter_key, lower_str);
4695
+ ASSERT_LT(iter_key, upper_str);
4696
+ } else {
4697
+ // If iterator is invalid, then
4698
+ // key < lower_bound or key >= upper_bound.
4699
+ ASSERT_TRUE(iter_key < lower_str || iter_key >= upper_str);
4700
+ }
4701
+ }
4702
+ // If iterator is invalid, the key and value should be empty.
4703
+ if (!iter_res->GetValid()) {
4704
+ ASSERT_TRUE(iter_key.empty());
4705
+ ASSERT_TRUE(iter_value.empty());
4706
+ }
4707
+ }
4708
+ result.reset();
4709
+ }
4710
+ }
4711
+ }
4712
+ // Status::Incomplete() will be returned when manually reading the trace
4713
+ // end, or Prepare() was not called.
4714
+ ASSERT_TRUE(s.IsIncomplete());
4715
+ ASSERT_TRUE(replayer->Next(nullptr).IsIncomplete());
4716
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4717
+ ASSERT_EQ(res_handler.GetNumWrites(), 9);
4718
+ ASSERT_EQ(res_handler.GetNumGets(), 3);
4719
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 8);
4720
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4721
+ res_handler.Reset();
4722
+ }
3840
4723
 
3841
4724
  ASSERT_OK(db2->Get(ro, handles[0], "a", &value));
3842
4725
  ASSERT_EQ("1", value);
@@ -3850,6 +4733,138 @@ TEST_F(DBTest2, TraceAndReplay) {
3850
4733
  ASSERT_OK(db2->Get(ro, handles[1], "rocksdb", &value));
3851
4734
  ASSERT_EQ("rocks", value);
3852
4735
 
4736
+ // Test execution of artificially created TraceRecords.
4737
+ uint64_t fake_ts = 1U;
4738
+ // Write
4739
+ batch.Clear();
4740
+ ASSERT_OK(batch.Put("trace-record-write1", "write1"));
4741
+ ASSERT_OK(batch.Put("trace-record-write2", "write2"));
4742
+ record.reset(new WriteQueryTraceRecord(batch.Data(), fake_ts++));
4743
+ ASSERT_OK(replayer->Execute(record, &result));
4744
+ ASSERT_TRUE(result != nullptr);
4745
+ ASSERT_OK(result->Accept(&res_handler)); // Write x 1
4746
+ ASSERT_OK(db2->Get(ro, handles[0], "trace-record-write1", &value));
4747
+ ASSERT_EQ("write1", value);
4748
+ ASSERT_OK(db2->Get(ro, handles[0], "trace-record-write2", &value));
4749
+ ASSERT_EQ("write2", value);
4750
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4751
+ ASSERT_EQ(res_handler.GetNumWrites(), 1);
4752
+ ASSERT_EQ(res_handler.GetNumGets(), 0);
4753
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 0);
4754
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4755
+ res_handler.Reset();
4756
+
4757
+ // Get related
4758
+ // Get an existing key.
4759
+ record.reset(new GetQueryTraceRecord(handles[0]->GetID(),
4760
+ "trace-record-write1", fake_ts++));
4761
+ ASSERT_OK(replayer->Execute(record, &result));
4762
+ ASSERT_TRUE(result != nullptr);
4763
+ ASSERT_OK(result->Accept(&res_handler)); // Get x 1
4764
+ // Get an non-existing key, should still return Status::OK().
4765
+ record.reset(new GetQueryTraceRecord(handles[0]->GetID(), "trace-record-get",
4766
+ fake_ts++));
4767
+ ASSERT_OK(replayer->Execute(record, &result));
4768
+ ASSERT_TRUE(result != nullptr);
4769
+ ASSERT_OK(result->Accept(&res_handler)); // Get x 2
4770
+ // Get from an invalid (non-existing) cf_id.
4771
+ uint32_t invalid_cf_id = handles[1]->GetID() + 1;
4772
+ record.reset(new GetQueryTraceRecord(invalid_cf_id, "whatever", fake_ts++));
4773
+ ASSERT_TRUE(replayer->Execute(record, &result).IsCorruption());
4774
+ ASSERT_TRUE(result == nullptr);
4775
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4776
+ ASSERT_EQ(res_handler.GetNumWrites(), 0);
4777
+ ASSERT_EQ(res_handler.GetNumGets(), 2);
4778
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 0);
4779
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4780
+ res_handler.Reset();
4781
+
4782
+ // Iteration related
4783
+ for (IteratorSeekQueryTraceRecord::SeekType seekType :
4784
+ {IteratorSeekQueryTraceRecord::kSeek,
4785
+ IteratorSeekQueryTraceRecord::kSeekForPrev}) {
4786
+ // Seek to an existing key.
4787
+ record.reset(new IteratorSeekQueryTraceRecord(
4788
+ seekType, handles[0]->GetID(), "trace-record-write1", fake_ts++));
4789
+ ASSERT_OK(replayer->Execute(record, &result));
4790
+ ASSERT_TRUE(result != nullptr);
4791
+ ASSERT_OK(result->Accept(&res_handler)); // Seek x 1 in one iteration
4792
+ // Seek to an non-existing key, should still return Status::OK().
4793
+ record.reset(new IteratorSeekQueryTraceRecord(
4794
+ seekType, handles[0]->GetID(), "trace-record-get", fake_ts++));
4795
+ ASSERT_OK(replayer->Execute(record, &result));
4796
+ ASSERT_TRUE(result != nullptr);
4797
+ ASSERT_OK(result->Accept(&res_handler)); // Seek x 2 in one iteration
4798
+ // Seek from an invalid cf_id.
4799
+ record.reset(new IteratorSeekQueryTraceRecord(seekType, invalid_cf_id,
4800
+ "whatever", fake_ts++));
4801
+ ASSERT_TRUE(replayer->Execute(record, &result).IsCorruption());
4802
+ ASSERT_TRUE(result == nullptr);
4803
+ }
4804
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4805
+ ASSERT_EQ(res_handler.GetNumWrites(), 0);
4806
+ ASSERT_EQ(res_handler.GetNumGets(), 0);
4807
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 4); // Seek x 2 in two iterations
4808
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 0);
4809
+ res_handler.Reset();
4810
+
4811
+ // MultiGet related
4812
+ // Get existing keys.
4813
+ record.reset(new MultiGetQueryTraceRecord(
4814
+ std::vector<uint32_t>({handles[0]->GetID(), handles[1]->GetID()}),
4815
+ std::vector<std::string>({"a", "foo"}), fake_ts++));
4816
+ ASSERT_OK(replayer->Execute(record, &result));
4817
+ ASSERT_TRUE(result != nullptr);
4818
+ ASSERT_OK(result->Accept(&res_handler)); // MultiGet x 1
4819
+ // Get all non-existing keys, should still return Status::OK().
4820
+ record.reset(new MultiGetQueryTraceRecord(
4821
+ std::vector<uint32_t>({handles[0]->GetID(), handles[1]->GetID()}),
4822
+ std::vector<std::string>({"no1", "no2"}), fake_ts++));
4823
+ ASSERT_OK(replayer->Execute(record, &result));
4824
+ ASSERT_TRUE(result != nullptr);
4825
+ ASSERT_OK(result->Accept(&res_handler)); // MultiGet x 2
4826
+ // Get mixed of existing and non-existing keys, should still return
4827
+ // Status::OK().
4828
+ record.reset(new MultiGetQueryTraceRecord(
4829
+ std::vector<uint32_t>({handles[0]->GetID(), handles[1]->GetID()}),
4830
+ std::vector<std::string>({"a", "no2"}), fake_ts++));
4831
+ ASSERT_OK(replayer->Execute(record, &result));
4832
+ ASSERT_TRUE(result != nullptr);
4833
+ MultiValuesTraceExecutionResult* mvr =
4834
+ dynamic_cast<MultiValuesTraceExecutionResult*>(result.get());
4835
+ ASSERT_TRUE(mvr != nullptr);
4836
+ ASSERT_OK(mvr->GetMultiStatus()[0]);
4837
+ ASSERT_TRUE(mvr->GetMultiStatus()[1].IsNotFound());
4838
+ ASSERT_EQ(mvr->GetValues()[0], "1");
4839
+ ASSERT_EQ(mvr->GetValues()[1], "");
4840
+ ASSERT_OK(result->Accept(&res_handler)); // MultiGet x 3
4841
+ // Get from an invalid (non-existing) cf_id.
4842
+ record.reset(new MultiGetQueryTraceRecord(
4843
+ std::vector<uint32_t>(
4844
+ {handles[0]->GetID(), handles[1]->GetID(), invalid_cf_id}),
4845
+ std::vector<std::string>({"a", "foo", "whatever"}), fake_ts++));
4846
+ ASSERT_TRUE(replayer->Execute(record, &result).IsCorruption());
4847
+ ASSERT_TRUE(result == nullptr);
4848
+ // Empty MultiGet
4849
+ record.reset(new MultiGetQueryTraceRecord(
4850
+ std::vector<uint32_t>(), std::vector<std::string>(), fake_ts++));
4851
+ ASSERT_TRUE(replayer->Execute(record, &result).IsInvalidArgument());
4852
+ ASSERT_TRUE(result == nullptr);
4853
+ // MultiGet size mismatch
4854
+ record.reset(new MultiGetQueryTraceRecord(
4855
+ std::vector<uint32_t>({handles[0]->GetID(), handles[1]->GetID()}),
4856
+ std::vector<std::string>({"a"}), fake_ts++));
4857
+ ASSERT_TRUE(replayer->Execute(record, &result).IsInvalidArgument());
4858
+ ASSERT_TRUE(result == nullptr);
4859
+ ASSERT_GT(res_handler.GetAvgLatency(), 0.0);
4860
+ ASSERT_EQ(res_handler.GetNumWrites(), 0);
4861
+ ASSERT_EQ(res_handler.GetNumGets(), 0);
4862
+ ASSERT_EQ(res_handler.GetNumIterSeeks(), 0);
4863
+ ASSERT_EQ(res_handler.GetNumMultiGets(), 3);
4864
+ res_handler.Reset();
4865
+
4866
+ replayer.reset();
4867
+
3853
4868
  for (auto handle : handles) {
3854
4869
  delete handle;
3855
4870
  }
@@ -3913,8 +4928,12 @@ TEST_F(DBTest2, TraceWithLimit) {
3913
4928
 
3914
4929
  std::unique_ptr<TraceReader> trace_reader;
3915
4930
  ASSERT_OK(NewFileTraceReader(env_, env_opts, trace_filename, &trace_reader));
3916
- Replayer replayer(db2, handles_, std::move(trace_reader));
3917
- ASSERT_OK(replayer.Replay());
4931
+ std::unique_ptr<Replayer> replayer;
4932
+ ASSERT_OK(
4933
+ db2->NewDefaultReplayer(handles, std::move(trace_reader), &replayer));
4934
+ ASSERT_OK(replayer->Prepare());
4935
+ ASSERT_OK(replayer->Replay(ReplayOptions(), nullptr));
4936
+ replayer.reset();
3918
4937
 
3919
4938
  ASSERT_TRUE(db2->Get(ro, handles[0], "a", &value).IsNotFound());
3920
4939
  ASSERT_TRUE(db2->Get(ro, handles[0], "b", &value).IsNotFound());
@@ -3984,8 +5003,12 @@ TEST_F(DBTest2, TraceWithSampling) {
3984
5003
 
3985
5004
  std::unique_ptr<TraceReader> trace_reader;
3986
5005
  ASSERT_OK(NewFileTraceReader(env_, env_opts, trace_filename, &trace_reader));
3987
- Replayer replayer(db2, handles_, std::move(trace_reader));
3988
- ASSERT_OK(replayer.Replay());
5006
+ std::unique_ptr<Replayer> replayer;
5007
+ ASSERT_OK(
5008
+ db2->NewDefaultReplayer(handles, std::move(trace_reader), &replayer));
5009
+ ASSERT_OK(replayer->Prepare());
5010
+ ASSERT_OK(replayer->Replay(ReplayOptions(), nullptr));
5011
+ replayer.reset();
3989
5012
 
3990
5013
  ASSERT_TRUE(db2->Get(ro, handles[0], "a", &value).IsNotFound());
3991
5014
  ASSERT_FALSE(db2->Get(ro, handles[0], "b", &value).IsNotFound());
@@ -4046,12 +5069,12 @@ TEST_F(DBTest2, TraceWithFilter) {
4046
5069
 
4047
5070
  ASSERT_OK(db_->EndTrace());
4048
5071
  // These should not get into the trace file as it is after EndTrace.
4049
- Put("hello", "world");
4050
- Merge("foo", "bar");
5072
+ ASSERT_OK(Put("hello", "world"));
5073
+ ASSERT_OK(Merge("foo", "bar"));
4051
5074
 
4052
5075
  // Open another db, replay, and verify the data
4053
5076
  std::string value;
4054
- std::string dbname2 = test::TmpDir(env_) + "/db_replay";
5077
+ std::string dbname2 = test::PerThreadDBPath(env_, "db_replay");
4055
5078
  ASSERT_OK(DestroyDB(dbname2, options));
4056
5079
 
4057
5080
  // Using a different name than db2, to pacify infer's use-after-lifetime
@@ -4084,8 +5107,12 @@ TEST_F(DBTest2, TraceWithFilter) {
4084
5107
 
4085
5108
  std::unique_ptr<TraceReader> trace_reader;
4086
5109
  ASSERT_OK(NewFileTraceReader(env_, env_opts, trace_filename, &trace_reader));
4087
- Replayer replayer(db2, handles_, std::move(trace_reader));
4088
- ASSERT_OK(replayer.Replay());
5110
+ std::unique_ptr<Replayer> replayer;
5111
+ ASSERT_OK(
5112
+ db2->NewDefaultReplayer(handles, std::move(trace_reader), &replayer));
5113
+ ASSERT_OK(replayer->Prepare());
5114
+ ASSERT_OK(replayer->Replay(ReplayOptions(), nullptr));
5115
+ replayer.reset();
4089
5116
 
4090
5117
  // All the key-values should not present since we filter out the WRITE ops.
4091
5118
  ASSERT_TRUE(db2->Get(ro, handles[0], "a", &value).IsNotFound());
@@ -4102,7 +5129,7 @@ TEST_F(DBTest2, TraceWithFilter) {
4102
5129
  ASSERT_OK(DestroyDB(dbname2, options));
4103
5130
 
4104
5131
  // Set up a new db.
4105
- std::string dbname3 = test::TmpDir(env_) + "/db_not_trace_read";
5132
+ std::string dbname3 = test::PerThreadDBPath(env_, "db_not_trace_read");
4106
5133
  ASSERT_OK(DestroyDB(dbname3, options));
4107
5134
 
4108
5135
  DB* db3_init = nullptr;
@@ -4196,9 +5223,9 @@ TEST_F(DBTest2, PinnableSliceAndMmapReads) {
4196
5223
  ASSERT_FALSE(pinned_value.IsPinned());
4197
5224
  ASSERT_EQ(pinned_value.ToString(), "bar");
4198
5225
 
4199
- dbfull()->TEST_CompactRange(0 /* level */, nullptr /* begin */,
4200
- nullptr /* end */, nullptr /* column_family */,
4201
- true /* disallow_trivial_move */);
5226
+ ASSERT_OK(dbfull()->TEST_CompactRange(
5227
+ 0 /* level */, nullptr /* begin */, nullptr /* end */,
5228
+ nullptr /* column_family */, true /* disallow_trivial_move */));
4202
5229
 
4203
5230
  // Ensure pinned_value doesn't rely on memory munmap'd by the above
4204
5231
  // compaction. It crashes if it does.
@@ -4242,10 +5269,10 @@ TEST_F(DBTest2, DISABLED_IteratorPinnedMemory) {
4242
5269
 
4243
5270
  // Since v is the size of a block, each key should take a block
4244
5271
  // of 400+ bytes.
4245
- Put("1", v);
4246
- Put("3", v);
4247
- Put("5", v);
4248
- Put("7", v);
5272
+ ASSERT_OK(Put("1", v));
5273
+ ASSERT_OK(Put("3", v));
5274
+ ASSERT_OK(Put("5", v));
5275
+ ASSERT_OK(Put("7", v));
4249
5276
  ASSERT_OK(Flush());
4250
5277
 
4251
5278
  ASSERT_EQ(0, bbto.block_cache->GetPinnedUsage());
@@ -4274,16 +5301,18 @@ TEST_F(DBTest2, DISABLED_IteratorPinnedMemory) {
4274
5301
  iter->Seek("3");
4275
5302
  ASSERT_TRUE(iter->Valid());
4276
5303
 
5304
+ ASSERT_OK(iter->status());
5305
+
4277
5306
  ASSERT_GT(bbto.block_cache->GetPinnedUsage(), 0);
4278
5307
  ASSERT_LT(bbto.block_cache->GetPinnedUsage(), 800);
4279
5308
  }
4280
5309
  ASSERT_EQ(0, bbto.block_cache->GetPinnedUsage());
4281
5310
 
4282
5311
  // Test compaction case
4283
- Put("2", v);
4284
- Put("5", v);
4285
- Put("6", v);
4286
- Put("8", v);
5312
+ ASSERT_OK(Put("2", v));
5313
+ ASSERT_OK(Put("5", v));
5314
+ ASSERT_OK(Put("6", v));
5315
+ ASSERT_OK(Put("8", v));
4287
5316
  ASSERT_OK(Flush());
4288
5317
 
4289
5318
  // Clear existing data in block cache
@@ -4342,20 +5371,20 @@ TEST_F(DBTest2, TestBBTTailPrefetch) {
4342
5371
  });
4343
5372
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
4344
5373
 
4345
- Put("1", "1");
4346
- Put("9", "1");
4347
- Flush();
5374
+ ASSERT_OK(Put("1", "1"));
5375
+ ASSERT_OK(Put("9", "1"));
5376
+ ASSERT_OK(Flush());
4348
5377
 
4349
5378
  expected_lower_bound = 0;
4350
5379
  expected_higher_bound = 8 * 1024;
4351
5380
 
4352
- Put("1", "1");
4353
- Put("9", "1");
4354
- Flush();
5381
+ ASSERT_OK(Put("1", "1"));
5382
+ ASSERT_OK(Put("9", "1"));
5383
+ ASSERT_OK(Flush());
4355
5384
 
4356
- Put("1", "1");
4357
- Put("9", "1");
4358
- Flush();
5385
+ ASSERT_OK(Put("1", "1"));
5386
+ ASSERT_OK(Put("9", "1"));
5387
+ ASSERT_OK(Flush());
4359
5388
 
4360
5389
  // Full compaction to make sure there is no L0 file after the open.
4361
5390
  ASSERT_OK(db_->CompactRange(CompactRangeOptions(), nullptr, nullptr));
@@ -4388,13 +5417,13 @@ TEST_F(DBTest2, TestBBTTailPrefetch) {
4388
5417
  options.max_open_files = -1;
4389
5418
  Reopen(options);
4390
5419
 
4391
- Put("1", "1");
4392
- Put("9", "1");
4393
- Flush();
5420
+ ASSERT_OK(Put("1", "1"));
5421
+ ASSERT_OK(Put("9", "1"));
5422
+ ASSERT_OK(Flush());
4394
5423
 
4395
- Put("1", "1");
4396
- Put("9", "1");
4397
- Flush();
5424
+ ASSERT_OK(Put("1", "1"));
5425
+ ASSERT_OK(Put("9", "1"));
5426
+ ASSERT_OK(Flush());
4398
5427
 
4399
5428
  ASSERT_TRUE(called.load());
4400
5429
  called = false;
@@ -4495,31 +5524,36 @@ TEST_F(DBTest2, TestCompactFiles) {
4495
5524
  GetSstFiles(env_, dbname_, &files);
4496
5525
  ASSERT_EQ(files.size(), 2);
4497
5526
 
4498
- port::Thread user_thread1(
4499
- [&]() { db_->CompactFiles(CompactionOptions(), handle, files, 1); });
5527
+ Status user_thread1_status;
5528
+ port::Thread user_thread1([&]() {
5529
+ user_thread1_status =
5530
+ db_->CompactFiles(CompactionOptions(), handle, files, 1);
5531
+ });
4500
5532
 
5533
+ Status user_thread2_status;
4501
5534
  port::Thread user_thread2([&]() {
4502
- ASSERT_OK(db_->IngestExternalFile(handle, {external_file2},
4503
- IngestExternalFileOptions()));
5535
+ user_thread2_status = db_->IngestExternalFile(handle, {external_file2},
5536
+ IngestExternalFileOptions());
4504
5537
  TEST_SYNC_POINT("TestCompactFiles::IngestExternalFile1");
4505
5538
  });
4506
5539
 
4507
5540
  user_thread1.join();
4508
5541
  user_thread2.join();
4509
5542
 
5543
+ ASSERT_OK(user_thread1_status);
5544
+ ASSERT_OK(user_thread2_status);
5545
+
4510
5546
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
4511
5547
  ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->ClearAllCallBacks();
4512
5548
  }
4513
5549
  #endif // ROCKSDB_LITE
4514
5550
 
4515
- // TODO: figure out why this test fails in appveyor
4516
- #ifndef OS_WIN
4517
5551
  TEST_F(DBTest2, MultiDBParallelOpenTest) {
4518
5552
  const int kNumDbs = 2;
4519
5553
  Options options = CurrentOptions();
4520
5554
  std::vector<std::string> dbnames;
4521
5555
  for (int i = 0; i < kNumDbs; ++i) {
4522
- dbnames.emplace_back(test::TmpDir(env_) + "/db" + ToString(i));
5556
+ dbnames.emplace_back(test::PerThreadDBPath(env_, "db" + ToString(i)));
4523
5557
  ASSERT_OK(DestroyDB(dbnames.back(), options));
4524
5558
  }
4525
5559
 
@@ -4544,7 +5578,6 @@ TEST_F(DBTest2, MultiDBParallelOpenTest) {
4544
5578
  }
4545
5579
 
4546
5580
  // Verify non-empty DBs can be recovered in parallel
4547
- dbs.clear();
4548
5581
  open_threads.clear();
4549
5582
  for (int i = 0; i < kNumDbs; ++i) {
4550
5583
  open_threads.emplace_back(
@@ -4561,11 +5594,11 @@ TEST_F(DBTest2, MultiDBParallelOpenTest) {
4561
5594
  ASSERT_OK(DestroyDB(dbnames[i], options));
4562
5595
  }
4563
5596
  }
4564
- #endif // OS_WIN
4565
5597
 
4566
5598
  namespace {
4567
5599
  class DummyOldStats : public Statistics {
4568
5600
  public:
5601
+ const char* Name() const override { return "DummyOldStats"; }
4569
5602
  uint64_t getTickerCount(uint32_t /*ticker_type*/) const override { return 0; }
4570
5603
  void recordTick(uint32_t /* ticker_type */, uint64_t /* count */) override {
4571
5604
  num_rt++;
@@ -4598,7 +5631,7 @@ TEST_F(DBTest2, OldStatsInterface) {
4598
5631
  options.statistics = stats;
4599
5632
  Reopen(options);
4600
5633
 
4601
- Put("foo", "bar");
5634
+ ASSERT_OK(Put("foo", "bar"));
4602
5635
  ASSERT_EQ("bar", Get("foo"));
4603
5636
  ASSERT_OK(Flush());
4604
5637
  ASSERT_EQ("bar", Get("foo"));
@@ -4646,6 +5679,7 @@ TEST_F(DBTest2, PrefixBloomReseek) {
4646
5679
  ASSERT_OK(Put("bbb1", ""));
4647
5680
 
4648
5681
  Iterator* iter = db_->NewIterator(ReadOptions());
5682
+ ASSERT_OK(iter->status());
4649
5683
 
4650
5684
  // Seeking into f1, the iterator will check bloom filter which returns the
4651
5685
  // file iterator ot be invalidate, and the cursor will put into f2, with
@@ -4684,6 +5718,7 @@ TEST_F(DBTest2, PrefixBloomFilteredOut) {
4684
5718
  ASSERT_OK(db_->CompactRange(cro, nullptr, nullptr));
4685
5719
 
4686
5720
  Iterator* iter = db_->NewIterator(ReadOptions());
5721
+ ASSERT_OK(iter->status());
4687
5722
 
4688
5723
  // Bloom filter is filterd out by f1.
4689
5724
  // This is just one of several valid position following the contract.
@@ -4691,6 +5726,7 @@ TEST_F(DBTest2, PrefixBloomFilteredOut) {
4691
5726
  // the behavior of the current implementation. If underlying implementation
4692
5727
  // changes, the test might fail here.
4693
5728
  iter->Seek("bbb1");
5729
+ ASSERT_OK(iter->status());
4694
5730
  ASSERT_FALSE(iter->Valid());
4695
5731
 
4696
5732
  delete iter;
@@ -4837,6 +5873,7 @@ TEST_F(DBTest2, SeekFileRangeDeleteTail) {
4837
5873
  ReadOptions ro;
4838
5874
  ro.total_order_seek = true;
4839
5875
  std::unique_ptr<Iterator> iter(db_->NewIterator(ro));
5876
+ ASSERT_OK(iter->status());
4840
5877
  iter->Seek("e");
4841
5878
  ASSERT_TRUE(iter->Valid());
4842
5879
  ASSERT_EQ("x", iter->key().ToString());
@@ -4854,6 +5891,7 @@ TEST_F(DBTest2, BackgroundPurgeTest) {
4854
5891
 
4855
5892
  ASSERT_OK(Put("a", "a"));
4856
5893
  Iterator* iter = db_->NewIterator(ReadOptions());
5894
+ ASSERT_OK(iter->status());
4857
5895
  ASSERT_OK(Flush());
4858
5896
  size_t value = options.write_buffer_manager->memory_usage();
4859
5897
  ASSERT_GT(value, base_value);
@@ -4912,7 +5950,7 @@ TEST_F(DBTest2, SameSmallestInSameLevel) {
4912
5950
  ASSERT_OK(Put("key", "2"));
4913
5951
  ASSERT_OK(db_->Merge(WriteOptions(), "key", "3"));
4914
5952
  ASSERT_OK(db_->Merge(WriteOptions(), "key", "4"));
4915
- Flush();
5953
+ ASSERT_OK(Flush());
4916
5954
  CompactRangeOptions cro;
4917
5955
  cro.change_level = true;
4918
5956
  cro.target_level = 2;
@@ -4920,14 +5958,14 @@ TEST_F(DBTest2, SameSmallestInSameLevel) {
4920
5958
  nullptr));
4921
5959
 
4922
5960
  ASSERT_OK(db_->Merge(WriteOptions(), "key", "5"));
4923
- Flush();
5961
+ ASSERT_OK(Flush());
4924
5962
  ASSERT_OK(db_->Merge(WriteOptions(), "key", "6"));
4925
- Flush();
5963
+ ASSERT_OK(Flush());
4926
5964
  ASSERT_OK(db_->Merge(WriteOptions(), "key", "7"));
4927
- Flush();
5965
+ ASSERT_OK(Flush());
4928
5966
  ASSERT_OK(db_->Merge(WriteOptions(), "key", "8"));
4929
- Flush();
4930
- dbfull()->TEST_WaitForCompact(true);
5967
+ ASSERT_OK(Flush());
5968
+ ASSERT_OK(dbfull()->TEST_WaitForCompact(true));
4931
5969
  #ifndef ROCKSDB_LITE
4932
5970
  ASSERT_EQ("0,4,1", FilesPerLevel());
4933
5971
  #endif // ROCKSDB_LITE
@@ -4936,8 +5974,8 @@ TEST_F(DBTest2, SameSmallestInSameLevel) {
4936
5974
  }
4937
5975
 
4938
5976
  TEST_F(DBTest2, FileConsistencyCheckInOpen) {
4939
- Put("foo", "bar");
4940
- Flush();
5977
+ ASSERT_OK(Put("foo", "bar"));
5978
+ ASSERT_OK(Flush());
4941
5979
 
4942
5980
  SyncPoint::GetInstance()->SetCallBack(
4943
5981
  "VersionBuilder::CheckConsistencyBeforeReturn", [&](void* arg) {
@@ -4972,10 +6010,11 @@ TEST_F(DBTest2, BlockBasedTablePrefixIndexSeekForPrev) {
4972
6010
  ASSERT_OK(Put("a1", large_value));
4973
6011
  ASSERT_OK(Put("x1", large_value));
4974
6012
  ASSERT_OK(Put("y1", large_value));
4975
- Flush();
6013
+ ASSERT_OK(Flush());
4976
6014
 
4977
6015
  {
4978
6016
  std::unique_ptr<Iterator> iterator(db_->NewIterator(ReadOptions()));
6017
+ ASSERT_OK(iterator->status());
4979
6018
  iterator->SeekForPrev("x3");
4980
6019
  ASSERT_TRUE(iterator->Valid());
4981
6020
  ASSERT_EQ("x1", iterator->key().ToString());
@@ -5087,7 +6126,7 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5087
6126
  ASSERT_OK(Put("xx1", ""));
5088
6127
  ASSERT_OK(Put("xz1", ""));
5089
6128
  ASSERT_OK(Put("zz", ""));
5090
- Flush();
6129
+ ASSERT_OK(Flush());
5091
6130
 
5092
6131
  // After reopening DB with prefix size 2 => 1, prefix extractor
5093
6132
  // won't take effective unless it won't change results based
@@ -5097,6 +6136,7 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5097
6136
 
5098
6137
  {
5099
6138
  std::unique_ptr<Iterator> iterator(db_->NewIterator(ReadOptions()));
6139
+ ASSERT_OK(iterator->status());
5100
6140
  iterator->Seek("xa");
5101
6141
  ASSERT_TRUE(iterator->Valid());
5102
6142
  ASSERT_EQ("xb", iterator->key().ToString());
@@ -5121,6 +6161,7 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5121
6161
 
5122
6162
  {
5123
6163
  std::unique_ptr<Iterator> iterator(db_->NewIterator(ro));
6164
+ ASSERT_OK(iterator->status());
5124
6165
 
5125
6166
  // SeekForPrev() never uses prefix bloom if it is changed.
5126
6167
  iterator->SeekForPrev("xg0");
@@ -5135,6 +6176,7 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5135
6176
  ub = Slice(ub_str);
5136
6177
  {
5137
6178
  std::unique_ptr<Iterator> iterator(db_->NewIterator(ro));
6179
+ ASSERT_OK(iterator->status());
5138
6180
 
5139
6181
  iterator->Seek("x");
5140
6182
  ASSERT_TRUE(iterator->Valid());
@@ -5181,6 +6223,8 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5181
6223
  if (expect_filter_check) {
5182
6224
  ASSERT_EQ(4, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
5183
6225
  }
6226
+
6227
+ ASSERT_OK(iterator->status());
5184
6228
  }
5185
6229
  {
5186
6230
  std::unique_ptr<Iterator> iterator(db_->NewIterator(ro));
@@ -5198,6 +6242,8 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5198
6242
  if (expect_filter_check) {
5199
6243
  ASSERT_EQ(6, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
5200
6244
  }
6245
+
6246
+ ASSERT_OK(iterator->status());
5201
6247
  }
5202
6248
 
5203
6249
  ub_str = "xg9";
@@ -5210,6 +6256,7 @@ TEST_F(DBTest2, ChangePrefixExtractor) {
5210
6256
  if (expect_filter_check) {
5211
6257
  ASSERT_EQ(7, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
5212
6258
  }
6259
+ ASSERT_OK(iterator->status());
5213
6260
  }
5214
6261
  }
5215
6262
  }
@@ -5229,29 +6276,29 @@ TEST_F(DBTest2, BlockBasedTablePrefixGetIndexNotFound) {
5229
6276
  Reopen(options);
5230
6277
 
5231
6278
  ASSERT_OK(Put("b1", "ok"));
5232
- Flush();
6279
+ ASSERT_OK(Flush());
5233
6280
 
5234
6281
  // Flushing several files so that the chance that hash bucket
5235
6282
  // is empty fo "b" in at least one of the files is high.
5236
6283
  ASSERT_OK(Put("a1", ""));
5237
6284
  ASSERT_OK(Put("c1", ""));
5238
- Flush();
6285
+ ASSERT_OK(Flush());
5239
6286
 
5240
6287
  ASSERT_OK(Put("a2", ""));
5241
6288
  ASSERT_OK(Put("c2", ""));
5242
- Flush();
6289
+ ASSERT_OK(Flush());
5243
6290
 
5244
6291
  ASSERT_OK(Put("a3", ""));
5245
6292
  ASSERT_OK(Put("c3", ""));
5246
- Flush();
6293
+ ASSERT_OK(Flush());
5247
6294
 
5248
6295
  ASSERT_OK(Put("a4", ""));
5249
6296
  ASSERT_OK(Put("c4", ""));
5250
- Flush();
6297
+ ASSERT_OK(Flush());
5251
6298
 
5252
6299
  ASSERT_OK(Put("a5", ""));
5253
6300
  ASSERT_OK(Put("c5", ""));
5254
- Flush();
6301
+ ASSERT_OK(Flush());
5255
6302
 
5256
6303
  ASSERT_EQ("ok", Get("b1"));
5257
6304
  }
@@ -5274,7 +6321,7 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5274
6321
  ASSERT_OK(Put("a1", large_value));
5275
6322
  ASSERT_OK(Put("x1", large_value));
5276
6323
  ASSERT_OK(Put("y1", large_value));
5277
- Flush();
6324
+ ASSERT_OK(Flush());
5278
6325
 
5279
6326
  ReadOptions ro;
5280
6327
  ro.total_order_seek = false;
@@ -5285,6 +6332,7 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5285
6332
  ASSERT_TRUE(iterator->Valid());
5286
6333
  ASSERT_EQ("x1", iterator->key().ToString());
5287
6334
  ASSERT_EQ(0, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
6335
+ ASSERT_OK(iterator->status());
5288
6336
  }
5289
6337
 
5290
6338
  std::string ub_str = "b9";
@@ -5296,6 +6344,7 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5296
6344
  iterator->Seek("b1");
5297
6345
  ASSERT_FALSE(iterator->Valid());
5298
6346
  ASSERT_EQ(1, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
6347
+ ASSERT_OK(iterator->status());
5299
6348
  }
5300
6349
 
5301
6350
  ub_str = "z";
@@ -5306,6 +6355,7 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5306
6355
  ASSERT_TRUE(iterator->Valid());
5307
6356
  ASSERT_EQ("x1", iterator->key().ToString());
5308
6357
  ASSERT_EQ(1, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
6358
+ ASSERT_OK(iterator->status());
5309
6359
  }
5310
6360
 
5311
6361
  ub_str = "c";
@@ -5315,6 +6365,7 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5315
6365
  iterator->Seek("b1");
5316
6366
  ASSERT_FALSE(iterator->Valid());
5317
6367
  ASSERT_EQ(2, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
6368
+ ASSERT_OK(iterator->status());
5318
6369
  }
5319
6370
 
5320
6371
  // The same queries without recreating iterator
@@ -5327,6 +6378,7 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5327
6378
  iterator->Seek("b1");
5328
6379
  ASSERT_FALSE(iterator->Valid());
5329
6380
  ASSERT_EQ(3, TestGetTickerCount(options, BLOOM_FILTER_PREFIX_CHECKED));
6381
+ ASSERT_OK(iterator->status());
5330
6382
 
5331
6383
  ub_str = "z";
5332
6384
  ub = Slice(ub_str);
@@ -5363,6 +6415,664 @@ TEST_F(DBTest2, AutoPrefixMode1) {
5363
6415
  ASSERT_EQ("a1", iterator->key().ToString());
5364
6416
  }
5365
6417
  }
6418
+
6419
+ class RenameCurrentTest : public DBTestBase,
6420
+ public testing::WithParamInterface<std::string> {
6421
+ public:
6422
+ RenameCurrentTest()
6423
+ : DBTestBase("rename_current_test", /*env_do_fsync=*/true),
6424
+ sync_point_(GetParam()) {}
6425
+
6426
+ ~RenameCurrentTest() override {}
6427
+
6428
+ void SetUp() override {
6429
+ env_->no_file_overwrite_.store(true, std::memory_order_release);
6430
+ }
6431
+
6432
+ void TearDown() override {
6433
+ env_->no_file_overwrite_.store(false, std::memory_order_release);
6434
+ }
6435
+
6436
+ void SetupSyncPoints() {
6437
+ SyncPoint::GetInstance()->DisableProcessing();
6438
+ SyncPoint::GetInstance()->SetCallBack(sync_point_, [&](void* arg) {
6439
+ Status* s = reinterpret_cast<Status*>(arg);
6440
+ assert(s);
6441
+ *s = Status::IOError("Injected IO error.");
6442
+ });
6443
+ }
6444
+
6445
+ const std::string sync_point_;
6446
+ };
6447
+
6448
+ INSTANTIATE_TEST_CASE_P(DistributedFS, RenameCurrentTest,
6449
+ ::testing::Values("SetCurrentFile:BeforeRename",
6450
+ "SetCurrentFile:AfterRename"));
6451
+
6452
+ TEST_P(RenameCurrentTest, Open) {
6453
+ Destroy(last_options_);
6454
+ Options options = GetDefaultOptions();
6455
+ options.create_if_missing = true;
6456
+ SetupSyncPoints();
6457
+ SyncPoint::GetInstance()->EnableProcessing();
6458
+ Status s = TryReopen(options);
6459
+ ASSERT_NOK(s);
6460
+
6461
+ SyncPoint::GetInstance()->DisableProcessing();
6462
+ Reopen(options);
6463
+ }
6464
+
6465
+ TEST_P(RenameCurrentTest, Flush) {
6466
+ Destroy(last_options_);
6467
+ Options options = GetDefaultOptions();
6468
+ options.max_manifest_file_size = 1;
6469
+ options.create_if_missing = true;
6470
+ Reopen(options);
6471
+ ASSERT_OK(Put("key", "value"));
6472
+ SetupSyncPoints();
6473
+ SyncPoint::GetInstance()->EnableProcessing();
6474
+ ASSERT_NOK(Flush());
6475
+
6476
+ ASSERT_NOK(Put("foo", "value"));
6477
+
6478
+ SyncPoint::GetInstance()->DisableProcessing();
6479
+ Reopen(options);
6480
+ ASSERT_EQ("value", Get("key"));
6481
+ ASSERT_EQ("NOT_FOUND", Get("foo"));
6482
+ }
6483
+
6484
+ TEST_P(RenameCurrentTest, Compaction) {
6485
+ Destroy(last_options_);
6486
+ Options options = GetDefaultOptions();
6487
+ options.max_manifest_file_size = 1;
6488
+ options.create_if_missing = true;
6489
+ Reopen(options);
6490
+ ASSERT_OK(Put("a", "a_value"));
6491
+ ASSERT_OK(Put("c", "c_value"));
6492
+ ASSERT_OK(Flush());
6493
+
6494
+ ASSERT_OK(Put("b", "b_value"));
6495
+ ASSERT_OK(Put("d", "d_value"));
6496
+ ASSERT_OK(Flush());
6497
+
6498
+ SetupSyncPoints();
6499
+ SyncPoint::GetInstance()->EnableProcessing();
6500
+ ASSERT_NOK(db_->CompactRange(CompactRangeOptions(), /*begin=*/nullptr,
6501
+ /*end=*/nullptr));
6502
+
6503
+ ASSERT_NOK(Put("foo", "value"));
6504
+
6505
+ SyncPoint::GetInstance()->DisableProcessing();
6506
+ Reopen(options);
6507
+ ASSERT_EQ("NOT_FOUND", Get("foo"));
6508
+ ASSERT_EQ("d_value", Get("d"));
6509
+ }
6510
+
6511
+ TEST_F(DBTest2, BottommostTemperature) {
6512
+ class TestListener : public EventListener {
6513
+ public:
6514
+ void OnFileReadFinish(const FileOperationInfo& info) override {
6515
+ UpdateFileTemperature(info);
6516
+ }
6517
+
6518
+ void OnFileWriteFinish(const FileOperationInfo& info) override {
6519
+ UpdateFileTemperature(info);
6520
+ }
6521
+
6522
+ void OnFileFlushFinish(const FileOperationInfo& info) override {
6523
+ UpdateFileTemperature(info);
6524
+ }
6525
+
6526
+ void OnFileSyncFinish(const FileOperationInfo& info) override {
6527
+ UpdateFileTemperature(info);
6528
+ }
6529
+
6530
+ void OnFileCloseFinish(const FileOperationInfo& info) override {
6531
+ UpdateFileTemperature(info);
6532
+ }
6533
+
6534
+ bool ShouldBeNotifiedOnFileIO() override { return true; }
6535
+
6536
+ std::unordered_map<uint64_t, Temperature> file_temperatures;
6537
+
6538
+ private:
6539
+ void UpdateFileTemperature(const FileOperationInfo& info) {
6540
+ auto filename = GetFileName(info.path);
6541
+ uint64_t number;
6542
+ FileType type;
6543
+ ASSERT_TRUE(ParseFileName(filename, &number, &type));
6544
+ if (type == kTableFile) {
6545
+ MutexLock l(&mutex_);
6546
+ auto ret = file_temperatures.insert({number, info.temperature});
6547
+ if (!ret.second) {
6548
+ // the same file temperature should always be the same for all events
6549
+ ASSERT_TRUE(ret.first->second == info.temperature);
6550
+ }
6551
+ }
6552
+ }
6553
+
6554
+ std::string GetFileName(const std::string& fname) {
6555
+ auto filename = fname.substr(fname.find_last_of(kFilePathSeparator) + 1);
6556
+ // workaround only for Windows that the file path could contain both
6557
+ // Windows FilePathSeparator and '/'
6558
+ filename = filename.substr(filename.find_last_of('/') + 1);
6559
+ return filename;
6560
+ }
6561
+
6562
+ port::Mutex mutex_;
6563
+ };
6564
+
6565
+ auto* listener = new TestListener();
6566
+
6567
+ Options options = CurrentOptions();
6568
+ options.bottommost_temperature = Temperature::kWarm;
6569
+ options.level0_file_num_compaction_trigger = 2;
6570
+ options.statistics = CreateDBStatistics();
6571
+ options.listeners.emplace_back(listener);
6572
+ Reopen(options);
6573
+
6574
+ auto size = GetSstSizeHelper(Temperature::kUnknown);
6575
+ ASSERT_EQ(size, 0);
6576
+ size = GetSstSizeHelper(Temperature::kWarm);
6577
+ ASSERT_EQ(size, 0);
6578
+ size = GetSstSizeHelper(Temperature::kHot);
6579
+ ASSERT_EQ(size, 0);
6580
+
6581
+ ASSERT_OK(Put("foo", "bar"));
6582
+ ASSERT_OK(Put("bar", "bar"));
6583
+ ASSERT_OK(Flush());
6584
+ ASSERT_OK(Put("foo", "bar"));
6585
+ ASSERT_OK(Put("bar", "bar"));
6586
+ ASSERT_OK(Flush());
6587
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
6588
+
6589
+ get_iostats_context()->Reset();
6590
+ IOStatsContext* iostats = get_iostats_context();
6591
+
6592
+ ColumnFamilyMetaData metadata;
6593
+ db_->GetColumnFamilyMetaData(&metadata);
6594
+ ASSERT_EQ(1, metadata.file_count);
6595
+ SstFileMetaData meta = metadata.levels[1].files[0];
6596
+ ASSERT_EQ(Temperature::kWarm, meta.temperature);
6597
+ uint64_t number;
6598
+ FileType type;
6599
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6600
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6601
+
6602
+ size = GetSstSizeHelper(Temperature::kUnknown);
6603
+ ASSERT_EQ(size, 0);
6604
+ size = GetSstSizeHelper(Temperature::kWarm);
6605
+ ASSERT_GT(size, 0);
6606
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6607
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.warm_file_read_count, 0);
6608
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6609
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_BYTES), 0);
6610
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_BYTES), 0);
6611
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_BYTES), 0);
6612
+
6613
+ ASSERT_EQ("bar", Get("foo"));
6614
+
6615
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6616
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.warm_file_read_count, 1);
6617
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6618
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_bytes_read, 0);
6619
+ ASSERT_GT(iostats->file_io_stats_by_temperature.warm_file_bytes_read, 0);
6620
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.cold_file_bytes_read, 0);
6621
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_BYTES), 0);
6622
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_BYTES), 0);
6623
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_BYTES), 0);
6624
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_COUNT), 0);
6625
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_COUNT), 0);
6626
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_COUNT), 0);
6627
+
6628
+ // non-bottommost file still has unknown temperature
6629
+ ASSERT_OK(Put("foo", "bar"));
6630
+ ASSERT_OK(Put("bar", "bar"));
6631
+ ASSERT_OK(Flush());
6632
+ ASSERT_EQ("bar", Get("bar"));
6633
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6634
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.warm_file_read_count, 1);
6635
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6636
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_bytes_read, 0);
6637
+ ASSERT_GT(iostats->file_io_stats_by_temperature.warm_file_bytes_read, 0);
6638
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.cold_file_bytes_read, 0);
6639
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_BYTES), 0);
6640
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_BYTES), 0);
6641
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_BYTES), 0);
6642
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_COUNT), 0);
6643
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_COUNT), 0);
6644
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_COUNT), 0);
6645
+
6646
+ db_->GetColumnFamilyMetaData(&metadata);
6647
+ ASSERT_EQ(2, metadata.file_count);
6648
+ meta = metadata.levels[0].files[0];
6649
+ ASSERT_EQ(Temperature::kUnknown, meta.temperature);
6650
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6651
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6652
+
6653
+ meta = metadata.levels[1].files[0];
6654
+ ASSERT_EQ(Temperature::kWarm, meta.temperature);
6655
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6656
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6657
+
6658
+ size = GetSstSizeHelper(Temperature::kUnknown);
6659
+ ASSERT_GT(size, 0);
6660
+ size = GetSstSizeHelper(Temperature::kWarm);
6661
+ ASSERT_GT(size, 0);
6662
+
6663
+ // reopen and check the information is persisted
6664
+ Reopen(options);
6665
+ db_->GetColumnFamilyMetaData(&metadata);
6666
+ ASSERT_EQ(2, metadata.file_count);
6667
+ meta = metadata.levels[0].files[0];
6668
+ ASSERT_EQ(Temperature::kUnknown, meta.temperature);
6669
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6670
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6671
+
6672
+ meta = metadata.levels[1].files[0];
6673
+ ASSERT_EQ(Temperature::kWarm, meta.temperature);
6674
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6675
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6676
+ size = GetSstSizeHelper(Temperature::kUnknown);
6677
+ ASSERT_GT(size, 0);
6678
+ size = GetSstSizeHelper(Temperature::kWarm);
6679
+ ASSERT_GT(size, 0);
6680
+
6681
+ // check other non-exist temperatures
6682
+ size = GetSstSizeHelper(Temperature::kHot);
6683
+ ASSERT_EQ(size, 0);
6684
+ size = GetSstSizeHelper(Temperature::kCold);
6685
+ ASSERT_EQ(size, 0);
6686
+ std::string prop;
6687
+ ASSERT_TRUE(dbfull()->GetProperty(
6688
+ DB::Properties::kLiveSstFilesSizeAtTemperature + std::to_string(22),
6689
+ &prop));
6690
+ ASSERT_EQ(std::atoi(prop.c_str()), 0);
6691
+
6692
+ Reopen(options);
6693
+ db_->GetColumnFamilyMetaData(&metadata);
6694
+ ASSERT_EQ(2, metadata.file_count);
6695
+ meta = metadata.levels[0].files[0];
6696
+ ASSERT_EQ(Temperature::kUnknown, meta.temperature);
6697
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6698
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6699
+
6700
+ meta = metadata.levels[1].files[0];
6701
+ ASSERT_EQ(Temperature::kWarm, meta.temperature);
6702
+ ASSERT_TRUE(ParseFileName(meta.name, &number, &type));
6703
+ ASSERT_EQ(listener->file_temperatures.at(number), meta.temperature);
6704
+ }
6705
+
6706
+ TEST_F(DBTest2, BottommostTemperatureUniversal) {
6707
+ const int kTriggerNum = 3;
6708
+ const int kNumLevels = 5;
6709
+ const int kBottommostLevel = kNumLevels - 1;
6710
+ Options options = CurrentOptions();
6711
+ options.compaction_style = kCompactionStyleUniversal;
6712
+ options.level0_file_num_compaction_trigger = kTriggerNum;
6713
+ options.num_levels = kNumLevels;
6714
+ options.statistics = CreateDBStatistics();
6715
+ DestroyAndReopen(options);
6716
+
6717
+ auto size = GetSstSizeHelper(Temperature::kUnknown);
6718
+ ASSERT_EQ(size, 0);
6719
+ size = GetSstSizeHelper(Temperature::kWarm);
6720
+ ASSERT_EQ(size, 0);
6721
+ size = GetSstSizeHelper(Temperature::kHot);
6722
+ ASSERT_EQ(size, 0);
6723
+ get_iostats_context()->Reset();
6724
+ IOStatsContext* iostats = get_iostats_context();
6725
+
6726
+ for (int i = 0; i < kTriggerNum; i++) {
6727
+ ASSERT_OK(Put("foo", "bar"));
6728
+ ASSERT_OK(Put("bar", "bar"));
6729
+ ASSERT_OK(Flush());
6730
+ }
6731
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
6732
+
6733
+ ColumnFamilyMetaData metadata;
6734
+ db_->GetColumnFamilyMetaData(&metadata);
6735
+ ASSERT_EQ(1, metadata.file_count);
6736
+ ASSERT_EQ(Temperature::kUnknown,
6737
+ metadata.levels[kBottommostLevel].files[0].temperature);
6738
+ size = GetSstSizeHelper(Temperature::kUnknown);
6739
+ ASSERT_GT(size, 0);
6740
+ size = GetSstSizeHelper(Temperature::kWarm);
6741
+ ASSERT_EQ(size, 0);
6742
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6743
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.warm_file_read_count, 0);
6744
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6745
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_BYTES), 0);
6746
+ ASSERT_EQ(options.statistics->getTickerCount(WARM_FILE_READ_BYTES), 0);
6747
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_BYTES), 0);
6748
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_COUNT), 0);
6749
+ ASSERT_EQ(options.statistics->getTickerCount(WARM_FILE_READ_COUNT), 0);
6750
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_COUNT), 0);
6751
+ ASSERT_EQ("bar", Get("foo"));
6752
+
6753
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6754
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.warm_file_read_count, 0);
6755
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_read_count, 0);
6756
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.hot_file_bytes_read, 0);
6757
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.warm_file_bytes_read, 0);
6758
+ ASSERT_EQ(iostats->file_io_stats_by_temperature.cold_file_bytes_read, 0);
6759
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_BYTES), 0);
6760
+ ASSERT_EQ(options.statistics->getTickerCount(WARM_FILE_READ_BYTES), 0);
6761
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_BYTES), 0);
6762
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_COUNT), 0);
6763
+ ASSERT_EQ(options.statistics->getTickerCount(WARM_FILE_READ_COUNT), 0);
6764
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_COUNT), 0);
6765
+
6766
+ ASSERT_OK(Put("foo", "bar"));
6767
+ ASSERT_OK(Put("bar", "bar"));
6768
+ ASSERT_OK(Flush());
6769
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
6770
+ db_->GetColumnFamilyMetaData(&metadata);
6771
+ ASSERT_EQ(2, metadata.file_count);
6772
+ ASSERT_EQ(Temperature::kUnknown, metadata.levels[0].files[0].temperature);
6773
+ size = GetSstSizeHelper(Temperature::kUnknown);
6774
+ ASSERT_GT(size, 0);
6775
+ size = GetSstSizeHelper(Temperature::kWarm);
6776
+ ASSERT_EQ(size, 0);
6777
+
6778
+ // Update bottommost temperature
6779
+ options.bottommost_temperature = Temperature::kWarm;
6780
+ Reopen(options);
6781
+ db_->GetColumnFamilyMetaData(&metadata);
6782
+ // Should not impact existing ones
6783
+ ASSERT_EQ(Temperature::kUnknown,
6784
+ metadata.levels[kBottommostLevel].files[0].temperature);
6785
+ size = GetSstSizeHelper(Temperature::kUnknown);
6786
+ ASSERT_GT(size, 0);
6787
+ size = GetSstSizeHelper(Temperature::kWarm);
6788
+ ASSERT_EQ(size, 0);
6789
+
6790
+ // new generated file should have the new settings
6791
+ ASSERT_OK(db_->CompactRange(CompactRangeOptions(), nullptr, nullptr));
6792
+ db_->GetColumnFamilyMetaData(&metadata);
6793
+ ASSERT_EQ(1, metadata.file_count);
6794
+ ASSERT_EQ(Temperature::kWarm,
6795
+ metadata.levels[kBottommostLevel].files[0].temperature);
6796
+ size = GetSstSizeHelper(Temperature::kUnknown);
6797
+ ASSERT_EQ(size, 0);
6798
+ size = GetSstSizeHelper(Temperature::kWarm);
6799
+ ASSERT_GT(size, 0);
6800
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_BYTES), 0);
6801
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_BYTES), 0);
6802
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_BYTES), 0);
6803
+ ASSERT_EQ(options.statistics->getTickerCount(HOT_FILE_READ_COUNT), 0);
6804
+ ASSERT_GT(options.statistics->getTickerCount(WARM_FILE_READ_COUNT), 0);
6805
+ ASSERT_EQ(options.statistics->getTickerCount(COLD_FILE_READ_COUNT), 0);
6806
+
6807
+ // non-bottommost file still has unknown temperature
6808
+ ASSERT_OK(Put("foo", "bar"));
6809
+ ASSERT_OK(Put("bar", "bar"));
6810
+ ASSERT_OK(Flush());
6811
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
6812
+ db_->GetColumnFamilyMetaData(&metadata);
6813
+ ASSERT_EQ(2, metadata.file_count);
6814
+ ASSERT_EQ(Temperature::kUnknown, metadata.levels[0].files[0].temperature);
6815
+ size = GetSstSizeHelper(Temperature::kUnknown);
6816
+ ASSERT_GT(size, 0);
6817
+ size = GetSstSizeHelper(Temperature::kWarm);
6818
+ ASSERT_GT(size, 0);
6819
+
6820
+ // check other non-exist temperatures
6821
+ size = GetSstSizeHelper(Temperature::kHot);
6822
+ ASSERT_EQ(size, 0);
6823
+ size = GetSstSizeHelper(Temperature::kCold);
6824
+ ASSERT_EQ(size, 0);
6825
+ std::string prop;
6826
+ ASSERT_TRUE(dbfull()->GetProperty(
6827
+ DB::Properties::kLiveSstFilesSizeAtTemperature + std::to_string(22),
6828
+ &prop));
6829
+ ASSERT_EQ(std::atoi(prop.c_str()), 0);
6830
+
6831
+ // Update bottommost temperature dynamically with SetOptions
6832
+ auto s = db_->SetOptions({{"bottommost_temperature", "kCold"}});
6833
+ ASSERT_OK(s);
6834
+ ASSERT_EQ(db_->GetOptions().bottommost_temperature, Temperature::kCold);
6835
+ db_->GetColumnFamilyMetaData(&metadata);
6836
+ // Should not impact the existing files
6837
+ ASSERT_EQ(Temperature::kWarm,
6838
+ metadata.levels[kBottommostLevel].files[0].temperature);
6839
+ size = GetSstSizeHelper(Temperature::kUnknown);
6840
+ ASSERT_GT(size, 0);
6841
+ size = GetSstSizeHelper(Temperature::kWarm);
6842
+ ASSERT_GT(size, 0);
6843
+ size = GetSstSizeHelper(Temperature::kCold);
6844
+ ASSERT_EQ(size, 0);
6845
+
6846
+ // new generated files should have the new settings
6847
+ ASSERT_OK(db_->CompactRange(CompactRangeOptions(), nullptr, nullptr));
6848
+ db_->GetColumnFamilyMetaData(&metadata);
6849
+ ASSERT_EQ(1, metadata.file_count);
6850
+ ASSERT_EQ(Temperature::kCold,
6851
+ metadata.levels[kBottommostLevel].files[0].temperature);
6852
+ size = GetSstSizeHelper(Temperature::kUnknown);
6853
+ ASSERT_EQ(size, 0);
6854
+ size = GetSstSizeHelper(Temperature::kWarm);
6855
+ ASSERT_EQ(size, 0);
6856
+ size = GetSstSizeHelper(Temperature::kCold);
6857
+ ASSERT_GT(size, 0);
6858
+ }
6859
+
6860
+ TEST_F(DBTest2, LastLevelStatistics) {
6861
+ Options options = CurrentOptions();
6862
+ options.bottommost_temperature = Temperature::kWarm;
6863
+ options.level0_file_num_compaction_trigger = 2;
6864
+ options.level_compaction_dynamic_level_bytes = true;
6865
+ options.statistics = CreateDBStatistics();
6866
+ Reopen(options);
6867
+
6868
+ // generate 1 sst on level 0
6869
+ ASSERT_OK(Put("foo", "bar"));
6870
+ ASSERT_OK(Put("bar", "bar"));
6871
+ ASSERT_OK(Flush());
6872
+ ASSERT_EQ("bar", Get("bar"));
6873
+
6874
+ ASSERT_GT(options.statistics->getTickerCount(NON_LAST_LEVEL_READ_BYTES), 0);
6875
+ ASSERT_GT(options.statistics->getTickerCount(NON_LAST_LEVEL_READ_COUNT), 0);
6876
+ ASSERT_EQ(options.statistics->getTickerCount(LAST_LEVEL_READ_BYTES), 0);
6877
+ ASSERT_EQ(options.statistics->getTickerCount(LAST_LEVEL_READ_COUNT), 0);
6878
+
6879
+ // 2nd flush to trigger compaction
6880
+ ASSERT_OK(Put("foo", "bar"));
6881
+ ASSERT_OK(Put("bar", "bar"));
6882
+ ASSERT_OK(Flush());
6883
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
6884
+ ASSERT_EQ("bar", Get("bar"));
6885
+
6886
+ ASSERT_EQ(options.statistics->getTickerCount(LAST_LEVEL_READ_BYTES),
6887
+ options.statistics->getTickerCount(WARM_FILE_READ_BYTES));
6888
+ ASSERT_EQ(options.statistics->getTickerCount(LAST_LEVEL_READ_COUNT),
6889
+ options.statistics->getTickerCount(WARM_FILE_READ_COUNT));
6890
+
6891
+ auto pre_bytes =
6892
+ options.statistics->getTickerCount(NON_LAST_LEVEL_READ_BYTES);
6893
+ auto pre_count =
6894
+ options.statistics->getTickerCount(NON_LAST_LEVEL_READ_COUNT);
6895
+
6896
+ // 3rd flush to generate 1 sst on level 0
6897
+ ASSERT_OK(Put("foo", "bar"));
6898
+ ASSERT_OK(Put("bar", "bar"));
6899
+ ASSERT_OK(Flush());
6900
+ ASSERT_EQ("bar", Get("bar"));
6901
+
6902
+ ASSERT_GT(options.statistics->getTickerCount(NON_LAST_LEVEL_READ_BYTES),
6903
+ pre_bytes);
6904
+ ASSERT_GT(options.statistics->getTickerCount(NON_LAST_LEVEL_READ_COUNT),
6905
+ pre_count);
6906
+ ASSERT_EQ(options.statistics->getTickerCount(LAST_LEVEL_READ_BYTES),
6907
+ options.statistics->getTickerCount(WARM_FILE_READ_BYTES));
6908
+ ASSERT_EQ(options.statistics->getTickerCount(LAST_LEVEL_READ_COUNT),
6909
+ options.statistics->getTickerCount(WARM_FILE_READ_COUNT));
6910
+ }
6911
+
6912
+ TEST_F(DBTest2, CheckpointFileTemperature) {
6913
+ class NoLinkTestFS : public FileTemperatureTestFS {
6914
+ using FileTemperatureTestFS::FileTemperatureTestFS;
6915
+
6916
+ IOStatus LinkFile(const std::string&, const std::string&, const IOOptions&,
6917
+ IODebugContext*) override {
6918
+ // return not supported to force checkpoint copy the file instead of just
6919
+ // link
6920
+ return IOStatus::NotSupported();
6921
+ }
6922
+ };
6923
+ auto test_fs = std::make_shared<NoLinkTestFS>(env_->GetFileSystem());
6924
+ std::unique_ptr<Env> env(new CompositeEnvWrapper(env_, test_fs));
6925
+ Options options = CurrentOptions();
6926
+ options.bottommost_temperature = Temperature::kWarm;
6927
+ options.level0_file_num_compaction_trigger = 2;
6928
+ options.env = env.get();
6929
+ Reopen(options);
6930
+
6931
+ // generate a bottommost file and a non-bottommost file
6932
+ ASSERT_OK(Put("foo", "bar"));
6933
+ ASSERT_OK(Put("bar", "bar"));
6934
+ ASSERT_OK(Flush());
6935
+ ASSERT_OK(Put("foo", "bar"));
6936
+ ASSERT_OK(Put("bar", "bar"));
6937
+ ASSERT_OK(Flush());
6938
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
6939
+ ASSERT_OK(Put("foo", "bar"));
6940
+ ASSERT_OK(Put("bar", "bar"));
6941
+ ASSERT_OK(Flush());
6942
+ auto size = GetSstSizeHelper(Temperature::kWarm);
6943
+ ASSERT_GT(size, 0);
6944
+
6945
+ std::map<uint64_t, Temperature> temperatures;
6946
+ std::vector<LiveFileStorageInfo> infos;
6947
+ ASSERT_OK(
6948
+ dbfull()->GetLiveFilesStorageInfo(LiveFilesStorageInfoOptions(), &infos));
6949
+ for (auto info : infos) {
6950
+ temperatures.emplace(info.file_number, info.temperature);
6951
+ }
6952
+
6953
+ test_fs->PopRequestedSstFileTemperatures();
6954
+ Checkpoint* checkpoint;
6955
+ ASSERT_OK(Checkpoint::Create(db_, &checkpoint));
6956
+ ASSERT_OK(
6957
+ checkpoint->CreateCheckpoint(dbname_ + kFilePathSeparator + "tempcp"));
6958
+
6959
+ // checking src file src_temperature hints: 2 sst files: 1 sst is kWarm,
6960
+ // another is kUnknown
6961
+ std::vector<std::pair<uint64_t, Temperature>> requested_temps;
6962
+ test_fs->PopRequestedSstFileTemperatures(&requested_temps);
6963
+ // Two requests
6964
+ ASSERT_EQ(requested_temps.size(), 2);
6965
+ std::set<uint64_t> distinct_requests;
6966
+ for (const auto& requested_temp : requested_temps) {
6967
+ // Matching manifest temperatures
6968
+ ASSERT_EQ(temperatures.at(requested_temp.first), requested_temp.second);
6969
+ distinct_requests.insert(requested_temp.first);
6970
+ }
6971
+ // Each request to distinct file
6972
+ ASSERT_EQ(distinct_requests.size(), requested_temps.size());
6973
+
6974
+ delete checkpoint;
6975
+ Close();
6976
+ }
6977
+
6978
+ TEST_F(DBTest2, FileTemperatureManifestFixup) {
6979
+ auto test_fs = std::make_shared<FileTemperatureTestFS>(env_->GetFileSystem());
6980
+ std::unique_ptr<Env> env(new CompositeEnvWrapper(env_, test_fs));
6981
+ Options options = CurrentOptions();
6982
+ options.bottommost_temperature = Temperature::kWarm;
6983
+ options.level0_file_num_compaction_trigger = 2;
6984
+ options.env = env.get();
6985
+ std::vector<std::string> cfs = {/*"default",*/ "test1", "test2"};
6986
+ CreateAndReopenWithCF(cfs, options);
6987
+ // Needed for later re-opens (weird)
6988
+ cfs.insert(cfs.begin(), kDefaultColumnFamilyName);
6989
+
6990
+ // Generate a bottommost file in all CFs
6991
+ for (int cf = 0; cf < 3; ++cf) {
6992
+ ASSERT_OK(Put(cf, "a", "val"));
6993
+ ASSERT_OK(Put(cf, "c", "val"));
6994
+ ASSERT_OK(Flush(cf));
6995
+ ASSERT_OK(Put(cf, "b", "val"));
6996
+ ASSERT_OK(Put(cf, "d", "val"));
6997
+ ASSERT_OK(Flush(cf));
6998
+ }
6999
+ ASSERT_OK(dbfull()->TEST_WaitForCompact());
7000
+
7001
+ // verify
7002
+ ASSERT_GT(GetSstSizeHelper(Temperature::kWarm), 0);
7003
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kUnknown), 0);
7004
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kCold), 0);
7005
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kHot), 0);
7006
+
7007
+ // Generate a non-bottommost file in all CFs
7008
+ for (int cf = 0; cf < 3; ++cf) {
7009
+ ASSERT_OK(Put(cf, "e", "val"));
7010
+ ASSERT_OK(Flush(cf));
7011
+ }
7012
+
7013
+ // re-verify
7014
+ ASSERT_GT(GetSstSizeHelper(Temperature::kWarm), 0);
7015
+ // Not supported: ASSERT_GT(GetSstSizeHelper(Temperature::kUnknown), 0);
7016
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kCold), 0);
7017
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kHot), 0);
7018
+
7019
+ // Now change FS temperature on bottommost file(s) to kCold
7020
+ std::map<uint64_t, Temperature> current_temps;
7021
+ test_fs->CopyCurrentSstFileTemperatures(&current_temps);
7022
+ for (auto e : current_temps) {
7023
+ if (e.second == Temperature::kWarm) {
7024
+ test_fs->OverrideSstFileTemperature(e.first, Temperature::kCold);
7025
+ }
7026
+ }
7027
+ // Metadata not yet updated
7028
+ ASSERT_EQ(Get("a"), "val");
7029
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kCold), 0);
7030
+
7031
+ // Update with Close and UpdateManifestForFilesState, but first save cf
7032
+ // descriptors
7033
+ std::vector<ColumnFamilyDescriptor> column_families;
7034
+ for (size_t i = 0; i < handles_.size(); ++i) {
7035
+ ColumnFamilyDescriptor cfdescriptor;
7036
+ // GetDescriptor is not implemented for ROCKSDB_LITE
7037
+ handles_[i]->GetDescriptor(&cfdescriptor).PermitUncheckedError();
7038
+ column_families.push_back(cfdescriptor);
7039
+ }
7040
+ Close();
7041
+ experimental::UpdateManifestForFilesStateOptions update_opts;
7042
+ update_opts.update_temperatures = true;
7043
+
7044
+ ASSERT_OK(experimental::UpdateManifestForFilesState(
7045
+ options, dbname_, column_families, update_opts));
7046
+
7047
+ // Re-open and re-verify after update
7048
+ ReopenWithColumnFamilies(cfs, options);
7049
+ ASSERT_GT(GetSstSizeHelper(Temperature::kCold), 0);
7050
+ // Not supported: ASSERT_GT(GetSstSizeHelper(Temperature::kUnknown), 0);
7051
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kWarm), 0);
7052
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kHot), 0);
7053
+
7054
+ // Change kUnknown to kHot
7055
+ test_fs->CopyCurrentSstFileTemperatures(&current_temps);
7056
+ for (auto e : current_temps) {
7057
+ if (e.second == Temperature::kUnknown) {
7058
+ test_fs->OverrideSstFileTemperature(e.first, Temperature::kHot);
7059
+ }
7060
+ }
7061
+
7062
+ // Update with Close and UpdateManifestForFilesState
7063
+ Close();
7064
+ ASSERT_OK(experimental::UpdateManifestForFilesState(
7065
+ options, dbname_, column_families, update_opts));
7066
+
7067
+ // Re-open and re-verify after update
7068
+ ReopenWithColumnFamilies(cfs, options);
7069
+ ASSERT_GT(GetSstSizeHelper(Temperature::kCold), 0);
7070
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kUnknown), 0);
7071
+ ASSERT_EQ(GetSstSizeHelper(Temperature::kWarm), 0);
7072
+ ASSERT_GT(GetSstSizeHelper(Temperature::kHot), 0);
7073
+
7074
+ Close();
7075
+ }
5366
7076
  #endif // ROCKSDB_LITE
5367
7077
 
5368
7078
  // WAL recovery mode is WALRecoveryMode::kPointInTimeRecovery.
@@ -5390,15 +7100,111 @@ TEST_F(DBTest2, PointInTimeRecoveryWithIOErrorWhileReadingWal) {
5390
7100
  Status s = TryReopen(options);
5391
7101
  ASSERT_TRUE(s.IsIOError());
5392
7102
  }
5393
- } // namespace ROCKSDB_NAMESPACE
5394
7103
 
5395
- #ifdef ROCKSDB_UNITTESTS_WITH_CUSTOM_OBJECTS_FROM_STATIC_LIBS
5396
- extern "C" {
5397
- void RegisterCustomObjects(int argc, char** argv);
7104
+ TEST_F(DBTest2, PointInTimeRecoveryWithSyncFailureInCFCreation) {
7105
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->LoadDependency(
7106
+ {{"DBImpl::BackgroundCallFlush:Start:1",
7107
+ "PointInTimeRecoveryWithSyncFailureInCFCreation:1"},
7108
+ {"PointInTimeRecoveryWithSyncFailureInCFCreation:2",
7109
+ "DBImpl::BackgroundCallFlush:Start:2"}});
7110
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->EnableProcessing();
7111
+
7112
+ CreateColumnFamilies({"test1"}, Options());
7113
+ ASSERT_OK(Put("foo", "bar"));
7114
+
7115
+ // Creating a CF when a flush is going on, log is synced but the
7116
+ // closed log file is not synced and corrupted.
7117
+ port::Thread flush_thread([&]() { ASSERT_NOK(Flush()); });
7118
+ TEST_SYNC_POINT("PointInTimeRecoveryWithSyncFailureInCFCreation:1");
7119
+ CreateColumnFamilies({"test2"}, Options());
7120
+ env_->corrupt_in_sync_ = true;
7121
+ TEST_SYNC_POINT("PointInTimeRecoveryWithSyncFailureInCFCreation:2");
7122
+ flush_thread.join();
7123
+ env_->corrupt_in_sync_ = false;
7124
+ ROCKSDB_NAMESPACE::SyncPoint::GetInstance()->DisableProcessing();
7125
+
7126
+ // Reopening the DB should not corrupt anything
7127
+ Options options = CurrentOptions();
7128
+ options.wal_recovery_mode = WALRecoveryMode::kPointInTimeRecovery;
7129
+ ReopenWithColumnFamilies({"default", "test1", "test2"}, options);
5398
7130
  }
5399
- #else
5400
- void RegisterCustomObjects(int /*argc*/, char** /*argv*/) {}
5401
- #endif // !ROCKSDB_UNITTESTS_WITH_CUSTOM_OBJECTS_FROM_STATIC_LIBS
7131
+
7132
+ TEST_F(DBTest2, RenameDirectory) {
7133
+ Options options = CurrentOptions();
7134
+ DestroyAndReopen(options);
7135
+ ASSERT_OK(Put("foo", "value0"));
7136
+ Close();
7137
+ auto old_dbname = dbname_;
7138
+ auto new_dbname = dbname_ + "_2";
7139
+ EXPECT_OK(env_->RenameFile(dbname_, new_dbname));
7140
+ options.create_if_missing = false;
7141
+ dbname_ = new_dbname;
7142
+ ASSERT_OK(TryReopen(options));
7143
+ ASSERT_EQ("value0", Get("foo"));
7144
+ Destroy(options);
7145
+ dbname_ = old_dbname;
7146
+ }
7147
+
7148
+ #ifndef ROCKSDB_LITE
7149
+ TEST_F(DBTest2, GetLatestSeqAndTsForKey) {
7150
+ Destroy(last_options_);
7151
+
7152
+ Options options = CurrentOptions();
7153
+ options.max_write_buffer_size_to_maintain = 64 << 10;
7154
+ options.create_if_missing = true;
7155
+ options.disable_auto_compactions = true;
7156
+ options.comparator = test::BytewiseComparatorWithU64TsWrapper();
7157
+ options.statistics = CreateDBStatistics();
7158
+
7159
+ Reopen(options);
7160
+
7161
+ constexpr uint64_t kTsU64Value = 12;
7162
+
7163
+ for (uint64_t key = 0; key < 100; ++key) {
7164
+ std::string ts;
7165
+ PutFixed64(&ts, kTsU64Value);
7166
+
7167
+ std::string key_str;
7168
+ PutFixed64(&key_str, key);
7169
+ std::reverse(key_str.begin(), key_str.end());
7170
+ ASSERT_OK(db_->Put(WriteOptions(), key_str, ts, "value"));
7171
+ }
7172
+
7173
+ ASSERT_OK(Flush());
7174
+
7175
+ constexpr bool cache_only = true;
7176
+ constexpr SequenceNumber lower_bound_seq = 0;
7177
+ auto* cfhi = static_cast_with_check<ColumnFamilyHandleImpl>(
7178
+ dbfull()->DefaultColumnFamily());
7179
+ assert(cfhi);
7180
+ assert(cfhi->cfd());
7181
+ SuperVersion* sv = cfhi->cfd()->GetSuperVersion();
7182
+ for (uint64_t key = 0; key < 100; ++key) {
7183
+ std::string key_str;
7184
+ PutFixed64(&key_str, key);
7185
+ std::reverse(key_str.begin(), key_str.end());
7186
+ std::string ts;
7187
+ SequenceNumber seq = kMaxSequenceNumber;
7188
+ bool found_record_for_key = false;
7189
+ bool is_blob_index = false;
7190
+
7191
+ const Status s = dbfull()->GetLatestSequenceForKey(
7192
+ sv, key_str, cache_only, lower_bound_seq, &seq, &ts,
7193
+ &found_record_for_key, &is_blob_index);
7194
+ ASSERT_OK(s);
7195
+ std::string expected_ts;
7196
+ PutFixed64(&expected_ts, kTsU64Value);
7197
+ ASSERT_EQ(expected_ts, ts);
7198
+ ASSERT_TRUE(found_record_for_key);
7199
+ ASSERT_FALSE(is_blob_index);
7200
+ }
7201
+
7202
+ // Verify that no read to SST files.
7203
+ ASSERT_EQ(0, options.statistics->getTickerCount(GET_HIT_L0));
7204
+ }
7205
+ #endif // ROCKSDB_LITE
7206
+
7207
+ } // namespace ROCKSDB_NAMESPACE
5402
7208
 
5403
7209
  int main(int argc, char** argv) {
5404
7210
  ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();