@@ -82,47 +82,15 @@ fn consume<R: Read + ?Sized>(this: &mut R, mut bytes_count: usize) -> io::Result
82
82
}
83
83
}
84
84
85
- /// Like Read::read_exact(), but seek back to the starting position of the reader in case of an
86
- /// error.
87
- #[ cfg( feature = "experimental" ) ]
88
- fn read_exact_or_seek_back < R : Read + Seek + ?Sized > ( this : & mut R , mut buf : & mut [ u8 ] ) -> io:: Result < ( ) > {
89
- let mut bytes_read = 0 ;
90
- while !buf. is_empty ( ) {
91
- match this. read ( buf) {
92
- Ok ( 0 ) => break ,
93
- Ok ( n) => {
94
- bytes_read += n as i64 ;
95
- let tmp = buf;
96
- buf = & mut tmp[ n..] ;
97
- }
98
- Err ( ref e) if e. kind ( ) == io:: ErrorKind :: Interrupted => { }
99
- Err ( e) => {
100
- if let Err ( error) = this. seek ( SeekFrom :: Current ( -bytes_read) ) {
101
- panic ! ( "Error while seeking back to the start: {}" , error) ;
102
- }
103
- return Err ( e)
104
- } ,
105
- }
106
- }
107
- if !buf. is_empty ( ) {
108
- if let Err ( error) = this. seek ( SeekFrom :: Current ( -bytes_read) ) {
109
- panic ! ( "Error while seeking back to the start: {}" , error) ;
110
- }
111
- Err ( io:: Error :: new ( io:: ErrorKind :: UnexpectedEof , "failed to fill whole buffer" ) )
112
- } else {
113
- Ok ( ( ) )
114
- }
115
- }
116
-
117
85
#[ cfg( feature = "experimental" ) ]
118
86
impl < ' a , R : Read + Seek > Decoder < ' a , BufReader < R > > {
119
87
fn read_skippable_frame_size ( & mut self ) -> io:: Result < usize > {
120
88
let mut magic_buffer = [ 0u8 ; U32_SIZE ] ;
121
- read_exact_or_seek_back ( self . reader . reader_mut ( ) , & mut magic_buffer) ?;
89
+ self . reader . reader_mut ( ) . read_exact ( & mut magic_buffer) ?;
122
90
123
91
// Read skippable frame size.
124
92
let mut buffer = [ 0u8 ; U32_SIZE ] ;
125
- read_exact_or_seek_back ( self . reader . reader_mut ( ) , & mut buffer) ?;
93
+ self . reader . reader_mut ( ) . read_exact ( & mut buffer) ?;
126
94
let content_size = u32:: from_le_bytes ( buffer) as usize ;
127
95
128
96
self . seek_back ( U32_SIZE * 2 ) ;
@@ -139,47 +107,27 @@ impl<'a, R: Read + Seek> Decoder<'a, BufReader<R>> {
139
107
/// Attempt to read a skippable frame and write its content to `dest`.
140
108
/// If it cannot read a skippable frame, the reader will be back to its starting position.
141
109
pub fn read_skippable_frame ( & mut self , dest : & mut [ u8 ] ) -> io:: Result < ( usize , MagicVariant ) > {
142
- let mut bytes_to_seek = 0 ;
143
-
144
- let res = ( || {
145
- let mut magic_buffer = [ 0u8 ; U32_SIZE ] ;
146
- read_exact_or_seek_back ( self . reader . reader_mut ( ) , & mut magic_buffer) ?;
147
- let magic_number = u32:: from_le_bytes ( magic_buffer) ;
148
-
149
- // Read skippable frame size.
150
- let mut buffer = [ 0u8 ; U32_SIZE ] ;
151
- read_exact_or_seek_back ( self . reader . reader_mut ( ) , & mut buffer) ?;
152
- let content_size = u32:: from_le_bytes ( buffer) as usize ;
153
-
154
- let op = self . reader . operation ( ) ;
155
- // FIXME: I feel like we should do that check right after reading the magic number, but
156
- // ZSTD does it after reading the content size.
157
- if !op. is_skippable_frame ( & magic_buffer) {
158
- bytes_to_seek = U32_SIZE * 2 ;
159
- return Err ( io:: Error :: new ( io:: ErrorKind :: Other , "Unsupported frame parameter" ) ) ;
160
- }
161
- if content_size > dest. len ( ) {
162
- bytes_to_seek = U32_SIZE * 2 ;
163
- return Err ( io:: Error :: new ( io:: ErrorKind :: Other , "Destination buffer is too small" ) ) ;
164
- }
110
+ let magic_buffer = self . reader . peek_4bytes ( ) ?;
111
+ let op = self . reader . operation ( ) ;
112
+ if !op. is_skippable_frame ( & magic_buffer) {
113
+ return Err ( io:: Error :: new ( io:: ErrorKind :: Other , "Unsupported frame parameter" ) ) ;
114
+ }
115
+ self . reader . clear_peeked_data ( ) ;
165
116
166
- if content_size > 0 {
167
- read_exact_or_seek_back ( self . reader . reader_mut ( ) , & mut dest[ ..content_size] ) ?;
168
- }
117
+ let magic_number = u32:: from_le_bytes ( magic_buffer) ;
118
+
119
+ // Read skippable frame size.
120
+ let mut buffer = [ 0u8 ; U32_SIZE ] ;
121
+ self . reader . reader_mut ( ) . read_exact ( & mut buffer) ?;
122
+ let content_size = u32:: from_le_bytes ( buffer) as usize ;
169
123
170
- Ok ( ( magic_number, content_size) )
171
- } ) ( ) ;
124
+ if content_size > dest. len ( ) {
125
+ return Err ( io:: Error :: new ( io:: ErrorKind :: Other , "Destination buffer is too small" ) ) ;
126
+ }
172
127
173
- let ( magic_number, content_size) =
174
- match res {
175
- Ok ( data) => data,
176
- Err ( err) => {
177
- if bytes_to_seek != 0 {
178
- self . seek_back ( bytes_to_seek) ;
179
- }
180
- return Err ( err) ;
181
- } ,
182
- } ;
128
+ if content_size > 0 {
129
+ self . reader . reader_mut ( ) . read_exact ( & mut dest[ ..content_size] ) ?;
130
+ }
183
131
184
132
let magic_variant = magic_number - MAGIC_SKIPPABLE_START ;
185
133
@@ -202,7 +150,13 @@ impl<'a, R: Read + Seek> Decoder<'a, BufReader<R>> {
202
150
203
151
// TODO: should we support legacy format?
204
152
let mut magic_buffer = [ 0u8 ; U32_SIZE ] ;
205
- self . reader . reader_mut ( ) . read_exact ( & mut magic_buffer) ?;
153
+ if self . reader . peeking ( ) {
154
+ magic_buffer = self . reader . peeked_data ( ) ;
155
+ self . reader . clear_peeked_data ( ) ;
156
+ }
157
+ else {
158
+ self . reader . reader_mut ( ) . read_exact ( & mut magic_buffer) ?;
159
+ }
206
160
let magic_number = u32:: from_le_bytes ( magic_buffer) ;
207
161
self . seek_back ( U32_SIZE ) ;
208
162
if magic_number & MAGIC_SKIPPABLE_MASK == MAGIC_SKIPPABLE_START {
@@ -240,7 +194,7 @@ impl<'a, R: Read + Seek> Decoder<'a, BufReader<R>> {
240
194
use crate :: map_error_code;
241
195
const MAX_FRAME_HEADER_SIZE_PREFIX : usize = 5 ;
242
196
let mut buffer = [ 0u8 ; MAX_FRAME_HEADER_SIZE_PREFIX ] ;
243
- read_exact_or_seek_back ( self . reader . reader_mut ( ) , & mut buffer) ?;
197
+ self . reader . reader_mut ( ) . read_exact ( & mut buffer) ?;
244
198
let size = frame_header_size ( & buffer)
245
199
. map_err ( map_error_code) ?;
246
200
let byte = buffer[ MAX_FRAME_HEADER_SIZE_PREFIX - 1 ] ;
0 commit comments