@@ -524,67 +524,19 @@ where
524
524
start : 0 ,
525
525
}
526
526
}
527
-
528
527
/// Process write requests or (if there is no data to write) wait for the
529
528
/// next write request or for a shutdown signal.
530
- #[ allow( clippy:: single_match) ]
531
- #[ allow( clippy:: comparison_chain) ]
532
529
fn run ( & mut self ) {
533
- use std:: io:: ErrorKind :: * ;
534
-
535
530
loop {
536
531
if self . descriptor . writer_pair . 0 . lock ( ) . unwrap ( ) . shutdown {
537
532
break ;
538
533
}
539
534
540
535
match & self . buf {
541
- Some ( buf) => {
542
- // We have data in our internal buffer; attempt to write it
543
- match self . inner . write ( & buf[ self . start ..] ) {
544
- Ok ( 0 ) => {
545
- // We received Ok, but nothing was written. The
546
- // behavior that produces this result is not clearly
547
- // defined in the docs, but it's probably safe to
548
- // assume that the correct response is to notify the
549
- // PeerManager of a disconnected peer, break the
550
- // loop, and shut down the TcpStream.
551
- self . peer_manager . socket_disconnected ( & self . descriptor ) ;
552
- self . peer_manager . process_events ( ) ;
553
- break ;
554
- }
555
- Ok ( bytes_written) => {
556
- // Define end s.t. the data written was buf[start..end]
557
- let end = self . start + bytes_written;
558
-
559
- if end == buf. len ( ) {
560
- // Everything was written, clear the buf and reset the start index
561
- self . buf = None ;
562
- self . start = 0 ;
563
- } else if end < buf. len ( ) {
564
- // Partial write; the new start index is exactly where the current
565
- // write ended.
566
- self . start = end;
567
- } else {
568
- panic ! ( "More bytes were written than were given" ) ;
569
- }
570
- }
571
- Err ( e) => match e. kind ( ) {
572
- TimedOut | Interrupted => {
573
- // Retry the write in the next loop
574
- // iteration if we received any of the above
575
- // errors. It would be nice to additionally
576
- // match HostUnreachable | NetworkDown |
577
- // ResourceBusy, but these require nightly
578
- // Rust.
579
- }
580
- _ => {
581
- // For all other errors, notify the
582
- // PeerManager, break, and shut down
583
- self . peer_manager . socket_disconnected ( & self . descriptor ) ;
584
- self . peer_manager . process_events ( ) ;
585
- break ;
586
- }
587
- } ,
536
+ Some ( _buf) => {
537
+ let shutdown = self . do_write ( ) ;
538
+ if shutdown {
539
+ break ;
588
540
}
589
541
}
590
542
None => {
@@ -628,6 +580,65 @@ where
628
580
// Send a signal to the Reader to do the same.
629
581
self . descriptor . shutdown_reader ( ) ;
630
582
}
583
+
584
+ /// Blocks on write() and handles the response accordingly.
585
+ ///
586
+ /// Returns whether the Writer should shut down.
587
+ #[ allow( clippy:: comparison_chain) ]
588
+ fn do_write ( & mut self ) -> bool {
589
+ use std:: io:: ErrorKind :: * ;
590
+
591
+ if let Some ( buf) = & self . buf {
592
+ match self . inner . write ( & buf[ self . start ..] ) {
593
+ Ok ( 0 ) => {
594
+ // We received Ok, but nothing was written. The
595
+ // behavior that produces this result is not clearly
596
+ // defined in the docs, but it's probably safe to
597
+ // assume that the correct response is to notify the
598
+ // PeerManager of a disconnected peer, break the
599
+ // loop, and shut down the TcpStream.
600
+ self . peer_manager . socket_disconnected ( & self . descriptor ) ;
601
+ self . peer_manager . process_events ( ) ;
602
+ return true ;
603
+ }
604
+ Ok ( bytes_written) => {
605
+ // Define end s.t. the data written was buf[start..end]
606
+ let end = self . start + bytes_written;
607
+
608
+ if end == buf. len ( ) {
609
+ // Everything was written, clear the buf and reset the start index
610
+ self . buf = None ;
611
+ self . start = 0 ;
612
+ } else if end < buf. len ( ) {
613
+ // Partial write; the new start index is exactly where the current
614
+ // write ended.
615
+ self . start = end;
616
+ } else {
617
+ panic ! ( "More bytes were written than were given" ) ;
618
+ }
619
+ }
620
+ Err ( e) => match e. kind ( ) {
621
+ TimedOut | Interrupted => {
622
+ // Retry the write in the next loop
623
+ // iteration if we received any of the above
624
+ // errors. It would be nice to additionally
625
+ // match HostUnreachable | NetworkDown |
626
+ // ResourceBusy, but these require nightly
627
+ // Rust.
628
+ }
629
+ _ => {
630
+ // For all other errors, notify the
631
+ // PeerManager, break, and shut down
632
+ self . peer_manager . socket_disconnected ( & self . descriptor ) ;
633
+ self . peer_manager . process_events ( ) ;
634
+ return true ;
635
+ }
636
+ } ,
637
+ }
638
+ }
639
+
640
+ false
641
+ }
631
642
}
632
643
633
644
/// A newtype for a TcpStream that can (and should) only be used for reading and
0 commit comments