Kernel Packet Traveling Diagram

源:http://mailman.ds9a.nl/pipermail/lartc/2002q2/004245.html

Network -----------+----------- | +--------------------------+ +-------+-------+ +---------+---------+ | IPCHAINS | | IPTABLES | | INPUT | | PREROUTING | +-------+-------+ | +-------+-------+ | | | | conntrack | | | | +-------+-------+ | | | | mangle | | <- MARK WRITE | | +-------+-------+ | | | | IMQ | | | | +-------+-------+ | | | | nat | | <- DEST REWRITE | | +-------+-------+ | DNAT or REDIRECT or DE-MASQUERADE | +---------+---------+ +------------+-------------+ | +-------+-------+ | QOS | | INGRESS | +-------+-------+ | packet is for +-------+-------+ packet is for this machine | INPUT | another address +--------------+ ROUTING +--------------+ | | + PDBB | | | +---------------+ | +-------+-------+ | | IPTABLES | | | INPUT | | | +-----+-----+ | | | | mangle | | | | +-----+-----+ | | | | filter | | | | +-----+-----+ | | +-------+-------+ | | +---------------------------+ +-------+-------+ | | | Local | +-------+-------+ +-------+-------+ | Process | | IPCHAINS | | IPTABLES | +-------+-------+ | FORWARD | | FORWARD | | +-------+-------+ | +-----+-----+ | +-------+-------+ | | | mangle | | <- MARK WRITE | OUTPUT | | | +-----+-----+ | | ROUTING | | | | filter | | +-------+-------+ | | +-----+-----+ | | | +-------+-------+ +-------+-------+ | | | IPTABLES | +---------------------------+ | OUTPUT | | | +-----------+ | | | | conntrack | | | | +-----+-----+ | | | | mangle | | <- MARK WRITE | | +-----+-----+ | | | | nat | | <-DEST REWRITE | | +-----+-----+ | DNAT or REDIRECT | | | filter | | | | +-----+-----+ | | +-------+-------+ | | | +----------------------+----------------------+ | +------------+------------+ | | +-------+-------+ +---------+---------+ | IPCHAINS | | IPTABLES | | OUTPUT | | POSTROUTING | +-------+------- | +-------+-------+ | | | | mangle | | <- MARK WRITE | | +-------+-------+ | | | | nat | | <- SOURCE REWRITE | | +-------+-------+ | SNAT or MASQUERADE | | | IMQ | | | | +-------+-------+ | | +---------+---------+ +------------+------------+ | +------+------+ | QOS | | EGRESS | +------+------+ | -----------+----------- Network

以上为linux中TC(Traffic Control)控制部分,和网络包在内核中的走向,下面是一个图。

Kernel Packet Traveling Diagram_第1张图片

 


这个图。我觉得,真是太经典了!

当然这个图和现在的kernel还是有点出入的,

在linux-2.6.36中。

 ip_forward_finish() -->return dst_output(skb);--->ip_output()

然后是POSTOUTING是

ip_output()-->NF_IP_POSTOUTING-->ip_finish_output()这样处理过程

 

如果是ip_gre 活ip_ip协议的话,那么是在ip_local_deliver_finish内,调用相应的handler函数,去掉gre/ip头后处理完成后再调用netif_rx()函数。相信在代码中都是一目了然的。代码内核版本为:2.6.36

 

发送流程:

/* * net/ipv4/ip_output.c */ int ip_local_out(struct sk_buff *skb) { err = __ip_local_out(skb); } int __ip_local_out(struct sk_buff *skb) { return nf_hook(NFPROTO_IPV4, NF_INET_LOCAL_OUT, skb, NULL, skb_dst(skb)->dev, dst_output); } /* 经过LOCAL_OUT过滤节点 * include/net/dst.h */ static inline int dst_output(struct sk_buff *skb) { return skb_dst(skb)->output(skb); } int ip_output(struct sk_buff *skb) { return NF_HOOK_COND(NFPROTO_IPV4, NF_INET_POST_ROUTING, skb, NULL, dev, ip_finish_output, !(IPCB(skb)->flags & IPSKB_REROUTED)); } /** * 经过POST_ROUTING过滤函数 **/ static int ip_finish_output(struct sk_buff *skb) { return ip_finish_output2(skb); } static inline int ip_finish_output2(struct sk_buff *skb) { else if (dst->neighbour) { printk(KERN_INFO "jsh ip_finish_output2 neighbour/n"); return dst->neighbour->output(skb); } } /* * net/core/dev.c */ int dev_hard_start_xmit(struct sk_buff *skb, struct net_device *dev, struct netdev_queue *txq) { rc = ops->ndo_start_xmit(skb, dev); } /* net/ipv4/ip_gre.c * 这个文件中有这样的赋值语句:ndo_start_xmit = ipgre_tunnel_xmit, * */ static netdev_tx_t ipgre_tunnel_xmit(struct sk_buff *skb, struct net_device *dev) { IPTUNNEL_XMIT(); } /* include/net/ipip.h * */ #define IPTUNNEL_XMIT() do {/ err = ip_local_out(skb);/ } while (0) /*net/ipv4/ip_output.c * */ int ip_local_out(struct sk_buff *skb) { err = __ip_local_out(skb); } int __ip_local_out(struct sk_buff *skb) { return nf_hook(NFPROTO_IPV4, NF_INET_LOCAL_OUT, skb, NULL, skb_dst(skb)->dev, dst_output); } /* * 通过LOCAL_OUT包过滤函数后进入ip_output()函数 * 进入如上ip_output() ---> dev_hard_start_xmit()的过程循环 */

你可能感兴趣的:(struct,filter,redirect,hook,DST,output)