leveldb/database/
comparator.rs1use leveldb_sys::*;
8use libc::{size_t, c_void, c_char};
9use std::slice;
10use std::cmp::Ordering;
11
12pub trait Comparator {
18 fn name(&self) -> *const c_char;
20 fn compare(&self, a: &[u8], b: &[u8]) -> Ordering {
22 a.cmp(b)
23 }
24
25 fn null() -> bool {
27 false
28 }
29}
30
31#[derive(Copy,Clone)]
33pub struct DefaultComparator;
34
35unsafe trait InternalComparator: Comparator where Self: Sized {
36 extern "C" fn name(state: *mut c_void) -> *const c_char {
37 let x = unsafe { &*(state as *mut Self) };
38 x.name()
39 }
40
41 extern "C" fn compare(
42 state: *mut c_void,
43 a: *const c_char,
44 a_len: size_t,
45 b: *const c_char,
46 b_len: size_t
47 ) -> i32 {
48 unsafe {
49 let a_slice = slice::from_raw_parts::<u8>(a as *const u8, a_len as usize);
50 let b_slice = slice::from_raw_parts::<u8>(b as *const u8, b_len as usize);
51 let x = &*(state as *mut Self);
52
53 match x.compare(&a_slice, &b_slice) {
54 Ordering::Less => -1,
55 Ordering::Equal => 0,
56 Ordering::Greater => 1,
57 }
58 }
59 }
60
61 extern "C" fn destructor(state: *mut c_void) {
62 let _x: Box<Self> = unsafe { Box::from_raw(state as *mut Self) };
63 }
65}
66
67unsafe impl<C: Comparator> InternalComparator for C {}
68
69
70#[allow(missing_docs)]
71pub fn create_comparator<T: Comparator>(x: Box<T>) -> *mut leveldb_comparator_t {
72 unsafe {
73 leveldb_comparator_create(Box::into_raw(x) as *mut c_void,
74 <T as InternalComparator>::destructor,
75 <T as InternalComparator>::compare,
76 <T as InternalComparator>::name)
77 }
78}
79
80impl Comparator for DefaultComparator {
81 fn name(&self) -> *const c_char {
82 "default_comparator".as_ptr() as *const c_char
83 }
84
85 fn null() -> bool {
86 true
87 }
88}