@@ -43,7 +43,7 @@
Loading
43 43
pub fn write_root_page(root: &mut Page, buffer: &mut [u8], version: u8, last_flush: u8) -> PRes<u8> {
44 44
    let (last_flush, offset) = prepare_buffer_flush(buffer, last_flush);
45 45
    root.write_u8(version);
46 -
    root.seek(offset + 1)?;
46 +
    root.seek(offset + 1);
47 47
    root.write_all(&buffer);
48 48
    Ok(last_flush)
49 49
}

@@ -106,9 +106,9 @@
Loading
106 106
}
107 107
108 108
impl PageOps for ReadPage {
109 -
    fn seek(&mut self, pos: u32) -> PRes<()> {
109 +
    fn seek(&mut self, pos: u32) {
110 +
        debug_assert!(pos + 2 < (1 << self.exp));
110 111
        self.pos = (pos + 2) as usize;
111 -
        Ok(())
112 112
    }
113 113
    fn get_index(&self) -> u64 {
114 114
        self.index
@@ -143,7 +143,8 @@
Loading
143 143
}
144 144
145 145
pub trait PageOps {
146 -
    fn seek(&mut self, pos: u32) -> PRes<()>;
146 +
    /// Seek the internal cursor of the page to the specified absolute position
147 +
    fn seek(&mut self, pos: u32);
147 148
    fn get_index(&self) -> u64;
148 149
    fn get_size_exp(&self) -> u8;
149 150
    fn clone_read(&self) -> ReadPage;
@@ -218,9 +219,9 @@
Loading
218 219
}
219 220
220 221
impl PageOps for Page {
221 -
    fn seek(&mut self, pos: u32) -> PRes<()> {
222 +
    fn seek(&mut self, pos: u32) {
223 +
        debug_assert!(pos + 2 < (1 << self.exp));
222 224
        self.pos = (pos + 2) as usize;
223 -
        Ok(())
224 225
    }
225 226
    fn get_index(&self) -> u64 {
226 227
        self.index

@@ -111,7 +111,7 @@
Loading
111 111
            let next = pag.read_u64();
112 112
            let mut pos = SEGMENT_DATA_OFFSET;
113 113
            loop {
114 -
                pag.seek(pos)?;
114 +
                pag.seek(pos);
115 115
                let data_page = pag.read_u64();
116 116
                let flag = pag.read_u8();
117 117
                if entry_exits(flag) {
@@ -157,12 +157,12 @@
Loading
157 157
158 158
impl<T: InfallibleRead + PageOps> SegmentPageRead for T {
159 159
    fn segment_read_entry(&mut self, segment_id: SegmentId, pos: u32) -> PRes<Option<(u64, u16)>> {
160 -
        self.seek(SEGMENT_HASH_OFFSET)?;
160 +
        self.seek(SEGMENT_HASH_OFFSET);
161 161
        let persistent_id = SegmentId::read(self);
162 162
        if persistent_id != segment_id {
163 163
            return Ok(None);
164 164
        }
165 -
        self.seek(pos)?;
165 +
        self.seek(pos);
166 166
        let record = self.read_u64();
167 167
        let flag = self.read_u8();
168 168
        let version = self.read_u16();
@@ -178,7 +178,7 @@
Loading
178 178
        let mut pos = SEGMENT_DATA_OFFSET;
179 179
        let mut recs = Vec::new();
180 180
        loop {
181 -
            self.seek(pos + 8)?;
181 +
            self.seek(pos + 8);
182 182
            let flag = self.read_u8();
183 183
            recs.push((pos, flag & FLAG_EXISTS == 1));
184 184
            pos += ADDRESS_ENTRY_SIZE;
@@ -194,7 +194,7 @@
Loading
194 194
        let mut pos = SEGMENT_DATA_OFFSET;
195 195
        let mut recs = Vec::new();
196 196
        loop {
197 -
            self.seek(pos + 8)?;
197 +
            self.seek(pos + 8);
198 198
            let flag = self.read_u8();
199 199
            if entry_exits(flag) {
200 200
                recs.push(pos);
@@ -211,7 +211,7 @@
Loading
211 211
        let elements = (ADDRESS_PAGE_SIZE - SEGMENT_DATA_OFFSET) / ADDRESS_ENTRY_SIZE;
212 212
        let mut pos = SEGMENT_DATA_OFFSET + (elements - 1) * ADDRESS_ENTRY_SIZE;
213 213
        loop {
214 -
            self.seek(pos + 8)?;
214 +
            self.seek(pos + 8);
215 215
            let flag = self.read_u8();
216 216
            if entry_exits(flag) {
217 217
                pos += ADDRESS_ENTRY_SIZE;
@@ -227,16 +227,16 @@
Loading
227 227
    }
228 228
229 229
    fn get_next(&mut self) -> PRes<u64> {
230 -
        self.seek(0)?;
230 +
        self.seek(0);
231 231
        Ok(self.read_u64())
232 232
    }
233 233
234 234
    fn get_prev(&mut self) -> PRes<u64> {
235 -
        self.seek(8)?;
235 +
        self.seek(8);
236 236
        Ok(self.read_u64())
237 237
    }
238 238
    fn empty(&mut self) -> PRes<bool> {
239 -
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET)?;
239 +
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET);
240 240
        Ok(self.read_u16() as u32 == ADDRESS_PAGE_ENTRY_COUNT)
241 241
    }
242 242
}
@@ -253,14 +253,14 @@
Loading
253 253
impl<T: InfallibleRead + InfallibleWrite + PageOps> SegmentPage for T {
254 254
    fn segment_insert_entry(&mut self, segment_id: SegmentId, pos: u32, record_page: u64) -> PRes<()> {
255 255
        debug_assert!(pos >= SEGMENT_DATA_OFFSET, "invalid page position {}", pos);
256 -
        self.seek(SEGMENT_HASH_OFFSET)?;
256 +
        self.seek(SEGMENT_HASH_OFFSET);
257 257
        let persistent_id = SegmentId::read(self);
258 258
        if persistent_id != segment_id {
259 259
            return Err(PersyError::SegmentNotFound);
260 260
        }
261 261
        // TODO: In case of restore this may get a wrong value, so on restore should be
262 262
        // re-calculated from the persistent flags.
263 -
        self.seek(pos)?;
263 +
        self.seek(pos);
264 264
        self.write_u64(record_page);
265 265
        self.write_u8(FLAG_EXISTS);
266 266
        self.write_u16(1);
@@ -268,51 +268,51 @@
Loading
268 268
    }
269 269
    fn segment_update_entry(&mut self, segment_id: SegmentId, pos: u32, record_page: u64) -> PRes<()> {
270 270
        debug_assert!(pos >= SEGMENT_DATA_OFFSET);
271 -
        self.seek(SEGMENT_HASH_OFFSET)?;
271 +
        self.seek(SEGMENT_HASH_OFFSET);
272 272
        let persistent_id = SegmentId::read(self);
273 273
        if persistent_id != segment_id {
274 274
            return Err(PersyError::RecordNotFound(PersyId(RecRef::new(self.get_index(), pos))));
275 275
        }
276 -
        self.seek(pos + 9)?;
276 +
        self.seek(pos + 9);
277 277
        let version = self.read_u16();
278 -
        self.seek(pos)?;
278 +
        self.seek(pos);
279 279
        self.write_u64(record_page);
280 -
        self.seek(pos + 9)?;
280 +
        self.seek(pos + 9);
281 281
        self.write_u16(inc_version(version));
282 282
        Ok(())
283 283
    }
284 284
    fn segment_delete_entry(&mut self, segment_id: SegmentId, pos: u32) -> PRes<bool> {
285 285
        debug_assert!(pos >= SEGMENT_DATA_OFFSET);
286 -
        self.seek(SEGMENT_HASH_OFFSET)?;
286 +
        self.seek(SEGMENT_HASH_OFFSET);
287 287
        let persistent_id = SegmentId::read(self);
288 288
        if persistent_id != segment_id {
289 289
            return Err(PersyError::RecordNotFound(PersyId(RecRef::new(self.get_index(), pos))));
290 290
        }
291 -
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET)?;
291 +
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET);
292 292
        let count = self.read_u16() + 1;
293 -
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET)?;
293 +
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET);
294 294
        self.write_u16(count);
295 -
        self.seek(pos + 8)?;
295 +
        self.seek(pos + 8);
296 296
        let flag = self.read_u8();
297 -
        self.seek(pos + 8)?;
297 +
        self.seek(pos + 8);
298 298
        self.write_u8(flag | FLAG_DELETED);
299 299
        Ok(count as u32 == ADDRESS_PAGE_ENTRY_COUNT)
300 300
    }
301 301
302 302
    fn set_segment_id(&mut self, id: SegmentId) -> PRes<()> {
303 -
        self.seek(SEGMENT_HASH_OFFSET)?;
303 +
        self.seek(SEGMENT_HASH_OFFSET);
304 304
        id.write(self);
305 305
        Ok(())
306 306
    }
307 307
308 308
    fn set_next(&mut self, next: u64) -> PRes<()> {
309 -
        self.seek(0)?;
309 +
        self.seek(0);
310 310
        self.write_u64(next);
311 311
        Ok(())
312 312
    }
313 313
314 314
    fn set_prev(&mut self, prev: u64) -> PRes<()> {
315 -
        self.seek(8)?;
315 +
        self.seek(8);
316 316
        self.write_u64(prev);
317 317
        Ok(())
318 318
    }
@@ -321,7 +321,7 @@
Loading
321 321
        let mut pos = SEGMENT_DATA_OFFSET;
322 322
        let mut count = 0;
323 323
        loop {
324 -
            self.seek(pos + 8)?;
324 +
            self.seek(pos + 8);
325 325
            let flag = self.read_u8();
326 326
            if flag & FLAG_DELETED == FLAG_DELETED {
327 327
                count += 1;
@@ -331,7 +331,7 @@
Loading
331 331
                break;
332 332
            }
333 333
        }
334 -
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET)?;
334 +
        self.seek(SEGMENT_PAGE_DELETE_COUNT_OFFSET);
335 335
        self.write_u8(count as u8);
336 336
        Ok(())
337 337
    }

@@ -217,7 +217,7 @@
Loading
217 217
                        let read;
218 218
                        {
219 219
                            let mut cur = self.allocator.load_page(free_cursor)?;
220 -
                            cur.seek(JOURNAL_PAGE_PREV_OFFSET)?;
220 +
                            cur.seek(JOURNAL_PAGE_PREV_OFFSET);
221 221
                            read = cur.read_u64();
222 222
                        }
223 223
                        if free_cursor != id.page {
@@ -305,7 +305,7 @@
Loading
305 305
            self.required_space(buffer.len() as u32, &mut jr)?;
306 306
            cur_page = jr.last_page;
307 307
            cur_pos = jr.last_pos;
308 -
            jr.current.seek(cur_pos)?;
308 +
            jr.current.seek(cur_pos);
309 309
            jr.current.write_all(&*buffer);
310 310
            if flush {
311 311
                self.allocator.flush_page(jr.current.clone())?;
@@ -325,12 +325,12 @@
Loading
325 325
        jr.last_page = jr.first_page;
326 326
        journal_pages.push(cur_page);
327 327
        let mut page = self.allocator.load_page(cur_page)?;
328 -
        page.seek(JOURNAL_PAGE_CONTENT_OFFSET)?;
328 +
        page.seek(JOURNAL_PAGE_CONTENT_OFFSET);
329 329
        loop {
330 330
            let tp = page.read_u8();
331 331
            if tp == 0 {
332 332
                let last_pos = page.cursor_pos() as u32;
333 -
                page.seek(JOURNAL_PAGE_NEXT_OFFSET)?;
333 +
                page.seek(JOURNAL_PAGE_NEXT_OFFSET);
334 334
                cur_page = page.read_u64();
335 335
                if cur_page == 0 {
336 336
                    jr.last_pos = last_pos - 1;
@@ -338,7 +338,7 @@
Loading
338 338
                }
339 339
                journal_pages.push(cur_page);
340 340
                page = self.allocator.load_page(cur_page)?;
341 -
                page.seek(JOURNAL_PAGE_CONTENT_OFFSET)?;
341 +
                page.seek(JOURNAL_PAGE_CONTENT_OFFSET);
342 342
                jr.last_page = cur_page;
343 343
            } else {
344 344
                let page_id = page.read_varint_u64();
@@ -378,15 +378,15 @@
Loading
378 378
            let last_pos = jr.last_pos;
379 379
            let new_page = self.allocator.allocate(JOURNAL_PAGE_EXP)?;
380 380
            if prev != 0 {
381 -
                jr.current.seek(JOURNAL_PAGE_NEXT_OFFSET)?;
381 +
                jr.current.seek(JOURNAL_PAGE_NEXT_OFFSET);
382 382
                jr.current.write_u64(new_page.get_index());
383 -
                jr.current.seek(last_pos)?;
383 +
                jr.current.seek(last_pos);
384 384
                jr.current.write_u8(0);
385 385
                self.allocator.flush_page(jr.current.clone())?;
386 386
            }
387 387
            jr.last_page = new_page.get_index();
388 388
            jr.current = new_page;
389 -
            jr.current.seek(JOURNAL_PAGE_PREV_OFFSET)?;
389 +
            jr.current.seek(JOURNAL_PAGE_PREV_OFFSET);
390 390
            jr.current.write_u64(prev);
391 391
            self.allocator.flush_page(jr.current.clone())?;
392 392
            jr.last_pos = JOURNAL_PAGE_CONTENT_OFFSET;
Files Coverage
src 92.78%
tests 98.56%
Project Totals (29 files) 93.81%
1
coverage:
2
  status:
3
    project:
4
      default:
5
        target: 80%
6
        threshold: 1.0%
7
    patch: off
Sunburst
The inner-most circle is the entire project, moving away from the center are folders then, finally, a single file. The size and color of each slice is representing the number of statements and the coverage, respectively.
Icicle
The top section represents the entire project. Proceeding with folders and finally individual files. The size and color of each slice is representing the number of statements and the coverage, respectively.
Grid
Each block represents a single file in the project. The size and color of each block is represented by the number of statements and the coverage, respectively.
Loading