Open VSwitch
- Home /
- Linux /
- KVM e QEMU /
- Open vSwitch
Introdução ao Open vSwitch
O Open vSwitch (OVS) é um switch virtual mais avançado e centralizável, enquanto a interface bridge do Linux é um switch virtual simples e local. A bridge do Linux funciona como um switch de camada 2 básico, ela conecta interfaces físicas e virtuais no mesmo domínio de broadcast. A bridge do Linux funciona bem em cenários simples de virtualização, mas depende da configuração manual de cada host, ou seja, cada bridge existe apenas naquele dentro do servidor onde ela foi configurada, Mas cada servidor não tem conhecimento do que acontece nos outros nós do sistema.
Já o Open vSwitch, por outro lado, foi projetado para ambientes maiores e distribuídos. Ele também atua como um switch virtual, mas adiciona recursos avançados como controle centralizado, integração com controladores externos, políticas de rede consistentes entre vários hosts e suporte nativo a tecnologias modernas como VLAN, LACP, VXLAN, GENEVE e GRE. Em vez de configurar cada host isoladamente, o OVS permite aplicar regras e topologias de rede de forma padronizada em todo o ambiente.
A arquitetura do Open vSwitch é dividida em duas partes funcionais: o módulo de kernel (plano de dados), que processa os pacotes recebidos com o máximo de velocidade, e ferramentas em espaço de usuário (plano de controle) para gerenciamento.
O daemon principal, ovs-vswitchd, gerencia as instâncias de switches locais, enquanto o ovsdb-server mantém um banco de dados persistente com as tabelas do switch, comunicando-se com clientes externos via JSON-RPC.
O OVS pode operar em dois modos distintos: o Modo Normal, onde atua como um switch de aprendizado de Camada 2 convencional, e o Modo de Fluxo, onde as decisões de encaminhamento são tomadas por tabelas de fluxo gerenciadas por um controlador SDN externo via protocolo OpenFlow.
Para integrar o Open vSwitch em ambientes de virtualização KVM gerenciados pelo libvirt, o administrador deve criar uma rede virtual que referencie a ponte do OVS, utilizando a tag <virtualport type='openvswitch'/> em sua definição XML.
Uma vez configurado, é possível realizar tarefas administrativas complexas via linha de comando, como o tagging de VLAN em portas específicas de máquinas virtuais através do comando ovs-vsctl set port <interface> tag=<ID>.
O ecossistema de ferramentas do OVS inclui utilitários poderosos como o ovs-vsctl para exibir a configuração atual, o ovs-ofctl para monitorar entradas de fluxo e o ovs-appctl, considerado o “canivete suíço” para a depuração de problemas de rede.
Intalando o Open vSwitch
No Ubuntu, a instalação do Open vSwitch é simples, já que o pacote está nos repositórios oficiais. Comece atualizando o índice de pacotes e instale o openvswitch-switch:
sudo apt update
sudo apt install -y openvswitch-switch
O pacote openvswitch-switch fornece o daemon ovs-vswitchd, o banco de dados ovsdb-server e as ferramentas de administração (ovs-vsctl, ovs-ofctl).
Verifique se o serviço está up:
systemctl status openvswitch-switch
Você também pode validar ao verificar a versão:
$ ovs-vsctl -V
ovs-vsctl (Open vSwitch) 3.3.4
DB Schema 8.5.1
Configurando o Open vSwitch no Linux
Vamos ver como configurar o Open vSwitch em um host Linux e integrá-lo ao libvirt para usar com as máquinas virtuais. A ideia é mostrar que o OVS pode existir sem interface física, mas que sem ela as VMs ficam isoladas da infraestrutura externa.
O Open vSwitch não precisa obrigatoriamente de uma interface física associada. Nesse caso, ele funciona como um switch totalmente virtual, permitindo comunicação apenas entre VMs conectadas a ele.
# Criando a bridge OVS:
ovs-vsctl add-br ovs-br0
Com esse comando, é criado um switch virtual Open vSwitch chamado ovs-br0. Todas as máquinas virtuais conectadas a essa bridge passam a compartilhar o mesmo domínio de camada 2, podendo trocar tráfego diretamente entre si, como se estivessem ligadas ao mesmo switch físico.
Agora vamos atribuir um endereço IP à bridge, isso permite que o próprio host Linux participe dessa rede.
ip addr add 10.10.10.1/24 dev ovs-br0
ip link set dev ovs-br0 up
Nesse estado, apenas o host e as VMs conectadas ao ovs-br0 conseguem se comunicar. Não existe acesso à rede física externa. Vale notar que essa configuração de endereço IP não é persistente.
Para que o libvirt saiba que existe uma rede baseada em Open vSwitch, é necessário definir uma rede XML, abaixo segue um exemplo:
<network>
<name>openvswitch</name>
<forward mode='bridge'/>
<bridge name='ovs-br0'/>
<virtualport type='openvswitch'/>
</network>
O forward mode='bridge' indica que o libvirt não fará NAT, nem roteamento. Ele apenas conecta a VM diretamente à bridge existente. Já o bridge name='ovs-br0' informa o nome da bridge que será usada e virtualport type='openvswitch' diz ao libvirt qual tecnologia de switch virtual está sendo usada. Sem esse parâmetro, o libvirt tenta usar o modelo padrão de bridge Linux, o que não funciona corretamente com Open vSwitch.
Depois de criar o XML, registre e ative a rede no libvirt.
virsh net-define openvswitch.xml
virsh net-start openvswitch
virsh net-autostart openvswitch
Se você quiser que as VMs tenham acesso à rede física, à LAN ou à internet, é necessário conectar uma interface física ao OVS. Essa interface passa a funcionar como um uplink, ligando o switch virtual ao switch físico real.
Antes de adicionar a interface ao OVS, ela não deve ter IP configurado.
ip addr flush dev eth1
Adicionando a interface física à bridge OVS
ovs-vsctl add-port ovs-br0 eth1
E por fim, suba a interface:
ip link set eth1 up
A partir desse ponto, qualquer máquina virtual conectada à rede openvswitch passa a ter acesso direto à infraestrutura física, desde que a interface eth1 esteja fisicamente conectada a um switch.
Nesse modelo, o Open vSwitch assume o papel de switch de camada 2, eliminando a necessidade de criar uma bridge Linux tradicional para alcançar o mesmo efeito. As VMs passam a se comportar como dispositivos conectados diretamente à rede física, podendo acessar servidores e equipamentos externos de forma transparente.
Configuração persistente das interfaces
Em ambientes com ifupdown, uma interface de rede só é colocada em estado up se ela tiver uma configuração IP ou se houver uma regra explícita mandando subir a interface. O problema é que quando usamos Open vSwitch, as interfaces físicas não recebem IP, nem são configuradas como bridge Linux, ou seja, elas são apenas portas do switch virtual.
Isso pode se tornar um problema quando o servidor for reiniciado, já que o ifupdown não inicia essas interfaces no boot. Para que elas subam sem nenhum configuração e fiquem ativas, podendo ser usadas pelos OVS sem problema, faça o seguinte:
$ cat /etc/network/interfaces
auto eth0
iface eth0 inet manual
up ip link set dev eth0 up
A linha auto eth0 faz o ifupdown tentar ativar a interface no boot, mesmo que não tenha nada conectado nelas. Já a linha iface eth0 inet manual, informa que a interface não terá IP, nem DHCP e nem terá configuração de camada 3. Basicamente, ela será usada apenas como interface de camada 2.
A linha up ip link set dev eth0 up força o kernel a colocar a interface em estado up, mesmo sem IP. Essa configuração é necessária já que o Open vSwitch não sobe interfaces por conta própria, essa é uma tarefa do kernel.
No netplan, a configuração seria assim:
ethernets:
eth0:
dhcp4: false
dhcp6: false
optional: true
Comandos do Open vSwitch
O comando ovs-vsctl show exibe a configuração completa do Open vSwitch no host. Ele mostra quais bridges existem, quais portas estão associadas a cada bridge e quais interfaces pertencem a cada porta.
$ ovs-vsctl show
dc64a977-d3a3-4716-8a3c-71bee5e8e4e6
Bridge ovs-br0
Port eth1
Interface eth1
Port vnet1
Interface vnet1
Port ovs-br0
Interface ovs-br0
type: internal
ovs_version: "2.17.9"
O comando ovs-vsctl list-ports ovs-br0 é usado para listar somente os nomes das portas associadas à bridge ovs-br0.
$ ovs-vsctl list-ports ovs-br0
eth1
vnet1
VLAN
O comando abaixo aplica uma tag de vlan na interface vnet0 para porta em modo access (untagged):
ovs-vsctl set port vnet0 tag=5
Quando um quadro ethernet entrar sem nenhuma tag por essa porta, o OVS adiciona a VLAN 5 internamente. Para permitir mais de uma VLAN na mesma porta, precisamos configurar um trunk, abaixo segue um exemplo:
ovs-vsctl set port vnet0 trunks=10,20,30
Ainda é possível configurar uma porta trunk com VLAN nativa (untagged) no Open vSwitch. Para isso, use o seguinte comando:
ovs-vsctl set port vnet0 trunks=10,20,30 tag=5
Nessa configuração, as VLANs 10, 20 e 30 são tratadas como tagged, ou seja, a máquina virtual deve enviar e receber quadros Ethernet já marcados com a tag correspondente (10, 20 ou 30).
Quadros Ethernet que chegam sem tag de VLAN são automaticamente associados pelo Open vSwitch à VLAN 5, que passa a atuar como a VLAN nativa (untagged) dessa porta.
Esse comportamento é equivalente ao de uma porta trunk 802.1Q com VLAN nativa em um switch físico, onde o tráfego sem tag é mapeado para uma VLAN específica, enquanto as demais VLANs trafegam de forma tagged.
Lista todas as bridges
O comando ovs-vsctl list-br lista apenas as bridges criadas no Open vSwitch.
$ ovs-vsctl list-br
ovs-br0
Lista todas as interfaces de uma bridge
O comando ovs-vsctl list-ports <bridge> exibe todas as interfaces associadas a uma bridge específica.
$ ovs-vsctl list-ports ovs-br0
eth1
vnet1
Adicionar uma bridge
O comando ovs-vsctl add-br <bridge> é usado para criar uma nova bridge Open vSwitch. É equivalente a criar um novo switch virtual.
ovs-vsctl add-br ovs-br0
Adicionar uma interface em uma bridge
O comando ovs-vsctl add-port <bridge> <interface> é usado para adicionar uma interface (física ou virtual) como porta da bridge.
ovs-vsctl add-port ovs-br0 eth2
A interface eth2 passa a ser controlada pelo Open vSwitch e deixa de operar de forma independente.
Ver informações gerais da bridge
O comando ovs-ofctl show <bridge> é usado para exibir informações gerais da bridge, como: mapeamento de número de porta para nome, capacidades do switch, endereço MAC, estado, velocidade e etc.
# ovs-ofctl show ovs-br0
OFPT_FEATURES_REPLY (xid=0x2): dpid:0000005000000101
n_tables:254, n_buffers:0
capabilities: FLOW_STATS TABLE_STATS PORT_STATS QUEUE_STATS ARP_MATCH_IP
actions: output enqueue set_vlan_vid set_vlan_pcp strip_vlan mod_dl_src mod_dl_dst mod_nw_src mod_nw_dst mod_nw_tos mod_tp_src mod_tp_dst
1(eth1): addr:00:50:00:00:01:01
config: 0
state: 0
speed: 0 Mbps now, 0 Mbps max
2(vnet1): addr:fe:54:00:4c:61:fe
config: 0
state: 0
current: 10MB-FD COPPER
speed: 10 Mbps now, 0 Mbps max
LOCAL(ovs-br0): addr:00:50:00:00:01:01
config: 0
state: 0
speed: 0 Mbps now, 0 Mbps max
OFPT_GET_CONFIG_REPLY (xid=0x4): frags=normal miss_send_len=0