File tree 1 file changed +35
-0
lines changed
1 file changed +35
-0
lines changed Original file line number Diff line number Diff line change @@ -244,6 +244,41 @@ impl<'data> ReadBufCursor<'data> {
244
244
self . buf . init = self . buf . filled . max ( self . buf . init ) ;
245
245
}
246
246
247
+ /// Read into a byte slice safely.
248
+ ///
249
+ /// This function provides a safe alternative to the [`as_mut`] and
250
+ /// [`advance`] APIS. It initializes the uninitialized part of the
251
+ /// buffer (if one exists) and passed it as a slice to the provided
252
+ /// closure. Then, it advances the filled part of the buffer by the
253
+ /// returned value.
254
+ #[ inline]
255
+ pub fn read_with < E > ( & mut self , f : impl FnOnce ( & mut [ u8 ] ) -> Result < usize , E > ) -> Result < ( ) , E > {
256
+ // Initialize the unfilled portion of this cursor.
257
+ if self . buf . init < self . buf . raw . len ( ) {
258
+ self . buf . raw [ self . buf . init ..] . fill ( MaybeUninit :: new ( 0 ) ) ;
259
+ self . buf . init = self . buf . raw . len ( ) ;
260
+ }
261
+
262
+ // SAFETY: The full buffer is initialized now.
263
+ let slice = unsafe {
264
+ core:: slice:: from_raw_parts_mut (
265
+ self . buf . raw [ self . buf . filled ..] . as_mut_ptr ( ) as * mut u8 ,
266
+ self . buf . raw . len ( ) - self . buf . filled ,
267
+ )
268
+ } ;
269
+
270
+ // Call the function.
271
+ let n = match f ( slice) {
272
+ Ok ( n) => n,
273
+ Err ( e) => return Err ( e) ,
274
+ } ;
275
+
276
+ // Advance the buffer.
277
+ self . buf . filled = self . buf . filled . checked_add ( n) . expect ( "overflow" ) ;
278
+
279
+ Ok ( ( ) )
280
+ }
281
+
247
282
#[ inline]
248
283
pub ( crate ) fn remaining ( & self ) -> usize {
249
284
self . buf . remaining ( )
You can’t perform that action at this time.
0 commit comments