0%

Openstack学习 —— 跨主机虚拟机访问1

前面已经有一篇博文讲解了同主机内的虚拟机通信,本篇则主要关注与跨主机虚拟机访问的详细解析。

创建网络 - 创建虚拟机实例 - 创建路由器

在上一篇文章中已经详细介绍了创建网络后主机上发生的事情。接下来,我们就创建两个虚拟机(nova自动调度到了两个节点上),然后来看看网络部分又发生了哪些事情。

注:openstack及ovs等CLI输出内容较多,文章中仅列出关注的部分内容

创建虚拟机

在创建虚拟机之前,需要创建规格(flavor)和上传镜像(image)

本文使用cirros作为测试镜像

1
2
3
4
5
6
7
8
$ openstack server create --flavor small --image cirros --network net1 --min 2 --max 2 vm
$ openstack server list
+--------------------------------------+------+--------+------------------+--------+--------+
| ID | Name | Status | Networks | Image | Flavor |
+--------------------------------------+------+--------+------------------+--------+--------+
| ebb1b8fa-6457-4e80-8a49-14093622ce5d | vm-2 | ACTIVE | net1=200.0.0.219 | cirros | small |
| fb619b6c-9954-4dbd-8b1e-461c1c3c4c7d | vm-1 | ACTIVE | net1=200.0.0.238 | cirros | small |
+--------------------------------------+------+--------+------------------+--------+--------+

发生了什么?

Compute

还是有必要简单介绍一下nova相关的操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
$ openstack server show vm-1
+-------------------------------------+--------------------------------------+
| Field | Value |
+-------------------------------------+--------------------------------------+
| OS-EXT-SRV-ATTR:hypervisor_hostname | node1 |
| OS-EXT-SRV-ATTR:instance_name | instance-00000039 |
| addresses | net1=200.0.0.238 |
| id | fb619b6c-9954-4dbd-8b1e-461c1c3c4c7d |
| name | vm-1 |
+-------------------------------------+--------------------------------------+
$ openstack server show vm-2
+-------------------------------------+--------------------------------------+
| Field | Value |
+-------------------------------------+--------------------------------------+
| OS-EXT-SRV-ATTR:hypervisor_hostname | node0 |
| OS-EXT-SRV-ATTR:instance_name | instance-0000003a |
| addresses | net1=200.0.0.219 |
| id | ebb1b8fa-6457-4e80-8a49-14093622ce5d |
| name | vm-2 |
+-------------------------------------+--------------------------------------+

从实例的信息中看到,分别在node1上创建了vm-1:instance-00000039,在node0上创建了vm-2:instance-0000003a。不妨分别在两个node上使用virsh list看看:

1
2
3
4
(node0)$ virsh list
Id Name State
-----------------------------------
21 instance-0000003a running
1
2
3
4
(node1)$ virsh list
Id Name State
-----------------------------------
11 instance-00000039 running

Network

1
2
3
4
5
6
7
8
$ openstack port list
+--------------------------------------+------+-------------------+----------------------------------------------------------------------------+--------+
| ID | Name | MAC Address | Fixed IP Addresses | Status |
+--------------------------------------+------+-------------------+----------------------------------------------------------------------------+--------+
| 02407769-97c6-45ae-8fba-ea464020951c | | fa:16:3e:ad:66:9e | ip_address='200.0.0.219', subnet_id='5875f007-7b0f-45af-b78f-82527e5d9a90' | ACTIVE |
| 17a89323-fd0a-44cc-a525-fcf8d2efb836 | | fa:16:3e:f6:db:c9 | ip_address='200.0.0.2', subnet_id='5875f007-7b0f-45af-b78f-82527e5d9a90' | ACTIVE |
| f4c391da-2295-479a-95c5-c7759132f2ea | | fa:16:3e:f5:ca:f5 | ip_address='200.0.0.238', subnet_id='5875f007-7b0f-45af-b78f-82527e5d9a90' | ACTIVE |
+--------------------------------------+------+-------------------+----------------------------------------------------------------------------+--------+

先记住两个port对应的ID:

ID IP Instance Node
02407769-97c6-45ae-8fba-ea464020951c 200.0.0.219 vm-1 node0
f4c391da-2295-479a-95c5-c7759132f2ea 200.0.0.238 vm-2 node1

node0

  • Linux bridge
1
2
3
4
$ brctl show
bridge name bridge id STP enabled interfaces
qbr02407769-97 8000.02989dedfae5 no qvb02407769-97
tap02407769-97
  • ovs
1
2
3
4
5
6
7
8
$ ovs-vsctl show
...
Bridge br-int
...
Port "qvo02407769-97"
tag: 1
Interface "qvo02407769-97"
...

别忘了留意tag: 1,后面分析时才会用到

  • MAC地址
1
2
3
4
5
6
7
8
9
$ ip link show
161: qbr02407769-97: ...
link/ether 02:98:9d:ed:fa:e5 brd ff:ff:ff:ff:ff:ff
162: qvo02407769-97@qvb02407769-97: ...
link/ether 2a:16:2b:d1:8d:a3 brd ff:ff:ff:ff:ff:ff
163: qvb02407769-97@qvo02407769-97: ...
link/ether 02:98:9d:ed:fa:e5 brd ff:ff:ff:ff:ff:ff
164: tap02407769-97: ...
link/ether fe:16:3e:ad:66:9e brd ff:ff:ff:ff:ff:ff
  • vm-1

可以使用virsh console xxx连入虚拟机的console进行操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
$ virsh console instance-0000003a
Connected to domain instance-0000003a
Escape character is ^]

login as 'cirros' user. default password: 'gocubsgo'. use 'sudo' for root.
vm-2 login: cirros
Password:
$ ifconfig
eth0 Link encap:Ethernet HWaddr FA:16:3E:AD:66:9E
inet addr:200.0.0.219 Bcast:200.0.0.255 Mask:255.255.255.0
inet6 addr: fe80::f816:3eff:fead:669e/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1450 Metric:1
RX packets:94 errors:0 dropped:0 overruns:0 frame:0
TX packets:122 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:9192 (8.9 KiB) TX bytes:10571 (10.3 KiB)
...

从上面我们可以看到,分别创建了:

  1. 一个linux网桥qbr02407769-97
  2. 一组接口对: qvb02407769-97@qvo02407769-97
  3. 一个tap接口:tap02407769-97

你或许已经发现了tap02407769-97接口与instance-0000003a的eth0的关系,是的,他们MAC地址相同,也即表示他们实际上就是同一个网络接口。

  • 连接关系整理

create_vm_ports

将上一篇文章中的dhcp的namespace也合入整个连接关系后:

create_vm_portswithdhcp

node1

同样收集node1上的各种信息

  • linux bridge
1
2
3
4
$ brctl show
bridge name bridge id STP enabled interfaces
qbrf4c391da-22 8000.aa5d4b2ddf79 no qvbf4c391da-22
tapf4c391da-22
  • ovs
1
2
3
4
5
6
7
8
$ ovs-vsctl show
...
Bridge br-int
...
Port "qvof4c391da-22"
tag: 6
Interface "qvof4c391da-22"
...

别忘了留意tag: 6,你也可以思考一下,为什么同一个subnet,node0上是1,node1上是6?

  • 连接关系

到现在,分布在两个node上的VM与br-int之间的通路已经清晰起来

create_vm_portswithnode1

小结

至此,两台虚拟机已经创建完毕。再加上实验环境介绍中的连接图:

create_vm_with_2node

不妨先从vm-1访问一下vm-2,先思考一下两个虚拟机是如何访问的。下一篇文章再继续探讨流量是如何从一个节点的虚拟机经历千山万水到达另外一个节点虚拟机上的。