use std::marker::PhantomData;
use std::sync::Arc;
use libc::{c_char, c_int, c_uchar};
use crate::ffi_util::bytes_from_raw;
use crate::{DBCompressionType, Temperature, ffi};
const DISABLE_COMPRESSION_OPTION: c_int = 0xff;
pub struct CompactionCancellationToken {
inner: *mut c_uchar,
}
unsafe impl Send for CompactionCancellationToken {}
unsafe impl Sync for CompactionCancellationToken {}
impl Default for CompactionCancellationToken {
fn default() -> Self {
Self::new()
}
}
impl CompactionCancellationToken {
pub fn new() -> Self {
let inner = unsafe { ffi::rocksdb_compaction_options_canceled_create() };
assert!(
!inner.is_null(),
"Could not create RocksDB compaction cancellation token"
);
Self { inner }
}
pub fn cancel(&self) {
unsafe {
ffi::rocksdb_compaction_options_canceled_set(self.inner, 1);
}
}
fn as_ptr(&self) -> *mut c_uchar {
self.inner
}
}
impl Drop for CompactionCancellationToken {
fn drop(&mut self) {
unsafe {
ffi::rocksdb_compaction_options_canceled_destroy(self.inner);
}
}
}
pub struct CompactionOptions {
pub(crate) inner: *mut ffi::rocksdb_compaction_options_t,
canceled: Option<Arc<CompactionCancellationToken>>,
}
unsafe impl Send for CompactionOptions {}
unsafe impl Sync for CompactionOptions {}
impl Default for CompactionOptions {
fn default() -> Self {
let inner = unsafe { ffi::rocksdb_compaction_options_create() };
assert!(
!inner.is_null(),
"Could not create RocksDB compaction options"
);
Self {
inner,
canceled: None,
}
}
}
impl Drop for CompactionOptions {
fn drop(&mut self) {
unsafe {
ffi::rocksdb_compaction_options_destroy(self.inner);
}
}
}
impl CompactionOptions {
pub fn set_compression(&mut self, t: DBCompressionType) {
unsafe {
ffi::rocksdb_compaction_options_set_compression(self.inner, t as c_int);
}
}
pub fn unset_compression(&mut self) {
unsafe {
ffi::rocksdb_compaction_options_set_compression(self.inner, DISABLE_COMPRESSION_OPTION);
}
}
pub fn get_compression(&self) -> Option<DBCompressionType> {
let raw = unsafe { ffi::rocksdb_compaction_options_get_compression(self.inner) };
DBCompressionType::try_from_raw(raw)
}
pub fn set_output_file_size_limit(&mut self, v: u64) {
unsafe {
ffi::rocksdb_compaction_options_set_output_file_size_limit(self.inner, v);
}
}
pub fn get_output_file_size_limit(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_options_get_output_file_size_limit(self.inner) }
}
pub fn set_max_subcompactions(&mut self, v: u32) {
unsafe {
ffi::rocksdb_compaction_options_set_max_subcompactions(self.inner, v);
}
}
pub fn get_max_subcompactions(&self) -> u32 {
unsafe { ffi::rocksdb_compaction_options_get_max_subcompactions(self.inner) }
}
pub fn set_allow_trivial_move(&mut self, v: bool) {
unsafe {
ffi::rocksdb_compaction_options_set_allow_trivial_move(self.inner, c_uchar::from(v));
}
}
pub fn get_allow_trivial_move(&self) -> bool {
unsafe { ffi::rocksdb_compaction_options_get_allow_trivial_move(self.inner) != 0 }
}
pub fn set_output_temperature_override(&mut self, v: Temperature) {
unsafe {
ffi::rocksdb_compaction_options_set_output_temperature_override(self.inner, v as c_int);
}
}
pub fn get_output_temperature_override(&self) -> Temperature {
let raw =
unsafe { ffi::rocksdb_compaction_options_get_output_temperature_override(self.inner) };
Temperature::from(raw)
}
pub fn set_canceled(&mut self, token: Arc<CompactionCancellationToken>) {
let ptr = token.as_ptr();
unsafe {
ffi::rocksdb_compaction_options_set_canceled(self.inner, ptr);
}
self.canceled = Some(token);
}
pub fn clear_canceled(&mut self) {
if self.canceled.is_none() {
return;
}
unsafe {
ffi::rocksdb_compaction_options_set_canceled(self.inner, std::ptr::null_mut());
}
self.canceled = None;
}
pub fn canceled(&self) -> Option<&Arc<CompactionCancellationToken>> {
self.canceled.as_ref()
}
}
type KeyPrefixGetter =
unsafe extern "C" fn(*const ffi::rocksdb_compaction_job_stats_t, *mut usize) -> *const c_char;
pub struct CompactionJobStats<'a> {
inner: *const ffi::rocksdb_compaction_job_stats_t,
_marker: PhantomData<&'a ()>,
}
impl<'a> CompactionJobStats<'a> {
pub(crate) unsafe fn from_ptr(
inner: *const ffi::rocksdb_compaction_job_stats_t,
) -> CompactionJobStats<'a> {
CompactionJobStats {
inner,
_marker: PhantomData,
}
}
pub fn elapsed_micros(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_elapsed_micros(self.inner) }
}
pub fn cpu_micros(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_cpu_micros(self.inner) }
}
pub fn has_accurate_num_input_records(&self) -> bool {
unsafe { ffi::rocksdb_compaction_job_stats_has_accurate_num_input_records(self.inner) != 0 }
}
pub fn num_input_records(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_input_records(self.inner) }
}
pub fn num_blobs_read(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_blobs_read(self.inner) }
}
pub fn num_input_files(&self) -> usize {
unsafe { ffi::rocksdb_compaction_job_stats_num_input_files(self.inner) }
}
pub fn num_input_files_at_output_level(&self) -> usize {
unsafe { ffi::rocksdb_compaction_job_stats_num_input_files_at_output_level(self.inner) }
}
pub fn num_filtered_input_files(&self) -> usize {
unsafe { ffi::rocksdb_compaction_job_stats_num_filtered_input_files(self.inner) }
}
pub fn num_filtered_input_files_at_output_level(&self) -> usize {
unsafe {
ffi::rocksdb_compaction_job_stats_num_filtered_input_files_at_output_level(self.inner)
}
}
pub fn num_output_records(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_output_records(self.inner) }
}
pub fn num_output_files(&self) -> usize {
unsafe { ffi::rocksdb_compaction_job_stats_num_output_files(self.inner) }
}
pub fn num_output_files_blob(&self) -> usize {
unsafe { ffi::rocksdb_compaction_job_stats_num_output_files_blob(self.inner) }
}
pub fn is_full_compaction(&self) -> bool {
unsafe { ffi::rocksdb_compaction_job_stats_is_full_compaction(self.inner) != 0 }
}
pub fn is_manual_compaction(&self) -> bool {
unsafe { ffi::rocksdb_compaction_job_stats_is_manual_compaction(self.inner) != 0 }
}
pub fn is_remote_compaction(&self) -> bool {
unsafe { ffi::rocksdb_compaction_job_stats_is_remote_compaction(self.inner) != 0 }
}
pub fn total_input_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_input_bytes(self.inner) }
}
pub fn total_skipped_input_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_skipped_input_bytes(self.inner) }
}
pub fn total_blob_bytes_read(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_blob_bytes_read(self.inner) }
}
pub fn total_output_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_output_bytes(self.inner) }
}
pub fn total_output_bytes_blob(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_output_bytes_blob(self.inner) }
}
pub fn num_input_files_trivially_moved(&self) -> usize {
unsafe { ffi::rocksdb_compaction_job_stats_num_input_files_trivially_moved(self.inner) }
}
pub fn num_records_replaced(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_records_replaced(self.inner) }
}
pub fn total_input_raw_key_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_input_raw_key_bytes(self.inner) }
}
pub fn total_input_raw_value_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_total_input_raw_value_bytes(self.inner) }
}
pub fn num_input_deletion_records(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_input_deletion_records(self.inner) }
}
pub fn num_expired_deletion_records(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_expired_deletion_records(self.inner) }
}
pub fn num_corrupt_keys(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_corrupt_keys(self.inner) }
}
pub fn file_write_nanos(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_file_write_nanos(self.inner) }
}
pub fn file_range_sync_nanos(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_file_range_sync_nanos(self.inner) }
}
pub fn file_fsync_nanos(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_file_fsync_nanos(self.inner) }
}
pub fn file_prepare_write_nanos(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_file_prepare_write_nanos(self.inner) }
}
pub fn smallest_output_key_prefix(&self) -> &'a [u8] {
self.key_prefix(ffi::rocksdb_compaction_job_stats_smallest_output_key_prefix)
}
pub fn largest_output_key_prefix(&self) -> &'a [u8] {
self.key_prefix(ffi::rocksdb_compaction_job_stats_largest_output_key_prefix)
}
pub fn num_single_del_fallthru(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_single_del_fallthru(self.inner) }
}
pub fn num_single_del_mismatch(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_job_stats_num_single_del_mismatch(self.inner) }
}
fn key_prefix(&self, getter: KeyPrefixGetter) -> &'a [u8] {
let mut len: usize = 0;
unsafe {
let ptr = getter(self.inner, &raw mut len);
bytes_from_raw(ptr, len)
}
}
}
pub struct CompactionFileInfo<'a> {
inner: *const ffi::rocksdb_compaction_file_info_t,
_marker: PhantomData<&'a ()>,
}
impl<'a> CompactionFileInfo<'a> {
pub(crate) unsafe fn from_ptr(
inner: *const ffi::rocksdb_compaction_file_info_t,
) -> CompactionFileInfo<'a> {
CompactionFileInfo {
inner,
_marker: PhantomData,
}
}
pub fn file_number(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_file_info_file_number(self.inner) }
}
pub fn level(&self) -> i32 {
unsafe { ffi::rocksdb_compaction_file_info_level(self.inner) }
}
pub fn oldest_blob_file_number(&self) -> u64 {
unsafe { ffi::rocksdb_compaction_file_info_oldest_blob_file_number(self.inner) }
}
}
pub struct BlobFileAdditionInfo<'a> {
inner: *const ffi::rocksdb_blob_file_addition_info_t,
_marker: PhantomData<&'a ()>,
}
impl<'a> BlobFileAdditionInfo<'a> {
pub(crate) unsafe fn from_ptr(
inner: *const ffi::rocksdb_blob_file_addition_info_t,
) -> BlobFileAdditionInfo<'a> {
BlobFileAdditionInfo {
inner,
_marker: PhantomData,
}
}
pub fn blob_file_path(&self) -> &'a [u8] {
let mut len: usize = 0;
unsafe {
let ptr = ffi::rocksdb_blob_file_addition_info_blob_file_path(self.inner, &raw mut len);
bytes_from_raw(ptr, len)
}
}
pub fn blob_file_number(&self) -> u64 {
unsafe { ffi::rocksdb_blob_file_addition_info_blob_file_number(self.inner) }
}
pub fn total_blob_count(&self) -> u64 {
unsafe { ffi::rocksdb_blob_file_addition_info_total_blob_count(self.inner) }
}
pub fn total_blob_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_blob_file_addition_info_total_blob_bytes(self.inner) }
}
}
pub struct BlobFileGarbageInfo<'a> {
inner: *const ffi::rocksdb_blob_file_garbage_info_t,
_marker: PhantomData<&'a ()>,
}
impl<'a> BlobFileGarbageInfo<'a> {
pub(crate) unsafe fn from_ptr(
inner: *const ffi::rocksdb_blob_file_garbage_info_t,
) -> BlobFileGarbageInfo<'a> {
BlobFileGarbageInfo {
inner,
_marker: PhantomData,
}
}
pub fn blob_file_path(&self) -> &'a [u8] {
let mut len: usize = 0;
unsafe {
let ptr = ffi::rocksdb_blob_file_garbage_info_blob_file_path(self.inner, &raw mut len);
bytes_from_raw(ptr, len)
}
}
pub fn blob_file_number(&self) -> u64 {
unsafe { ffi::rocksdb_blob_file_garbage_info_blob_file_number(self.inner) }
}
pub fn garbage_blob_count(&self) -> u64 {
unsafe { ffi::rocksdb_blob_file_garbage_info_garbage_blob_count(self.inner) }
}
pub fn garbage_blob_bytes(&self) -> u64 {
unsafe { ffi::rocksdb_blob_file_garbage_info_garbage_blob_bytes(self.inner) }
}
}