Suricata6.0流表管理源码注释四:流的建立02

本文深入探讨Suricata6.0流表管理,重点在于FlowGetNew函数,涉及从线程局部队列到全局内存池的流程。当无法获取新Flow时,系统进入紧急模式,通过FlowTimeoutsEmergency设置紧急老化时间。FlowGetUsedFlow函数在资源紧张时,从已使用Flow中寻找可用实例,利用flow_prune_idx策略提高查找效率。
摘要由CSDN通过智能技术生成

这篇文章接着上篇继续解释流的建立,其中最重要的一个函数FlowGetNew,主要目的是获取一个flow,获取过程中也是非常曲折的,求爷爷告奶奶才能求来一个flow。

1. FlowGetNew 这个函数也分几个方面理解:

FlowHandlePacket-》FlowGetFlowFromHash-》FlowGetNew

a。从线程自己的flow队列里获取flow,如果获取成功则返回flow,如果没有就从全局flow内存池获取一个flow队列,再从flow队列里获取flow。

b。如果线程自己的flow队列和全局flow内存池也没有可用的flow队列,且flow内存超过配置上限,则设置进入紧急模式。

c。接b,设置紧急模式之后,调用函数FlowGetUsedFlow获取flow,这个函数是从正在使用的全局flow_hash的bucket链表里获取一个,后续会注释这个函数。

d。如果线程自己的flow队列和全局flow内存池也没有可用的flow队列,且flow内存没有超过配置上限,则直接在内存上分配flow即调用函数FlowAlloc。

static Flow *FlowGetNew(ThreadVars *tv, FlowLookupStruct *fls, const Packet *p)
{
    //获取紧急模式标志
    const bool emerg = ((SC_ATOMIC_GET(flow_flags) & FLOW_EMERGENCY) != 0);

    //检查是否可以生成flow,icmp错误包不生成flow
    //如果是紧急模式,tcp非sync的包不生成flow,可以看出sync包优先生成flow
    if (FlowCreateCheck(p, emerg) == 0) {
        return NULL;
    }

    //从线程自己的flow队列里获取flow,如果获取成功则返回flow
    /* get a flow from the spare queue */
    Flow *f = FlowQueuePrivateGetFromTop(&fls->spare_queue);
    if (f == NULL) {
        //如果获取flow失败,就从全局flow内存池获取一个flow队列,再从flow队列里获取flow。
        //FlowSpareSync这个函数主要是从空闲的全局flow内存池获取一个flow队列,给自己用
        f = FlowSpareSync(tv, fls, p, emerg);
    }

    //全局flow内存池也没有可用的flow队列
    if (f == NULL) {
        /* If we reached the max memcap, we get a used flow */
        //判断如果flow内存超过配置上限,则进入紧急模式。
        if (!(FLOW_CHECK_MEMCAP(sizeof(Flow) + FlowStorageSize()))) {
            /* declare state of emergency */
            if (!(SC_ATOMIC_GET(flow_flags) & FLOW_EMERGENCY)) {
                //没有设置紧急模式标志才会设置,设置过
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

种菜的

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值