4、容器虚拟化网络概述

Docker 网络

Docker 的网络实现其实就是利用了 Linux 上的网络名称空间和虚拟网络设备(特别是 veth pair)。

Linux 网络命名空间:https://www.jianshu.com/p/369e50201bce

Linux虚拟网络设备之veth: https://segmentfault.com/a/1190000009251098

监控和调整Linux网络堆栈:接收数据:https://blog.packagecloud.io/eng/2016/06/22/monitoring-tuning-linux-networking-stack-receiving-data/

Linux网络-数据包的发送过程:https://segmentfault.com/a/1190000008926093

Docker网络核心原理   http://blog.51cto.com/ganbing/2087598

 

基本原理

首先,要实现网络通信,机器需要至少一个网络接口(物理接口或虚拟接口)来收发数据包;此外,如果不同子网之间要进行通信,需要路由机制。

Docker 中的网络接口默认都是虚拟的接口。虚拟接口的优势之一是转发效率较高。Linux 通过在内核中进行数据复制来实现虚拟接口之间的数据转发,发送接口的发送缓存中的数据包被直接复制到接收接口的接收缓存中。

对于本地系统和容器内系统看来就像是一个正常的以太网卡,只是它不需要真正同外部网络设备通信,速度要快很多。

Docker 容器网络就利用了这项技术。它在本地主机和容器内分别创建一个虚拟接口,并让它们彼此连通(这样的一对接口叫做 veth pair)。

 

veth设备的特点

 

  • veth和其它的网络设备都一样,一端连接的是内核协议栈。
  • veth设备是成对出现的,另一端两个设备彼此相连
  • 一个设备收到协议栈的数据发送请求后,会将数据发送到另一个设备上去。

 

参考自  http://blog.51cto.com/ganbing/2087598    https://segmentfault.com/a/1190000009251098

使用docker run命令创建一个执行shell(/bin/bash)的Docker容器,假设容器名称为con1。
     在con1容器中可以看到它有两个网卡lo和eth0。lo设备不必多说,是容器的回环网卡;eth0即为容器与外界通信的网卡,eth0的ip 为 172.17.0.2/16,和宿主机上的网桥docker0在同一个网段。

     查看con1的路由表,可以发现con1的默认网关正是宿主机的docker0网卡,通过测试, con1可以顺利访问外网和宿主机网络,因此表明con1的eth0网卡与宿主机的docker0网卡是相互连通的。

     这时再来查看(ifconfig)宿主机的网络设备,会发现有一块以"veth"开头的网卡,如veth60b16bd,我们可以大胆猜测这块网卡肯定是veth设备了,而veth pair总是成对出现的。veth pair通常用来连接两个network namespace,

     那么另一个应该是Docker容器con1中的eth0了。之前已经判断con1容器的eth0和宿主机的docker0是相连的,那么veth60b16bd也应该是与docker0相连的,不难想到,docker0就不只是一个简单的网卡设备了,而是一个网桥。

     真实情况正是如此,下图即为Docker默认网络模式(bridge模式)下的网络环境拓扑图,创建了docker0网桥,并以eth pair连接各容器的网络,容器中的数据通过docker0网桥转发到eth0网卡上。

    这里的网桥概念等同于交换机,为连在其上的设备转发数据帧。网桥上的veth网卡设备相当于交换机上的端口,可以将多个容器或虚拟机连接在上面,这些端口工作在二层,所以是不需要配置IP信息的。

    图中docker0网桥就为连在其上的容器转发数据帧,使得同一台宿主机上的Docker容器之间可以相互通信。


    大家应该注意到docker0既然是二层设备,它上面怎么设置了IP呢?docker0是普通的linux网桥,它是可以在上面配置IP的,可以认为其内部有一个可以用于配置IP信息的网卡接口

   (如同每一个Open vSwitch网桥都有一个同名的内部接口一样)。在Docker的桥接网络模式中,docker0的IP地址作为连于之上的容器的默认网关地址存在。

在Linux中,可以使用brctl命令查看和管理网桥(需要安装bridge-utils软件包),比如查看本机上的Linux网桥以及其上的端口:

# yum install bridge-utils

# brctl show   //四个虚拟接口

bridge name    bridge id            STP enabled    interfaces
docker0        8000.02428f0e6a12    no             veth6a95f3bveth6d97324veth7314b3evethb2e752fvethdb62bce

更多关于brctl命令的功能和用法,大家通过man brctl或brctl --help查阅。

    docker0网桥是在Docker daemon启动时自动创建的,其IP默认为172.17.0.1/16,之后创建的Docker容器都会在docker0子网的范围内选取一个未占用的IP使用,并连接到docker0网桥上。

    除了使用docker0网桥外,还可以使用自己创建的网桥,比如创建一个名为br0的网桥,配置IP:

# ip link show    //veth7314b3e和if8是一对

1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
2: ens33: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP mode DEFAULT group default qlen 1000link/ether 00:0c:29:ee:53:1e brd ff:ff:ff:ff:ff:ff
3: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP mode DEFAULT group default link/ether 02:42:8f:0e:6a:12 brd ff:ff:ff:ff:ff:ff
9: veth7314b3e@if8: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default link/ether 42:a0:eb:96:15:cf brd ff:ff:ff:ff:ff:ff link-netnsid 0
11: vethb2e752f@if10: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default link/ether 5a:8e:fa:1c:7f:8d brd ff:ff:ff:ff:ff:ff link-netnsid 1
13: veth6d97324@if12: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default link/ether 4a:2f:07:20:53:15 brd ff:ff:ff:ff:ff:ff link-netnsid 2
17: vethdb62bce@if16: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default link/ether 8a:1a:78:56:07:d8 brd ff:ff:ff:ff:ff:ff link-netnsid 3
19: veth6a95f3b@if18: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default link/ether aa:02:b6:a3:44:87 brd ff:ff:ff:ff:ff:ff link-netnsid 4

 

iptables规则
 Docker安装完成后,将默认在宿主机系统上增加一些iptables规则,以用于Docker容器和容器之间以及和外界的通信,可以使用iptables-save命令查看。其中nat表中的POSTROUTING链有这么一条规则:

-A POSTROUTING -s 172.17.0.0/16 ! -o docker0 -j MASQUERADE

参数说明:
-s :源地址172.17.0.0/16
-o:指定数据报文流出接口为docker0
-j :动作为MASQUERADE(地址伪装)

   上面这条规则关系着Docker容器和外界的通信,含义是:将源地址为172.17.0.0/16的数据包(即Docker容器发出的数据),当不是从docker0网卡发出时做SNAT。

    这样一来,从Docker容器访问外网的流量,在外部看来就是从宿主机上发出的,外部感觉不到Docker容器的存在。
   那么,外界想到访问Docker容器的服务时该怎么办呢?我们启动一个简单的web服务容器,观察iptables规则有何变化。

 

OVS:全称是Open VSwitch,就是一个虚拟交换机,用于虚拟机VM环境。在虚拟化环境中,一个虚拟交换机主要有两个作用:传递虚拟机VM之间的通信,以及实现VM和外界网络的通信。

OVS主要由以下4层组成:

虚拟网卡:位于虚拟机内,在虚拟机创建后,会挂载在OVS上,每个虚拟网卡都有不同的MAC地址。

虚拟交换层:通过2个ovs虚拟交换机完成通信。OVS除提供基本网络交换外,还提供一些高级功能,如NetFlow等。

bond层:bond是由linux提供的将多个物理网卡绑定在一起的技术,另一种说法叫trunk。Bond模式主要有:负载平衡、主备模式。目前主要使用的是主备模式,在主备模式下,有一个网卡是主用状态,其它网卡均是备用状态。这一层是可选的,如果没有这一层,物理网卡可以直接挂在ovs上。

物理网卡:真正执行收发包的物理设备,一般都会挂载在trunk上,常见的物理网卡有Intel 82599 10G网卡、Intel 82576 1G网卡、Intel I350 1G网卡、SIGMA mellanox 10G网卡。

按照这样的解释,应该就比较清楚了。

OVS与传统的硬件交换机工作原理也没什么区别,就是基于MAC地址实现报文的交换。

host   https://blog.csdn.net/wangguohe/article/details/81535942

容器不会获得一个独立的network namespace,而是与宿主机共用一个。
这里写图片描述

在容器中使用ifconfig查看网络发现显示的是宿主机的网络

host

父进程在创建子进程时,如果不使用```CLONE_NEWNET```这个参数标志,那么创建出的子进程会与父 进程共享同一个网络namespace。

Docker就是采用了这个简单的原理,在创建进程启动容器的过程中,没有传入CLONE_NEWNET参数标志,实现Docker Container与宿主机共享同一个网络环境,即实现host网络模式。

优势:

  • 可以直接使用宿主机的IP地址与外界进行通信,若宿主机的eth0是一个公有IP,那么容器也拥有这个公有IP。
  • 同时容器内服务的端口也可以使用宿主机的端口,无需额外进行NAT转换。

缺陷:

  • 最明显的是Docker Container网络环境隔离性的弱化,即容器不再拥有隔离、独立的网络栈。
  • 使用host模式的Docker Container虽然可以让容器内部的服务和传统情况无差别、无改造的使用,但是由于网络隔离性的弱化,该容器会与宿主机共享竞争网络栈的使用;
  • 容器内部将不再拥有所有的端口资源,原因是部分端口资源已经被宿主机本身的服务占用,还有部分端口已经用以bridge网络模式容器的端口映射。

none

获取独立的network namespace,但不为容器进行任何网络配置,之后用户可以自己进行配置,容器内部只能使用loopback网络设备,不会再有其他的网络资源。

创建docker网络

# docker network ls

NETWORK ID          NAME                DRIVER              SCOPE
5ebae7e509fa        bridge              bridge              local    //默认网络
b255b50dc21e        host                host                local
db26f5263d07        none                null                local

# docker container run --help

 --network string                 Connect a container to a network (default "default")   //string指明要使用哪个网络,默认是bridge

# docker network inspect bridge    //查看bridge的信息

# docker container inspect web1   //查看容器web1的详细信息

 

转载于:https://www.cnblogs.com/hanshanxiaoheshang/p/10397966.html

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

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

相关文章

Linux whoami命令、Linux su命令、Linux w命令

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 Linux whoami命令用于显示自身用户名称。 显示自身的用户名称&#xff0c;本指令相当于执行"id -un"指令。 语法 whoami […

Weekly 10

Algorithm 1.Remove Element What 移除数组中的指定元素,返回处理后的长度sum,并且数组前sum长度的元素为处理后的元素,不用额外数组&#xff0c;O(1)。How 用快慢指针,快指针遍历,遇到不等于指定元素的替换掉慢指针,然后慢指针前进一位即可。Key Codesclass Solution {public …

大数据计算:如何仅用1.5KB内存为十亿对象计数

摘要&#xff1a;AddThis的数据分析副总监Matt Abrams在High Scalability上发表了一篇文章&#xff0c;介绍了他们公司如何应对大数据。Matt Abrams表示&#xff0c;AddThis仅仅用了1.5KB内存的内存就计算了十亿个不同的对象&#xff0c;这与他们所使用的计算方法分不开的。 A…

C#关键字的个人理解与注释

C#关键字注释&#xff1a;abstract&#xff1a;抽象as&#xff1a;类型转换&#xff08;返回转换结果&#xff09;base&#xff1a;基类bool&#xff1a;布尔类型break&#xff1a;条件中断语句byte&#xff1a;字节case&#xff1a;条件语句catch&#xff1a;异常捕获后执行ch…

Linux declare命令、Linux tail 命令

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 Linux declare命令用于声明 shell 变量。 declare为shell指令&#xff0c;在第一种语法中可用来声明变量并设置变量的属性([rix]即为变…

详解Nagios配置文件的逻辑关系

1.主配置文件/usr/local/nagios/etc/nagios.cfg a.定义了用户和组 b.定义了某些具体参数 c.定义了配置文件和可以存放配置文件的文件夹 d.通过开头的#号去注释选项以达到关闭配置的效果 e.更改配置后&#xff0c;可以通过命令 /usr/local/nagios/bin/nagios –v /usr/local/na…

10 步让你成为更优秀的程序员

这篇文章要介绍的&#xff0c;是我作为专业程序员这些年来学到的能真正提高我的代码质量和整体工作效率的10件事情。 1. 永远不要复制代码 不惜任何代价避免重复的代码。如果一个常用的代码片段出现在了程序中的几个不同地方&#xff0c;重构它&#xff0c;把它放到一个自己的函…

《流浪地球》 电影全集

《流浪地球》 电影全集 《流浪地球》是由郭帆导演&#xff0c;吴京特别出演&#xff0c;屈楚萧、李光洁、吴孟达等人主演的科幻片《流浪地球》宣布定档2019大年初一。同时&#xff0c;影片发布了一款定档预告片&#xff0c;预告片开头传来一段广播声音&#xff1a;“太阳急速老…

kotlin之plus、copyOf、reverse、forEach、filter、map、reduce、fold等函数解释和使用

kotlin之::函数调用、plus&#xff08;增加元素&#xff09;、copyOf&#xff08;复制数组&#xff09;、reverse&#xff08;翻转数组&#xff09;、forEach&#xff08;遍历数组&#xff09;、filter&#xff08;过滤数组&#xff09;、map函数操作及扩展、reduce函数、fold函…

linux 常用命令 杂记

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 1.cat cat 命令用于连接文件并打印到标准输出设备上。 使用权限 所有使用者 2.Linux chgrp命令用于变更文件或目录的所属群组。 3.Linux…

C程序员要学C++吗?

最近网友问到这一问题&#xff0c;但我更希望被问的是“C程序员需要学面向对象编程吗&#xff1f;”&#xff0c;那就让我先从回答这一问题开始&#xff0c;并做适当的扩展。 就我的成长经历来看&#xff0c;C程序员必须学习面向对象编程&#xff01;面向对象编程语言有其天然的…

追女生心理研究(本人母胎单身,就是想做准备,并无其他意思)

聊天话题&#xff1a; 1。兴趣爱好&#xff1a;美食&#xff0c;旅游&#xff0c;宠物等 2。现在和曾经的自己&#xff0c;分享自己的经历 3。我变成我们&#xff0c;未来规划 4。分析隐私&#xff0c;比如一些小秘密 5。价值观&#xff0c;对未来的规划等 聊天话题技巧 …

dlopen 和 dlsym 动态调用函数

Linux/unix 提供了使用 dlopen 和 dlsym 方法动态加载库和调用函数&#xff0c;这套方法在 macOS 和 iOS 上也支持。dlopen 打开一个库&#xff0c;获取句柄。dlsym 在打开的库中查找符号的值。dlclose 关闭句柄。dlerror 返回一个描述最后一次调用dlopen、dlsym&#xff0c;或…

通过腾讯地图服务获取行政区划信息

接口说明地址&#xff1a; https://lbs.qq.com/webservice_v1/guide-region.html 以下是源代码及表创建脚本。 源码及相关文件下载转载于:https://www.cnblogs.com/challengesoflife/p/10405366.html

情感学习聊天方法

1.非正常聊天法 出人意料的聊天技巧&#xff0c;展示幽默感&#xff0c;让对方对自己产生兴趣 比如对方说&#xff1a;你的朋友圈好多美女啊。回答还好了&#xff0c;没有了。场面会一度尴尬 但可以这么说&#xff1a;你这样是在间接夸自己是美女。或者&#xff1a;还好啦&a…

面向对象设计的优点

一旦明白了软件设计的真谛&#xff08;参见《软件设计的真谛》&#xff09;&#xff0c;我们就更能理解面向对象设计的优点。简单说来&#xff0c;它更便于我们在软件中构建更真实的虚拟世界。 首先&#xff0c;对象的引入方便了在软件虚拟世界中模拟现实世界。现实世界是由很…

利用SVD-推荐未尝过的菜肴2

推荐未尝过的菜肴-基于SVD的评分估计 实际上数据集要比我们上一篇展示的myMat要稀疏的多。 from numpy import linalg as la from numpy import * def loadExData2():return[[0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 5],[0, 0, 0, 3, 0, 4, 0, 0, 0, 0, 3],[0, 0, 0, 0, 4, 0, 0, 1, 0,…

在图像中截取小图并保存

实现以横向步长step_row、纵向步长step_col&#xff0c;在一幅大图上剪裁宽度为width、高度为height的小图像&#xff0c;图像命名形式为“数字(递增)_大图名”格式&#xff0c;将小图保存在argv[6]的文件夹中。 #include <opencv2/opencv.hpp> #include <string> …

Linux 文件与目录管理、ls、cd、pwd、mkdir、rmdir、cp、 rm

见&#xff1a;http://www.runoob.com/linux/linux-file-content-manage.html我们知道Linux的目录结构为树状结构&#xff0c;最顶级的目录为根目录 /。 其他目录通过挂载可以将它们添加到树中&#xff0c;通过解除挂载可以移除它们。 在开始本教程前我们需要先知道什么是绝对路…

软件设计的真谛

假设我们身边的一切都是用制造材料加以描述的&#xff1a;“空调”不是“空调”&#xff0c;而是“由金属和塑料做成的物体”&#xff1b;“书”不是“书”&#xff0c;而是“由纤维和墨做成的物体”。沟通时我们也不用“空调”和“书”这样的词汇&#xff0c;而是“金属和塑料…