retina_core/conntrack/conn/tcp_conn/
mod.rspub mod reassembly;
use self::reassembly::TcpFlow;
use crate::conntrack::conn::conn_info::ConnInfo;
use crate::conntrack::pdu::{L4Context, L4Pdu};
use crate::protocols::packet::tcp::{FIN, RST};
use crate::protocols::stream::ParserRegistry;
use crate::subscription::{Subscription, Trackable};
pub(crate) struct TcpConn {
    pub(crate) ctos: TcpFlow,
    pub(crate) stoc: TcpFlow,
}
impl TcpConn {
    pub(crate) fn new_on_syn(ctxt: L4Context, max_ooo: usize) -> Self {
        let flags = ctxt.flags;
        let next_seq = ctxt.seq_no.wrapping_add(1 + ctxt.length as u32);
        let ack = ctxt.ack_no;
        TcpConn {
            ctos: TcpFlow::new(max_ooo, next_seq, flags, ack),
            stoc: TcpFlow::default(max_ooo),
        }
    }
    #[inline]
    pub(crate) fn reassemble<T: Trackable>(
        &mut self,
        segment: L4Pdu,
        info: &mut ConnInfo<T>,
        subscription: &Subscription<T::Subscribed>,
        registry: &ParserRegistry,
    ) {
        if segment.dir {
            self.ctos
                .insert_segment::<T>(segment, info, subscription, registry);
        } else {
            self.stoc
                .insert_segment::<T>(segment, info, subscription, registry);
        }
    }
    #[inline]
    pub(crate) fn is_terminated(&self) -> bool {
        (self.ctos.consumed_flags & self.stoc.consumed_flags & FIN != 0
            && self.ctos.last_ack == self.stoc.next_seq
            && self.stoc.last_ack == self.ctos.next_seq)
            || (self.ctos.consumed_flags & RST | self.stoc.consumed_flags & RST) != 0
    }
    #[inline]
    pub(super) fn update_flags(&mut self, flags: u8, dir: bool) {
        if dir {
            self.ctos.consumed_flags |= flags;
        } else {
            self.stoc.consumed_flags |= flags;
        }
    }
}