Chinaunix首页 | 论坛 | 博客
  • 博客访问: 3514379
  • 博文数量: 1805
  • 博客积分: 135
  • 博客等级: 入伍新兵
  • 技术积分: 3345
  • 用 户 组: 普通用户
  • 注册时间: 2010-03-19 20:01
文章分类

全部博文(1805)

文章存档

2017年(19)

2016年(80)

2015年(341)

2014年(438)

2013年(349)

2012年(332)

2011年(248)

分类: LINUX

2014-06-05 09:42:06

一、conntrack的标识

1、连接跟踪是根据报文的L3L4层头信息来标识一条连接的。我们先来看一下具体根据哪些信息来标识的。

 

数据结构

这个是非常重要的一个数据结构,整个连接跟踪的查找,建立,关联,更新都是依据该结构体的。该结构体包含了用来标识一条连接的全部信息,我们这里把这些信息称为元组。

/include/net/netfilter/nf_conntrack_tuple.h

struct nf_conntrack_tuple
{
     struct nf_conntrack_man src;  //源端信息

   //目的端信息。
    /* These are the parts of the tuple which are fixed. */
    struct {
        union nf_inet_addr u3;  //目的IP地址
    //目的端口的信息,不同协议使用不同的报文字段
        union {
             /* Add other protocols here. */
            __be16 all;
            struct {
                __be16 port;//TCP报文就使用目的端口
            } tcp;
            struct {
                 __be16 port;//UDP报文就使用目的端口
            } udp;
            struct {
                u_int8_t type, code;//ICMPP报文使用type,cod两个字段
            } icmp;
            。。。。。。。 //其他协议此处省略
        } u;
        //传输层协议类型,既L4协议类型
        u_int8_t protonum;
        //标识连接的方向,一条连接分两个方向,一来一回
        /* The direction (for tuplehash) */
        u_int8_t dir;
    } dst;
};


struct nf_conntrack_man
{
     union nf_inet_addr u3; //IP地址
    //L4协议源端信息
    union nf_conntrack_man_proto u;
    //L3协议类型
    u_int16_t l3num;
};


//L4层源端的信息。
union nf_conntrack_man_proto
{
    /* Add other protocols here. */
    __be16 all;
    struct {
        __be16 port;
    } tcp;
    struct {
        __be16 port;
    } udp;
    struct {
        __be16 id;
    } icmp;
    。。。。。。//其他协议此处省略
};

从上面数据结构定义看,标识一条连接的元组为:

TCP  源IP,源端口,L3协议类型,目的IP,目的端口号,L4协议类型

UDP  源IP,源端口,L3协议类型,目的IP,目的端口号,L4协议类型

ICMP 源IPL3协议类型,目的IPidtypecode,L4协议类型

其他协议这里就不介绍了。我也不熟

二、conntrack的定义

一个连接包含正反两个方向的两条报文流。

struct nf_conn {

    //对连接的引用计数

    struct nf_conntrack ct_general;

    spinlock_t lock;

 

    //正向和反向的连接元组信息。

    struct nf_conntrack_tuple_hash tuplehash[IP_CT_DIR_MAX];

    //该连接的连接状态

    unsigned long status;

    //如果该连接是期望连接,指向跟其关联的主连接

    struct nf_conn *master;

    //连接垃圾回收定时器

    struct timer_list timeout;

    /*存储特定协议的连接跟踪信息*/

    union nf_conntrack_proto proto;

 

    /*指向扩展结构,该结构中包含一些基于连接的功能扩展处理函数 */

    struct nf_ct_ext *ext;
   //网络命名空间

    struct net *ct_net;

};

 

struct nf_conntrack_tuple_hash {

    struct hlist_nulls_node hnnode;

    struct nf_conntrack_tuple tuple;

};

 

每个struct nf_conn实例代表一个连接。每个skb都有一个指针,指向和它相关联的连接。

struct sk_buff {

      struct nf_conntrack *nfct;//指向struct nf_conn实例

kmemcheck_bitfield_begin(flags1);

    __u8 local_df:1,

   cloned:1,

  ip_summed:2,

  nohdr:1,

  nfctinfo:3; //记录报文的连接状态。

  kmemcheck_bitfield_end(flags1);

};

三、conntrack的存储



/include/net/netns/conntrack.h

 

每个网络命名空间有如下一个数据结构的实例,来管理和存放生成的连接的一些信息。

struct netns_ct 


{

    atomic_t count;

    unsigned int expect_count;

    unsigned int htable_size; 

    struct kmem_cache *nf_conntrack_cachep;

    struct hlist_nulls_head *hash;//存放已经经过确认的连接hash

    struct hlist_head *expect_hash;//期望连接hash

    struct hlist_nulls_head unconfirmed; //存放没经过确认的连接hash

    struct hlist_nulls_head dying;

    struct ip_conntrack_stat *stat;

 

    int hash_vmalloc;

    int expect_vmalloc;

    char *slabname;

};

(未完待续)



阅读(393) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~