linux2.4中netfilter_nat_alg机制分析--以FTP流程为例,分析NAT和ALG
以FTP流程为例,分析NAT和ALG
网络环境:
×5+6=1286)
创建×5+6=1286),更新skb的应用层信息(这里应用层信息还是×5+6=1286)
创建×5+6=1286)
创建×5+6=1286),更新skb的应用层信息(这里应用层信息修改为“227 Entering PORT Mode(202,100,100,1,5,6)\r\n”)
/************数据连接开始***************/
阶段四:
src/dst/sport/dport: 202.100.100.2/202.100.100.1/20/1286 server->client
SYN data connection
1. PREROUTING
Conntrack:ip_conntrack_in中,得到
tuple.src.ip=202.100.100.2;
tuple.dst.ip=202.100.100.1;
tuple.dst.protonum=tcp;
tuple.src.u.tcp.port=20;
tuple.dst.u.tcp.port=1286;
这是一个新的tuple,所以调用init_conntrack,得到反向tuple:
repl_tuple:
repl_tuple.src.ip=202.100.100.1;
repl_tuple.dst.ip=202.100.100.2;
repl_tuple.dst.protonum=tcp;
repl_tuple.src.u.tcp.port=1286;
repl_tuple.dst.u.tcp.port=20;
conntrack->tuplehash[IP_CT_DIR_ORIGINAL].tuple = *tuple;
conntrack->tuplehash[IP_CT_DIR_ORIGINAL].ctrack = conntrack;
conntrack->tuplehash[IP_CT_DIR_REPLY].tuple = repl_tuple;
conntrack->tuplehash[IP_CT_DIR_REPLY].ctrack = conntrack;
通过expected = LIST_FIND(&ip_conntrack_expect_list, expect_cmp,struct ip_conntrack_expect *, tuple);,可以得到其所属exp,并找到conntrack->helper
最后,有:
__set_bit(IPS_EXPECTED_BIT, &conntrack->status);
conntrack->master = expected;
expected->sibling = conntrack;
至此,控制报文和数据报文建立如下关系:
控制报文的conntrack:
IP_CT_DIR_ORIGINAL:src/dst/sport/dport:192.168.1.2/202.100.100.2/3333/21
IP_CT_DIR_REPLY:src/dst/sport/dport:202.100.100.2/202.100.100.1/21/2222
控制报文有conntrack_help的handle处理;
数据报文的conntrack:
IP_CT_DIR_ORIGINAL:src/dst/sport/dport:202.100.100.2/202.100.100.1/20/1286
IP_CT_DIR_REPLY:src/dst/sport/dport:202.100.100.1/202.100.100.2/1286/20
数据报文的conntrack_help为NULL;
它们之间联系用的exp为:
exp_ftp_info->port = 256*5+6 = 1286;
exp.tuple.src.ip=202.100.100.2;
exp.tuple.dst.ip=202.100.100.1;
exp.tuple.dst.protonum= IPPROTO_TCP;
exp.tuple.src.u.all=0;
exp.tuple.dst.u.tcp.port=1286;
设置*ctinfo = IP_CT_RELATED;(相关)
NAT:ip_nat_fn中,得到skb的conntrack信息,并得到info = &ct->nat.info。显然,这个conntrack是新的,并没有nat.info。并且,这个conntrack是有exp的,所以,会进行call_expect操作。
这里进入的就是ftp的expect函数:ftp_nat_expected:
首先,获取conntrack->master,就是ftp的控制连接的conntrack;以及exp_info信息;
由于是PORT模式,所以得到:
newdstip = master->tuplehash[IP_CT_DIR_ORIGINAL].tuple.src.ip;//192.168.1.2
newsrcip = master->tuplehash[IP_CT_DIR_ORIGINAL].tuple.dst.ip;//202.100.100.2
由于HOOK2MANIP(hooknum) == IP_NAT_MANIP_DST,所以得到:
newip = newdstip; //192.168.1.2;
建立mr信息:
mr.rangesize=1;
mr.range[0].flags= IP_NAT_RANGE_MAP_IPS | IP_NAT_RANGE_PROTO_SPECIFIED;
mr.range[0].min_ip=192.168.1.2;
mr.range[0].max_ip=192.168.1.2;
mr.range[0].min= exp_ftp_info->port;
mr.range[0].max= exp_ftp_info->port;
然后,调用ip_nat_setup_info,得到:
orig_tp:src/dst/sport/dport:202.100.100.2/202.100.100.1/20/1286;
new_tp:src/dst/sport/dport:202.100.100.2/192.168.1.2/20/4444;
reply_tp:src/dst/sport/dport:192.168.1.2/202.100.100.2/4444/20;
inv_tp:src/dst/sport/dport:202.100.100.1/202.100.100.2/1286/20;
通过ip_conntrack_alter_reply,更改数据报文的reply方向的tuple为:src/dst/sport/dport:192.168.1.2/202.100.100.2/1286/4444
建立nat_info:
/*用于ORIGINAL方向的报文的DNAT
manip.direction=IP_CT_DIR_ORIGINAL;
manip.hooknum=NF_IP_PRE_ROUTING;
manip.maniptype=IP_NAT_MANIP_DST;
manip.manip.ip=192.168.1.2;
manip.manip.u.tcp.port=4444;
*/
/*用于REPLY方向的报文的SNAT
manip.direction=IP_CT_DIR_REPLY;
manip.hooknum=NF_IP_POST_ROUTING;
manip.maniptype=IP_NAT_MANIP_SRC;
manip.manip.ip=202.100.100.1;
manip.manip.u.tcp.port=1286;
*/
这里由于conntrack->master存在,所以不会挂接help
从而得到数据连接的新的conntrack:
IP_CT_DIR_ORIGINAL:src/dst/sport/dport:202.100.100.2/202.100.100.1/20/1286
IP_CT_DIR_REPLY:src/dst/sport/dport:192.168.1.2/202.100.100.2/4444/20
然后,调用do_bindings,进行skb的地址转换:由:
202.100.100.2/202.100.100.2/20/1286更改为:202.100.100.2/192.168.1.2/20/4444
2.POSTROUTING
Conntrack:ip_refrag,不处理conntrack相关;
NAT:ip_nat_fn中,得到skb的conntrack信息,并得到info = &ct->nat.info。直接调用do_bindings:
由于不满足
info->manips[i].direction == dir
&& info->manips[i].hooknum == hooknum
故不进行地址变换处理(实际上在PREROUTING中已经转变过了,这里不需要再做了);
阶段五:
src/dst/sport/dport:192.168.1.2/202.100.100.2/4444/20 client->server
SYN+ACK data connection
1. PREROUTING:
Conntrack:ip_conntrack_in中,得到:
tuple:
tuple.src.ip=192.168.1.2;
tuple.dst.ip=202.100.100.2;
tuple.dst.protonum=tcp;
tuple.src.u.tcp.port=4444;
tuple.dst.u.tcp.port=20;
它正好是conntrck->tuplehash[IP_CT_DIR_REPLY]方向的tuple记录信息
*ctinfo = IP_CT_ESTABLISHED + IP_CT_IS_REPLY;
set_bit(IPS_SEEN_REPLY_BIT, &ct->status);
NAT:ip_nat_fn中,得到先前建立的NAT地址信息表:info = &ct->nat.info,
进入do_bindings,但由于不满足:
info->manips[i].direction == dir
&& info->manips[i].hooknum == hooknum
故不处理;
且没有helper
2. POSTROUTING
Conntrack:ip_refrag,不处理conntrack相关;
NAT:ip_nat_fn中,得到skb的conntrack信息,并得到info = &ct->nat.info。直接调用do_bindings:
满足
info->manips[i].direction == dir(IP_CT_DIR_REPLY)
&& info->manips[i].hooknum == hooknum(NF_IP_POST_ROUTING)
故进行SNAT转换,skb的地址转换:由:
192.168.1.2/202.100.100.2/4444/20更改为:202.100.100.1/202.100.100.2/1286/20
无helper
/***********************总结*******************************/
1. Netfilter:提供一个5个hook点的框架;
2. Conntrack:记录报文的运行轨迹。包括ORIGINAL和REPLY两个方向;
3. NAT:依据iptables的NAT规则,建立Conntrack的nat_info信息,并更改报文的地址信息;
4. ALG:用于更改某些报文的应用层中的地址信息;
处理模式:
1. 控制报文:
² PREROUTING:
Ø Conntrack:建立新的Conntrack信息:ORIGINAL+REPLY;
Ø NAT:无
² POSTROUTING:
Ø Conntrack:无
Ø NAT:根据iptables规则,建立该Conntrack的nat_info:SNAT+DNAT,并更改报文地址;并更改Conntrack中记录的REPLY方向的tuple信息(地址改为NAT处理后的值)
2. 应用层含有数据连接地址信息的控制报文:
² PREROUTING:
Ø Conntrack:找到已经建立的Conntrack信息;利用conntrack->help,建立exp结构,建立所exp的tuple信息
Ø NAT:可能不处理 或者 利用nat->help更新应用层报文中的地址信息,并更改exp中的地址信息
² POSTROUTING:
Ø Conntrack:无
Ø NAT:可能不处理 或者 利用nat->help更新应用层报文中的地址信息,并更改exp中的地址信息
3. 数据报文到达:
² PREROUTING:
Ø Conntrack:建立新的Conntrack信息:ORIGINAL+REPLY;且正好就是要expect的tuple;故与控制报文的Conntrack关联上;
Ø NAT:通过调用nat->exp函数,利用控制报文的Conntrack信息,建立自己的nat_info:SNAT+DNAT;并更改Conntrack中记录的REPLY方向的tuple信息(地址改为NAT处理后的值)
² POSTROUTING:
Ø Conntrack:无
Ø NAT:利用自己的nat_info,更改报文的地址信息
linux2.4中netfilter_nat_alg机制分析--以FTP流程为例,分析NAT和ALG的更多相关文章
- 图解Janusgraph系列-并发安全:锁机制(本地锁+分布式锁)分析
图解Janusgraph系列-并发安全:锁机制(本地锁+分布式锁)分析 大家好,我是洋仔,JanusGraph图解系列文章,实时更新~ 图数据库文章总目录: 整理所有图相关文章,请移步(超链):图数据 ...
- RxJava && Agera 从源码简要分析基本调用流程(1)
版权声明:本文由晋中望原创文章,转载请注明出处: 文章原文链接:https://www.qcloud.com/community/article/123 来源:腾云阁 https://www.qclo ...
- .NET中反射机制的使用与分析
.NET中反射机制的使用与分析 [日期:2008-06-30] 来源: 作者:志伟 .NET反射的定义:审查元数据并收集关于它的类型信息的能力. 元数据是一种二进制信息,用以对存储在公共语言 ...
- 【转载】linux2.6内核initrd机制解析
题记 很久之前就分析过这部分内容,但是那个时候不够深入,姑且知道这么个东西存在,到底怎么用,来龙去脉咋回事就不知道了.前段时间工作上遇到了一个initrd的问题,没办法只能再去研究研究,还好,有点眉目 ...
- Servlet容器Tomcat中web.xml中url-pattern的配置详解[附带源码分析]
目录 前言 现象 源码分析 实战例子 总结 参考资料 前言 今天研究了一下tomcat上web.xml配置文件中url-pattern的问题. 这个问题其实毕业前就困扰着我,当时忙于找工作. 找到工作 ...
- Java中JIN机制及System.loadLibrary() 的执行过程
Android平台Native开发与JNI机制详解 http://mysuperbaby.iteye.com/blog/915425 个人认为下面这篇转载的文章写的很清晰很不错. 注意Android平 ...
- Android事件传递机制详解及最新源码分析——ViewGroup篇
版权声明:本文出自汪磊的博客,转载请务必注明出处. 在上一篇<Android事件传递机制详解及最新源码分析--View篇>中,详细讲解了View事件的传递机制,没掌握或者掌握不扎实的小伙伴 ...
- Android事件传递机制详解及最新源码分析——Activity篇
版权声明:本文出自汪磊的博客,转载请务必注明出处. 在前两篇我们共同探讨了事件传递机制<View篇>与<ViewGroup篇>,我们知道View触摸事件是ViewGroup传递 ...
- Linux内核中锁机制之RCU、大内核锁
在上篇博文中笔者分析了关于完成量和互斥量的使用以及一些经典的问题,下面笔者将在本篇博文中重点分析有关RCU机制的相关内容以及介绍目前已被淘汰出内核的大内核锁(BKL).文章的最后对<大话Linu ...
随机推荐
- unity linear space时 photoshop blend的正确设置
gamma correction的dcc设置 ps在线性空间下工作 blend的时候颜色设置 勾选用灰度系数混合rgb 1.0 这样就是在线性空间下工作了 这样素材在数学上是正确的 r8g8b8a8格 ...
- [Python爬虫] 之二十九:Selenium +phantomjs 利用 pyquery抓取节目信息信息
一.介绍 本例子用Selenium +phantomjs爬取节目(http://tv.cctv.com/epg/index.shtml?date=2018-03-25)的信息 二.网站信息 三.数据抓 ...
- Android打印机--小票打印格式及模板设置
小票打印就是向打印设备发送控制打印格式的指令集,而这些打印格式须要去查询相应打印机的API文档,这里我把经常使用的api给封装了一下 文字对齐方式 打印字体大小 字体是否加粗 打印二维码 打印条形码 ...
- maven镜像制作
故事背景: 需要在客户现场部署测试demo,由于部署环境不提供外网环境,应用所需依赖无法通过外网下载. 初步的解决方案,在本地起一个maven的容器,将代码copy到maven的容器内,进行打包操作, ...
- 使用HTML5画布(canvas)生成阴影效果
来源:GBin1.com 使用HTML5的画布特性,我们可以创建图形,在这片文章中,我们将创建图形的阴影. var canvas = document.getElementById('shadowca ...
- Office 如何双面打印Word文档
打印之前勾选手动双面打印,然后开始打印(不管当前文档有几页,要打印几份,会只打印奇数页面) 只要开始打印奇数页面,就会有一个弹出窗口,当完成之后把打印的东西拿出来,整个翻面再放回打印机,点击确定会 ...
- ASP.NET MVC扩展之HtmlHelper辅助方法
什么是HtmlHelper辅助方法? 其实就是HtmlHelper类的扩展方法,如下所示: namespace System.Web.Mvc.Html { public static class Fo ...
- 初识 Swift编程语言(中文版)
前言 今天Apple公布了新的编程语言Swift.也提供了一本将近400页的 The Swift Programming Language(Swift编程语言). 尽管我没有开发人员账号.没法实际上机 ...
- 阻塞与非阻塞、同步与异步、I/O模型
1. 概念理解 在进行网络编程时,我们常常见到同步(Sync)/异步(Async),阻塞(Block)/非阻塞(Unblock)四种调用方式: 同步/异步主要针对C端: 同步: 所谓同步,就是在c端 ...
- 一次vm 虚拟机时间倒流而导致的oracle 数据库启动故障
一次vm 虚拟机时间倒流而导致的oracle 数据库启动故障 本文是原创文章.若转载请注明出处: http://blog.csdn.net/msdnchina/article/details/3878 ...