changeset 112:c0dbaae40771

Add test verifying behavior for corrupt data; fix TableIterator::reset() behavior
author Lewin Bormann <lbo@spheniscida.de>
date Sat, 24 Dec 2016 14:22:42 +0000
parents 74096ebd4337
children 0d848c6665f5
files src/table_reader.rs
diffstat 1 files changed, 57 insertions(+), 10 deletions(-) [+]
line wrap: on
line diff
--- a/src/table_reader.rs	Sat Dec 24 13:41:32 2016 +0000
+++ b/src/table_reader.rs	Sat Dec 24 14:22:42 2016 +0000
@@ -151,13 +151,12 @@
 
     // Iterators read from the file; thus only one iterator can be borrowed (mutably) per scope
     fn iter<'a>(&'a mut self) -> TableIterator<'a, R, C, FP> {
-        let mut iter = TableIterator {
+        let iter = TableIterator {
             current_block: self.indexblock.iter(), // just for filling in here
             index_block: self.indexblock.iter(),
             table: self,
             init: false,
         };
-        iter.skip_to_next_entry();
         iter
     }
 }
@@ -175,11 +174,11 @@
 impl<'a, C: Comparator, R: Read + Seek, FP: FilterPolicy> TableIterator<'a, R, C, FP> {
     // Skips to the entry referenced by the next entry in the index block.
     // This is called once a block has run out of entries.
-    fn skip_to_next_entry(&mut self) -> bool {
+    fn skip_to_next_entry(&mut self) -> Result<bool> {
         if let Some((_key, val)) = self.index_block.next() {
-            self.load_block(&val).is_ok()
+            self.load_block(&val).map(|_| true)
         } else {
-            false
+            Ok(false)
         }
     }
 
@@ -198,11 +197,17 @@
     type Item = (Vec<u8>, Vec<u8>);
 
     fn next(&mut self) -> Option<Self::Item> {
-        self.init = true;
+        if !self.init {
+            self.init = true;
+            if self.skip_to_next_entry().is_err() {
+                return None;
+            }
+        }
+
         if let Some((key, val)) = self.current_block.next() {
             Some((key, val))
         } else {
-            if self.skip_to_next_entry() {
+            if self.skip_to_next_entry().unwrap_or(false) {
                 self.next()
             } else {
                 None
@@ -269,7 +274,6 @@
     fn reset(&mut self) {
         self.index_block.reset();
         self.init = false;
-        self.skip_to_next_entry();
     }
 
     // This iterator is special in that it's valid even before the first call to next(). It behaves
@@ -279,7 +283,11 @@
     }
 
     fn current(&self) -> Option<Self::Item> {
-        self.current_block.current()
+        if self.init {
+            self.current_block.current()
+        } else {
+            None
+        }
     }
 }
 
@@ -309,7 +317,7 @@
         let mut d = Vec::with_capacity(512);
         let mut opt = Options::default();
         opt.block_restart_interval = 2;
-        opt.block_size = 64;
+        opt.block_size = 32;
 
         {
             let mut b = TableBuilder::new(opt, StandardComparator, &mut d, BloomPolicy::new(4));
@@ -328,6 +336,40 @@
     }
 
     #[test]
+    fn test_table_reader_checksum() {
+        let (mut src, size) = build_table();
+        println!("{}", size);
+
+        src[45] = 0;
+
+        let mut table = Table::new(Cursor::new(&src as &[u8]),
+                                   size,
+                                   StandardComparator,
+                                   BloomPolicy::new(4),
+                                   Options::default())
+            .unwrap();
+
+        {
+            let iter = table.iter();
+            // Last block is skipped
+            assert_eq!(iter.count(), 3);
+
+        }
+
+        {
+            let iter = table.iter();
+
+            for (k, _) in iter {
+                if k == build_data()[2].0.as_bytes() {
+                    return;
+                }
+            }
+
+            panic!("Should have hit 3rd record in table!");
+        }
+    }
+
+    #[test]
     fn test_table_iterator_fwd() {
         let (src, size) = build_table();
         let data = build_data();
@@ -346,6 +388,9 @@
                        (k.as_ref(), v.as_ref()));
             i += 1;
         }
+
+        assert_eq!(i, data.len());
+        println!("tot len: {}", data.len());
     }
 
     #[test]
@@ -367,6 +412,7 @@
         assert!(iter.current().is_none());
 
         assert!(iter.next().is_some());
+        let first = iter.current();
         assert!(iter.valid());
         assert!(iter.current().is_some());
 
@@ -377,6 +423,7 @@
         iter.reset();
         assert!(!iter.valid());
         assert!(iter.current().is_none());
+        assert_eq!(first, iter.next());
     }
 
     #[test]