#![feature(test)] extern crate test; extern crate keeshond_datapack; use keeshond_datapack::{ReadSeek, DataId, DataObject, DataError, DataStore, DataMultistore, TrustPolicy, DataHandle, LoadErrorMode}; use keeshond_datapack::source::{PackageError, Source, SourceManager, TrustLevel}; use test::Bencher; use std::io::{Cursor, Read}; use std::cell::RefCell; use std::rc::Rc; const NUM_ITER : usize = 1_000; const TEST_ITEMS : [&'static str; 8] = [ "item1", "item2", "item3", "item4", "directory/anotherdirectory/subitem1", "directory/anotherdirectory/subitem2", "directory/anotherdirectory/subitem3", "directory/anotherdirectory/subitem4", ]; struct TestSourceIter { items : Vec<&'static str>, index : usize } impl<'a> TestSourceIter { fn new() -> TestSourceIter { let items = TEST_ITEMS.to_vec(); TestSourceIter { items, index : 0 } } } impl Iterator for TestSourceIter { type Item = Result; fn next(&mut self) -> Option> { if self.index < self.items.len() { let pathname = self.items[self.index].to_string(); self.index += 1; return Some(Ok(pathname)); } None } } pub struct TestSource { } impl TestSource { pub fn new() -> TestSource { TestSource { } } } impl Source for TestSource { fn get_uri(&self) -> &str { "null" } fn has_package(&self, package_name : &str) -> bool { package_name == "foopackage" } fn list_packages(&mut self) -> Vec { vec!["foopackage".to_string()] } fn read_file(&mut self, _package_name : &str, _pathname : &str) -> Result, PackageError> { Ok(Box::new(Cursor::new("12345678"))) } fn iter_entries(&mut self, _package_name : &str, _type_name : &str) -> Box>> { Box::new(TestSourceIter::new()) } fn trust_level(&self, _package_name: &str) -> TrustLevel { TrustLevel::TrustedSource } } //////////////////////////////////////////////////////////////////////////////// struct TextData { text : String } impl DataObject for TextData { fn folder_name() -> &'static str where Self : Sized { "text" } fn trust_policy() -> TrustPolicy { TrustPolicy::UntrustedOk } fn want_file(_pathname : &str) -> bool where Self : Sized { true } fn from_package_source(source : &mut Box, package_name : &str, pathname : &str) -> Result where Self : Sized { let mut reader = source.read_file(package_name, pathname)?; let mut text = String::new(); let result = reader.read_to_string(&mut text); if result.is_err() { return Err(DataError::BadData("Couldn't read string".to_string())); } Ok(TextData{ text }) } } //////////////////////////////////////////////////////////////////////////////// fn make_store() -> DataStore { let source = TestSource::new(); let source_manager = Rc::new(RefCell::new(SourceManager::new())); source_manager.borrow_mut().add_source(Box::new(source)); let mut store = DataStore::::new(source_manager); store.load_package("foopackage").expect("Failed to load package."); store } fn make_multistore() -> DataMultistore { let source = TestSource::new(); let source_manager = Rc::new(RefCell::new(SourceManager::new())); source_manager.borrow_mut().add_source(Box::new(source)); let multistore = DataMultistore::new(source_manager); multistore.store_mut::().load_package("foopackage").expect("Failed to load package."); multistore } fn test_ids(store : &DataStore) -> Vec> { let mut ids = Vec::new(); for name in &TEST_ITEMS { ids.push(store.get_id("foopackage", name).unwrap()); } ids } fn test_handles() -> Vec> { let mut handles = Vec::new(); for name in &TEST_ITEMS { handles.push(DataHandle::with_path("foopackage", name)); } handles } #[bench] fn bench_create(bencher : &mut Bencher) { bencher.iter(|| { make_store(); }); } #[bench] fn bench_get_id(bencher : &mut Bencher) { let store = make_store(); bencher.iter(|| { for _ in 0..NUM_ITER { for name in &TEST_ITEMS { store.get_id("foopackage", name).unwrap(); } } }); } #[bench] fn bench_get_handle(bencher : &mut Bencher) { let mut store = make_store(); let handles = test_handles(); let mut count = 0; for handle in handles.iter() { handle.resolve(&mut store, LoadErrorMode::Fatal); } bencher.iter(|| { for _ in 0..NUM_ITER { for handle in handles.iter() { if let Some(item) = handle.get(&mut store, LoadErrorMode::Fatal) { count += item.text.len(); } } } }); } #[bench] fn bench_get_data(bencher : &mut Bencher) { let store = make_store(); let ids = test_ids(&store); let mut count = 0; bencher.iter(|| { for _ in 0..NUM_ITER { for id in ids.iter() { if let Some(item) = store.get(*id) { count += item.text.len(); } } } }); } #[bench] fn bench_get_data_mut(bencher : &mut Bencher) { let mut store = make_store(); let ids = test_ids(&store); let mut count = 0; bencher.iter(|| { for _ in 0..NUM_ITER { for id in ids.iter() { if let Some(item) = store.get_mut(*id) { count += item.text.len(); } } } }); } #[bench] fn bench_get_store(bencher : &mut Bencher) { let multistore = make_multistore(); let ids = test_ids(&multistore.store::()); let mut count = 0; bencher.iter(|| { for _ in 0..NUM_ITER { for id in ids.iter() { if let Some(item) = multistore.store::().get(*id) { count += item.text.len(); } } } }); }