1+ //! RWSV means "read, write, seek, validate"
2+
13#![ no_main]
24
35use std:: io:: { self , Cursor , Read , Seek , Write } ;
46
5- use crc_store:: { Config , CrcStore } ;
6- use crc_store_fuzz:: { Method , SeekFrom , Setup } ;
7- use libfuzzer_sys:: fuzz_target;
7+ use crc_store:: { Config , CrcStore , ValidateError } ;
8+ use io:: Error as IoError ;
9+ use io:: ErrorKind :: InvalidInput ;
10+ use libfuzzer_sys:: { arbitrary, fuzz_target} ;
811
912const MAX_READ_BUF_LEN : u32 = 4194304 ; // 4 MB
1013
1114/// Maximum seek is arbitrarily set to 1 megabyte (1000 ^ 2).
1215const MAX_SEEK : i64 = 1_000_000 ;
1316
17+ #[ derive( arbitrary:: Arbitrary , Debug ) ]
18+ pub struct Setup {
19+ pub seg_len : u32 ,
20+ pub buf_len : u32 ,
21+ pub validate_on_read : bool ,
22+ pub initial_bytes : Vec < u8 > ,
23+ pub methods : Vec < Method > ,
24+ }
25+
26+ #[ derive( arbitrary:: Arbitrary , Debug ) ]
27+ pub enum Method {
28+ Read { buf_len : u32 } ,
29+ Write { buf : Vec < u8 > } ,
30+ Seek { seek_from : SeekFrom } ,
31+ Validate ,
32+ }
33+
34+ #[ derive( arbitrary:: Arbitrary , Debug ) ]
35+ pub enum SeekFrom {
36+ Start ( u64 ) ,
37+ End ( i64 ) ,
38+ Current ( i64 ) ,
39+ }
40+
1441fuzz_target ! ( |setup: Setup | {
1542 let _ = execute_setup( setup) ;
1643} ) ;
@@ -35,49 +62,44 @@ fn call_method(store: &mut CrcStore<Cursor<Vec<u8>>>, method: Method) -> io::Res
3562 match method {
3663 Method :: Read { buf_len } => {
3764 if buf_len > MAX_READ_BUF_LEN {
38- return Err ( io:: Error :: new (
39- io:: ErrorKind :: InvalidInput ,
40- "read buffer length too large" ,
41- ) ) ;
65+ return Err ( IoError :: new ( InvalidInput , "read buffer length too large" ) ) ;
4266 }
4367 let mut buf = vec ! [ 0u8 ; buf_len as usize ] ;
4468 store. read ( & mut buf) ?;
69+ Ok ( ( ) )
4570 }
4671 Method :: Write { mut buf } => {
4772 store. write ( & mut buf) ?;
73+ Ok ( ( ) )
4874 }
4975 Method :: Seek { seek_from } => {
5076 let arg = match seek_from {
5177 SeekFrom :: Start ( n) => {
5278 if n >= MAX_SEEK as u64 {
53- return Err ( io:: Error :: new (
54- io:: ErrorKind :: InvalidInput ,
55- "seek distance too large" ,
56- ) ) ;
79+ return Err ( IoError :: new ( InvalidInput , "seek too large" ) ) ;
5780 }
5881 io:: SeekFrom :: Start ( n)
5982 }
6083 SeekFrom :: Current ( n) => {
6184 if n >= MAX_SEEK || n <= -MAX_SEEK {
62- return Err ( io:: Error :: new (
63- io:: ErrorKind :: InvalidInput ,
64- "seek distance too large" ,
65- ) ) ;
85+ return Err ( IoError :: new ( InvalidInput , "seek too large" ) ) ;
6686 }
6787 io:: SeekFrom :: Current ( n)
6888 }
6989 SeekFrom :: End ( n) => {
7090 if n >= MAX_SEEK || n <= -MAX_SEEK {
71- return Err ( io:: Error :: new (
72- io:: ErrorKind :: InvalidInput ,
73- "seek distance too large" ,
74- ) ) ;
91+ return Err ( IoError :: new ( InvalidInput , "seek too large" ) ) ;
7592 }
7693 io:: SeekFrom :: End ( n)
7794 }
7895 } ;
7996 store. seek ( arg) ?;
97+ Ok ( ( ) )
8098 }
99+ Method :: Validate => match store. validate ( ) {
100+ Err ( ValidateError :: Io ( e) ) => Err ( e) ,
101+ Err ( _) => Err ( IoError :: new ( InvalidInput , "validation error" ) ) ,
102+ Ok ( _) => Ok ( ( ) ) ,
103+ } ,
81104 }
82- Ok ( ( ) )
83105}
0 commit comments