pub struct IOStatWrapper<T, C> { /* private fields */ }Expand description
A wrapper around an IO object that tracks operations and statistics.
Implementations§
Source§impl<T, C> IOStatWrapper<T, C>
impl<T, C> IOStatWrapper<T, C>
Sourcepub fn new(obj: T, start_seek_pos: u64) -> IOStatWrapper<T, C> ⓘ
pub fn new(obj: T, start_seek_pos: u64) -> IOStatWrapper<T, C> ⓘ
Create a new IOStatWrapper with a manually given seek position. Detecting the seek position automatically is not possible without specialization.
Examples found in repository?
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 for byte in (&mut instrumented_buf_file).bytes() {
15 xor_result ^= byte.unwrap();
16 }
17 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
18
19 // Demonstrate how BufReader reduces the number of read calls
20 println!("Buffered read was called successfully {} times",
21 instrumented_buf_file.read_call_counter().success_ctr());
22 println!("Inner read was called successfully {} times",
23 instrumented_raw_file.read_call_counter().success_ctr());
24}More examples
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.stream_position().unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.seek(SeekFrom::Current(0)).unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}Sourcepub fn into_inner(self) -> T
pub fn into_inner(self) -> T
Extract the original I/O object.
Source§impl<T: Read, C> IOStatWrapper<T, C>
impl<T: Read, C> IOStatWrapper<T, C>
Sourcepub fn read_call_counter(&self) -> &SuccessFailureCounter<u64>
pub fn read_call_counter(&self) -> &SuccessFailureCounter<u64>
Returns the number of times Read::read() was invoked.
Examples found in repository?
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 for byte in (&mut instrumented_buf_file).bytes() {
15 xor_result ^= byte.unwrap();
16 }
17 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
18
19 // Demonstrate how BufReader reduces the number of read calls
20 println!("Buffered read was called successfully {} times",
21 instrumented_buf_file.read_call_counter().success_ctr());
22 println!("Inner read was called successfully {} times",
23 instrumented_raw_file.read_call_counter().success_ctr());
24}More examples
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.stream_position().unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.seek(SeekFrom::Current(0)).unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}Sourcepub fn read_byte_counter(&self) -> usize
pub fn read_byte_counter(&self) -> usize
Returns the total number of bytes read.
Source§impl<T: Seek, C> IOStatWrapper<T, C>
impl<T: Seek, C> IOStatWrapper<T, C>
Sourcepub fn seek_call_counter(&self) -> &SuccessFailureCounter<u64>
pub fn seek_call_counter(&self) -> &SuccessFailureCounter<u64>
Returns the number of times Seek::seek() was invoked.
Examples found in repository?
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.stream_position().unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}More examples
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.seek(SeekFrom::Current(0)).unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}Sourcepub fn seek_pos(&self) -> u64
pub fn seek_pos(&self) -> u64
Get the current seek position without doing an actual seek operation.
This is accomplished by storing a separate position integer. When debug assertions are on we assert after every seek operation that the cursor is where we expect it to be.
Examples found in repository?
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.stream_position().unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}More examples
6fn main() {
7 let file_obj = File::open("Cargo.toml").unwrap();
8 let mut instrumented_raw_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(file_obj, 0);
9 let buffered_io = BufReader::new(&mut instrumented_raw_file);
10 let mut instrumented_buf_file = IOStatWrapper::<_, Vec<IopInfoPair>>::new(buffered_io, 0);
11
12 // Do something so that the loop doesn't get optimized out
13 let mut xor_result: u8 = 0x00;
14 let mut read_buf: [u8; 1] = [0x00; 1];
15 loop {
16 let bytes_read = instrumented_buf_file.read(&mut read_buf).unwrap();
17 if bytes_read == 0 {
18 break;
19 }
20 xor_result ^= read_buf[0];
21 assert_eq!(instrumented_buf_file.seek_pos(),
22 instrumented_buf_file.seek(SeekFrom::Current(0)).unwrap());
23 }
24 println!("XOR of all bytes in Cargo.toml is {:#x}", xor_result);
25
26 // Demonstrate how BufReader reduces the number of read calls
27 println!("Buffered read was called successfully {} times",
28 instrumented_buf_file.read_call_counter().success_ctr());
29 println!("Buffered seek was called successfully {} times",
30 instrumented_buf_file.seek_call_counter().success_ctr());
31 println!("Inner read was called successfully {} times",
32 instrumented_raw_file.read_call_counter().success_ctr());
33 println!("Inner seek was called successfully {} times",
34 instrumented_raw_file.seek_call_counter().success_ctr());
35}Source§impl<T: Write, C> IOStatWrapper<T, C>
impl<T: Write, C> IOStatWrapper<T, C>
Sourcepub fn write_call_counter(&self) -> &SuccessFailureCounter<u64>
pub fn write_call_counter(&self) -> &SuccessFailureCounter<u64>
Returns the number of times Write::write() was invoked.
Sourcepub fn write_flush_counter(&self) -> &SuccessFailureCounter<u64>
pub fn write_flush_counter(&self) -> &SuccessFailureCounter<u64>
Returns the number of times Write::flush() was invoked.
pub fn write_byte_counter(&self) -> usize
Trait Implementations§
Source§impl<T: Read, C: Extend<IopInfoPair>> Read for IOStatWrapper<T, C>
We wrap most methods of Read, including provided ones, and pass calls through to the inner I/O object.
The I/O operation log and statistics are only explicitly updated in the Read::read() function, as it is expected that the other methods are implemented with it.
Notably, we do not passthrough Read::bytes(), Read::chain(), and Read::take() as the structs they return have private implementation details that we need to see to have correct type generics. However, for this reason, we do not expect other Read implementations to have their own implementations either, so this shouldn’t be an issue.
impl<T: Read, C: Extend<IopInfoPair>> Read for IOStatWrapper<T, C>
We wrap most methods of Read, including provided ones, and pass calls through to the inner I/O object.
The I/O operation log and statistics are only explicitly updated in the Read::read() function, as it is expected that the other methods are implemented with it.
Notably, we do not passthrough Read::bytes(), Read::chain(), and Read::take() as the structs they return have private implementation details that we need to see to have correct type generics. However, for this reason, we do not expect other Read implementations to have their own implementations either, so this shouldn’t be an issue.
Source§fn read(&mut self, buf: &mut [u8]) -> IOResult<usize>
fn read(&mut self, buf: &mut [u8]) -> IOResult<usize>
Passthrough for the inner_io read call that increments a call counter and appends a IopResults::Read object to the log.
Source§fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> IOResult<usize>
fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> IOResult<usize>
read, except that it reads into a slice of buffers. Read moreSource§fn read_to_end(&mut self, buf: &mut Vec<u8>) -> IOResult<usize>
fn read_to_end(&mut self, buf: &mut Vec<u8>) -> IOResult<usize>
buf. Read moreSource§fn read_to_string(&mut self, buf: &mut String) -> IOResult<usize>
fn read_to_string(&mut self, buf: &mut String) -> IOResult<usize>
buf. Read moreSource§fn read_exact(&mut self, buf: &mut [u8]) -> IOResult<()>
fn read_exact(&mut self, buf: &mut [u8]) -> IOResult<()>
buf. Read moreSource§fn by_ref(&mut self) -> &mut Selfwhere
Self: Sized,
fn by_ref(&mut self) -> &mut Selfwhere
Self: Sized,
Read. Read moreSource§fn is_read_vectored(&self) -> bool
fn is_read_vectored(&self) -> bool
can_vector)Source§fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> Result<(), Error>
fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> Result<(), Error>
read_buf)Source§fn read_buf_exact(&mut self, cursor: BorrowedCursor<'_>) -> Result<(), Error>
fn read_buf_exact(&mut self, cursor: BorrowedCursor<'_>) -> Result<(), Error>
read_buf)cursor. Read moreSource§impl<T: Seek, C: Extend<IopInfoPair>> Seek for IOStatWrapper<T, C>
We wrap all methods of Seek, including provided ones, and pass calls through to the inner I/O object.
The I/O operation log and statistics are only explicitly updated in the Seek::seek() function, as it is expected that the other methods are implemented with it.
impl<T: Seek, C: Extend<IopInfoPair>> Seek for IOStatWrapper<T, C>
We wrap all methods of Seek, including provided ones, and pass calls through to the inner I/O object.
The I/O operation log and statistics are only explicitly updated in the Seek::seek() function, as it is expected that the other methods are implemented with it.
Source§fn seek(&mut self, pos: SeekFrom) -> IOResult<u64>
fn seek(&mut self, pos: SeekFrom) -> IOResult<u64>
Passthrough for the inner_io seek call that increments a call counter and appends a IopResults::Seek object to the log.
Source§fn stream_position(&mut self) -> IOResult<u64>
fn stream_position(&mut self) -> IOResult<u64>
Source§impl<T: Write, C: Extend<IopInfoPair>> Write for IOStatWrapper<T, C>
We wrap all methods of Write, including provided ones, and pass calls through to the inner I/O object.
The I/O operation log and statistics are explicitly updated in the Write::write() and Write::flush() functions, as it is expected that the other methods are implemented with them.
impl<T: Write, C: Extend<IopInfoPair>> Write for IOStatWrapper<T, C>
We wrap all methods of Write, including provided ones, and pass calls through to the inner I/O object.
The I/O operation log and statistics are explicitly updated in the Write::write() and Write::flush() functions, as it is expected that the other methods are implemented with them.
Source§fn write(&mut self, buf: &[u8]) -> IOResult<usize>
fn write(&mut self, buf: &[u8]) -> IOResult<usize>
Passthrough for the inner_io write call that increments a call counter and appends a IopResults::Write object to the log.
Source§fn flush(&mut self) -> IOResult<()>
fn flush(&mut self) -> IOResult<()>
Passthrough for the inner_io write call that increments a call counter and appends a IopResults::Flush object to the log.
Source§fn write_all(&mut self, buf: &[u8]) -> IOResult<()>
fn write_all(&mut self, buf: &[u8]) -> IOResult<()>
Source§fn write_fmt(&mut self, fmt: Arguments<'_>) -> IOResult<()>
fn write_fmt(&mut self, fmt: Arguments<'_>) -> IOResult<()>
Source§fn by_ref(&mut self) -> &mut Selfwhere
Self: Sized,
fn by_ref(&mut self) -> &mut Selfwhere
Self: Sized,
Write. Read moreSource§fn is_write_vectored(&self) -> bool
fn is_write_vectored(&self) -> bool
can_vector)