本文发自 http://www.binss.me/blog/learning-computer-network-by-the-output-of-ifconfig/,转载请注明出处。
在折腾linux的过程中,有不止100个新名词蹦跶到我面前,而我却由于还有砖还要搬而无可奈何,只能把其先记到小本本里。最近趁着闲下来把这些词进行了归类,并一一查阅资料,最后结合自身的理解,通过文章的形式进行知识的沉淀。本篇主要以ifconfig的输出为例,对Linux的网络设备进行说明。
在计算机网络课上,我学习到主要的网络设备有以下这些:
网卡(Network Interface Card,NIC)
又称网络适配器(Network Adapter),是一块用于计算机网络通讯的基础硬件,属于OSI模型的第一层(Physical)和第二层(Data Link)。一般来说,其通过唯一的MAC地址来标识自己。
常见的网卡可达到10/100/1000Mbits/sMbps),这就是我们常说的百兆、千兆网卡。常用的标准有Ethernet(有线网卡)和Wi-Fi(无线网卡)。
中继器(Repeater)
一种将输入信号增强放大的硬件设备。它工作于OSI模型的第一层(Physical)。它通过对数据信号的重新发送或者转发,来扩大数据的传输距离。
网桥(Network Bridge)
又称桥接器,是一种用于网络桥接的硬件设备。它工作于OSI模型的第二层(Data Link)。
网桥将网络的多个网段在数据链路层连接起来。相对于中继器只是简单地转发信号,网桥在对帧进行转发时,根据其存储的MAC table进行过滤,只转发MAC地址在table内的帧。
由于交换机的普及,网桥已经很少见了。
路由器(Router)
又称网关(Gateway),是一种用于网络路由硬件设备。它工作于OSI模型的第三层(Network)。
提供路由与转发两种功能,即可以决定数据包从来源端到目的端所经过的路由路径(host到host之间的传输路径),也可以在内部把输入端的数据包移送至适当的输出端。
路由器中维护着一张路由表,记录着有去往不同网络地址应送往的端口号。当一台路由器收到一个IP数据包时,它将根据数据包中的目的IP地址项查找路由表,根据查找的结果将此IP数据包送往对应端口。
交换机(Switch)
交换机能为子网中提供更多的连接端口,以便连接更多的电脑。
这个种类就多了,目前有二层交换机(Data link),相当于强化版网桥;三层交换机(Network),有一定的路由功能,还有四层交换机(transport)和七层交换器。
以上这些设备概念,是我们分析ifconfig的输出的基础。让我们查看下本机(ubuntu 14.04)上的网络设备:
$ ifconfig
docker0 Link encap:Ethernet HWaddr 02:42:c5:73:4c:74
inet addr:172.17.42.1 Bcast:0.0.0.0 Mask:255.255.0.0
inet6 addr: fe80::42:c5ff:fe73:4c74/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:19 errors:0 dropped:0 overruns:0 frame:0
TX packets:3 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:1300 (1.3 KB) TX bytes:258 (258.0 B)
eth0 Link encap:Ethernet HWaddr f2:3c:91:18:9f:1e
inet addr:106.186.116.111 Bcast:106.186.116.255 Mask:255.255.255.0
inet6 addr: fe80::f03c:91ff:fe18:9f1e/64 Scope:Link
inet6 addr: 2400:8900::f03c:91ff:fe18:9f1e/64 Scope:Global
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:505691 errors:0 dropped:0 overruns:0 frame:0
TX packets:371319 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:580961694 (580.9 MB) TX bytes:532954539 (532.9 MB)
eth0:1 Link encap:Ethernet HWaddr f2:3c:91:18:9f:1e
inet addr:192.168.192.143 Bcast:0.0.0.0 Mask:255.255.128.0
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:11992 errors:0 dropped:0 overruns:0 frame:0
TX packets:11992 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:2477900 (2.4 MB) TX bytes:2477900 (2.4 MB)
veth741a889 Link encap:Ethernet HWaddr 92:94:59:84:6e:e8
inet6 addr: fe80::9094:59ff:fe84:6ee8/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:8 errors:0 dropped:0 overruns:0 frame:0
TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:648 (648.0 B) TX bytes:648 (648.0 B)
eth开头的是网卡:eth0 表示第一块网卡
Link encap:Ethernet HWaddr f2:3c:91:18:9f:1e
连接类型为Ethernet ,网卡的MAC地址为 f2:3c:91:18:9f:1e
inet addr:106.186.116.111 Bcast:106.186.116.255 Mask:255.255.255.0
网卡的IPv4地址为106.186.116.111,广播地址为106.186.116.255,掩码为255.255.255.0
inet6 addr: fe80::f03c:91ff:fe18:9f1e/64 Scope:Link
inet6 addr: 2400:8900::f03c:91ff:fe18:9f1e/64 Scope:Global
网卡的IPv6本地链路地址为fe80::f03c:91ff:fe18:9f1e/64(内网使用,路由器不会转发包含它的包),全局地址为2400:8900::f03c:91ff:fe18:9f1e/64(任何网络下使用)
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
Ethernet接口的相关内核模块已加载,支持广播,网卡处于就绪状态,支持组播,最大传输单元(包)为1500字节,权值(越低越高,然而用ifconfig设并不会起作用)
RX packets:505691 errors:0 dropped:0 overruns:0 frame:0
接收数据包总数、出错数、丢弃数(系统原因丢弃)、丢弃数(网卡的fifo已满丢弃)、frame alignment错误数
TX packets:371319 errors:0 dropped:0 overruns:0 carrier:0
发送数据包总数、出错数、丢弃数(系统原因丢弃)、丢弃数(网卡的fifo已满丢弃),丢失carriers数
collisions:0 txqueuelen:1000
冲突包数(可体现网络拥塞程度)为0,发送队列的长度
RX bytes:580961694 (580.9 MB) TX bytes:532954539 (532.9 MB)
接收的总流量为580.9 MB,发送的总流量为532.9 MB
eth0:1 Link encap:Ethernet HWaddr f2:3c:91:18:9f:1e
inet addr:192.168.192.143 Bcast:0.0.0.0 Mask:255.255.128.0
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
eth0虚拟出来的一块网卡,其MAC地址为f2:3c:91:18:9f:1e,用于分配给eth0第2个IP:192.168.192.143(内网)
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:11992 errors:0 dropped:0 overruns:0 frame:0
TX packets:11992 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:2477900 (2.4 MB) TX bytes:2477900 (2.4 MB)
lo开头为loop设备:
它是一个指向本机(127.0.0.1)的设备,一般是用来作网络应用的自测,从而避免了局域网和外网的其它主机或用户的访问。
和eth的不同之处还有:
-
MTU非常大,因为是发给本机,所以不用担心缓冲区满之类的拥塞问题。
-
发送包数等于接收包数,发送总流量等于接收总流量,因为是自发自收。
-
txqueuelen为0,因为根本无需队列(?)。
然后我们还发现有叫docker0和veth741a889的设备,这些是什么呢?在对其进行分析之前,我们先了解下Linux中的虚拟设备:
在Linux中,如何进行网络的虚拟化?换句话说,如果新建一台虚拟机,那么虚拟机的网卡从何而来?答案是通过软件模拟一个。随着虚拟化技术的发展,越来越多的虚拟设备被加入了Linux。 再次强调,不同于之前介绍的网络设备是一个独立的硬件,虚拟设备完全由软件实现。
虚拟网卡(virtual network interface,VIF)
虚拟网卡通过实现一个字符设备来支持物理层,从而使应用层和物理层就通过这个字符设备联系起来,从这个字符设备读出来的就是虚拟网卡发往物理层的字节流,写入字符设备的数据作为字节流被虚拟网卡接收。
虚拟网卡可以像网卡一样进行配置,常见的虚拟网卡可有TUN/TAP和VEth。
TUN/TAP(Tunnel)
TUN工作在OSI第三层(network),实现了IP包的转发,相当于路由。
TAP工作在OSI第二层(data link),实现了Ethernet帧的转发,相当于网桥。
操作系统通过TUN/TAP设备向绑定该设备的用户空间的程序发送数据,反之,用户空间的程序也可以像操作硬件网络设备那样通过TUN/TAP设备发送数据,然后TUN/TAP设备会向操作系统的网络栈push(或inject)数据包,从而模拟从外部接受数据的过程。
TUN常用于VPN,通过使用TUN,VPN能够在IP包被发出去之前将其进行加密。
TAP常用于虚拟机,为虚拟机提供网卡。
创建tap
ip tuntap add mode tap
创建tun
ip tuntap add mode tun
VEth(Virtual Ethernet)
VEth是成对出现的,它的作用是反转通讯数据的方向,当数据从网络栈发送到VEth的一端时,数据被传送到VEth的另外一端流出,然后放回网络栈,相当于把需要接受的数据转换成需要发送的数据,
常用于虚拟化中穿透network namespace,把从一个 network namespace 发出的数据包转发到另一个 namespace。
创建一对VEth,名为veth1和veth2
ip link add veth1 type veth peer name veth2
虚拟网桥
Bridge也是一种虚拟设备,用于将多块网卡(包括虚拟网卡)连接起来。
值得注意的是, Linux中虚拟网桥是通用网络设备抽象的一种,能够绑定IP 地址。因此在把网卡接入到网桥上后,网卡原来绑定的IP会失效,如果还要像原来那样收发数据,需要把该IP绑定到网桥上。
添加网桥br0
ip link add br0 type bridge
把网卡接入网桥,在把eth0和eth1接入到br0后,两个网卡就可以进行通信了。
ip link set eth0 master br0
ip link set eth1 master br0
为网桥绑定ip
ip addr add xx.xx.xx.xx/xx dev br0
我们看回ifconfig的输出:
docker0 Link encap:Ethernet HWaddr 02:42:c5:73:4c:74
inet addr:172.17.42.1 Bcast:0.0.0.0 Mask:255.255.0.0
UP BROADCAST MULTICAST MTU:1500 Metric:1
RX packets:0 errors:0 dropped:0 overruns:0 frame:0
TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:0 (0.0 B) TX bytes:0 (0.0 B)
veth741a889 Link encap:Ethernet HWaddr 92:94:59:84:6e:e8
inet6 addr: fe80::9094:59ff:fe84:6ee8/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:8 errors:0 dropped:0 overruns:0 frame:0
TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:648 (648.0 B) TX bytes:648 (648.0 B)
通过ethtool可以查看设备的类型:
$ ethtool -i docker0
driver: bridge
version: 2.3
firmware-version: N/A
bus-info: N/A
supports-statistics: no
supports-test: no
supports-eeprom-access: no
supports-register-dump: no
supports-priv-flags: no
同理可以知道veth741a889为VEth设备。
通过观察,我发现docker0网桥随着docker的启动而启动,而VEth设备在容器启动的时候才动态创建。根据官方文档,Docker通过docker0网桥在内核层连通了其他的物理或虚拟网卡,从而将所有容器和宿主都放到同一个物理网络下。每次启动一个容器的时候,Docker会新建一对VETH设备,其中一个插在docker0上,另一个插在该容器里,然后从可用的地址段中选择一个空闲的IP地址分配给容器的VEth,使用docker0的IP作为默认网关,从而实现宿主机和容器的双向数据通讯。
我们可以验证一下:
$ ethtool -S veth741a889
NIC statistics:
peer_ifindex: 23
$ ip link
24: veth741a889: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default
link/ether 92:94:59:84:6e:e8 brd ff:ff:ff:ff:ff:ff
可以查到在宿主机上veth741a889的peer_ifindex为24,和它相对应的VEth设备的peer_ifindex为23。
然后我们进入容器查询:
root@4c04df175784:/# ip route show
default via 172.17.42.1 dev eth0
172.17.0.0/16 dev eth0 proto kernel scope link src 172.17.0.1
root@4c04df175784:/# ifconfig
eth0 Link encap:Ethernet HWaddr 02:42:ac:11:00:05
inet addr:172.17.0.5 Bcast:0.0.0.0 Mask:255.255.0.0
inet6 addr: fe80::42:acff:fe11:5/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:8 errors:0 dropped:0 overruns:0 frame:0
TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:648 (648.0 B) TX bytes:648 (648.0 B)
root@4c04df175784:/# ethtool -S eth0
NIC statistics:
peer_ifindex: 24
root@4c04df175784:/# ethtool -i eth0
driver: veth
version: 1.0
firmware-version:
bus-info:
supports-statistics: yes
supports-test: no
supports-eeprom-access: no
supports-register-dump: no
supports-priv-flags: no
从这里可以看出veth741a889的“伙伴”确实是在容器中,被重命名为eth0作为容器的网卡,并绑定了ip172.17.0.5,网关为网桥的ip172.17.42.1。
至此,ifconfig的输出认识完毕。
1F zhikun 8 years, 1 month ago 回复
强!