diff --git a/Cargo.toml b/Cargo.toml index 8b4c9c3adce6834ada5f9fcad08271867a1107fa..be435a36cf1e4e77affc2803f1bffd726259c775 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,6 +6,8 @@ edition = "2021" [lib] name = "level_db_rust" path = "src/lib.rs" +# 过程宏 +proc-macro = false # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html @@ -13,10 +15,10 @@ path = "src/lib.rs" rand = "0.8.5" tokio = "1.24.1" jemallocator = "0.5" -jemalloc-sys = {version = "0.5", features = ["stats"]} +jemalloc-sys = { version = "0.5", features = ["stats"] } [dev-dependencies] -criterion = {version = "0.4.0", features = ["html_reports"]} +criterion = { version = "0.4.0", features = ["html_reports"] } crc32fast = "1.3.2" skiplist = "0.4.0" diff --git a/src/db/db_format.rs b/src/db/db_format.rs index f318f2c4804de49d4fa8124c01c5c2bc20c49ccd..4b4a7c791d252768c90e29f2a4bda4591af1de86 100644 --- a/src/db/db_format.rs +++ b/src/db/db_format.rs @@ -3,9 +3,8 @@ use std::io::Write; use std::sync::Arc; use crate::db::db_format::ValueType::{KTypeDeletion, KTypeValue}; use crate::db::file_meta_data::FileMetaData; -use crate::traits::coding_trait::CodingTrait; use crate::traits::comparator_trait::Comparator; -use crate::util::coding::Coding; +use crate::util::coding::{Encoder, varint_length}; use crate::util::slice::Slice; use crate::util::unsafe_slice::UnsafeSlice; @@ -20,17 +19,17 @@ pub enum ValueType { pub struct ParsedInternalKey { user_key: Slice, sequence: u64, - value_type: ValueType + value_type: ValueType, } #[derive(Debug)] pub struct InternalKey { - rep_: Slice + rep_: Slice, } /// InternalKeyComparator pub struct InternalKeyComparator { - user_comparator_: Arc + user_comparator_: Arc, } /// 查找键 @@ -93,7 +92,6 @@ impl Default for ParsedInternalKey { } impl ParsedInternalKey { - pub fn debug_string(&self) -> Slice { Slice::default() } @@ -119,13 +117,13 @@ impl ParsedInternalKey { /// Attempt to parse an internal key from "internal_key". On success, /// stores the parsed data in "*result", and returns true. /// On error, returns false, leaves "*result" in an undefined state. - pub fn parse_internal_key(internal_key : Slice, target: ParsedInternalKey) -> bool { + pub fn parse_internal_key(internal_key: Slice, target: ParsedInternalKey) -> bool { // line 173 todo!() } /// Returns the user key portion of an internal key. - pub fn extract_user_key(internal_key : Slice) -> Slice { + pub fn extract_user_key(internal_key: Slice) -> Slice { todo!() } } @@ -154,7 +152,7 @@ impl InternalKey { ParsedInternalKey::new(user_key, sequence, value_type) .append_internal_key(result); - Self{ + Self { // rep_: result // todo result值如何赋值 rep_: Slice::default() @@ -261,16 +259,17 @@ impl LookupKey { let need = user_key_size + 13; // A conservative estimate let mut data = Vec::with_capacity(need); let buf = data.as_mut_slice(); - let klength = Coding::varint_length(user_key_size + 8); - let mut offset = 0; + let mut encoder = Encoder::with_buf(buf); // write key size - offset = Coding::encode_varint32(klength as u32, buf, offset); - // write key slice - offset += (&mut buf[offset..]).write(user_key.as_ref()).expect("write user_key"); - // write sequence number and value type - Coding::encode_fixed64( - pack_sequence_and_type(sequence, ValueType::KTypeValue), - buf, offset); + let klength = varint_length((user_key_size + 8) as u64); + // 需要保证写入的数据不会超过buf.len(), 否则会溢出 + unsafe { + encoder.uncheck_put_varint32(klength as u32); + // write key slice + encoder.uncheck_put_buf(user_key.as_ref()); + // write sequence number and value type + encoder.uncheck_put_fixed64(pack_sequence_and_type(sequence, ValueType::KTypeValue)); + } LookupKey { data: Slice::from_vec(data), @@ -327,6 +326,7 @@ pub fn pack_sequence_and_type(seq_no: usize, v_type: ValueType) -> u64 { } pub struct Config {} + impl Config { /// Maximum encoding length of a BlockHandle pub const K_NUM_LEVELS: usize = 7; diff --git a/src/db/log_reader.rs b/src/db/log_reader.rs index c7b69ddc0bddef07154941ce3dd2010bd90b3c8c..099240adcdac9bca46dd7375dc85b6df21d2162e 100644 --- a/src/db/log_reader.rs +++ b/src/db/log_reader.rs @@ -3,8 +3,7 @@ use std::io::{Read, Seek, Write}; use std::io::SeekFrom::Start; use crate::db::log_writer::{K_BLOCK_SIZE, K_FIRST_TYPE, K_FULL_TYPE, K_LAST_TYPE, K_MIDDLE_TYPE}; -use crate::traits::coding_trait::CodingTrait; -use crate::util::coding::Coding; +use crate::util::coding::Decoder; use crate::util::crc::{AsCrc, CRC}; use crate::util::Result; use crate::util::slice::Slice; @@ -101,7 +100,9 @@ impl LogReader { return Ok(()); } let crc_bytes = &self.buf[(self.buf_read_idx - 7)..(self.buf_read_idx - 3)]; - let expect = Coding::decode_fixed32(crc_bytes); + let mut decoder = Decoder::with_buf(crc_bytes); + + let expect = decoder.get_fixed32()?; let data = &self.buf[(self.buf_read_idx - 1)..(self.buf_read_idx + data_len)]; let crc = data.as_crc(); let mask = CRC::mask(crc); diff --git a/src/db/log_wr_test.rs b/src/db/log_wr_test.rs index 001b1e750bb3cb5d9803aee1011324de4eb10b5b..95f67eeedda8e17e395b1cb7065bce8d7418a02c 100644 --- a/src/db/log_wr_test.rs +++ b/src/db/log_wr_test.rs @@ -1,10 +1,8 @@ - mod test { use std::fs::File; use crate::db::log_reader::LogReader; use crate::db::log_writer::LogWriter; - use crate::traits::coding_trait::CodingTrait; - use crate::util::coding::Coding; + use crate::util::coding::Decoder; use crate::util::crc::{AsCrc, ToMask}; use crate::util::slice::Slice; use crate::util::Result; @@ -13,7 +11,7 @@ mod test { fn write() -> Result<()> { let file = Box::new(File::create("../../1.bin")?); let mut writer = LogWriter::new(file); - let sample: Vec = ('0'..='9').map(|a|a as u8).collect(); + let sample: Vec = ('0'..='9').map(|a| a as u8).collect(); for i in 0..100 { let slice = generate_slice(i, &sample); writer.add_record(slice)?; @@ -25,7 +23,7 @@ mod test { fn read() -> Result<()> { let file = Box::new(File::open("../../1.bin")?); let mut reader = LogReader::new(file, true, 0); - let sample: Vec = ('0'..='9').map(|a|a as u8).collect(); + let sample: Vec = ('0'..='9').map(|a| a as u8).collect(); for i in 0..100 { let slice = reader.read_next().expect("not error").expect("must have record"); let expect = generate_slice(i, &sample); @@ -38,15 +36,16 @@ mod test { fn generate_slice(i: usize, sample: &Vec) -> Slice { let mut slice = Vec::with_capacity(64); for j in 0..=i { - slice.push(sample[j%10]); + slice.push(sample[j % 10]); } Slice::from_vec(slice) } #[test] fn test() { - let expect_crc_bytes = [0xD1, 0xB1, 0x09, 0x9A]; - let expect_crc = Coding::decode_fixed32(expect_crc_bytes.as_ref()); + let expect_crc_bytes: [u8; 4] = [0xD1, 0xB1, 0x09, 0x9A]; + let mut decoder = Decoder::with_buf(&expect_crc_bytes); + let expect_crc = unsafe { decoder.uncheck_get_fixed32() }; let raw_bytes = [0x01_u8, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39]; let crc = raw_bytes.as_crc().to_mask(); @@ -55,7 +54,5 @@ mod test { println!("expect_crc: {}, crc: {}, crc1: {}", expect_crc, crc, crc1); assert_eq!(expect_crc, crc); assert_eq!(expect_crc, crc1); - } - } \ No newline at end of file diff --git a/src/db/log_writer.rs b/src/db/log_writer.rs index 42406db3f609f86e330a8e039f8f53ee9541a3c3..485ce95374567f7a0cac9138b293d68f2b833f59 100644 --- a/src/db/log_writer.rs +++ b/src/db/log_writer.rs @@ -1,6 +1,5 @@ use std::io::Write; -use crate::traits::coding_trait::CodingTrait; -use crate::util::coding::Coding; +use crate::util::coding::Encoder; use crate::util::crc::{AsCrc, CRC}; use crate::util::slice::Slice; use crate::util::Result; @@ -73,13 +72,13 @@ impl LogWriter { } fn emit_physical_record(&mut self, record_type: u8, data: &[u8]) -> Result<()> { + let mut crc = CRC::extend(self.type_crc[record_type as usize], data); + crc = CRC::mask(crc); let mut header = [0_u8; K_HEADER_SIZE]; + Encoder::with_buf(&mut header).put_varint32(crc); header[4] = (data.len() & 0xff) as u8; header[5] = (data.len() >> 8) as u8; header[6] = record_type; - let mut crc = CRC::extend(self.type_crc[record_type as usize], data); - crc = CRC::mask(crc); - Coding::encode_fixed32(crc, header.as_mut(), 0); self.file_writer.write(header.as_ref())?; self.block_offset += K_HEADER_SIZE; if !data.is_empty() { diff --git a/src/db/mem_table.rs b/src/db/mem_table.rs index 3a521fb483ff8ce8da7905820b41f625e9dd77e8..a00340098649c4da1da8205f608971f48accc226 100644 --- a/src/db/mem_table.rs +++ b/src/db/mem_table.rs @@ -2,13 +2,12 @@ use std::io::Write; use std::sync::{Arc, Mutex}; use crate::db::db_format::{LookupKey, ValueType}; use crate::db::skip_list::SkipList; -use crate::traits::coding_trait::CodingTrait; use crate::traits::comparator_trait::Comparator; use crate::traits::DataIterator; use crate::util::arena::ArenaRef; use crate::util::slice::Slice; use crate::util::{Arena, Result}; -use crate::util::coding::Coding; +use crate::util::coding::{Encoder, varint_length}; use crate::util::unsafe_slice::UnsafeSlice; /// 内存表 @@ -18,8 +17,7 @@ pub struct MemTable { arena: ArenaRef, } -impl MemTable { - +impl MemTable { /// 创建内存表 /// /// # Arguments @@ -39,7 +37,7 @@ impl MemTable { Self { cmp, list, - arena + arena, } } @@ -72,21 +70,24 @@ impl MemTable { let key_size = key_buf.len(); let value_size = value_buf.len(); let internal_key_size = key_size + 8; - let encoded_len = Coding::varint_length(key_size) + let encoded_len = varint_length(key_size as u64) + internal_key_size - + Coding::varint_length(value_size) + + varint_length(value_size as u64) + value_size; let mut lock = self.arena.lock()?; let buf = lock.allocate(encoded_len); - let mut offset = 0; - // write key size - offset = Coding::encode_varint32(internal_key_size as u32, buf, offset); - // write key slice - offset += (&mut buf[offset..]).write(key_buf)?; - // write seq_no and type - offset = Coding::encode_fixed64((seq_no << 8 | v_type.get_value()) as u64, buf, offset); - // write value slice - (&mut buf[offset..]).write(value_buf)?; + let mut encoder = Encoder::with_buf(buf); + // 需要保证写入的数据不会超过buf.len(), 否则溢出 + unsafe { + // write key size + encoder.uncheck_put_varint32(internal_key_size as u32); + // write key slice + encoder.uncheck_put_buf(key_buf); + // write seq_no and type + encoder.uncheck_put_fixed64((seq_no << 8 | v_type.get_value()) as u64); + // write value slice + encoder.uncheck_put_buf(value_buf); + } // let slice = Slice::from_buf(buf); self.list.insert(UnsafeSlice::new_with_arena(buf, self.arena.clone())?) } @@ -95,12 +96,9 @@ impl MemTable { pub fn get(&self, _key: &LookupKey) -> Result> { todo!() } - } mod test { #[test] - fn test() { - - } + fn test() {} } \ No newline at end of file diff --git a/src/db/version_edit.rs b/src/db/version_edit.rs index 792d00afe2b09ccd289cba0486b0ff2d98a5d4d5..ec0a502b3554b0f152a14ed448957f8be3dc9f97 100644 --- a/src/db/version_edit.rs +++ b/src/db/version_edit.rs @@ -3,8 +3,7 @@ use std::iter::Map; use crate::db::db_format::InternalKey; use crate::db::file_meta_data::FileMetaData; use crate::db::version_edit; -use crate::traits::coding_trait::CodingTrait; -use crate::util::coding::Coding; +use crate::util::coding::Encoder; use crate::util::slice::Slice; use crate::util::Result; use crate::util::status::{LevelError, Status}; @@ -37,7 +36,7 @@ pub enum Tag { kDeletedFile = 6, kNewFile = 7, // 8 was used for large value refs - kPrevLogNumber = 9 + kPrevLogNumber = 9, } impl Tag { @@ -81,7 +80,7 @@ impl VersionEdit { #[inline] pub fn new() -> Self { Self { - comparator_ : String::new(), + comparator_: String::new(), log_number_: 0, prev_log_number_: 0, next_file_number_: 0, @@ -93,7 +92,7 @@ impl VersionEdit { has_last_sequence_: false, compact_pointers_: vec![], deleted_files_: vec![], - new_files_: vec![] + new_files_: vec![], } } @@ -131,27 +130,27 @@ impl VersionEdit { // compact_pointers_ don't clear } - pub fn set_comparator_name(&mut self, name: Slice){ + pub fn set_comparator_name(&mut self, name: Slice) { self.has_comparator_ = true; self.comparator_ = name.into(); } - pub fn set_log_number(&mut self, num: u64){ + pub fn set_log_number(&mut self, num: u64) { self.has_log_number_ = true; self.log_number_ = num; } - pub fn set_prev_log_number(&mut self, num: u64){ + pub fn set_prev_log_number(&mut self, num: u64) { self.has_prev_log_number_ = true; self.prev_log_number_ = num; } - pub fn set_next_file(&mut self, num: u64){ + pub fn set_next_file(&mut self, num: u64) { self.has_next_file_number_ = true; self.next_file_number_ = num; } - pub fn set_last_sequence(&mut self, seq: u64){ + pub fn set_last_sequence(&mut self, seq: u64) { self.has_last_sequence_ = true; self.last_sequence_ = seq; } @@ -202,59 +201,59 @@ impl VersionEdit { /// ``` /// /// ``` - pub fn encode_to(&self, target: &mut Vec) { - let mut position: usize = 0; + pub fn encode_to(&self, target: &mut Vec) -> Result<()> { + let mut encoder = Encoder::with_vec(target); if self.has_comparator_ { - position += Coding::put_varint32(target, position, Tag::k_comparator.get_value() as u32); - position += Coding::put_length_prefixed_slice(target, position, self.comparator_.len()); + encoder.put_varint32(Tag::k_comparator.get_value() as u32)?; + encoder.put_varint32(self.comparator_.len() as u32)?; + // fixme 需要正确使用 put_length_prefixed_slice 将slice长度及slice内容编码到target + // encoder.put_length_prefixed_slice(self.comparator_.len())?; } - if self.has_log_number_ { - let mut offset = Coding::put_varint32(target, position, Tag::kLogNumber.get_value() as u32); - position = position + offset; - - offset = Coding::put_varint64(target, position, self.log_number_); - position = position + offset; + encoder.put_varint32(Tag::kLogNumber.get_value() as u32)?; + encoder.put_varint64(self.log_number_)?; } if self.has_prev_log_number_ { - position += Coding::put_varint32(target, position, Tag::kPrevLogNumber.get_value() as u32); - position += Coding::put_varint64(target, position, self.prev_log_number_); + encoder.put_varint32(Tag::kPrevLogNumber.get_value() as u32)?; + encoder.put_varint64(self.prev_log_number_)?; } if self.has_next_file_number_ { - position += Coding::put_varint32(target, position, Tag::kNextFileNumber.get_value() as u32); - position += Coding::put_varint64(target, position, self.next_file_number_); + encoder.put_varint32(Tag::kNextFileNumber.get_value() as u32)?; + encoder.put_varint64(self.next_file_number_)?; } if self.has_last_sequence_ { - position += Coding::put_varint32(target, position, Tag::kLastSequence.get_value() as u32); - position += Coding::put_varint64(target, position, self.last_sequence_); + encoder.put_varint32(Tag::kLastSequence.get_value() as u32)?; + encoder.put_varint64(self.last_sequence_)?; } for i in 0..self.compact_pointers_.len() { - position += Coding::put_varint32(target, position, Tag::kCompactPointer.get_value() as u32); - position += Coding::put_varint32(target, position, self.compact_pointers_[i].0); - position += Coding::put_length_prefixed_slice(target, position, - self.compact_pointers_[i].1.encode_len()); + encoder.put_varint32(Tag::kCompactPointer.get_value() as u32)?; + encoder.put_varint32(self.compact_pointers_[i].0)?; + // fixme 需要正确使用put_length_prefixed_slice + // encoder.put_length_prefixed_slice( self.compact_pointers_[i].1.encode_len())?; } for i in 0..self.deleted_files_.len() { - position += Coding::put_varint32(target, position, Tag::kDeletedFile.get_value() as u32); - position += Coding::put_varint32(target, position, self.deleted_files_[i].0); - position += Coding::put_varint64(target, position, self.deleted_files_[i].1); + encoder.put_varint32(Tag::kDeletedFile.get_value() as u32)?; + encoder.put_varint32(self.deleted_files_[i].0)?; + encoder.put_varint64(self.deleted_files_[i].1)?; } for i in 0..self.new_files_.len() { let f: &FileMetaData = &self.new_files_[i].1; - position += Coding::put_varint32(target, position, Tag::kNewFile.get_value() as u32); + encoder.put_varint32(Tag::kNewFile.get_value() as u32)?; // level - position += Coding::put_varint32(target, position, self.new_files_[i].0); - position += Coding::put_varint64(target, position, f.get_number()); - position += Coding::put_varint64(target, position, f.get_file_size()); - position += Coding::put_length_prefixed_slice(target, position, f.get_smallest().encode_len()); - position += Coding::put_length_prefixed_slice(target, position, f.get_largest().encode_len()); + encoder.put_varint32(self.new_files_[i].0)?; + encoder.put_varint64(f.get_number())?; + encoder.put_varint64(f.get_file_size())?; + // fixme 需要正确使用put_length_prefixed_slice + // encoder.put_length_prefixed_slice( f.get_smallest().encode_len())?; + // encoder.put_length_prefixed_slice( f.get_largest().encode_len())?; } + Ok(()) } /// 将 source 中的数据解码至 self VersionEdit 中 @@ -275,18 +274,18 @@ impl VersionEdit { let version_edit = VersionEdit::new(); - let msg : Option = Option::None; + let msg: Option = Option::None; // todo Coding::get_varint32 存在问题。开发暂停 - while msg.is_none() && Coding::get_varint32(source) != 0_u32 { - let tag_value = Coding::get_varint32(source); - let tag = Tag::from_value(tag_value); - - if tag.is_none() { - return LevelError::corruption_string("VersionEdit", "unknown tag"); - } - - } + // while msg.is_none() && Coding::get_varint32(source) != 0_u32 { + // let tag_value = Coding::get_varint32(source); + // let tag = Tag::from_value(tag_value); + // + // if tag.is_none() { + // return LevelError::corruption_string("VersionEdit", "unknown tag"); + // } + // + // } todo!() } @@ -295,13 +294,13 @@ impl VersionEdit { let debug_str = String::from("VersionEdit {"); let mut has_comparator_str = String::default(); - if(self.has_comparator_){ + if (self.has_comparator_) { has_comparator_str.push_str(format!("\n Comparator: {}", self.comparator_.as_str()).as_str()); } let mut has_log_number__str = String::default(); // if(self.has_log_number_){ - // todo + // todo // // let append_log_number = logging.AppendNumberTo(&r, self.log_number_); // let append_log_number = self.log_number_ + "".as_ref(); // has_log_number__str.push_str(format!("\n LogNumber: {}", append_log_number).as_str()); @@ -316,7 +315,7 @@ impl VersionEdit { /// 静态方法 impl<'a> VersionEdit { pub fn get_internal_key(input: Slice) -> Result { - let key= InternalKey::default(); + let key = InternalKey::default(); todo!() diff --git a/src/db/version_edit_test.rs b/src/db/version_edit_test.rs index 4791a04f6f1f2fd4910150ecc122eb63779a0bb6..47dc33c22de21196608df01304d45960034e1a0b 100644 --- a/src/db/version_edit_test.rs +++ b/src/db/version_edit_test.rs @@ -3,6 +3,7 @@ mod test { use crate::db::version_edit; use crate::db::version_edit::{Tag, VersionEdit}; use crate::util::slice::Slice; + use crate::util::Result; #[test] fn test_tag() { @@ -15,14 +16,16 @@ mod test { } #[test] - fn test_version_edit_encode_to() { + fn test_version_edit_encode_to() -> Result<()> { let mut target: Vec = vec![]; let version_edit = VersionEdit::new_with_log_number(6); - version_edit.encode_to(&mut target); + version_edit.encode_to(&mut target)?; println!("target: {}.", &target.len()); // todo // assert_eq!(target.len(), 2); + + Ok(()) } #[test] diff --git a/src/lib.rs b/src/lib.rs index c0dce0021b0ec5283db9efe17a9e28a72b023211..c1c31315b33dcfda861afa319b3505378cc7c1c7 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,3 +1,5 @@ +#![feature(core_ffi_c)] +#![feature(core_intrinsics)] extern crate core; pub mod db; diff --git a/src/table/filter_block.rs b/src/table/filter_block.rs index 8ef56a3dbe6611599f45150925e4fdec64dfcc3f..484635408664e705bb6258f84ce9713aa4aac276 100644 --- a/src/table/filter_block.rs +++ b/src/table/filter_block.rs @@ -1,9 +1,8 @@ use std::io::Write; use std::sync::Arc; use crate::debug; -use crate::traits::coding_trait::CodingTrait; use crate::traits::filter_policy_trait::{FilterPolicy, FilterPolicyPtr}; -use crate::util::coding::Coding; +use crate::util::coding::Encoder; use crate::util::slice::Slice; use crate::util::Result; @@ -124,7 +123,7 @@ pub struct FilterBlockReader { // Number of entries in offset array num: usize, // Encoding parameter (see kFilterBaseLg in .cc file) - base_lg: usize + base_lg: usize, } impl FilterBlock for FilterBlockBuilder { @@ -133,11 +132,11 @@ impl FilterBlock for FilterBlockBuilder { } fn new_with_policy_capacity(policy: FilterPolicyPtr, capacity: usize) -> Self { - let keys:Vec = Vec::with_capacity(capacity); - let start:Vec = Vec::with_capacity(capacity); - let result:Vec = Vec::with_capacity(capacity); - let tmp_keys:Vec = vec![]; - let filter_offsets:Vec = vec![]; + let keys: Vec = Vec::with_capacity(capacity); + let start: Vec = Vec::with_capacity(capacity); + let result: Vec = Vec::with_capacity(capacity); + let tmp_keys: Vec = vec![]; + let filter_offsets: Vec = vec![]; Self { policy, @@ -145,7 +144,7 @@ impl FilterBlock for FilterBlockBuilder { start, result, tmp_keys, - filter_offsets + filter_offsets, } } @@ -154,7 +153,7 @@ impl FilterBlock for FilterBlockBuilder { let filters_number = block_offset / (FILTER_BASE as u64); let len = self.filter_offsets.len() as u64; - assert!(filters_number >= len); + assert!(filters_number >= len); // 当已经生成的filter的数目小于需要生成的filter的总数时,那么就继续创建filter。 while filters_number > len { @@ -180,17 +179,16 @@ impl FilterBlock for FilterBlockBuilder { let array_offset = self.result.len() as u32; // 当前需要写入的位置。result 中可能存在数据,因此为 offset ==> self.result.len() 的位置 - let mut offset: usize = self.result.len(); let dst: &mut Vec = &mut self.result; // let mut dst_append = self.result.as_mut_slice(); + let mut encoder = Encoder::with_vec(dst); for i in 0..self.filter_offsets.len() { - offset = Coding::put_fixed32_with_vex(dst, self.filter_offsets[i]); + encoder.put_fixed32(self.filter_offsets[i])?; } - - offset = Coding::put_fixed32_with_vex(dst, array_offset); + encoder.put_fixed32(array_offset)?; // Save encoding parameter in result - Coding::put_varint64_with_vex(dst, FILTER_BASE_LG as u64); + encoder.put_varint64(FILTER_BASE_LG as u64)?; Ok(Slice::from_buf(&self.result)) } @@ -245,9 +243,9 @@ impl FilterBlockBuilder { // 依次拿到每个key for i in 0..num_keys { // 拿到key的长度 - let length = self.start[i+1] - self.start[i]; + let length = self.start[i + 1] - self.start[i]; // 这里拿到每个key的数据 - let base = &self.keys[self.start[i]..(self.start[i]+length)]; + let base = &self.keys[self.start[i]..(self.start[i] + length)]; // 生成相应的key,并且放到tmp_keys里面 let mut tmp_key = Vec::with_capacity(length); @@ -265,7 +263,7 @@ impl FilterBlockBuilder { keys.push(&tmp_key); } // let create_filter:Slice = self.policy.create_filter_with_len(num_keys, keys); - let create_filter:Slice = self.policy.create_filter(keys); + let create_filter: Slice = self.policy.create_filter(keys); debug!("create_filter:{:?}.", create_filter); self.result.write(create_filter.as_ref()); @@ -291,8 +289,8 @@ impl FilterBlockReader { data, offset, num: 0, - base_lg: 0 - } + base_lg: 0, + }; }; // let buf = contents.as_ref()[contents_len-5..]; @@ -305,7 +303,7 @@ impl FilterBlockReader { data, offset, num: 0, - base_lg: 0 + base_lg: 0, } } diff --git a/src/table/filter_block_test.rs b/src/table/filter_block_test.rs index 8c0709c06e8949ed85153eef9e72738902655b80..f4254157787d1cd31761298b92fdf2f9b3af4883 100644 --- a/src/table/filter_block_test.rs +++ b/src/table/filter_block_test.rs @@ -5,9 +5,7 @@ mod test { use crate::table::filter_block; use crate::table::filter_block::{FilterBlock, FilterBlockBuilder, FilterBlockReader}; use crate::table::filter_block_test_filter_policy::TestHashFilter; - use crate::traits::coding_trait::CodingTrait; use crate::traits::filter_policy_trait::FilterPolicy; - use crate::util::coding::Coding; use crate::util::slice::Slice; use crate::util::hash::{Hash, ToHash}; diff --git a/src/table/filter_block_test_filter_policy.rs b/src/table/filter_block_test_filter_policy.rs index 244a330c2f15da8da9801e0d4010f8b463773146..8c799971887e0bc38282d5262989fd0c4f699658 100644 --- a/src/table/filter_block_test_filter_policy.rs +++ b/src/table/filter_block_test_filter_policy.rs @@ -1,9 +1,8 @@ use std::borrow::BorrowMut; use std::cmp::max; use std::usize::MAX; -use crate::traits::coding_trait::CodingTrait; use crate::traits::filter_policy_trait::FilterPolicy; -use crate::util::coding::Coding; +use crate::util::coding::Decoder; use crate::util::hash::Hash; use crate::util::slice::Slice; @@ -45,7 +44,7 @@ impl FilterPolicy for TestHashFilter { // for [0, len) for i in 0..keys.len() { let h = Hash::hash_code(keys[i].as_ref(), 1); // seed 固定为 1 - offset = Coding::put_fixed32(bloom_filter, offset, h); + // offset = Coding::put_fixed32(bloom_filter, offset, h); } Slice::from_buf(bloom_filter) @@ -59,11 +58,15 @@ impl FilterPolicy for TestHashFilter { let mut pos = 0; while pos < len { - let buf = &bloom_filter_data[pos..(pos+4)]; + let buf = &bloom_filter_data[pos..(pos + 4)]; - let h_bl = Coding::decode_fixed32(buf); + let mut decoder = Decoder::with_buf(buf); + if !decoder.can_get() { + return false; + } + let h_bl = unsafe { decoder.uncheck_get_fixed32() }; if h == h_bl { - return true + return true; } pos += 4; @@ -83,7 +86,7 @@ fn test_create_filter() { let s2 = Slice::try_from("world").unwrap(); let s3 = Slice::try_from("hello world").unwrap(); - let mut keys : Vec<&Slice> = Vec::new(); + let mut keys: Vec<&Slice> = Vec::new(); keys.push(&s1); keys.push(&s2); keys.push(&s3); @@ -103,17 +106,17 @@ fn test_create_filter() { // 因为不存在,所以验证不通过 let key_not_match = policy.key_may_match(&Slice::try_from("helloworld").unwrap(), - &bloom_filter); + &bloom_filter); assert!(!key_not_match); // 因为存在,所以验证通过 let key_may_match = policy.key_may_match(&Slice::try_from("hello world").unwrap(), - &bloom_filter); + &bloom_filter); assert!(key_may_match); // 因为不存在,所以验证不通过 let key_not_match = policy.key_may_match(&Slice::try_from("foo").unwrap(), - &bloom_filter); + &bloom_filter); assert!(!key_not_match); // 验证通过 @@ -138,7 +141,7 @@ fn test_create_filter_with_long_len() { let s2 = Slice::try_from("world").unwrap(); let s3 = Slice::try_from("hello world").unwrap(); - let mut keys : Vec<&Slice> = Vec::new(); + let mut keys: Vec<&Slice> = Vec::new(); keys.push(&s1); keys.push(&s2); keys.push(&s3); @@ -193,7 +196,7 @@ fn test_create_filter_with_short_len() { let s2 = Slice::try_from("world").unwrap(); let s3 = Slice::try_from("hello world").unwrap(); - let mut keys : Vec<&Slice> = Vec::new(); + let mut keys: Vec<&Slice> = Vec::new(); keys.push(&s1); keys.push(&s2); keys.push(&s3); diff --git a/src/table/format.rs b/src/table/format.rs index 47c243c89776b657f4451c2de7eca17815c9006f..28596cf5eb191c1d38512f280043fd7df7c16a70 100644 --- a/src/table/format.rs +++ b/src/table/format.rs @@ -1,5 +1,3 @@ -use crate::traits::coding_trait::CodingTrait; -use crate::util::coding; use crate::util::slice::Slice; use crate::util::Result; use crate::util::status::Status; diff --git a/src/traits/coding_trait.rs b/src/traits/coding_trait.rs deleted file mode 100644 index a936950d1399e8881be994efcdbfeff589b793b3..0000000000000000000000000000000000000000 --- a/src/traits/coding_trait.rs +++ /dev/null @@ -1,309 +0,0 @@ -use crate::util::slice::Slice; - -pub trait CodingTrait { - - ///32位定长编码写入字符串 - /// 自动扩容, 后续@王旭 调整 - /// - /// * `dst`: 目标字符串 - /// * `value`: 编码值 - /// - /// returns: usize 返回的最新的偏移量 - fn put_fixed32_with_vex(dst: &mut Vec, value: u32) -> usize; - - ///32位定长编码写入字符串 - /// - /// # Arguments - /// - /// * `dst`: 目标字符串 - /// * `offset`: 偏移量 - /// * `value`: 编码值 - /// - /// returns: usize 返回的最新的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut string = String::from("encode:"); - /// put_fixed32(&mut string, 65535); - /// ``` - fn put_fixed32(dst: &mut [u8], offset: usize, value: u32) -> usize; - - ///64位定长编码写入字符串 - /// - /// # Arguments - /// - /// * `dst`: 目标字符串 - /// * `value`: 编码值 - /// - /// returns: () - /// - /// # Examples - /// - /// ``` - /// let mut string = String::from("encode:"); - /// put_fixed64(&mut string, 65535); - /// ``` - fn put_fixed64(dst: &mut [u8], offset: usize, value: u64) -> usize; - /// 32位变长编码写入字符串 - /// - /// # Arguments - /// - /// * `dst`: 目标字符串 - /// * `value`: 编码值 - /// - /// returns: () - /// - /// # Examples - /// - /// ``` - /// let mut string = String::from("encode:"); - /// put_varint32(&mut string, 65535); - /// ``` - fn put_varint32(dst: &mut [u8], offset: usize, value: u32) -> usize; - - /// 64位变长编码写入字符串 - /// 自动扩容, 后续@王旭 调整 - /// - /// * `dst`: 目标字符串 - /// * `value`: 编码值 - /// - /// returns: usize 返回的最新的偏移量 - fn put_varint64_with_vex(dst: &mut Vec, value: u64) -> usize; - - /// 64位变长编码写入字符串 - /// - /// # Arguments - /// - /// * `dst`: 目标字符串 - /// * `value`: 编码值 - /// - /// returns: () - /// - /// # Examples - /// - /// ``` - /// let mut string = String::from("encode:"); - /// put_varint64(&mut string, 65535); - /// ``` - fn put_varint64(dst: &mut [u8], offset: usize, value: u64) -> usize; - /// 将slice的长度写入目标字符串 - /// - /// # Arguments - /// - /// * `dst`: 目标字符串 - /// * `value_len`: Slice类型的编码值长度 - /// - /// returns: () - /// - /// # Examples - /// - /// ``` - /// - /// ``` - // fn put_length_prefixed_slice(dst: &mut [u8], offset: usize, value: &Slice) -> usize; - fn put_length_prefixed_slice(dst: &mut [u8], offset: usize, value_len: usize) -> usize; - /// 从slice的开头解码一个32位的变长整数, 并将slice的索引置于解码后的位置 - /// - /// # Arguments - /// - /// * `input`: slice - /// - /// returns: u32 - /// - /// # Examples - /// - /// ``` - /// - /// ``` - fn get_varint32(input: &Slice) -> u32; - /// 从slice的开头解码一个64位的变长整数, 并将slice的索引置于解码后的位置 - /// - /// # Arguments - /// - /// * `input`: slice - /// - /// returns: u32 - /// - /// # Examples - /// - /// ``` - /// - /// ``` - fn get_varint64(input: &Slice) -> u64; - /// 从slice数据中读取长度 返回长度的Slice - /// - /// # Arguments - /// - /// * `input`: 输入数据 - /// - /// returns: () - /// - /// # Examples - /// - /// ``` - /// - /// ``` - fn get_length_prefixed_slice(input: &mut Slice) -> Slice; - /// 32位变长正整数编码 - /// - /// # Arguments - /// - /// * `value`: 编码值 - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset =encode_varint32(value, &mut buf, 0); - /// ``` - fn encode_varint32(value: u32, buf: &mut [u8], offset: usize) -> usize; - /// 变长正整数编码 - /// - /// # Arguments - /// - /// * `value`: 编码值 - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset =encode_varint64(value, &mut buf, 0); - /// ``` - fn encode_varint64(value: u64, buf: &mut [u8], offset: usize) -> usize; - /// 获取变长编码后的长度 - /// - /// # Arguments - /// - /// * `value`: 编码值 - /// - /// returns: i32 - /// - /// # Examples - /// - /// ``` - /// - /// ``` - /// 从slice的开头解码一个32位的变长整数, 并将slice的索引置于解码后的位置 - fn varint_length(value: usize) -> usize; - /// 32位定长正整数编码 - /// - /// # Arguments - /// - /// * `value`: 编码值 - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset = Self::encode_fixed32(value, &mut buf, 0); - /// ``` - fn encode_fixed32(value: u32, buf: &mut [u8], offset: usize) -> usize; - /// 64位定长正整数编码 - /// - /// # Arguments - /// - /// * `value`: - /// * `buf`: - /// * `offset`: - /// - /// returns: usize - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - /// let value: u64 = 65534; - /// let offset = encode_fixed64(value, &mut buf, 0); - /// ``` - fn encode_fixed64(value: u64, buf: &mut [u8], offset: usize) -> usize; - /// 32位定长解码 - /// - /// # Arguments - /// - /// * `buf`: 待解码数据 - /// - /// returns: u32 - /// - /// # Examples - /// - /// ``` - /// - /// ``` - fn decode_fixed32(buf: &[u8]) -> u32; - /// 64位定长解码 - /// - /// # Arguments - /// - /// * `buf`: 待解码数据 - /// - /// returns: u64 - /// - /// # Examples - /// - /// ``` - /// - /// ``` - fn decode_fixed64(buf: &[u8]) -> u64; -} - -macro_rules! coding_trait { - {$TRAIT: ident, $TYPE: ty} => { - pub trait $ TRAIT { - /// 变长正整数编码 - /// - /// # Arguments - /// - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset = value.varint(&mut buf, 0); - /// ``` - fn varint(self, buf: &mut [u8], offset: usize) -> usize; - /// 定长正整数编码 - /// - /// # Arguments - /// - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset = value.fixedint(&mut buf, 0); - /// ``` - fn fixedint(self, buf: &mut [u8], offset: usize) -> usize; - } - } -} - -coding_trait!(Coding32,u32); - -coding_trait!(Coding64,u64); - diff --git a/src/traits/mod.rs b/src/traits/mod.rs index a1332ef7548ed05a5d266799f00c677e3720015f..c772c64e0af8dd8aa920a43c2a5da6f147397d51 100644 --- a/src/traits/mod.rs +++ b/src/traits/mod.rs @@ -1,7 +1,6 @@ pub mod iterator; pub mod comparator_trait; -pub mod coding_trait; pub mod filter_policy_trait; diff --git a/src/util/coding.rs b/src/util/coding.rs index 1727700ff4589f43a1c95166e6ee04d0cdf21e53..4fe6fd17528da771ba9346a9e4d8546ffc91d029 100644 --- a/src/util/coding.rs +++ b/src/util/coding.rs @@ -1,247 +1,1857 @@ -use std::io::Write; -use crate::traits::coding_trait::CodingTrait; -use crate::traits::coding_trait::Coding32; -use crate::traits::coding_trait::Coding64; +use std::{intrinsics, ptr}; +use std::alloc::{alloc, Layout}; +use std::ops::Deref; +use jemalloc_sys::malloc; + +use crate::util::coding::EncodeData::{Buffer, Slices, Vector}; +use crate::util::coding::MutEncodeData::{MutBuffer, MutSlices, MutVector}; +use crate::util::Result; use crate::util::slice::Slice; +use crate::util::status::LevelError; + +/// 获取变长编码的长度 +/// +/// # Arguments +/// +/// * `value`: 待编码数据 +/// +/// returns: usize +/// +/// # Examples +/// +/// ``` +/// use level_db_rust::util::coding::varint_length; +/// // length == 2 +/// let length = varint_length(255); +/// ``` +pub fn varint_length(mut value: u64) -> usize { + let mut len = 1; + while value >= 128 { + value >>= 7; + len += 1; + } + len +} + +/// 默认为大端bytes 小端bytes会转为大端bytes +macro_rules! swap_bytes { + ($x: expr, noswap) => ($x); + ($x: expr, swap) => ($x.swap_bytes()); + ($x:expr)=>{ + if cfg!(target_endian = "big") { + swap_bytes!($x, noswap) + } else { + swap_bytes!($x, swap) + } + } +} + +/// 判断数据类型所需的字节数 +macro_rules! type_capacity { + (u32) => (4); + (u64) => (8) +} + +/// vec扩容 计算容量差值 将vec扩容到所需的容量并会更新vec的长度信息 +macro_rules! vec_resize { + ($vec: ident, $len: expr, $offset: expr) => { + if $offset + $len >= $vec.len() { + let add = $offset + $len - $vec.len(); + // 手动扩容 + $vec.reserve(add); + // 需要手动更新容量 + unsafe { $vec.set_len($vec.len() + add); } + } + } +} + +/// 从MutEncoderData中获取读写指针 如果是MutVector类型,当要写入的长度大于vec容量时会手动扩容 +macro_rules! get_mut_ptr { + ($data: ident, $len: expr, $offset: ident)=>{ + match $data { + MutVector(vec) => { + let length = $len; + // vec会进行扩容 + vec_resize!(vec, length, $offset); + vec.as_mut_ptr() + } + MutBuffer(buf) => { + // buf不进行扩容 + // value的byte数 > buf.len() - offset 时不安全, 内存溢出 + buf.as_mut_ptr() + } + MutSlices(slice) => { + // slice不进行扩容, 直接取切片 + // value的byte数 > slice.size() - offset 时不安全, 内存溢出 + (*slice).as_mut_ptr() + } + } + } +} -macro_rules! varint { - ($TYPE: ty, $NAME: ident, $SNAME: expr) => { - fn $NAME(mut value: $TYPE, buf: &mut [u8], mut offset: usize) -> usize { - while value >= 128 { - buf[offset] = (value | 128) as u8; - offset += 1; - value >>= 7; +/// 从EncoderData中获取只读指针 +macro_rules! get_ptr { + ($data: ident)=>{ + match $data { + Vector(vec) => { + vec.as_ptr() + } + Buffer(buf) => { + buf.as_ptr() } - buf[offset] = value as u8; + Slices(slice) => { + (*slice).as_ptr() + } + } + } +} - offset + 1 +/// 检查长度 长度不足以写入或者读取时返回错误 +macro_rules! check_length { + ($offset: expr, $write_len: expr, $data_len: expr) => { + if $offset + $write_len >= $data_len { + return Err(LevelError::invalid_argument( + Slice::from("offset + write_len must < data_len"), + Slice::from(format!("offset = {}, write_len = {} data_len = {}", $offset, $write_len, $data_len)))); } }; - - ($TYPE: ty, $NAME: ident) => { - varint!( $TYPE, $NAME, stringify!($NAME)); + ($offset: expr, $limit: expr) => { + if $offset >= $limit { + return Err(LevelError::invalid_argument( + Slice::from("offset must < limit"), + Slice::from(format!("offset = {}, limit = {}", $offset, $limit)) + )); + } } } -pub struct Coding {} +/// 定长编码 +macro_rules! encode_fixed { + ($name: ident, $type: ty, $capacity: ident) => { + /// 定长编码 unsafe + /// + /// # Safety + /// * offset < buf/slice的长度, 否则指针越界 + /// * offset + value的字节数 < buf/slice.len(), 否则写数据溢出 + /// + /// # Arguments + /// + /// * `data`: 存放编码数据的容器 + /// * `offset`: 编码的起始偏移量 + /// * `value`: 待编码的数据 + /// + /// returns: () + /// + /// # Examples + /// + /// ``` + /// let mut vec = vec![]; + /// // [0, 0, 4, 210] + /// unsafe { + /// uncheck_encode_fixed32(&mut MutVector(&mut vec), 0, 1234); + /// } + /// ``` + #[inline] + unsafe fn $name(data: &mut MutEncodeData, offset: usize, value: $type) { + let mut_ptr = get_mut_ptr!(data, type_capacity!($capacity), offset); + unsafe { + // 移动指针 + let end = mut_ptr.add(offset); + // 写入数据 + ptr::write(end as *mut $type, swap_bytes!(value)); + } + } + }; +} + +encode_fixed!(uncheck_encode_fixed32, u32, u32); +encode_fixed!(uncheck_encode_fixed64, u64, u64); -impl CodingTrait for Coding { - fn put_fixed32_with_vex(dst: &mut Vec, value: u32) -> usize { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - Self::encode_fixed32(value, &mut buf, 0); - dst.push(buf[0]); - dst.push(buf[1]); - dst.push(buf[2]); - dst.push(buf[3]); +/// 32位变长编码 +/// +/// # Safety +/// * offset + 写入字节数 < data.len(), 否则溢出(vec除外) +/// +/// # Arguments +/// +/// * `data`: 存储编码的数据 +/// * `offset`: 编码的偏移量 +/// * `value`: 待编码数据 +/// +/// returns: usize +/// +/// # Examples +/// +/// ``` +/// let mut vec = vec![]; +/// let mut offset = 0; +/// // [255, 255, 3] +/// unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 65535); } +/// ``` +unsafe fn uncheck_encode_varint32(data: &mut MutEncodeData, offset: usize, value: u32) -> usize { + let length = varint_length(value as u64); + let mut_ptr = get_mut_ptr!(data, length, offset); - dst.len() - } + return if value < (1 << 7) { + ptr::write(mut_ptr.add(offset), value as u8); + offset + 1 + } else if value < (1 << 14) { + ptr::write(mut_ptr.add(offset) as *mut [u8; 2], [ + (value | 128) as u8, + (value >> 7) as u8, + ]); + offset + 2 + } else if value < (1 << 21) { + ptr::write(mut_ptr.add(offset) as *mut [u8; 3], [ + (value | 128) as u8, + (value >> 7 | 128) as u8, + (value >> 14) as u8, + ]); + offset + 3 + } else if value < (1 << 28) { + ptr::write(mut_ptr.add(offset) as *mut [u8; 4], [ + (value | 128) as u8, + (value >> 7 | 128) as u8, + (value >> 14 | 128) as u8, + (value >> 21) as u8 + ]); + offset + 4 + } else { + ptr::write(mut_ptr.add(offset) as *mut [u8; 5], [ + (value | 128) as u8, + (value >> 7 | 128) as u8, + (value >> 14 | 128) as u8, + (value >> 21 | 128) as u8, + (value >> 28) as u8, + ]); + offset + 5 + }; +} - fn put_fixed32(dst: &mut [u8], mut offset: usize, value: u32) -> usize { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - Self::encode_fixed32(value, &mut buf, 0); - dst[offset] = buf[0]; - offset += 1; - dst[offset] = buf[1]; - offset += 1; - dst[offset] = buf[2]; + +/// 64位变长编码 +/// # Safety +/// * offset + 写入字节数 < data.len(), 否则溢出(vec除外) +/// +/// # Arguments +/// +/// * `data`: 存储编码的数据 +/// * `offset`: 编码的偏移量 +/// * `value`: 待编码数据 +/// +/// returns: usize +/// +/// # Examples +/// +/// ``` +/// let mut vec = vec![]; +/// let mut offset = 0; +/// // offset = 7, vec = [255, 255, 208, 148, 181, 244, 1] +/// unsafe { offset = uncheck_encode_varint64(&mut MutVector(&mut vec), offset, 8_3980_4651_1103) }; +/// ``` +unsafe fn uncheck_encode_varint64(data: &mut MutEncodeData, mut offset: usize, mut value: u64) -> usize { + let length = varint_length(value); + let mut_ptr = get_mut_ptr!(data, length, offset); + + while value >= 128 { + ptr::write(mut_ptr.add(offset), (value | 128) as u8); + value >>= 7; offset += 1; - dst[offset] = buf[3]; - offset + 1 } + ptr::write(mut_ptr.add(offset), value as u8); + offset + 1 +} - fn put_fixed64(dst: &mut [u8], mut offset: usize, value: u64) -> usize { - let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - Self::encode_fixed64(value, &mut buf, 0); - dst[offset] = buf[0]; - offset += 1; - dst[offset] = buf[1]; - offset += 1; - dst[offset] = buf[2]; - offset += 1; - dst[offset] = buf[3]; - offset += 1; - dst[offset] = buf[4]; - offset += 1; - dst[offset] = buf[5]; - offset += 1; - dst[offset] = buf[6]; - offset += 1; - dst[offset] = buf[7]; - offset + 1 +/// 定长解码 +macro_rules! decode_fixed { + {$name: ident, $type: ty} => { + /// 定长整数解码 不安全 + /// + /// # Safety + /// * offset + 读取字节数 < data.len(), 否则溢出 + /// + /// # Arguments + /// + /// * `data`: 待解码数据 + /// * `offset`: 解码位置偏移量 + /// + /// returns: u32 + /// + /// # Examples + /// + /// ``` + /// let vec = vec![0, 0, 255, 255]; + /// // 65535 + /// let result = unsafe { uncheck_decode_fixed32(&Vector(&vec), 0) }; + /// ``` + #[inline] + unsafe fn $name(data: &EncodeData, offset: usize) -> $type { + // offset + 读取字节 >= data.len() 时会溢出 + let ptr = get_ptr!(data); + swap_bytes!(unsafe {ptr::read(ptr.add(offset) as *mut $type)}) + } } +} - varint!(u32,encode_varint32); +decode_fixed!(uncheck_decode_fixed32, u32); +decode_fixed!(uncheck_decode_fixed64, u64); - varint!(u64,encode_varint64); +/// 变长解码 +macro_rules! decode_varint { + ($name: ident, $type: ty, $max_shift: expr) => { + /// 变长整数解码 不安全 + /// + /// # Safety + /// * offset + 读取字节数 < data.len(), 否则溢出 + /// + /// # Arguments + /// + /// * `vec`: 待解码数据 + /// * `offset`: 解码位置偏移量 + /// + /// returns: u32 + /// + /// # Examples + /// + /// ``` + /// let vec = vec![255, 255, 3]; + /// println!("{:?}", vec); + /// let mut offset = 0; + /// // 65535 + /// let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + /// ``` + unsafe fn $name(data: &EncodeData, mut offset: usize, limit: usize) -> ($type, usize) { + let ptr = get_ptr!(data); - fn put_varint32(dst: &mut [u8], mut offset: usize, value: u32) -> usize { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let var_offset = Self::encode_varint32(value, &mut buf, 0); - for i in 0..var_offset { - dst[offset] = buf[i]; - offset += 1; + // shift的类型是u32 + let mut shift = 0 as u32; + let mut i = offset; + let mut value = 0 as $type; + while shift <= $max_shift && i < limit { + let byte = unsafe { ptr::read(ptr.add(i)) }; + i += 1; + if byte & 128 != 0 { + value |= (((byte & 127) as $type).overflowing_shl(shift).0) as $type; + offset += 1; + } else { + value |= (byte as $type).overflowing_shl(shift).0; + offset += 1; + return (value, offset); + } + shift += 7; + } + (value, offset) } - offset } +} + +decode_varint!(uncheck_decode_varint32, u32, 28); +decode_varint!(uncheck_decode_varint64, u64, 63); + +/// 写入buf +/// +/// # Safety +/// * offset + buf.len() < data.len() , 否则在data不是vec类型的的情况下不会自动扩容, 写入时会溢出 +/// +/// # Arguments +/// +/// * `data`: 存储编码的数据 +/// * `offset`: 编码的偏移量 +/// * `buf`: 待写入的buf +/// +/// returns: () +/// +/// # Examples +/// +/// ``` +/// let mut vec = vec![]; +/// +/// let buf = [1, 2, 3, 4, 5]; +/// // vec = [1, 2, 3, 4, 5] +/// unsafe { uncheck_write_buf(&mut MutVector(&mut vec), 0, &buf); } +/// ``` +unsafe fn uncheck_write_buf(data: &mut MutEncodeData, offset: usize, buf: &[u8]) { + let mut_ptr = get_mut_ptr!(data, buf.len(), offset).add(offset); + ptr::copy_nonoverlapping(buf.as_ptr(), mut_ptr, buf.len()); + intrinsics::forget(buf); +} + + +/// 读取buf 读取时需要知道需要读取的长度 +/// +/// # Safety +/// * offset + len < data.len() , 否则溢出 +/// +/// # Arguments +/// +/// * `data`: 存储编码的数据 +/// * `offset`: 解码的偏移量 +/// +/// returns: &[u8] +/// +/// # Examples +/// +/// ``` +/// let vec = vec![1, 2, 3, 4, 5, 1, 2, 3, 4]; +/// // [1, 2, 3, 4, 5] +/// let buf = unsafe { uncheck_read_buf(&Vector(&vec), 0, 5) }; +/// ``` +unsafe fn uncheck_read_buf(data: &EncodeData, offset: usize, len: usize) -> Slice { + let ptr: *const u8 = get_ptr!(data).add(offset); + let dst: *mut u8 = alloc(Layout::from_size_align_unchecked(len, 4)); + intrinsics::copy_nonoverlapping(ptr, dst, len); + Slice::from_raw_parts(dst, len) +} + +#[derive(Debug)] +enum EncodeData<'a> { + Vector(&'a Vec), + Buffer(&'a [u8]), + Slices(&'a Slice), +} + +#[derive(Debug)] +enum MutEncodeData<'a> { + MutVector(&'a mut Vec), + MutBuffer(&'a mut [u8]), + MutSlices(&'a mut Slice), +} + +#[derive(Debug)] +pub struct Encoder<'a> { + offset: usize, + data: MutEncodeData<'a>, +} + +#[derive(Debug)] +pub struct Decoder<'a> { + offset: usize, + data: EncodeData<'a>, + limit: usize, +} - fn put_varint64_with_vex(dst: &mut Vec, value: u64) -> usize { - let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - let var_offset = Self::encode_varint64(value, &mut buf, 0); +/// 实现put_fixed +macro_rules! put_fixed { + ($name:ident, $var_name:ident, $type:ty, $capacity: ident, uncheck) => { + /// 编码定长整数 不检查长度 + /// + /// # Safety + /// * offset + type_size < data.len() , 否则溢出 + /// + /// # Arguments + /// + /// * `value`: 待编码的数据 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// unsafe { + /// // [0, 0, 255, 255] + /// encoder.uncheck_put_fixed32(65535); + /// // [0, 0, 255, 255, 0, 0, 255, 255] + /// encoder.uncheck_put_fixed32(65535); + /// } + /// ``` + pub unsafe fn $name(&mut self, value: $type) { + $var_name(&mut self.data, self.offset, value); + self.offset += type_capacity!($capacity); + } + }; + ($name:ident, $var_name:ident, $type:ty, $capacity: ident, check) => { + /// 编码定长整数 会检查长度 + /// + /// # Arguments + /// + /// * `value`: 待编码的数据 + /// + /// returns: Result<()> + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// // [0, 0, 255, 255] + /// encoder.put_fixed32(65535)?; + /// ``` + pub fn $name(&mut self, value: $type) -> Result<()> { + // vec类型自动扩容, buf 和 slice类型检查长度 + if let MutVector(_) = self.data {} else { check_length!(self.offset, type_capacity!($capacity), self.len()) }; + unsafe {$var_name(&mut self.data, self.offset, value);} + self.offset += type_capacity!($capacity); + Ok(()) + } + }; +} - for i in 0..var_offset { - dst.push(buf[i]); +/// 实现put_varint +macro_rules! put_varint { + ($name:ident, $var_name:ident, $type:ty, uncheck) => { + /// 编码变长整数 不检查长度 + /// + /// # Safety + /// * offset + varint_length < data.len() , 否则溢出 + /// + /// # Arguments + /// + /// * `value`: 待编码的数据 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// unsafe { + /// // [255, 255, 3] + /// encoder.uncheck_put_varint32(65535); + /// // [255, 255, 3, 255, 255, 3] + /// encoder.uncheck_put_varint64(65535); + /// } + /// ``` + pub unsafe fn $name(&mut self, value: $type) { + self.offset = $var_name(&mut self.data, self.offset, value); + } + }; + ($name:ident, $var_name:ident, $type:ty, check) => { + /// 编码变长整数 会检查长度 + /// + /// # Arguments + /// + /// * `value`: 待编码的数据 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// // [255, 255, 3] + /// encoder.put_varint32(65535)?; + /// // [255, 255, 3, 255, 255, 3] + /// encoder.put_varint64(65535)?; + /// ``` + pub fn $name(&mut self, value: $type) -> Result<()> { + // vec类型自动扩容, buf 和 slice类型检查长度 + if let MutVector(_) = self.data {} else { check_length!(self.offset, varint_length(value as u64), self.len()) }; + unsafe { self.offset = $var_name(&mut self.data, self.offset, value) } + Ok(()) } + } +} - dst.len() +impl<'a> Encoder<'a> { + /// 以vec做为容器生成encoder + /// 编码时当容量不足时会扩容 + /// 如果以追加的方式进行编码推荐使用vec做为容器 + /// 使用vec容器时, 推荐使用uncheck的方法 + /// + /// # Arguments + /// + /// * `vec`: vec + /// + /// returns: Encoder + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// ``` + pub fn with_vec(vec: &'a mut Vec) -> Self { + Self { + offset: 0, + data: MutVector(vec), + } + } + /// 以切片做为容器生成encoder + /// 编码时当容量不足时可能会造成内存溢出 + /// 需要提前规划好需要使用的容量, 并保证调用编码方式时不会溢出 + /// + /// # Arguments + /// + /// * `buf`: buf + /// + /// returns: Encoder + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut buf = [0; 20]; + /// unsafe { + /// let mut encoder = Encoder::with_buf(&mut buf); + /// } + /// ``` + pub fn with_buf(buf: &'a mut [u8]) -> Self { + Self { + offset: 0, + data: MutBuffer(buf), + } } - fn put_varint64(dst: &mut [u8], mut offset: usize, value: u64) -> usize { - let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - let var_offset = Self::encode_varint64(value, &mut buf, 0); - for i in 0..var_offset { - dst[offset] = buf[i]; - offset += 1; + /// 以slice做为容器生成encoder + /// 编码时当容量不足时会溢出 + /// + /// # Arguments + /// + /// * `slice`: slice + /// + /// returns: Encoder + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// use level_db_rust::util::slice::Slice; + /// let mut slice = Slice::from_vec(vec![0; 20]); + /// unsafe { + /// let mut encoder = Encoder::with_slice(&mut slice); + /// } + /// ``` + pub fn with_slice(slice: &'a mut Slice) -> Self { + Self { + offset: 0, + data: MutSlices(slice), } - offset } - // fn put_length_prefixed_slice(dst: &mut [u8], offset: usize, value: &Slice) -> usize { - fn put_length_prefixed_slice(dst: &mut [u8], offset: usize, value_len: usize) -> usize { - Self::put_varint64(dst, offset, value_len as u64); - offset + /// 从encoder的数据中生成decoder + /// + /// returns: Decoder + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut data = vec![1, 2, 3]; + /// let encoder = Encoder::with_vec(&mut data); + /// let decoder = encoder.create_decoder(); + /// ``` + pub fn create_decoder(&'a self) -> Decoder<'a> { + Decoder::from_encoder(self) + } + + put_fixed!(uncheck_put_fixed32, uncheck_encode_fixed32, u32, u32, uncheck); + put_fixed!(uncheck_put_fixed64, uncheck_encode_fixed64, u64, u64, uncheck); + put_fixed!(put_fixed32, uncheck_encode_fixed32, u32, u32, check); + put_fixed!(put_fixed64, uncheck_encode_fixed64, u64, u64, check); + + put_varint!(uncheck_put_varint32, uncheck_encode_varint32, u32, uncheck); + put_varint!(uncheck_put_varint64, uncheck_encode_varint64, u64, uncheck); + put_varint!(put_varint32, uncheck_encode_varint32, u32, check); + put_varint!(put_varint64, uncheck_encode_varint64, u64, check); + + /// 向encoder中直接写入数据不用进行编码 + /// 向vec中写入时会自动扩容 + /// # Safety + /// * self.offset + buf.len() > self.data , 如果data不是vec的话不会自动扩容, 会溢出 + /// + /// # Arguments + /// + /// * `buf`: 待写入的数据 + /// + /// returns: () + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// let buf = [1, 2, 3]; + /// // vec: [1, 2, 3] + /// unsafe { encoder.uncheck_put_buf(&buf) } + /// ``` + pub unsafe fn uncheck_put_buf(&mut self, buf: &[u8]) { + uncheck_write_buf(&mut self.data, self.offset, buf); + self.offset += buf.len(); + } + + /// 向encoder中直接写入数据不用进行编码 + /// 向vec中写入时会自动扩容 + /// 会检查是否能够写入 + /// + /// # Arguments + /// + /// * `buf`: 待写入的数据 + /// + /// returns: Result<(), Status> + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// let buf = [1, 2, 3]; + /// // vec: [1, 2, 3] + /// encoder.put_buf(&buf)? + /// ``` + pub fn put_buf(&mut self, buf: &[u8]) -> Result<()> { + // vec类型自动扩容 buf 和 slice类型检查长度 + if let MutVector(_) = self.data {} else { check_length!(self.offset, buf.len(), self.len()) }; + unsafe { uncheck_write_buf(&mut self.data, self.offset, buf); } + self.offset += buf.len(); + Ok(()) + } + + /// 写入slice时先写入slice的长度做为前缀 + /// slice(data:[1,2,3],size:3), 写入后[3,1,2,3] + /// + /// # Safety + /// * u32的字节数(4) + slice的字节数(slice.size()) < self.data.len(), 否则溢出(vec除外) + /// + /// # Arguments + /// + /// * `slice`: 待写入的slice + /// + /// returns: () + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// use level_db_rust::util::slice::Slice; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// let slice = Slice::from_vec(vec![1, 2, 3]); + /// // vec: [3, 1, 2, 3] + /// // The first '3' of the vec is the length of the slice, + /// // and the following '1,2,3' is the data of the slice + /// unsafe { encoder.uncheck_put_length_prefixed_slice(&slice); } + /// ``` + pub unsafe fn uncheck_put_length_prefixed_slice(&mut self, slice: &Slice) { + self.uncheck_put_varint32(slice.size() as u32); + self.uncheck_put_buf(slice); + } + + /// 写入slice时先写入slice的长度做为前缀 + /// + /// # Arguments + /// + /// * `slice`: 待写入的slice + /// + /// returns: Result<(), Status> + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// use level_db_rust::util::slice::Slice; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// let slice = Slice::from_vec(vec![1, 2, 3]); + /// // vec: [3, 1, 2, 3] + /// // The first '3' of the vec is the length of the slice, + /// // and the following '1,2,3' is the data of the slice + /// encoder.put_length_prefixed_slice(&slice)?; + /// ``` + pub fn put_length_prefixed_slice(&mut self, slice: &Slice) -> Result<()> { + self.put_varint32(slice.size() as u32)?; + self.put_buf(slice)?; + Ok(()) + } + + /// 获取当前编码到的位置 + /// + /// returns: usize + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// // offset: 0 + /// let offset = encoder.offset(); + /// encoder.put_varint32(65535)?; + /// // offset: 3 + /// let offset = encoder.offset(); + /// ``` + #[inline] + pub fn offset(&self) -> usize { + self.offset } - fn get_varint32(input: &Slice) -> u32 { - let cow = input.borrow_data(); - let bytes = cow.as_bytes(); - let mut result = 0_u32; - let mut shift = 0_u32; - let limit = input.size(); - let mut i = 0; - while shift <= 28 && i < limit { - let b = bytes[i]; - i += 1; - if (b & 128) != 0 { - result |= ((b & 127) << shift) as u32; - } else { - result |= (b << shift) as u32; + /// 获取容器的长度 + /// + /// returns: usize + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Encoder; + /// let mut vec = vec![]; + /// let mut encoder = Encoder::with_vec(&mut vec); + /// // len: 0 + /// let len = encoder.len(); + /// encoder.put_varint32(65535)?; + /// // len: 3 + /// let len = encoder.len(); + /// ``` + pub fn len(&self) -> usize { + match self.data { + MutVector(ref vec) => { + vec.len() + } + MutBuffer(ref buf) => { + buf.len() } - shift += 7; - } - result - } - - fn get_varint64(input: &Slice) -> u64 { - let cow = input.borrow_data(); - let bytes = cow.as_bytes(); - let mut result = 0_u64; - let mut shift = 0_u64; - let limit = input.size(); - let mut i = 0; - while shift <= 63 && i < limit { - let b = bytes[i]; - i += 1; - if (b & 128) != 0 { - result |= ((b & 127) << shift) as u64; - } else { - result |= (b << shift) as u64; + MutSlices(ref slice) => { + slice.size() } - shift += 7; } - result } +} + +macro_rules! get_fixed { + ($name:ident, $var_name:ident, $type:ty, $capacity: ident, uncheck) => { + /// 定长解码 + /// # Safety + /// * self.offset < self.limit 先调用 encoder.can_get() 确定可以解码再调用, 否则溢出 + /// + /// returns: u32/u64 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let mut vec = vec![0, 0, 255, 255]; + /// let mut decoder = Decoder::with_vec(&mut vec); + /// // 65535 + /// let value = unsafe { decoder.uncheck_get_fixed32() }; + /// ``` + #[inline] + pub unsafe fn $name(&mut self) -> $type { + let value = $var_name(&self.data, self.offset); + self.offset += type_capacity!($capacity); + value + } + }; + ($name:ident, $var_name:ident, $type:ty, $capacity: ident, check) => { + /// 定长解码 + /// # Safety + /// * self.offset < self.limit 先调用 encoder.can_get() 确定可以解码再调用 否则溢出 + /// + /// returns: u32/u64 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let mut vec = vec![0, 0, 255, 255]; + /// let mut decoder = Decoder::with_vec(&mut vec); + /// // 65535 + /// let value = decoder.get_fixed32()?; + /// ``` + #[inline] + pub fn $name(&mut self) -> Result<$type> { + check_length!(self.offset, self.limit); + let value = unsafe { $var_name(&self.data, self.offset) }; + self.offset += type_capacity!($capacity); + Ok(value) + } + } +} + +macro_rules! get_varint { + ($name:ident, $var_name:ident, $type:ty, uncheck) => { + /// 变长解码 + /// + /// returns: u32/u64 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let mut vec = vec![255, 255, 3]; + /// let mut decoder = Decoder::with_vec(&mut vec); + /// // 65535 + /// let value = unsafe { decoder.uncheck_get_varint32() }; + /// ``` + #[inline] + pub unsafe fn $name(&mut self) -> $type { + let res = $var_name(&self.data, self.offset, self.limit); + self.offset = res.1; + res.0 + } + }; + ($name:ident, $var_name:ident, $type:ty, check) => { + /// 变长解码 + /// + /// returns: u32/u64 + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let mut vec = vec![255, 255, 3]; + /// let mut decoder = Decoder::with_vec(&mut vec); + /// // 65535 + /// let value = decoder.get_varint32()?; + /// ``` + #[inline] + pub fn $name(&mut self) -> Result<$type> { + check_length!(self.offset, self.limit); + let res = unsafe { $var_name(&self.data, self.offset, self.limit) }; + self.offset = res.1; + Ok(res.0) + } + } +} - fn get_length_prefixed_slice(input: &mut Slice) -> Slice { - let decode = Coding::get_varint32(input); - Slice::from_buf(decode.to_le_bytes().as_mut_slice()) +impl<'a> Decoder<'a> { + pub fn with_slice(slice: &'a Slice) -> Self { + Self { + offset: 0, + limit: slice.size(), + data: Slices(slice), + } + } + pub fn with_buf(buf: &'a [u8]) -> Self { + Self { + offset: 0, + limit: buf.len(), + data: Buffer(buf), + } + } + pub fn with_vec(vec: &'a Vec) -> Self { + Self { + offset: 0, + data: Vector(vec), + limit: vec.len(), + } } - fn varint_length(mut value: usize) -> usize { - let mut len = 1; - while value >= 128 { - value >>= 7; - len += 1; + pub fn from_encoder(encoder: &'a Encoder) -> Self { + Self { + offset: 0, + limit: encoder.len(), + data: match encoder.data { + MutVector(ref vec) => { + Vector(vec) + } + MutBuffer(ref buf) => { + Buffer(buf) + } + MutSlices(ref slice) => { + Slices(slice) + } + }, } - len } - fn encode_fixed32(value: u32, buf: &mut [u8], mut offset: usize) -> usize { - (&mut buf[offset..]).write(&value.to_le_bytes()).unwrap(); - offset+4 + /// 判断是否有数据可以读取 + /// 数据读取到末尾 不满足 offset < limit 时为false + /// 如果使用了uncheck的方法 需要调用这个方法判断是否可以读取 否则可能会溢出 + /// + /// returns: bool + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let mut vec = vec![255, 255, 3]; + /// let mut decoder = Decoder::with_vec(&mut vec); + /// // true + /// let can_get = decoder.can_get(); + /// decoder.get_varint32()?; + /// // false + /// let can_get = decoder.can_get(); + /// ``` + #[inline] + pub fn can_get(&self) -> bool { + self.offset < self.limit } - fn encode_fixed64(value: u64, buf: &mut [u8], mut offset: usize) -> usize { - (&mut buf[offset..]).write(&value.to_le_bytes()).unwrap(); - offset+8 + get_fixed!(uncheck_get_fixed32, uncheck_decode_fixed32, u32, u32, uncheck); + get_fixed!(uncheck_get_fixed64, uncheck_decode_fixed64, u64, u64, uncheck); + get_fixed!(get_fixed32, uncheck_decode_fixed32, u32, u32, check); + get_fixed!(get_fixed64, uncheck_decode_fixed64, u64, u64, check); + + get_varint!(uncheck_get_varint32, uncheck_decode_varint32, u32, uncheck); + get_varint!(uncheck_get_varint64, uncheck_decode_varint64, u64, uncheck); + get_varint!(get_varint32, uncheck_decode_varint32, u32, check); + get_varint!(get_varint64, uncheck_decode_varint64, u64, check); + + /// 解码出slice 不检查长度 + /// + /// # Safety + /// * self.offset < self.len() , 否则溢出 + /// + /// returns: Slice + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![3, 1, 2, 3]; + /// let mut decoder = Decoder::with_vec(&vec); + /// // [1, 2, 3] + /// let slice = unsafe { decoder.uncheck_get_length_prefixed_slice() }; + /// ``` + pub unsafe fn uncheck_get_length_prefixed_slice(&mut self) -> Slice { + let size = self.uncheck_get_varint32() as usize; + self.uncheck_get_buf(size) + } + + /// 解码出slice + /// + /// returns: Result + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![3, 1, 2, 3]; + /// let mut decoder = Decoder::with_vec(&vec); + /// // [1, 2, 3] + /// let slice = decoder.get_length_prefixed_slice()?; + /// ``` + pub fn get_length_prefixed_slice(&mut self) -> Result { + check_length!(self.offset, self.limit); + let size = unsafe { self.uncheck_get_varint32() } as usize; + unsafe { Ok(self.uncheck_get_buf(size)) } + } + + /// 获取buf 不检查长度 + /// + /// # Safety + /// * self.offset + len < self.limit, 否则溢出 + /// + /// # Arguments + /// + /// * `data`: 待解码数据 + /// * `len`: 解码buf的长度, 必须要指定的, 否则无法正确读取 + /// + /// returns: Slice + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![1, 2, 3]; + /// let mut decoder = Decoder::with_vec(&vec); + /// // [1, 2, 3] + /// let buf = unsafe { decoder.uncheck_get_buf(3) }; + /// ``` + pub unsafe fn uncheck_get_buf(&mut self, len: usize) -> Slice { + let slice = uncheck_read_buf(&self.data, self.offset, len); + self.offset += len; + slice + } + + /// 读取buf + /// + /// # Arguments + /// + /// * `data`: 待解码数据 + /// * `len`: 读取buf的长度, 必须要指定的, 否则无法正确读取 + /// + /// returns: Result, Status> + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![1, 2, 3]; + /// let mut decoder = Decoder::with_vec(&vec); + /// // [1, 2, 3] + /// let buf = decoder.get_buf(3)?; + /// ``` + pub fn get_buf(&self, len: usize) -> Result { + check_length!(self.offset, len, self.limit); + unsafe { + Ok(uncheck_read_buf(&self.data, self.offset, len)) + } + } + + /// 跳过一段长度 偏移量会移动到跳过后的位置继续读取 未检查偏移量 + /// + /// # Safety + /// * offset + skip < self.limit, 否则会出现未定义行为, 读取将溢出 + /// + /// # Arguments + /// + /// * `skip`: 需要跳过的长度 + /// + /// returns: usize + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![255, 1, 255, 255, 3]; + /// // offset: 0 + /// let mut decoder = Decoder::with_vec(&vec); + /// // offset: 2 + /// unsafe { decoder.uncheck_skip(2) }; + /// // value: 65535 + /// let value = decoder.get_varint32()?; + /// ``` + pub unsafe fn uncheck_skip(&mut self, skip: usize) -> usize { + self.offset += skip; + self.offset } + /// 跳过一段长度 偏移量会移动到跳过后的位置继续读取 + /// + /// # Arguments + /// + /// * `skip`: 需要跳过的长度 + /// + /// returns: Result + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![255, 1, 255, 255, 3]; + /// // offset: 0 + /// let mut decoder = Decoder::with_vec(&vec); + /// // offset: 2 + /// decoder.skip(2)?; + /// // value: 65535 + /// let value = decoder.get_varint32()?; + /// ``` + pub fn skip(&mut self, skip: usize) -> Result { + check_length!(self.offset, self.limit); + self.offset += skip; + Ok(self.offset) + } - fn decode_fixed32(buf: &[u8]) -> u32 { - return (buf[0] as u32) | - (buf[1] as u32) << 8 | - (buf[2] as u32) << 16 | - (buf[3] as u32) << 24; + /// 获取当前编码到的位置 + /// + /// returns: usize + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![255, 1, 255, 255, 3]; + /// let mut decoder = Decoder::with_vec(&vec); + /// // offset: 0 + /// let value = decoder.get_varint32()?; + /// // offset: 2 + /// let offset = decoder.offset(); + /// ``` + pub fn offset(&self) -> usize { + self.offset } - fn decode_fixed64(buf: &[u8]) -> u64 { - return (buf[0]) as u64 | - (buf[1] as u64) << 8 | - (buf[2] as u64) << 16 | - (buf[3] as u64) << 24 | - (buf[4] as u64) << 32 | - (buf[5] as u64) << 40 | - (buf[6] as u64) << 48 | - (buf[7] as u64) << 56; + /// 获取编码数据的可解码限制 + /// offset < limit + /// + /// returns: usize + /// + /// # Examples + /// + /// ``` + /// use level_db_rust::util::coding::Decoder; + /// let vec = vec![255, 1, 255, 255, 3]; + /// let mut decoder = Decoder::with_vec(&vec); + /// // limit: 5 + /// let limit = decoder.limit(); + /// ``` + pub fn limit(&self) -> usize { + self.limit } } -macro_rules! coding_impl { - {$TRAIT: ident, $TYPE: ty, $VAR_NAME: ident, $FIXED_NAME: ident} => { - impl $TRAIT for $TYPE { - /// 变长正整数编码 - /// - /// # Arguments - /// - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset = value.varint(&mut buf, 0); - /// ``` - fn varint(self, buf: &mut [u8], offset: usize) -> usize { - Coding::$VAR_NAME (self, buf, offset) - } - /// 定长正整数编码 - /// - /// # Arguments - /// - /// * `buf`: 目标数组 - /// * `offset`: 偏移量 - /// - /// returns: usize : 编码后的偏移量 - /// - /// # Examples - /// - /// ``` - /// let mut buf: [u8; 4] = [0, 0, 0, 0]; - /// let value: u32 = 65534; - /// let offset = value.fixedint(&mut buf, 0); - /// ``` - fn fixedint(self, buf: &mut [u8], offset: usize) -> usize { - Coding::$FIXED_NAME (self, buf, offset) - } +#[test] +fn test_varint_length() { + let length = varint_length(1); + assert_eq!(1, length); + let length = varint_length(127); + assert_eq!(1, length); + let length = varint_length(128); + assert_eq!(2, length); + let length = varint_length(255); + assert_eq!(2, length); + let length = varint_length(16383); + assert_eq!(2, length); + let length = varint_length(16384); + assert_eq!(3, length); + let length = varint_length(65535); + assert_eq!(3, length); + let length = varint_length(209_7151); + assert_eq!(3, length); + let length = varint_length(209_7152); + assert_eq!(4, length); + let length = varint_length(2_6843_5455); + assert_eq!(4, length); + let length = varint_length(2_6843_5456); + assert_eq!(5, length); + // 1 << 35 + let length = varint_length(343_5973_8367); + assert_eq!(5, length); + let length = varint_length(343_5973_8368); + assert_eq!(6, length); + let length = varint_length(4_3980_4651_1103); + assert_eq!(6, length); + let length = varint_length(4_3980_4651_1104); + assert_eq!(7, length); + let length = varint_length(562_9499_5342_1311); + assert_eq!(7, length); + let length = varint_length(562_9499_5342_1312); + assert_eq!(8, length); + let length = varint_length(7_2057_5940_3792_7935); + assert_eq!(8, length); + let length = varint_length(7_2057_5940_3792_7936); + assert_eq!(9, length); + let length = varint_length(922_3372_0368_5477_5807); + assert_eq!(9, length); + let length = varint_length(922_3372_0368_5477_5808); + assert_eq!(10, length); +} + +#[test] +fn test_encode_fixed() { + let mut vec = vec![]; + unsafe { uncheck_encode_fixed32(&mut MutVector(&mut vec), 0, 1234); } + println!("{:?}", vec); + assert_eq!(vec![0, 0, 4, 210], vec); + assert_eq!(4, vec.len()); + + unsafe { uncheck_encode_fixed32(&mut MutVector(&mut vec), 4, 3_0000_0000); } + println!("{:?}", vec); + assert_eq!(8, vec.len()); + assert_eq!(vec![0, 0, 4, 210, 17, 225, 163, 0], vec); + + let mut vec = vec![]; + unsafe { uncheck_encode_fixed64(&mut MutVector(&mut vec), 0, 8_3980_4651_1103); } + println!("{:?}", vec); + assert_eq!(8, vec.len()); + + unsafe { uncheck_encode_fixed64(&mut MutVector(&mut vec), 8, 900_3372_0368_5477_5808); } + println!("{:?}", vec); + assert_eq!(16, vec.len()); + assert_eq!(vec![0, 0, 7, 163, 82, 148, 63, 255, 124, 242, 103, 42, 101, 106, 0, 0], vec); +} + +#[test] +fn test_decode_fixed() { + let mut vec = vec![]; + unsafe { + uncheck_encode_fixed32(&mut MutVector(&mut vec), 0, 1234); + uncheck_encode_fixed32(&mut MutVector(&mut vec), 4, 128); + uncheck_encode_fixed32(&mut MutVector(&mut vec), 8, 255); + uncheck_encode_fixed32(&mut MutVector(&mut vec), 12, 65535); + uncheck_encode_fixed32(&mut MutVector(&mut vec), 16, 10000000); + } + println!("{:?}", vec); + assert_eq!(vec![0, 0, 4, 210, 0, 0, 0, 128, 0, 0, 0, 255, 0, 0, 255, 255, 0, 152, 150, 128], vec); + + let result = unsafe { uncheck_decode_fixed32(&Vector(&vec), 0) }; + println!("{}", result); + assert_eq!(1234, result); + + let result = unsafe { uncheck_decode_fixed32(&Vector(&vec), 4) }; + println!("{}", result); + assert_eq!(128, result); + + let result = unsafe { uncheck_decode_fixed32(&Vector(&vec), 8) }; + println!("{}", result); + assert_eq!(255, result); + + let result = unsafe { uncheck_decode_fixed32(&Vector(&vec), 12) }; + println!("{}", result); + assert_eq!(65535, result); + + let result = unsafe { uncheck_decode_fixed32(&Vector(&vec), 16) }; + println!("{}", result); + assert_eq!(10000000, result); + + let mut vec = vec![]; + unsafe { + uncheck_encode_fixed64(&mut MutVector(&mut vec), 0, 8_3980_4651_1103); + uncheck_encode_fixed64(&mut MutVector(&mut vec), 8, 900_3372_0368_5477_5808); + } + println!("{:?}", vec); + assert_eq!(vec![0, 0, 7, 163, 82, 148, 63, 255, 124, 242, 103, 42, 101, 106, 0, 0], vec); + + let result = unsafe { uncheck_decode_fixed64(&Vector(&vec), 0) }; + println!("{}", result); + assert_eq!(8_3980_4651_1103, result); + + let result = unsafe { uncheck_decode_fixed64(&Vector(&vec), 8) }; + println!("{}", result); + assert_eq!(900_3372_0368_5477_5808, result); +} + +#[test] +fn test_encode_varint() { + let mut vec = vec![]; + let mut offset = 0; + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 2); } + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 128); } + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 255); } + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 65535); } + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 10000000); } + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 209_7152); } + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 2_6843_5456); } + println!("{:?}", vec); + println!("offset: {}", offset); + + assert_eq!(21, offset); + assert_eq!(vec![2, 128, 1, 255, 1, 255, 255, 3, 128, 173, 226, 4, 128, 128, 128, 1, 128, 128, 128, 128, 1], vec); + + let mut vec = vec![]; + let mut offset = 0; + + unsafe { offset = uncheck_encode_varint64(&mut MutVector(&mut vec), offset, 65535) }; + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint64(&mut MutVector(&mut vec), offset, 8_3980_4651_1103) }; + println!("{:?}", vec); + println!("offset: {}", offset); + + unsafe { offset = uncheck_encode_varint64(&mut MutVector(&mut vec), offset, 900_3372_0368_5477_5808) }; + println!("{:?}", vec); + println!("offset: {}", offset); + + assert_eq!(19, offset); + assert_eq!(vec![255, 255, 3, 255, 255, 208, 148, 181, 244, 1, 128, 128, 168, 171, 166, 229, 153, 249, 124], vec); +} + +#[test] +fn test_decode_varint() { + let vec = vec![2, 128, 1, 255, 1, 255, 255, 3, 128, 173, 226, 4, 128, 128, 128, 1, 128, 128, 128, 128, 1]; + println!("{:?}", vec); + let mut offset = 0; + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 2); + + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 128); + + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 255); + + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 65535); + + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 10000000); + + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 209_7152); + + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(res.0, 2_6843_5456); + + println!("decode varint64: "); + let vec = vec![255, 255, 3, 255, 255, 208, 148, 181, 244, 1, 128, 128, 168, 171, 166, 229, 153, 249, 124]; + println!("{:?}", vec); + let mut offset = 0; + let res = unsafe { uncheck_decode_varint64(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(65535, res.0); + + let res = unsafe { uncheck_decode_varint64(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(8_3980_4651_1103, res.0); + + let res = unsafe { uncheck_decode_varint64(&Vector(&vec), offset, vec.len()) }; + offset = res.1; + println!("value: {}", res.0); + println!("offset: {}", offset); + assert_eq!(900_3372_0368_5477_5808, res.0); +} + + +#[test] +fn test_write_buf() { + let mut vec = vec![]; + + let buf = [1, 2, 3, 4, 5]; + unsafe { uncheck_write_buf(&mut MutVector(&mut vec), 0, &buf); } + + println!("{:?}", vec); + assert_eq!(vec![1, 2, 3, 4, 5], vec); + + let buf = [1, 2, 3, 4]; + unsafe { uncheck_write_buf(&mut MutVector(&mut vec), 5, &buf); } + + println!("{:?}", vec); + assert_eq!(vec![1, 2, 3, 4, 5, 1, 2, 3, 4], vec); +} + +#[test] +fn test_read_buf() { + let vec = vec![1, 2, 3, 4, 5, 1, 2, 3, 4]; + let buf = unsafe { uncheck_read_buf(&Vector(&vec), 0, 5) }; + println!("{:?}", buf); + assert_eq!(&[1_u8, 2, 3, 4, 5] as &[u8; 5], buf.deref()); + let buf = unsafe { uncheck_read_buf(&Vector(&vec), 5, 4) }; + println!("{:?}", buf); + assert_eq!(&[1_u8, 2, 3, 4] as &[u8; 4], buf.deref()); + +} + +#[test] +fn test_mixed_encode_decode() { + // 混合类型编码 解码 varint32 varint64 fixed32 fixed64 write_buf read_buf + let mut vec = vec![]; + let mut offset = 0; + unsafe { uncheck_encode_fixed32(&mut MutVector(&mut vec), offset, 3) }; + offset += 4; + offset = unsafe { uncheck_encode_varint32(&mut MutVector(&mut vec), offset, 655535) }; + unsafe { uncheck_encode_fixed64(&mut MutVector(&mut vec), offset, 7) }; + offset += 8; + offset = unsafe { uncheck_encode_varint64(&mut MutVector(&mut vec), offset, 8_3980_4651_1103) }; + let buf = [1, 2, 3, 4]; + unsafe { uncheck_write_buf(&mut MutVector(&mut vec), offset, &buf) }; + offset += buf.len(); + println!("{:?}", vec); + println!("offset: {}", offset); + + offset = 0; + let value = unsafe { uncheck_decode_fixed32(&Vector(&vec), offset) }; + println!("{}", value); + assert_eq!(3, value); + offset += 4; + let res = unsafe { uncheck_decode_varint32(&Vector(&vec), offset, (&vec).len()) }; + println!("{}", res.0); + assert_eq!(655535, res.0); + offset = res.1; + let value = unsafe { uncheck_decode_fixed64(&Vector(&vec), offset) }; + println!("{}", value); + assert_eq!(7, value); + offset += 8; + let res = unsafe { uncheck_decode_varint64(&Vector(&vec), offset, (&vec).len()) }; + println!("{}", res.0); + assert_eq!(8_3980_4651_1103, res.0); + offset = res.1; + + let buf = unsafe { uncheck_read_buf(&Vector(&vec), offset, 4) }; + println!("{:?}", buf); + assert_eq!(&[1_u8, 2, 3, 4] as &[u8; 4], buf.deref()); + + println!("offset: {}", offset); + assert_eq!(22, offset); +} + +#[test] +fn test_put_fixed() -> Result<()> { + let mut vec = vec![]; + + unsafe { + let mut encoder = Encoder::with_vec(&mut vec); + println!("{:?}", encoder); + encoder.uncheck_put_fixed32(2); + encoder.uncheck_put_fixed32(128); + encoder.uncheck_put_fixed32(255); + encoder.uncheck_put_fixed32(65535); + encoder.uncheck_put_fixed32(10000000); + encoder.uncheck_put_fixed64(655535); + encoder.uncheck_put_fixed64(8_3980_4651_1103); + encoder.uncheck_put_fixed64(900_3372_0368_5477_5808); + println!("{:?}", &encoder); + if let MutVector(data) = encoder.data { + assert_eq!(&mut vec![0, 0, 0, 2, 0, 0, 0, 128, 0, 0, 0, 255, 0, 0, 255, 255, 0, 152, 150, + 128, 0, 0, 0, 0, 0, 10, 0, 175, 0, 0, 7, 163, 82, 148, 63, 255, 124, + 242, 103, 42, 101, 106, 0, 0], + data); + } + } + + let mut encoder = Encoder::with_vec(&mut vec); + println!("{:?}", encoder); + encoder.put_fixed32(2)?; + encoder.put_fixed32(128)?; + encoder.put_fixed32(255)?; + encoder.put_fixed32(65535)?; + encoder.put_fixed32(10000000)?; + encoder.put_fixed64(655535)?; + encoder.put_fixed64(8_3980_4651_1103)?; + encoder.put_fixed64(900_3372_0368_5477_5808)?; + println!("{:?}", &encoder); + if let MutVector(data) = encoder.data { + assert_eq!(&mut vec![0, 0, 0, 2, 0, 0, 0, 128, 0, 0, 0, 255, 0, 0, 255, 255, 0, 152, 150, + 128, 0, 0, 0, 0, 0, 10, 0, 175, 0, 0, 7, 163, 82, 148, 63, 255, 124, + 242, 103, 42, 101, 106, 0, 0], + data); + } + + let mut buf = [0; 20]; + unsafe { + let mut encoder = Encoder::with_buf(&mut buf); + println!("{:?}", encoder); + encoder.uncheck_put_fixed32(2); + encoder.uncheck_put_fixed64(655535); + encoder.uncheck_put_fixed64(8_3980_4651_1103); + println!("{:?}", &encoder); + if let MutVector(data) = encoder.data { + assert_eq!(&mut vec![0, 0, 0, 2, 0, 0, 0, 0, 0, 10, 0, 175, 0, 0, 7, 163, 82, 148, 63, 255], + data); } } + + + let mut slice = Slice::from_vec(vec![0; 20]); + unsafe { + let mut encoder = Encoder::with_slice(&mut slice); + println!("{:?}", encoder); + encoder.uncheck_put_fixed32(2); + encoder.uncheck_put_fixed64(655535); + encoder.uncheck_put_fixed64(8_3980_4651_1103); + println!("{:?}", &encoder); + if let MutVector(data) = encoder.data { + assert_eq!(&mut vec![0, 0, 0, 2, 0, 0, 0, 0, 0, 10, 0, 175, 0, 0, 7, 163, 82, 148, 63, 255], + data); + } + } + + Ok(()) +} + +#[test] +fn test_get_fixed() -> Result<()> { + let mut vec = vec![]; + + unsafe { + let mut encoder = Encoder::with_vec(&mut vec); + println!("{:?}", encoder); + encoder.uncheck_put_fixed32(2); + encoder.uncheck_put_fixed32(128); + encoder.uncheck_put_fixed32(255); + encoder.uncheck_put_fixed32(65535); + encoder.uncheck_put_fixed32(10000000); + encoder.uncheck_put_fixed64(655535); + encoder.uncheck_put_fixed64(8_3980_4651_1103); + encoder.uncheck_put_fixed64(900_3372_0368_5477_5808); + println!("{:?}", &encoder.data); + println!("{:?}", &encoder); + if let MutVector(data) = encoder.data { + assert_eq!(&mut vec![0, 0, 0, 2, 0, 0, 0, 128, 0, 0, 0, 255, 0, 0, 255, 255, 0, 152, 150, 128, 0, 0, 0, 0, 0, 10, 0, 175, 0, 0, 7, 163, 82, 148, 63, 255, 124, 242, 103, 42, 101, 106, 0, 0], + data); + } + } + + let mut decoder = Decoder::with_vec(&mut vec); + + while decoder.can_get() { + let value = unsafe { decoder.uncheck_get_fixed32() }; + println!("{}", value); + } + let mut decoder = Decoder::with_vec(&mut vec); + + println!("{}", decoder.can_get()); + assert_eq!(true, decoder.can_get()); + + assert_eq!(2, unsafe { decoder.uncheck_get_fixed32() }); + assert_eq!(128, unsafe { decoder.uncheck_get_fixed32() }); + assert_eq!(255, unsafe { decoder.uncheck_get_fixed32() }); + assert_eq!(65535, unsafe { decoder.uncheck_get_fixed32() }); + assert_eq!(10000000, unsafe { decoder.uncheck_get_fixed32() }); + assert_eq!(655535, unsafe { decoder.uncheck_get_fixed64() }); + assert_eq!(8_3980_4651_1103, unsafe { decoder.uncheck_get_fixed64() }); + assert_eq!(900_3372_0368_5477_5808, unsafe { decoder.uncheck_get_fixed64() }); + + println!("{}", decoder.can_get()); + assert_eq!(false, decoder.can_get()); + + let mut decoder = Decoder::with_vec(&mut vec); + + println!("{}", decoder.can_get()); + assert_eq!(true, decoder.can_get()); + + assert_eq!(2, decoder.get_fixed32()?); + assert_eq!(128, decoder.get_fixed32()?); + assert_eq!(255, decoder.get_fixed32()?); + assert_eq!(65535, decoder.get_fixed32()?); + assert_eq!(10000000, decoder.get_fixed32()?); + assert_eq!(655535, decoder.get_fixed64()?); + assert_eq!(8_3980_4651_1103, decoder.get_fixed64()?); + assert_eq!(900_3372_0368_5477_5808, decoder.get_fixed64()?); + + println!("{}", decoder.can_get()); + assert_eq!(false, decoder.can_get()); + + Ok(()) +} + +#[test] +fn test_put_varint() -> Result<()> { + let mut vec = vec![]; + unsafe { + let mut encoder = Encoder::with_vec(&mut vec); + encoder.uncheck_put_varint32(2); + encoder.uncheck_put_varint32(128); + encoder.uncheck_put_varint32(255); + encoder.uncheck_put_varint32(65535); + encoder.uncheck_put_varint32(10000000); + encoder.uncheck_put_varint64(655535); + encoder.uncheck_put_varint64(8_3980_4651_1103); + encoder.uncheck_put_varint64(900_3372_0368_5477_5808); + println!("{:?}", vec); + assert_eq!(vec![2, 128, 1, 255, 1, 255, 255, 3, 128, 173, 226, 4, 175, 129, 40, 255, 255, 208, 148, 181, 244, 1, 128, 128, 168, 171, 166, 229, 153, 249, 124], + vec); + } + { + let mut encoder = Encoder::with_vec(&mut vec); + encoder.put_varint32(2)?; + encoder.put_varint32(128)?; + encoder.put_varint32(255)?; + encoder.put_varint32(65535)?; + encoder.put_varint32(10000000)?; + encoder.put_varint64(655535)?; + encoder.put_varint64(8_3980_4651_1103)?; + encoder.put_varint64(900_3372_0368_5477_5808)?; + println!("{:?}", vec); + assert_eq!(vec![2, 128, 1, 255, 1, 255, 255, 3, 128, 173, 226, 4, 175, 129, 40, 255, 255, 208, 148, 181, 244, 1, 128, 128, 168, 171, 166, 229, 153, 249, 124], + vec); + } + Ok(()) } -coding_impl!(Coding32,u32,encode_varint32,encode_fixed32); +#[test] +fn test_get_varint() -> Result<()> { + let mut vec = vec![]; + unsafe { + let mut encoder = Encoder::with_vec(&mut vec); + encoder.uncheck_put_varint32(2); + encoder.uncheck_put_varint32(128); + encoder.uncheck_put_varint32(255); + encoder.uncheck_put_varint32(65535); + encoder.uncheck_put_varint32(10000000); + encoder.uncheck_put_varint64(655535); + encoder.uncheck_put_varint64(8_3980_4651_1103); + encoder.uncheck_put_varint64(900_3372_0368_5477_5808); + println!("{:?}", vec); + }; + { + let mut decoder = Decoder::with_vec(&mut vec); + assert_eq!(2, decoder.get_varint32()?); + assert_eq!(128, decoder.get_varint32()?); + assert_eq!(255, decoder.get_varint32()?); + assert_eq!(65535, decoder.get_varint32()?); + assert_eq!(10000000, decoder.get_varint32()?); + assert_eq!(655535, decoder.get_varint64()?); + assert_eq!(8_3980_4651_1103, decoder.get_varint64()?); + assert_eq!(900_3372_0368_5477_5808, decoder.get_varint64()?); + }; + Ok(()) +} + +#[test] +fn test_put_buf() -> Result<()> { + let mut vec = vec![]; + let mut encoder = Encoder::with_vec(&mut vec); + let buf = [1, 2, 3]; + unsafe { encoder.uncheck_put_buf(&buf) } + println!("{:?}", buf); + encoder.put_buf(&buf)?; + assert_eq!(&[1_u8, 2, 3, 1, 2, 3], vec.as_slice()); + println!("{:?}", vec); + + Ok(()) +} + +#[test] +fn test_get_buf() -> Result<()> { + let mut vec = vec![]; + { + let mut encoder = Encoder::with_vec(&mut vec); + let buf = [1, 2, 3]; + unsafe { encoder.uncheck_put_buf(&buf) } + println!("{:?}", buf); + assert_eq!(&[1_u8, 2, 3], vec.clone().as_slice()); + } + let mut decoder = Decoder::with_vec(&vec); + let buf = unsafe { decoder.uncheck_get_buf(3) }; + println!("{:?}", buf); + assert_eq!(Slice::from_vec(vec![1, 2, 3]), buf); + assert_eq!(3, decoder.offset); + + Ok(()) +} + +#[test] +fn test_put_length_prefixed_slice() { + let mut vec = vec![]; + { + let mut encoder = Encoder::with_vec(&mut vec); + let slice = Slice::from_vec(vec![1, 2, 3]); + unsafe { encoder.uncheck_put_length_prefixed_slice(&slice); } + assert_eq!(4, encoder.offset) + } + println!("{:?}", vec); + assert_eq!(&vec![3, 1, 2, 3], &vec); +} + +#[test] +fn test_get_length_prefixed_slice() { + let mut vec = vec![]; + { + let mut encoder = Encoder::with_vec(&mut vec); + let slice = Slice::from_vec(vec![1, 2, 3]); + unsafe { encoder.uncheck_put_length_prefixed_slice(&slice); } + } + println!("{:?}", vec); + assert_eq!(vec![3, 1, 2, 3], vec); + + let mut decoder = Decoder::with_vec(&vec); + let slice = unsafe { decoder.uncheck_get_length_prefixed_slice() }; + println!("{:?}", slice); + assert_eq!(&[1_u8, 2, 3], &*slice); + assert_eq!(4, decoder.offset) +} + +#[test] +fn test_mixed_put_get() { + let mut vec = vec![]; + let mut encoder = Encoder::with_vec(&mut vec); + + unsafe { + encoder.uncheck_put_fixed32(3); + encoder.uncheck_put_varint32(65535); + encoder.uncheck_put_fixed64(7); + encoder.uncheck_put_varint64(8_3980_4651_1103); + let buf = [1, 2, 3]; + encoder.uncheck_put_buf(&buf); + let slice = Slice::from_vec(vec![1, 2, 3]); + encoder.uncheck_put_length_prefixed_slice(&slice); + } + + let mut decoder = Decoder::with_vec(&vec); + unsafe { + assert_eq!(3, decoder.uncheck_get_fixed32()); + assert_eq!(65535, decoder.uncheck_get_varint32()); + assert_eq!(7, decoder.uncheck_get_fixed64()); + assert_eq!(8_3980_4651_1103, decoder.uncheck_get_varint64()); + let buf = [1_u8, 2, 3]; + assert_eq!(&buf, &*decoder.uncheck_get_buf(3)); + let slice = Slice::from_vec(vec![1, 2, 3]); + assert_eq!(slice, decoder.uncheck_get_length_prefixed_slice()) + } +} + +#[test] +fn test_offset_len_skip() -> Result<()> { + let mut vec = vec![]; + let mut encoder = Encoder::with_vec(&mut vec); + assert_eq!(0, encoder.offset()); + assert_eq!(0, encoder.len()); + encoder.put_varint32(65535)?; + assert_eq!(3, encoder.offset()); + assert_eq!(3, encoder.len()); + + encoder.put_varint32(65535)?; + assert_eq!(6, encoder.offset()); + assert_eq!(6, encoder.len()); + + encoder.put_varint32(65535)?; + assert_eq!(9, encoder.offset()); + assert_eq!(9, encoder.len()); + + let mut decoder = Decoder::with_vec(&vec); + assert_eq!(0, decoder.offset()); + assert_eq!(9, decoder.limit()); + + let value = decoder.get_varint32()?; + assert_eq!(3, decoder.offset()); + assert_eq!(9, decoder.limit()); + assert_eq!(65535, value); + + decoder.skip(3)?; + + let value = decoder.get_varint32()?; + assert_eq!(9, decoder.offset()); + assert_eq!(9, decoder.limit()); + assert_eq!(65535, value); + + let mut decoder = Decoder::with_vec(&vec); + assert_eq!(0, decoder.offset()); + assert_eq!(9, decoder.limit()); + + let value = decoder.get_varint32()?; + assert_eq!(3, decoder.offset()); + assert_eq!(9, decoder.limit()); + assert_eq!(65535, value); + + unsafe { decoder.uncheck_skip(3); } + + let value = decoder.get_varint32()?; + assert_eq!(9, decoder.offset()); + assert_eq!(9, decoder.limit()); + assert_eq!(65535, value); + + Ok(()) +} + +#[test] +fn test_from_into() { + let mut data = vec![1, 2, 3]; + let encoder = Encoder::with_vec(&mut data); + println!("{:?}", encoder); + + let decoder = encoder.create_decoder(); + println!("{:?}", decoder); + assert_eq!(0, decoder.offset); + let empty = &vec![]; + assert_eq!(vec![1, 2, 3], *if let Vector(data) = decoder.data { data } else { empty }); + assert_eq!(3, decoder.limit); +} -coding_impl!(Coding64,u64,encode_varint64,encode_fixed64); \ No newline at end of file +#[test] +fn test_type_capacity() { + let type_capacity = type_capacity!(u32); + println!("u32: {}", type_capacity); + assert_eq!(4, type_capacity); + let type_capacity = type_capacity!(u64); + println!("u64: {}", type_capacity); + assert_eq!(8, type_capacity); +} \ No newline at end of file diff --git a/src/util/coding_test.rs b/src/util/coding_test.rs deleted file mode 100644 index 1531ad0f440208695cb6adbc6f38c3312315a585..0000000000000000000000000000000000000000 --- a/src/util/coding_test.rs +++ /dev/null @@ -1,174 +0,0 @@ -mod test { - use crate::traits::coding_trait::{Coding32, Coding64, CodingTrait}; - use crate::util::coding::{Coding}; - - #[test] - fn test_put_fixed32() { - let mut dst = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]; - let value = 65535; - Coding::put_fixed32(&mut dst, 2, value); - assert_eq!([0, 0, 255, 255, 0, 0, 0, 0, 0, 0, 0, 0] as [u8; 12], dst); - } - - #[test] - fn test_put_fixed64() { - let mut dst = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]; - let value = 65535; - Coding::put_fixed64(&mut dst, 2, value); - assert_eq!([0, 0, 255, 255, 0, 0, 0, 0, 0, 0, 0, 0] as [u8; 12], dst); - } - - #[test] - fn test_put_varint32() { - let mut value = 65535; - let mut dst = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]; - let offset = Coding::put_varint32(&mut dst, 2, value); - println!("offset:{:?}", offset); - assert_eq!(offset, 4); - println!("dst:{:?}", dst); - assert_eq!([0, 0, 255, 255, 0, 0, 0, 0, 0, 0, 0, 0] as [u8; 12], dst); - } - - #[test] - fn test_put_varint64() { - let mut value = 65535; - let mut dst = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]; - let offset = Coding::put_varint64(&mut dst, 2, value); - println!("offset:{:?}", offset); - assert_eq!(offset, 4); - println!("dst:{:?}", dst); - assert_eq!([0, 0, 255, 255, 0, 0, 0, 0, 0, 0, 0, 0] as [u8; 12], dst); - } - - #[test] - fn test_encode_varint32() { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let mut value: u32 = 65534; - let offset = Coding::encode_varint32(value, &mut buf, 0); - println!("offset:{:?}", offset); - assert_eq!(offset, 2); - println!("buf:{:?}", buf); - assert_eq!(buf, [254, 255, 3, 0]); - } - - #[test] - fn test_encode_varint64() { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let mut value: u64 = 65535; - let offset = Coding::encode_varint64(value, &mut buf, 0); - println!("offset:{:?}", offset); - assert_eq!(offset, 2); - println!("buf:{:?}", buf); - assert_eq!(buf, [255, 255, 3, 0]); - } - - #[test] - fn test_encode_fixed32() { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let mut value: u32 = 65534; - let offset = Coding::encode_fixed32(value, &mut buf, 0); - assert_eq!(offset, 4); - println!("offset:{:?}", offset); - assert_eq!(buf, [254, 255, 0, 0]); - println!("buf:{:?}", buf); - } - - #[test] - fn test_encode_fixed64() { - let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - let mut value: u64 = 65535; - let offset = Coding::encode_fixed64(value, &mut buf, 0); - assert_eq!(offset, 8); - println!("offset:{:?}", offset); - assert_eq!(buf, [255, 255, 0, 0, 0, 0, 0, 0]); - println!("buf:{:?}", buf); - } - - #[test] - fn test_varint_u32() { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let value: u32 = 65534; - println!("value[binary]:{:b}", value); - let offset = value.varint(&mut buf, 0); - println!("offset:{:?}", offset); - println!("buf:{:?}", buf); - assert_eq!(buf, [255, 255, 3, 0]); - } - - #[test] - fn test_varint_u64() { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let value: u64 = 65534; - println!("value[binary]:{:b}", value); - let offset = value.varint(&mut buf, 0); - println!("offset:{:?}", offset); - println!("buf:{:?}", buf); - } - - #[test] - fn test_fixed_u32() { - let mut buf: [u8; 4] = [0, 0, 0, 0]; - let value: u32 = 123; - println!("value[binary]:{:b}", value); - let offset = value.fixedint(&mut buf, 0); - println!("offset:{:?}", offset); - println!("buf:{:?}", buf); - } - - #[test] - fn test_fixed_u64() { - let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - let value: u64 = 123; - println!("value[binary]:{:b}", value); - let offset = value.fixedint(&mut buf, 0); - println!("offset:{:?}", offset); - println!("buf:{:?}", buf); - } - - #[test] - fn test_varint_length() { - let len = Coding::varint_length(65535 as u64 as usize); - println!("len: {:?}", len); - assert_eq!(len, 3); - } - - #[test] - fn test_put_length_prefixed_slice() { - // let mut buf: [u8; 4] = [0, 0, 0, 0]; - // Coding::encode_fixed32(&data, &mut buf, 0); - // let mut string = String::from("len:"); - // let slice = Slice::from("data"); - // let mut slice = Slice::from_buf(data.to_le_bytes().as_mut_slice()); - // Coding::put_length_prefixed_slice(&mut string, &mut slice); - // println!("{:?}", string) - } - - #[test] - fn test_get_length_prefixed_slice() { - // let data = 12_u32; - // Coding::put_fixed32(, data); - // let mut string = String::from("len:"); - // let mut slice = Slice::from_buf(data.to_le_bytes().as_mut_slice()); - // Coding::put_length_prefixed_slice(&mut string, &mut slice); - } - - #[test] - fn test_decode_fixed32() { - let mut value = 65535_u32; - let mut buf: [u8; 4] = [0, 0, 0, 0]; - Coding::encode_fixed32(value, &mut buf, 0); - let decode = Coding::decode_fixed32(&mut buf); - println!("value:{:?}", value); - assert_eq!(decode, value); - } - - #[test] - fn test_decode_fixed64() { - let mut value = 65535_u64; - let mut buf: [u8; 8] = [0, 0, 0, 0, 0, 0, 0, 0]; - Coding::encode_fixed64(value, &mut buf, 0); - let decode = Coding::decode_fixed64(&mut buf); - println!("value:{:?}", value); - assert_eq!(decode, value); - } -} diff --git a/src/util/crc.rs b/src/util/crc.rs index d15bb3aa856d980cc8a4c033bace50a46b0cfbf9..c2f0443aa4bcb40b5403a499f6c8eb914567234d 100644 --- a/src/util/crc.rs +++ b/src/util/crc.rs @@ -1,7 +1,6 @@ use std::mem::size_of; use std::slice; -use crate::traits::coding_trait::CodingTrait; -use crate::util::coding::Coding; +use crate::util::coding::{Decoder}; use crate::util::slice::Slice; static K_MASK_DELTA: u32 = 0xa282ead8; @@ -240,7 +239,6 @@ const K_STRIDE_EXTENSION_TABLE3: [u32; 256] = [ /// 可以被计算 crc 值的特质 /// 默认实现了 &[T], Vec[T], Slice, &str, String pub trait AsCrc { - #[inline] fn as_crc(&self) -> u32 { self.as_crc_extend(0) @@ -281,7 +279,7 @@ impl AsCrc for Slice { } } -impl AsCrc for Vec { +impl AsCrc for Vec { #[inline] fn as_crc_extend(&self, crc: u32) -> u32 { self.as_slice().as_crc_extend(crc) @@ -324,8 +322,8 @@ macro_rules! step1 { /// Process one of the 4 strides of 4-byte data. macro_rules! step4 { - ($name: ident, $data: tt, $s: tt, $i: tt) => { - $name = Coding::decode_fixed32(&$data[$s+$i*4..]) ^ + ($name: ident, $data: tt, $decoder: ident, $s: tt, $i: tt) => { + $name = unsafe{ $decoder.uncheck_get_fixed32() } ^ K_STRIDE_EXTENSION_TABLE3[$name as u8 as usize] ^ K_STRIDE_EXTENSION_TABLE2[($name >> 8) as u8 as usize] ^ K_STRIDE_EXTENSION_TABLE1[($name >> 16) as u8 as usize] ^ @@ -335,11 +333,11 @@ macro_rules! step4 { /// Process a 16-byte swath of 4 strides, each of which has 4 bytes of data. macro_rules! step16 { - ($c0: tt, $c1: tt, $c2: tt, $c3: tt, $data: tt, $s: tt) => { - step4!($c0, $data, $s, 0); - step4!($c1, $data, $s, 1); - step4!($c2, $data, $s, 2); - step4!($c3, $data, $s, 3); + ($c0: tt, $c1: tt, $c2: tt, $c3: tt, $data: tt, $decoder: ident, $s: tt) => { + step4!($c0, $data, $decoder, $s, 0); + step4!($c1, $data, $decoder, $s, 1); + step4!($c2, $data, $decoder, $s, 2); + step4!($c3, $data, $decoder, $s, 3); $s += 16; } } @@ -386,18 +384,19 @@ impl CRC { } if n - s >= 16 { - let mut crc0 = Coding::decode_fixed32(&data[s..]) ^ l; - let mut crc1 = Coding::decode_fixed32(&data[(s + 4)..]); - let mut crc2 = Coding::decode_fixed32(&data[(s + 8)..]); - let mut crc3 = Coding::decode_fixed32(&data[(s + 12)..]); + let mut decoder = Decoder::with_buf(data); + let mut crc0 = unsafe { decoder.uncheck_get_fixed32() } ^ l; + let mut crc1 = unsafe { decoder.uncheck_get_fixed32() }; + let mut crc2 = unsafe { decoder.uncheck_get_fixed32() }; + let mut crc3 = unsafe { decoder.uncheck_get_fixed32() }; s += 16; // println!("c0: {:x}, c1: {:x}, c2: {:x}, c3: {:x}, s: {}", crc0, crc1, crc2, crc3, s); while (n - s) >= 16 { - step16!(crc0, crc1, crc2, crc3, data, s); + step16!(crc0, crc1, crc2, crc3, data, decoder, s); // println!("step16, c0: {:x}, c1: {:x}, c2: {:x}, c3: {:x}, s: {}", crc0, crc1, crc2, crc3, s); } while (n - s) >= 4 { - step4!(crc0, data, s, 0); + step4!(crc0, data, decoder, s, 0); // swap variables (crc1, crc2, crc3) = (crc0, crc1, crc2); s += 4; diff --git a/src/util/hash.rs b/src/util/hash.rs index 641c7bc87f7fce360bc818f2ff35c75507303255..575ac3ca4e2ed3735524ac70e02000bee17d98c8 100644 --- a/src/util/hash.rs +++ b/src/util/hash.rs @@ -1,9 +1,7 @@ use std::ops::{BitXor, Mul}; use std::mem::size_of; use std::slice as stds; - -use crate::traits::coding_trait::CodingTrait; -use crate::util::coding::Coding; +use crate::util::coding::Decoder; use crate::util::r#const::HASH_DEFAULT_SEED; @@ -11,7 +9,6 @@ use crate::util::slice::Slice; /// 一种可以计算 hash 的特质 pub trait ToHash { - fn to_hash(&self) -> u32; fn to_hash_with_seed(&self, seed: u32) -> u32; @@ -143,13 +140,15 @@ impl Hash { let mul_first = n.mul(murmur_hash as usize); // x = data_size * murmur_hash let mut h: u32 = seed.bitxor(mul_first as u32); // h = seed ^ x + let mut decoder = Decoder::with_buf(data); + // 每次按照四字节长度读取字节流中的数据 w,并使用普通的哈希函数计算哈希值。 let mut position: usize = 0; while position + 4 <= limit { //每次解码前4个字节,直到最后剩下小于4个字节 // rust的 &[u8] 是胖指针,带长度信息的,会做range check,所以是安全的。 // 虽然decode_fixed32 中也是解码4字节,但传入整个data在方法上不明确,因此传 [position..(position + 4)], 可以更加方便理解,对性能无影响 - let w = Coding::decode_fixed32(&data[position..(position + 4)]); + let w = unsafe { decoder.uncheck_get_fixed32() }; // 向后移动4个字节 position += 4; diff --git a/src/util/mem_debug.rs b/src/util/mem_debug.rs index bef8a837f271a8644bd1d2365d2e17c3dba126a4..93a79a2e49f6915f0aa1d2fb259dc6dfdf14b41a 100644 --- a/src/util/mem_debug.rs +++ b/src/util/mem_debug.rs @@ -1,4 +1,4 @@ -use std::ffi::{c_char, c_void}; +use core::ffi::{c_char, c_void}; use std::ptr::{null, null_mut}; extern "C" fn write_cb(_: *mut c_void, message: *const c_char) { diff --git a/src/util/mod.rs b/src/util/mod.rs index 3e9bd120b6b1e8768d8bc6f561f93c9b774d4dd8..53143b252d0b996cab13a661bd3b845b7380a9f4 100644 --- a/src/util/mod.rs +++ b/src/util/mod.rs @@ -13,7 +13,6 @@ mod slice_test; pub mod cache; mod cache_test; pub mod coding; -mod coding_test; pub mod arena; mod arena_test; diff --git a/src/util/slice.rs b/src/util/slice.rs index 1f923b8f8c61d1ca03cd47a75658d7f5ef6237f1..215e17f7835c44e358509720d2a0d6335d479f03 100644 --- a/src/util/slice.rs +++ b/src/util/slice.rs @@ -1,9 +1,10 @@ +use core::ops::{Range, RangeFrom}; use std::mem; use std::borrow::Cow; use std::cmp::Ordering; use std::fmt::{Display, Formatter}; use std::mem::ManuallyDrop; -use std::ops::Deref; +use std::ops::{Deref, DerefMut, RangeTo}; #[derive(Debug)] pub struct Slice { @@ -26,7 +27,6 @@ impl Default for Slice { } impl Slice { - /// 从 &mut [u8] 转到 Slice, 这里存在内存拷贝开销 #[inline] pub fn from_buf(buf: &[u8]) -> Self { @@ -62,7 +62,7 @@ impl Slice { #[inline] pub fn as_sub_ref(&self, start: usize, length: usize) -> &[u8] { - &(**self)[start..(start+length)] + &(**self)[start..(start + length)] } /// 移除头部 n 个元素 @@ -145,7 +145,7 @@ impl From for Vec { } } -impl > From for Slice { +impl> From for Slice { #[inline] fn from(r: R) -> Self { Self { @@ -207,13 +207,72 @@ impl core::ops::Index for Slice { } } +impl core::ops::Index> for Slice { + type Output = [u8]; + + /// 获取指定下标范围的数据 + fn index(&self, range: Range) -> &Self::Output { + assert!(range.end <= self.size()); + &(**self)[range.start..range.end] + } +} + +impl core::ops::Index> for Slice { + type Output = [u8]; + + /// 获取指定下标范围的数据 + fn index(&self, range: RangeFrom) -> &Self::Output { + &(**self)[range.start..] + } +} + +impl core::ops::Index> for Slice { + type Output = [u8]; + + /// 获取指定下标范围的数据 + fn index(&self, range: RangeTo) -> &Self::Output { + assert!(range.end <= self.size()); + &(**self)[..range.end] + } +} + +impl core::ops::IndexMut> for Slice { + /// 获取指定下标范围的数据 + fn index_mut(&mut self, index: Range) -> &mut Self::Output { + assert!(index.end <= self.size()); + &mut (**self)[..index.end] + } +} + +impl core::ops::IndexMut> for Slice { + /// 获取指定下标范围的数据 + fn index_mut(&mut self, index: RangeFrom) -> &mut Self::Output { + &mut (**self)[index.start..] + } +} + +impl core::ops::IndexMut> for Slice { + /// 获取指定下标范围的数据 + fn index_mut(&mut self, index: RangeTo) -> &mut Self::Output { + assert!(index.end <= self.size()); + &mut (**self)[..index.end] + } +} + + impl Deref for Slice { type Target = [u8]; /// Slice 解引用到 &[u8] #[inline] fn deref(&self) -> &Self::Target { - &*self.data + &*self.data + } +} + +impl DerefMut for Slice { + fn deref_mut(&mut self) -> &mut Self::Target { + &mut *self.data } }