//eprintln!("data={:?}", DumpHex(&data));
check
- ::<_,_,_,true>(ic.mtu, &data, &mut packets, |header| {
+ ::<_,_,_,Slip2Mime>(ic.mtu, &data, &mut packets, |header| {
let addr = ip_packet_addr::<false>(header)?;
if addr != ic.link.client.0 { throw!(PE::Src(addr)) }
Ok(())
if let Some(got) = got {
//eprintln!("got={:?}", DumpHex(&got));
check
- ::<_,_,_,false>(ic.mtu, &got, &mut rx_queue, |header| {
+ ::<_,_,_,SlipNoConv>(ic.mtu, &got, &mut rx_queue, |header| {
let addr = ip_packet_addr::<true>(header)?;
if addr != ic.link.client.0 { throw!(PE::Dst(addr)) }
Ok(())
#[error("bad, IPv{vsn}, len={len}")] Bad { len: usize, vsn: u8 },
}
-pub fn check<AC, EH, OUT, const TO_MIME: bool>(
+pub trait SlipMime { const CONV_TO: Option<bool>; }
+#[derive(Copy,Clone,Debug)] pub struct Slip2Mime;
+#[derive(Copy,Clone,Debug)] pub struct Mime2Slip;
+#[derive(Copy,Clone,Debug)] pub struct SlipNoConv;
+impl SlipMime for Slip2Mime { const CONV_TO: Option<bool> = Some(true); }
+impl SlipMime for Mime2Slip { const CONV_TO: Option<bool> = Some(false); }
+impl SlipMime for SlipNoConv { const CONV_TO: Option<bool> = None; }
+
+pub fn check<AC, EH, OUT, M: SlipMime>(
mtu: u32,
data: &[u8],
out: &mut OUT,
while let Some((i, was_mime)) = walk.iter().enumerate().find_map(
|(i,&c)| match c {
- SLIP_MIME_ESC => Some((i,true)),
- SLIP_ESC => Some((i,false)),
+ SLIP_ESC => Some((i,false)),
+ SLIP_MIME_ESC if M::CONV_TO.is_some() => Some((i,true)),
_ => None,
}
) {
let _ = wheader.write(&walk[0..i]);
- walk[i] = if was_mime { SLIP_ESC } else { SLIP_MIME_ESC };
- if was_mime != TO_MIME {
+ if M::CONV_TO.is_some() {
+ walk[i] = if was_mime { SLIP_ESC } else { SLIP_MIME_ESC };
+ }
+ if Some(was_mime) != M::CONV_TO {
let c = match walk.get(i+1) {
Some(&SLIP_ESC_END) => SLIP_ESC,
Some(&SLIP_ESC_ESC) => SLIP_END,
use PacketError as PE;
const MTU: u32 = 10;
- fn chk(i: &[u8], exp_p: &[&[u8]], exp_e: &[PacketError]) {
+ fn chk<M: SlipMime>(i: &[u8], exp_p: &[&[u8]], exp_e: &[PacketError]) {
let mut got_e = vec![];
- let got_p = check::<_,_,true>(MTU, i, |_|Ok(()), |e| got_e.push(e));
+ let mut got_p = vec![];
+ check::<_,_,_,M>(MTU, i, &mut got_p, |_|Ok(()), |e| got_e.push(e));
assert_eq!( got_p.iter().map(|b| DumpHex(b)).collect_vec(),
exp_p.iter().map(|b| DumpHex(b)).collect_vec() );
assert_eq!( got_e,
exp_e );
}
- chk( &[ SLIP_END, SLIP_ESC, SLIP_ESC_END, b'-', b'X' ],
+ chk::<Slip2Mime>
+ ( &[ SLIP_END, SLIP_ESC, SLIP_ESC_END, b'-', b'X' ],
&[ &[ b'-', SLIP_ESC_END, SLIP_ESC, b'X' ] ],
&[ PE::Empty ]);
- chk( &[ SLIP_END, SLIP_ESC, b'y' ], &[],
+ chk::<Slip2Mime>
+ ( &[ SLIP_END, SLIP_ESC, b'y' ], &[],
&[ PE::Empty, PE::SLIP ]);
- chk( &[ SLIP_END, b'-', b'y' ],
+ chk::<Slip2Mime>
+ ( &[ SLIP_END, b'-', b'y' ],
&[ &[ SLIP_ESC, b'y' ] ],
&[ PE::Empty ]);
- chk( &[b'x'; 20],
+ chk::<Slip2Mime>
+ ( &[b'x'; 20],
&[ ],
&[ PE::MTU { len: 20, mtu: MTU } ]);
}