@@ -309,34 +309,43 @@ impl EventParser {
309
309
// * the first line should be appended to the incomplete line, if any
310
310
311
311
if let Some ( incomplete_line) = self . incomplete_line . as_mut ( ) {
312
- let line = lines
313
- . next ( )
314
- // split always returns at least one item
315
- . unwrap ( ) ;
316
- trace ! (
317
- "extending line from previous chunk: {:?}+{:?}" ,
318
- logify( incomplete_line) ,
319
- logify( line)
320
- ) ;
312
+ trace ! ( "incomplete_line {:?}" , incomplete_line) ;
313
+ if let Some ( line) = lines. next ( ) {
314
+ trace ! (
315
+ "extending line from previous chunk: {:?}+{:?}" ,
316
+ logify( incomplete_line) ,
317
+ logify( line)
318
+ ) ;
321
319
322
- self . last_char_was_cr = false ;
323
- if !line. is_empty ( ) {
324
- // Checking the last character handles lines where the last character is a
325
- // terminator, but also where the entire line is a terminator.
326
- match line. last ( ) . unwrap ( ) {
327
- b'\r' => {
328
- incomplete_line. extend_from_slice ( & line[ ..line. len ( ) - 1 ] ) ;
329
- let il = self . incomplete_line . take ( ) ;
330
- self . complete_lines . push_back ( il. unwrap ( ) ) ;
331
- self . last_char_was_cr = true ;
332
- }
333
- b'\n' => {
334
- incomplete_line. extend_from_slice ( & line[ ..line. len ( ) - 1 ] ) ;
335
- let il = self . incomplete_line . take ( ) ;
336
- self . complete_lines . push_back ( il. unwrap ( ) ) ;
337
- }
338
- _ => incomplete_line. extend_from_slice ( line) ,
339
- } ;
320
+ self . last_char_was_cr = false ;
321
+ if !line. is_empty ( ) {
322
+ // Checking the last character handles lines where the last character is a
323
+ // terminator, but also where the entire line is a terminator.
324
+ match line. last ( ) . unwrap ( ) {
325
+ b'\r' => {
326
+ trace ! ( "\\ r branch" ) ;
327
+ incomplete_line. extend_from_slice ( & line[ ..line. len ( ) - 1 ] ) ;
328
+ let il = self . incomplete_line . take ( ) ;
329
+ self . complete_lines . push_back ( il. unwrap ( ) ) ;
330
+ self . last_char_was_cr = true ;
331
+ }
332
+ b'\n' => {
333
+ trace ! ( "\\ n branch" ) ;
334
+ incomplete_line. extend_from_slice ( & line[ ..line. len ( ) - 1 ] ) ;
335
+ let il = self . incomplete_line . take ( ) ;
336
+ self . complete_lines . push_back ( il. unwrap ( ) ) ;
337
+ }
338
+ _ => {
339
+ trace ! (
340
+ "other branch, extending slice {:?} with {:?}" ,
341
+ incomplete_line,
342
+ line
343
+ ) ;
344
+ incomplete_line. extend_from_slice ( line) ;
345
+ trace ! ( "Now we have {:?}" , incomplete_line) ;
346
+ }
347
+ } ;
348
+ }
340
349
}
341
350
}
342
351
@@ -397,6 +406,7 @@ impl EventParser {
397
406
#[ cfg( test) ]
398
407
mod tests {
399
408
use super :: { Error :: * , * } ;
409
+ use proptest:: proptest;
400
410
use test_case:: test_case;
401
411
402
412
fn field < ' a > ( key : & ' a str , value : & ' a str ) -> Result < Option < ( & ' a str , & ' a str ) > > {
@@ -693,4 +703,13 @@ mod tests {
693
703
std:: fs:: read ( format ! ( "test-data/{}" , name) )
694
704
. unwrap_or_else ( |_| panic ! ( "couldn't read {}" , name) )
695
705
}
706
+
707
+ proptest ! {
708
+ #[ test]
709
+ fn test_decode_and_buffer_lines_does_not_crash( next in "(\r \n |\r |\n )*event: [^\n \r :]*(\r \n |\r |\n )" , previous in "(\r \n |\r |\n )*event: [^\n \r :]*(\r \n |\r |\n )" ) {
710
+ let mut parser = EventParser :: new( ) ;
711
+ parser. incomplete_line = Some ( previous. as_bytes( ) . to_vec( ) ) ;
712
+ parser. decode_and_buffer_lines( Bytes :: from( next) ) ;
713
+ }
714
+ }
696
715
}
0 commit comments