我需要知道如何列出所有路由表的 ID。例如,我可以运行:
ip rule add fwmark 2 table 104
ip route add dev eth0 default via 192.168.3.7 table 104
呼吁ip rule list
演出:
0: from all lookup local
32765: from all fwmark 0x2 lookup 104
32766: from all lookup main
32767: from all lookup default
并呼吁大家关注ip route show table 104
:
default via 192.168.3.7 dev eth0
如果我随后调用ip rule del table 104
,则后续调用会ip rule list
显示:
0: from all lookup local
32766: from all lookup main
32767: from all lookup default
但是,调用ip route show table 104
仍然显示:
default via 192.168.3.7 dev eth0
我知道我可以使用 刷新表ip route flush table 104
。我希望能够刷新所有不是 、 和 的表local
。main
因此default
我希望能够列出现有表。
我见过有人使用cat /etc/iproute2/rt_tables
,但这只会产生:
#
# reserved values
#
255 local
254 main
253 default
0 unspec
#
# local
#
#1 inr.ruhep
我该怎么做才能获取当前存在的所有表名?提前致谢!
答案1
有一种方法可以列出所有表的所有路由条目。ip route show table all
使用一些 shell 管道魔法,您可以提取所有表名和 ID,如下所示:
ip route show table all | grep "table" | sed 's/.*\(table.*\)/\1/g' | awk '{print $2}' | sort | uniq
或者
ip route show table all | grep -Po 'table \K[^\s]+' | sort -u
如果您只关心数字表名称,请添加一些 grep 过滤:
ip route show table all | grep "table" | sed 's/.*\(table.*\)/\1/g' | awk '{print $2}' | sort | uniq | grep -e "[0-9]"
或者
ip route show table all | grep -Po 'table \K[^\s]+' | sort -u | grep -e "[0-9]"
答案2
我该怎么做才能获取当前存在的所有表名?
该文件/etc/iproute2/rt_tables
是表的唯一来源名称在系统上。在内部,路由表具有整数标识符。
您的问题的其余部分有点令人困惑。如果某个表未被规则引用,则它实际上被“删除”,因为它对系统的路由没有影响。因此,您可以列出所有积极的路由表如下:
ip rule list | awk '/lookup/ {print $NF}'
查找lookup
路由规则中的所有操作并打印目标。
路由表似乎由 64 位整数标识。如果您真的想找到所有具有规则的路由表,即使是对您的系统没有影响的非活动路由表,您也可以简单地从 1 到 2^64 进行循环迭代:
seq 0 $(echo '2 64 ^ p' | dc) | xargs -iTABLE sh -c 'echo === TABLE ===; ip route show table TABLE'
...但是这将需要永远的时间,因为 64 位覆盖了很大的空间。
答案3
(egrep '^\s*[0-9]' /etc/iproute2/rt_tables | awk '{print $2}' | sort -u; ip rule list | awk '/lookup/ {print $NF}' | sort -u; ip route show table all | sed 's/.*\(table.*\)/\1/g' | awk '{if($0 ~ /table/) print $2; else print "main";}' | sort -u) | sort | uniq -c
感谢这个线程引出了这个组合,它显示了当前包含路由、被规则引用和命名的所有路由表,每个有内容、被引用和被命名的表旁边都有一个 3,或者如果三个条件中的一个或两个适用,则有一个 2 或 1。
答案4
这是我根据从此线程收集的信息编写的脚本。它适用于运行 Marshmallow 6.0.1 的旧 Note 5(设置为可轻松复制/粘贴到运行 su 的 adb shell 终端中)
# Tested on Samsung Galaxy Note5 running Android Marshmallow 6.0.1 - needs root and termux app installed
# Must be run as root
# Termux app must be installed so column will work. This first line adds termux to the search path for the current console session - probably not necessary if you are typing all this into the termux app on the device
export PATH=$PATH:/data/data/com.termux/files/usr/bin:/data/data/com.termux/files/usr/bin/applets; export LD_LIBRARY_PATH=/data/data/com.termux/files/usr/lib; \
echo -e "\nRouting table names and where they are present and populated:"; (echo "Table Name,\"ip rule list\",\"ip route show table <name>\",\"/data/misc/net/rt_tables\""; (egrep '^\s*[0-9]' /data/misc/net/rt_tables | awk '{print $2 ",file"}' | sort -u; ip rule list | awk '/lookup/ {print $NF ",rule"}' | sort -u; ip route show table all | sed 's/.*\(table.*\)/\1/g' | awk '{{if($0 ~ /table/) printf $2; else printf "main";}; print ",route"}' | sort -u) | sort | awk 'BEGIN{FS=","} {dnames[$1]=1; if($2=="file"){dfile[$1]=1}; if($2=="rule"){drule[$1]=1}; if($2=="route"){droute[$1]=1};} END {for (name in dnames) {printf name; printf "," ; if(drule[name]==1){printf "rule"}; printf "," ; if(droute[name]==1){printf "route"}; printf "," ; if(dfile[name]==1){printf "file"};print "" }}' |sort )| column -t -s',' -o' | '
输出如下所示:
Routing table names and where they are present and populated:
Table Name | "ip rule list" | "ip route show table <name>" | "/data/misc/net/rt_tables"
0 | | route |
1 | rule | route |
61 | rule | route |
legacy_network | rule | | file
legacy_system | rule | route | file
local | rule | route | file
local_network | rule | route | file
main | rule | route | file
rmnet0 | rule | route | file
rmnet1 | rule | route | file
以下是适用于 CentOS 7 的相同脚本:
# Tested on CentOS 7
echo -e "\nRouting table names and where they are present and populated:"; (echo "Table Name,\"ip rule list\",\"ip route show table <name>\",\"/etc/iproute2/rt_tables\""; (egrep '^\s*[0-9]' /etc/iproute2/rt_tables | awk '{print $2 ",file"}' | sort -u; ip rule list | awk '/lookup/ {print $NF ",rule"}' | sort -u; ip route show table all | sed 's/.*\(table.*\)/\1/g' | awk '{{if($0 ~ /table/) printf $2; else printf "main";}; print ",route"}' | sort -u) | sort | awk 'BEGIN{FS=","} {dnames[$1]=1; if($2=="file"){dfile[$1]=1}; if($2=="rule"){drule[$1]=1}; if($2=="route"){droute[$1]=1};} END {for (name in dnames) {printf name; printf "," ; if(drule[name]==1){printf "rule"}; printf "," ; if(droute[name]==1){printf "route"}; printf "," ; if(dfile[name]==1){printf "file"};print "" }}' |sort )| column -t -s',' -o' | '