chiark / gitweb /
wip debug
[hippotat.git] / src / slip.rs
1 // Copyright 2021 Ian Jackson and contributors to Hippotat
2 // SPDX-License-Identifier: AGPL-3.0-or-later
3 // There is NO WARRANTY.
4
5 use crate::prelude::*;
6
7 pub static SLIP_END_SLICE: &[u8] = &[SLIP_END];
8
9 #[throws(AE)]
10 pub fn check_checkmtu_mimeswap<const TO_MIME: bool>
11   (ic: &InstanceConfig, data: &mut [u8])
12 {
13 //  eprintln!("before: {}", DumpHex(data));
14
15   for mut packet in data.split_mut(|&c| c == SLIP_END) {
16     if packet.len() > ic.mtu.sat() {
17       throw!(anyhow!("mtu exceeded ({} > {})", packet.len(), ic.mtu));
18     }
19
20     while let Some((i, _)) = packet.iter().enumerate().find(
21       |(_,&c)| c == if TO_MIME { SLIP_ESC } else { SLIP_MIME_ESC }
22     ) {
23       packet[i] = if TO_MIME { SLIP_MIME_ESC } else { SLIP_ESC };
24       match packet.get(i+1) {
25         Some(&SLIP_ESC_END) |
26         Some(&SLIP_ESC_ESC) => Ok(()),
27         _ => Err(anyhow!("SLIP escape not followed by ESC_END or ESC_ESC")),
28       }?;
29       packet = &mut packet[i+2 ..];
30     }
31   }
32
33 //  eprintln!(" after: {}", DumpHex(data));
34 }
35
36 pub type Frame = Vec<u8>;
37 pub type FramesData = Vec<Vec<u8>>;
38
39 #[derive(Default)]
40 pub struct Frames {
41   frames: FramesData,
42   total_len: usize,
43 }
44
45 impl Debug for Frames {
46   #[throws(fmt::Error)]
47   fn fmt(&self, f: &mut fmt::Formatter) {
48     write!(f, "Frames{{n={},len={}}}", &self.frames.len(), &self.total_len)?;
49   }
50 }
51
52 impl Frames {
53   #[throws(Frame)]
54   pub fn add(&mut self, max: u32, frame: Frame) {
55     if frame.len() == 0 { return }
56     let new_total = self.total_len + frame.len() + 1;
57     if new_total > max.sat() { throw!(frame) }
58     self.total_len = new_total;
59     self.frames.push(frame);
60   }
61 }
62
63 impl From<Frames> for FramesData {
64   fn from(frames: Frames) -> FramesData { frames.frames }
65 }
66
67 struct DumpHex<'b>(pub &'b [u8]);
68 impl Display for DumpHex<'_> {
69   #[throws(fmt::Error)]
70   fn fmt(&self, f: &mut fmt::Formatter) {
71     for v in self.0 { write!(f, "{:02x}", v)?; }
72   }
73 }