Linux 路由三大件

对于 Linux 网络,好奇心强的同学一定思考过两个问题:

 

  • 当我们发出一个包的时候,Linux 是如何决策该从哪个网卡(假设有多个网卡)、哪个下一跳发出这个包,用什么 IP 作为 source......
  • 当 Linux 收到一个包时,又是如何决定往哪里送的,是发送给本地程序、其他虚拟接口,还是转发到其他机器......

今天,我们就来分析这两个问题的核心所在:路由。

我们学习计算机网络的时候,一般都会了解到基于目的地址(cidr)的路由(ip route),但是在 Linux 2.0 之后,RPDB (Routing Policy DataBase)诞生了,引入了更丰富的路由策略(ip rule)。除此以外,我们还可以通过 iptables 来操纵数据包,作为路由策略实施的依据,间接地影响路由过程。

至此,我们就认识了 Linux 路由的三大件。那么,三大件分别是什么原理,又是是如何交互的呢?且看下文分析。

注:虽然 Linux 提出了 nftables 来替换 iptables,但 iptables 仍然是事实上的标准

RPDB

首先我们来看看 RPDB,RPDB 由两部分组成,一个是 rule 列表,一个是 routing table 列表。

rule

ip rule 命令可以展示所有的 rule,每个 rule 由 selector(依据什么特征选择包) 和对应 action(对包做什么) 组成。

selector 主要有几种类型:

  • 出/入接口的 index,如 eth0、eth1
  • fwmark: 包携带的标记
  • Tunnel id
  • src/dst addr/port
  • type of service
  • priority
  • ......

action 主要由几种类型:

  • 传递给特定的 route
  • 跳转到其它的 rule
  • Drop/reject 这个包
  • ......

routing table

routing table 最开始只有一个,RPDB 后引入了多个(可以通过 cat /etc/iproute2/rt_tables 查看),默认有三个:

  • local,dst 为本地或者广播地址的路由
  • main,默认的路由
  • default,一般为空,为后处理预留空间

ip route 命令默认展示的是 main table,ip route show table local 形式可以展示其它 table。

routing table 里面每个 route 代表了 dst 为某个/些/类地址 的数据包应该 通过哪个渠道 转发。route 由几部分组成:

  • types
    • unicast,单播,最常见
    • unreachable,丢包并返回 ICMP 消息
    • blackhole, 默默丢包
    • ......
  • socpe,目标地址的范围: cat /etc/iproute2/rt_scopes,默认有三个
    • link,只在本设备有效,通常是直连
    • host,只在本机有效
    • global,全局有效,可传播,是默认值
    • ......
  • proto,路由由谁创建和维护: /etc/iproute2/rt_protos,默认有三个
    • kernel,内核创建,长期有效
    • boot,临时的
    • static,手动创建,override 动态路由(由路由协议维护entry)
    • ......
  • preference,优先级,一般都是数字越小,优先级越高
  • dev,通过的设备名字,如 eth0
  • nexthop,下一跳
  • src,设置发出包的 src ip
  • ......

RPDB 运行逻辑

参考 fib_lookup 函数:如果你没有动过 RPDB,那么直接用 mian table 进行路由查找(fib_table_lookup)了;如果动过,则通过 __fib_lookup/fib_rules_lookup 进行 rule 匹配,匹配逻辑为:

  • 无论是出还是入方向的每个包,都会遍历所有 rule,按照 priority,由 0 开始
  • 第一个匹配的 rule 会执行 action
  • 如果 action 是 lookup route table,则用对应 table 进行路由查找(fib_table_lookup),如果查找失败,则继续执行下一个 rule
  • 如果没有任何 rule 匹配,则报错

路由查找逻辑为:

  • 最长前缀匹配(也是被认为最精准的)的 route 被选中
  • 如果有多个匹配,则 preference、tos/dscp、自然顺序都会被进行考虑,最后仅剩一个匹配
  • 如果没有匹配,则返回 rule 匹配,继续检查下一个 rule

iptables

iptables 主要用于包过滤、修改和 NAT。再次拿出下面这张神图,来阐释它五大表和五大链,及其生效顺序和范围:

 资料直通车:Linux内核源码技术学习路线+视频教程内核源码

学习直通车:Linux内核源码内存调优文件系统进程管理设备驱动/网络协议栈

三大件的交互过程

了解了各自原理之后,我们当然想知道它们是怎么交互的。上面那张图实际上已经阐释了他们之间的交互,不过下面这张图能看得更清晰:

原图:http://www.adminsehow.com/2011/09/iptables-packet-traverse-map/

实践

这是一个完全没动过的环境:

我们现在来设计一个需求:源端口为 30300 的包,默默丢弃;源端口为 30301 的包,丢弃并报错;源端口为 30302 的包,用新的 route table 转发。
先看看实施前的结果,用 http://taobao.com 来测试

nc -zv taobao.com 443 -p 30300
Connection to taobao.com (59.82.122.115) 443 port [tcp/https] succeeded!
nc -zv taobao.com 443 -p 30301
Connection to taobao.com (106.11.226.158) 443 port [tcp/https] succeeded!
nc -zv taobao.com 443 -p 30302
Connection to taobao.com (106.11.226.158) 443 port [tcp/https] succeeded!

虽然实现这个需求有很多方式,但是我这里为了演示三大件的交互而选择了下面的这种方式:

首先需要标记这三种类型的包,由于是本地发包,我们采用 mangle output

iptables -A OUTPUT -t mangle -o enp0s1 -p tcp --sport 30300 -j MARK --set-mark 1
iptables -A OUTPUT -t mangle -o enp0s1 -p tcp --sport 30301 -j MARK --set-mark 2
iptables -A OUTPUT -t mangle -o enp0s1 -p tcp --sport 30302 -j MARK --set-mark 3

iptables -t mangle -L 展示,iptables -t mangle -F 清理。

然后增加相应的 route table

echo 2 custom >> /etc/iproute2/rt_tables
ip route add default via 192.168.64.1 dev enp0s1 src 192.168.64.4 table custom

以及 rule

ip rule add from all fwmark 1 blackhole
ip rule add from all fwmark 2 prohibited
ip rule add from all fwmark 3 table custom

结果发现 30302 依然能通,但是 30300 和 30301 都超时了,没看出来返回的错误。
采用 traceroute 的 tcp 模式作为测试工具则能够看出一些差别。

ip rule add from all fwmark 2 unreachable 对应结果也确实符合期望

traceroute -T --sport=30301 --port=443 tabao.com
traceroute to tabao.com (128.14.151.194), 30 hops max, 60 byte packets
send: Network is unreachable

原文作者:九零后程序员

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/68709.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Qt+C++自定义控件仪表盘动画仿真

程序示例精选 QtC自定义控件仪表盘动画仿真 如需安装运行环境或远程调试&#xff0c;见文章底部个人QQ名片&#xff0c;由专业技术人员远程协助&#xff01; 前言 这篇博客针对<<QtC自定义控件仪表盘动画仿真>>编写代码&#xff0c;代码整洁&#xff0c;规则&…

企业有VR全景拍摄的需求吗?能带来哪些好处?

在传统图文和平面视频逐渐疲软的当下&#xff0c;企业商家如何做才能让远在千里之外的客户更深入、更直接的详细了解企业品牌和实力呢&#xff1f;千篇一律的纸质材料已经过时了&#xff0c;即使制作的再精美&#xff0c;大家也会审美疲劳&#xff1b;但是你让客户远隔千里&…

机器人CPP编程基础-05完结The End

非常不可思议……之前四篇博文竟然有超过100的阅读量…… 此文此部分终结&#xff0c;没有继续写下去的必要了。 插入一个分享&#xff1a; 编程基础不重要了&#xff0c;只要明确需求&#xff0c;借助AI工具就能完成一个项目。 当然也不是一次成功&#xff0c;工具使用也需要…

docker安装及优化详解

目录 一、部署20版的docker 1.1 安装依赖包 1.2 设置阿里云镜像源 1.3 安装docker-ce 社区版 1.4 关闭增强机制 1.5 开启服务 1.6 设置镜像加速 1.7 网络优化 二、linux 系统中的命令 记10条(cd ls pwd mv cp ) 2.1 查询docker 版本 2.2 搜索镜像 2.3 技能点 2.…

2023年网络安全比赛--综合渗透测试(超详细)

一、竞赛时间 180分钟 共计3小时 二、竞赛阶段 竞赛阶段 任务阶段 竞赛任务 竞赛时间 分值 1.扫描目标靶机将靶机开放的所有端口,当作flag提交(例:21,22,23); 2.扫描目标靶机将靶机的http服务版本信息当作flag提交(例:apache 2.3.4); 3.靶机网站存在目录遍历漏洞,请将…

【百度翻译api】中文自动翻译为英文

欸&#xff0c;最近想做一些nlp的项目&#xff0c;做完了中文的想做做英文的&#xff0c;但是呢&#xff0c;国内爬虫爬取的肯定都是中文 &#xff0c;爬取外网的技术我没有尝试过&#xff0c;没有把握。所以我决定启用翻译&#xff0c;在这期间chatGPT给了我非常多的方法&…

力扣 198. 打家劫舍

题目来源&#xff1a;https://leetcode.cn/problems/house-robber/description/ C题解&#xff1a;因为是间接偷窃&#xff0c;所以偷nums[i]家前&#xff0c;一定偷过第i-2或者i-3家&#xff0c;因为i-1不能偷。 例如12345共5家&#xff0c;先偷第1家&#xff0c;那么2不能偷…

Linux / Ubuntu磁盘扩容

测试时遇到了shell脚本执行错误的问题&#xff0c;找到脚本编写的楼哥&#xff0c;才发现自己给虚拟机的磁盘已经满了&#xff0c;没想到啊&#xff0c;业务的解压操作&#xff0c;这么费磁盘&#xff0c;那就需要进行磁盘的扩展&#xff0c;记录一下 1、首先停掉虚拟机&#…

Visual Studio 如何放大代码字体的大小

1.打开Visual Studio&#xff0c;新建一个程序&#xff0c;一段代码&#xff0c;为接下去的操作做好准备。单击菜单栏的【工具】选项。 2.在跳出来菜单中找到【选项】&#xff08;一般在最后一项&#xff09;&#xff0c;然后单击。跳出新的窗口。 3.跳出新的窗口后&#xff…

Ubuntu 连接海康智能相机步骤(亲测,成功读码)

ubuntu20.04下连接海康智能相机 Ubuntu 连接海康智能相机步骤(亲测&#xff0c;已成功读码)输出的结果 Ubuntu 连接海康智能相机步骤(亲测&#xff0c;已成功读码) (就是按照海康的提供的步骤和源码连接相机&#xff0c;流水账) 安装Ubuntu20.04安装gcc和g&#xff0c;IDmvs只…

ansible的playbook剧本

playbook剧本 PlayBook1.playbooks 本身由以下各部分组成2.示例&#xff1a;3.运行playbook补充参数&#xff1a; 4.定义、引用变量5.指定远程主机sudo切换用户6.when条件判断7.迭代8.Templates 模块1.先准备一个以 .j2 为后缀的 template 模板文件&#xff0c;设置引用的变量2…

ICLR2020 Query2Box:基于BOX嵌入的向量空间知识推理8.15

Query2Box&#xff1a;基于BOX嵌入的向量空间知识推理 摘要介绍 摘要 在大规模不完全知识图谱上回答复杂的逻辑查询是一项基础性但具有挑战性的任务。最近&#xff0c;一种解决这个问题的很有前途的方法是将KG实体和查询嵌入到向量空间中&#xff0c;这样回答查询的实体紧密嵌…