2013年9月2日星期一

iptables 企业应用之应用层过滤、日志记录

本邮件内容由第三方提供,如果您不想继续收到该邮件,可 点此退订
iptables 企业应用之应用层过滤、日志记录  阅读原文»

每日博报 精彩不止一点关闭
iptables 企业应用之应用层过滤、日志记录

iptables已经发展成为一个功能强大的防火墙,它已具备通常只会在专有的商业防火墙中才能发现的大多数功能。例如,iptables提供了全面的协议状态跟踪、数据包的应用层检查、速率限制和一个功能强大的机制以指定过滤策略和提供NAT功能。我在工作中逐渐领略到它的强大,在此跟大家分享一下我工作中的经验。

iptables相关概念:

1、表

2、链

3、匹配条件

4、动作

5iptables语法

6、企业应用案例

(1)流量访问控制

(2)日志记录

1、表:

表是iptables构建块,它描述了其功能的大类,iptables共有4个表:filternatmangle、和raw。过滤规则应用于filterNAT规则应用于nat表,用于修改分组数据的特定规则应用于mangle表,而独立于Netfilter连接跟踪子系统起作用的规则应用于raw表。

2、链:

每个表都有自己的一组内置链,用户还可以对链进行自定义;当一个数据包由内核中的路由计算确定为指向本地linux系统,它将经过INPUT链的检查;OUTPUT链保留给有Linux系统自身生成的数据包;FORWARD链管理经过linux系统路由的数据包(即iptables防火墙用于连接两个网络,并且两个网络之间的数据包必须流经该防火墙)。nat表中的PREROUTINGPOSTROUTING分别用于在内核进行IP路由计算之前和之后修改数据包的头部。

3、匹配条件:

iptables匹配指的是数据包必须匹配的条件,只有当数据包满足所有的匹配条件时,iptables才会采取相应的动作;匹配分为通用匹配和扩展匹配:

通用匹配:

-s | --src | --source [!] HOST/NET

-d |--dst | --destination [!] HOST/NET

#iptables -t filter -A INPUT -s 172.16.0.0/16 -d 172.16.1.1 -j ACCEPT

-i incoming_interface 指定报文进入接口

-o outgoing_interface 指定报文流出接口

一个IO的传奇一生(2)  阅读原文»

一个IO的传奇一生(2)

EXT3文件写操作

如果应用层发起的是一个Word文档的写操作请求,那么通过上述分析,IO会走到sys_write的地方,然后执行file->f_op->write方法。对于EXT3,该方法注册的是do_sync_writeDo_sync_write的实现如下:

ssize_t do_sync_write(struct file *filp, const char __user *buf, size_t len, loff_t *ppos)
struct iovec iov = { .iov_base = (void __user *)buf, .iov_len = len };
struct kiocb kiocb;
init_sync_kiocb(&kiocb, filp);
kiocb.ki_pos = *ppos;
kiocb.ki_left = len;
ret = filp->f_op->aio_write(&kiocb, &iov, 1, kiocb.ki_pos);
if (ret != -EIOCBRETRY)
wait_on_retry_sync_kiocb(&kiocb);
if (-EIOCBQUEUED == ret)
ret = wait_on_sync_kiocb(&kiocb);
*ppos = kiocb.ki_pos;

该方法会直接调用非阻塞写处理函数,然后等待IO完成。对于具体EXT3文件读写过程函数调用关系可以参考《Ext3文件系统读写过程分》。对EXT3文件写操作主要考虑两种情况,一种情况是DIRECTIO方式;另一种情况是pagecache的写方式。DirectIO方式会直接绕过缓存处理机制,pagecache缓存方式是应用中经常采用的方式,性能会比DirectIO高出不少。对于每一个EXT3文件,都会在内存中维护一棵Radixtree,这棵radixtree就是用来管理来pagecache页的。当IO想往磁盘上写入的时候,EXT3会查找其对应的radixtree,看是否已经存在与写入地址相匹配的page页,如果存在那么直接将数据合并到这个page页中,并且结束一次IO过程,直接结束应用层请求。如果被访问的地址还没有对应的page页,那么需要为访问的地址空间分配page页,并且从磁盘上加载数据到page页内存,最后将这个page页加入到radixtree中。

对于一些大文件,如果不采用radixtree去管理page页,那么需要耗费大量的时间去查找一个文件内对应地址的page页。为了提高查找效率,Linux采用了radixtree的这种管理方式。Radixtree是通用的字典类型数据结构,radixtree又被称之为PAT位树(PatriciaTrieorcritbittree)。Radixtree是一种多叉搜索树,树的叶子节点是实际的数据条目。下图是一个radixtree的例子,该radixtree的分叉为4,树高为4,树中的每个叶子节点用来快速定位8位文件内偏移地址,可以定位256page页。例如,图中虚线对应的两个叶子节点的地址值为0x000000100x11111010,通过这两个地址值,可以很容易的定位到相应的page缓存页。

通过radixtree可以解决大文件page页查询问题。在Linux的实现过程中,EXT3写操作处理函数会调用generic_file_buffered_write完成page页缓存写过程。在该函数中,其实现逻辑说明如下:

generic_file_buffered_write(struct kiocb *iocb, const struct iovec *iov,
unsigned long nr_segs, loff_t pos, loff_t *ppos,
size_t count, ssize_t written)
/* 找到缓存的page页 */
page = __grab_cache_page(mapping,index,&cached_page,&lru_pvec);
/* 处理ext3日志等事情 */
status = a_ops->prepare_write(file, page, offset, offset+bytes);
/* 将用户数据拷贝至page页 */
copied = filemap_copy_from_user(page, offset, buf, bytes);
/* 设置page页为dirty */
status = a_ops->commit_write(file, page, offset, offset+bytes);

第一步通过radixtree找到内存中缓存的page页,如果page页不存在,重新分配一个。第二步通过ext3_prepare_write处理EXT3日志,并且如果page是一个新页的话,那么需要从磁盘读入数据,装载进page页。第三步是将用户数据拷贝至指定的page页。最后一步将操作的Page页设置成dirty。便于writeback机制将dirty页同步到磁盘。

Pagecache会占用Linux的大量内存,当内存紧张的时候,需要从pagecache中回收一些内存页,另外,dirtypage在内存中聚合一段时间之后,需要被同步到磁盘。应该在3.0内核之前,Linux采用pdflush机制将dirtypage同步到磁盘,在之后的版本中,Linux采用了writeback机制进行dirtypage的刷新工作。有关于writeback机制的一些源码分析可以参考《writeback机制源码分》。总的来说,如果用户需要写EXT3文件时,默认采用的是writeback阅读更多内容

没有评论:

发表评论