1use std::io::BufRead;
8
9pub fn read_line<R: BufRead + ?Sized>(r: &mut R, buf: &mut Vec<u8>) -> std::io::Result<usize> {
13  let mut read = 0;
14  loop {
15    let (done, used) = {
16      let available = match r.fill_buf() {
17        Ok(n) => n,
18        Err(ref e) if e.kind() == std::io::ErrorKind::Interrupted => continue,
19
20        Err(e) => return Err(e),
21      };
22      match memchr::memchr(b'\n', available) {
23        Some(i) => {
24          let end = i + 1;
25          buf.extend_from_slice(&available[..end]);
26          (true, end)
27        }
28        None => match memchr::memchr(b'\r', available) {
29          Some(i) => {
30            let end = i + 1;
31            buf.extend_from_slice(&available[..end]);
32            (true, end)
33          }
34          None => {
35            buf.extend_from_slice(available);
36            (false, available.len())
37          }
38        },
39      }
40    };
41    r.consume(used);
42    read += used;
43    if done || used == 0 {
44      return Ok(read);
45    }
46  }
47}