Artigos e tutoriais
   FRR - Linux e o roteamento dinamico
Autor: Patrick Brandão, patrickbrandao@gmail.com
Cópia autorizada somente quando preservar a referência ao autor.


frr_sources


Fontes:

frr_intro


Introdução

Antigamente, por volta de 1993, o roteamento (criar e deletar rotas) no Linux era um trabalho puramente manual e realizado com o comando "route".

O trabalho sério, realizados por gateways com protocolos automatizados era deixado para roteadores profissionais (3com, Cisco, Juniper, etc...) e o Linux se limitava a servidores e aplicações de host.

Um tímido processo chamado "routed" implementava um único protocolo de roteamento dinâmico para Linux, o RIP.

Um programador chamado Kunihiro Ishiguro desenvolveu então um software chamado Zebra (GNU Zebra), um framework para aprendizado e compartilhamento de informações de roteamento por meio de protocolos dinâmicos, cujas rotas são aplicadas na tabela de rotas do Kernel Linux.

O framework Zebra era tão elegante e estável que passou a ser referência de roteamento dinâmico em sistemas Unix, e sua fama fez parecer que ele era o único software desse tipo.



No desenho acima temos, como base de tudo, o hardware. Executando sobre o hardware e mantendo controle dos dispositivos PCI, memória, processador e demais periféricos o Kernel Linux. No Kernel temos todas as funções de rede para criação e processamento de pacotes IP, incluindo as interfaces lógicas de rede (eth0, eth1, loopback), e principalmente a tabela de rotas.

Dentro do Kernel Linux onde há um espaço de memória alocado para armazenar a tabela de rotas, esse espaço é o que denominamos FIB (Forward Information Base).

A cada pacote IP recebido ou criado num sistema Linux, o IP de destino do pacote é localizado na tabela de rotas, e através dele sabe-se qual o proximo salto do pacote.

Quando o administrador de sistema insere uma rota usando o comando "route" ou "ip route", tal rota é diretamente inserida na FIB por meio de uma API (RTNL).

Quando o administrador, ou algum script de gerencia de rede (ifup, NetworkManager, netplan, rc.inet1, etc...), adiciona um endereço IP em uma interface, o que de fato acontece é o envio de uma mensagem por meio de socket RTNL, o Kernel recebe a mensagem e efetiva o pedido, criando a rota da rede local (rota para rede diretamente conectada) e associando o endereço IP à interface.

Essa maneira simples de trabalhar, baseado em mensagens, permite que qualquer programa (rodando como root ou com NET_CAPABILITIES) a capacidade de inserir e remover rotas na FIB.

Ao criar um software que implemente um protocolo de roteamento, como é o caso do "routed", basta que tal software envie mensagens RTNL para obter uma cópia da tabela de rota quanto inserir nela uma nova rota aprendida por meio de um roteador vizinho. Não há mistério nisso, e o código é pequeno e simples.

No entanto, quando se deseja criar vários softwares, onde cada um aprende e ensina rotas usando um protocolo diferente, um problema sério surge: a concorrência no acesso a tabela de rotas do kernel. Este problema cria um fenômeno chamado "rota presa", que trata-se uma rota que foi inserida erroneamente, ou foi inserida por um software e apagada por outro, sem que esses software tenham uma comunicação entre si para evitar tais problemas ou sinalizar preferencia sobre uma rota.

A forma mais elegante de resolver este problema é criar uma nova camada de software, essa camada cria uma tabela de rotas chamada RIB (Route Information Base).

Um software, que aqui se chama ZEBRA, fica responsável por manter um banco de dados de informações aprendidas por diferentes protocolos, e associa a cada um deles uma prioridade.

Exemplo: uma informação (rota) aprendida pelo protocolo OSPF (metric 110) não vence uma rota aprendida através de eBGP (metric 20). Na RIB precisam constar ambas as informações, o Zebra aplicará ao kernel somente a rota vencedora (eBGP nesse caso). Se ocorrer um withdrawn no eBGP que remova a informação da RIB, o Zebra notificará o Kernel, removendo a rota aprendida via eBGP e inserindo a rota alternativa, aprendida via OSPF. Se ocorrer, por coincidência de ambas as rotas terem o mesmo IP de gateway, nenhuma notificação é enviada ao kernel, pois afinal, nada de fato mudou a nível de FIB, somente a nível de RIB, "seria trocar 6 por meia-dúzia".




É importante informar que, embora na RIB as rotas tenham diferentes métricas (eBGP=20, iBGP=220, OSPF=110), a melhor rota é inserida no kernel com uma métrica fixa (proto zebra metric 20).



Ao ser executado num modelo cliente-servidor, o zebra permite que qualquer protocolo de roteamento possa ser implementado sem que alterações drásticas precisem ser feitas em sua estrutura.

Bastaria escrever o software cliente e conecta-lo ao socket do zebra, e enviar as informações aprendidas à RIB.

Cada ZClient (software cliente zebra) fica responsável pela sua própria configuração, cabendo a ele ler o arquivo inicial, interpretá-lo e obedecê-lo.

Aqui mora um perigo: a ausência do arquivo de configuração, ou a incapacidade de lê-lo (permissões), ou corrupção na sintaxe pode fazer com que o ZClient não seja iniciado.

Exemplo: se você editar manualmente o arquivo ospfd.conf e escrever uma palavra desconhecida, o processo ospfd (ZClient de OSPFv2) não irá iniciar.

A melhor abordagem é criar todos os arquivos de configuração vazios e configurá-los via terminal zebra, o VTYSH.

Vou ensinar como operar o VTYSH mais tarde.




Evolução do projeto Zebra

Kunihiro Ishiguro criou o projeto Zebra, que foi muito tempo depois copiado (fork) e mantido por outra equipe de desenvolvedores, denominado projeto Quagga.

O Quagga mantinha inicialmente uma boa evolução do código, criando novos recursos, principalmente recursos adicionais no BGP e suporte a IPv6 (ainda sim ficou muito bugado, tenha dó).

Nesse momento da história, softwares como Debian, Ubuntu, VyAtta, VyOS, EdgeOS, entre outros, implementaram o Quagga com grande sucesso comercial.

Devida a alta demanda por estabilidade, novos recursos, maior flexibilidade e, principalmente, pressão por parte de grandes empresas que contribuíram para projetos de software open-source (Cumulus Networks, VMWare, Dell, etc...) e que precisavam de desenvolvedores mais comprometidos a frente do projeto Zebra/Quagga, a Linux Foundation apoiou um novo fork do projeto, vindo a chamá-lo de FRR - Free Range Routing (tradução direta: Faixa Livre para Roteamento).





frr_install


Instalação via pacotes

Usaremos como base o Debian 10.5

Não recomendo que você realize o tutorial em ambiente de produção, portanto, pratique em maquinas virtuais de laboratórios (EVE-NG, GNS3, VirtualBox, VMWare, etc...).

O FRR não pode ser executado em um Linux que já rode o Quagga.
Se você instalou o Quagga, remova-o antes de iniciar os estudo do FRR.

Comandos (1 por linha) para instalação dos pacotes:


    apt-get -y update
    apt-get -y upgrade

    apt-get -y install frr






frr_startup


Configuração inicial

Observe a pasta /etc/frr/


    ls -lah /etc/frr/

# total 20K
# drwxr-x---   2 frr  frr  4.0K Aug 11 03:01 .
# drwxr-xr-x 108 root root 4.0K Aug 11 03:01 ..
# -rw-r-----   1 frr  frr  1.9K Jan  7  2020 daemons
# -rw-r-----   1 frr  frr   120 Jan  7  2020 frr.conf
# -rw-r-----   1 frr  frr    32 Jan  7  2020 vtysh.conf


Os arquivos frr.conf e vtysh.conf não precisam nem devem ser editados, inicialmente.
Se você por algum motivo estragá-los, basta deixá-los em branco que tudo ficará bem.

Por segurança vamos fazer uma copia dos arquivos originais:


    mkdir -p /etc/frr/backup/

    cp /etc/frr/daemons     /etc/frr/backup/
    cp /etc/frr/frr.conf    /etc/frr/backup/
    cp /etc/frr/vtysh.conf  /etc/frr/backup/


O arquivo daemons é o mais importante de todos. Ele informa aos scripts de serviço do FRR quais aplicações ZClient você deseja executar. Por padrão todos os ZClients ficam desativados. Como editar esse arquivo é muito perigoso para leigos, segue abaixo os comandos simples para ativa-los:


# Ativar BGP:
    sed -i 's#bgpd=no#bgpd=yes#' /etc/frr/daemons

# Ativar OSPFD (OSPFv2 - IPv4):
    sed -i 's#ospfd=no#ospfd=yes#' /etc/frr/daemons

# Ativar OSPF6D (OSPFv3 - IPv6):
    sed -i 's#ospf6d=no#ospf6d=yes#' /etc/frr/daemons

# Ativar RIPD (RIPv2 - IPv4):
    sed -i 's#ripd=no#ripd=yes#' /etc/frr/daemons

# Ativar RIPNGD (RIPv3 - IPv6):
    sed -i 's#ripngd=no#ripngd=yes#' /etc/frr/daemons

# Ativar ISISD (IS-IS - Protocolo igp Cisco):
    sed -i 's#isisd=no#isisd=yes#' /etc/frr/daemons

# Ativar PIMD (PIM - Roteamento Multicast):
    sed -i 's#pimd=no#pimd=yes#' /etc/frr/daemons

# Ativar LDPD (LDP - Labels MPLS para rotas igp):
    sed -i 's#ldpd=no#ldpd=yes#' /etc/frr/daemons

# Ativar NHRPD (NHRP - roteamento entre tuneis):
    sed -i 's#nhrpd=no#nhrpd=yes#' /etc/frr/daemons

# Ativar EIGRPD (EIGRP - protocolo igp Cisco):
    sed -i 's#eigrpd=no#eigrpd=yes#' /etc/frr/daemons

# Ativar BABELD (BABEL - protocolo igp dual-stack):
    sed -i 's#babeld=no#babeld=yes#' /etc/frr/daemons

# Ativar SHARPD (SHARP - protocolo exemplo zclient):
    sed -i 's#sharpd=no#sharpd=yes#' /etc/frr/daemons

# Ativar PBRD (PBR - gestao de regras para Police Based Routing):
    sed -i 's#pbrd=no#pbrd=yes#' /etc/frr/daemons

# Ativar BFDD (BFD - protocolo de adjacencia instantanea):
    sed -i 's#bfdd=no#bfdd=yes#' /etc/frr/daemons


Para desativar todos, execute:


    sed -i 's#bgpd=yes#bgpd=no#' /etc/frr/daemons
    sed -i 's#ospfd=yes#ospfd=no#' /etc/frr/daemons
    sed -i 's#ospf6d=yes#ospf6d=no#' /etc/frr/daemons
    sed -i 's#ripd=yes#ripd=no#' /etc/frr/daemons
    sed -i 's#ripngd=yes#ripngd=no#' /etc/frr/daemons
    sed -i 's#isisd=yes#isisd=no#' /etc/frr/daemons
    sed -i 's#pimd=yes#pimd=no#' /etc/frr/daemons
    sed -i 's#ldpd=yes#ldpd=no#' /etc/frr/daemons
    sed -i 's#nhrpd=yes#nhrpd=no#' /etc/frr/daemons
    sed -i 's#eigrpd=yes#eigrpd=no#' /etc/frr/daemons
    sed -i 's#babeld=yes#babeld=no#' /etc/frr/daemons
    sed -i 's#sharpd=yes#sharpd=no#' /etc/frr/daemons
    sed -i 's#pbrd=yes#pbrd=no#' /etc/frr/daemons
    sed -i 's#bfdd=yes#bfdd=no#' /etc/frr/daemons


Neste artigo usaremos apenas os protocolos OSPFv2, OSPFv3, BABEL e BGP, portanto ative-os:


    sed -i 's#bgpd=no#bgpd=yes#' /etc/frr/daemons
    sed -i 's#ospfd=no#ospfd=yes#' /etc/frr/daemons
    sed -i 's#ospf6d=no#ospf6d=yes#' /etc/frr/daemons
    sed -i 's#babeld=no#babeld=yes#' /etc/frr/daemons


É imperativo garantir a existência dos arquivos de configuração de cada processo e as permissões da pasta /etc/frr:


    touch /etc/frr/frr.conf
    touch /etc/frr/vtysh.conf
    touch /etc/frr/staticd.conf

    touch /etc/frr/bgpd.conf
    touch /etc/frr/ospfd.conf
    touch /etc/frr/ospf6d.conf
    touch /etc/frr/ripd.conf
    touch /etc/frr/ripngd.conf
    touch /etc/frr/isisd.conf
    touch /etc/frr/pimd.conf
    touch /etc/frr/ldpd.conf
    touch /etc/frr/nhrpd.conf
    touch /etc/frr/eigrpd.conf
    touch /etc/frr/babeld.conf
    touch /etc/frr/sharpd.conf
    touch /etc/frr/pbrd.conf
    touch /etc/frr/bfdd.conf

    chown frr:frr  /etc/frr/*.conf
    chmod 600      /etc/frr/*.conf


Existe um Zclient chamado staticd, responsável por gerir rotas estáticas. A execução dele é imperativa e não é possível desativa-lo se o servidor zebra for iniciado.

Antigamente, quando o servidor zebra sofria com algum problema computacional e travava, isso fatalmente tornava toda pilha de roteamento dinâmico inútil, visto que sem os commits da RIB a rede fica sem convergência. A única forma de restaurar o serviço era matar e reiniciar os processos MANUALMENTE.

Na pilha Zebra a ordem de execução dos processos é vital para seu funcionamento. O servidor zebra deve ser iniciado primeiro, abrir o socket e aguardar por mensagens dos aplicativos.

Os aplicativos de roteamento ao serem executados devem encontrar o socket pronto para leitura e escrita.

Um processo cliente travado é igualmente traumático para a rede do backbone, mas não é fatal para a pilha zebra, visto que basta que o aplicativo que falhou seja reiniciado.

Você não vai querer fazer isso manualmente, como era feito antigamente. O pacote FRR conta com uma herança do Quagga para resolver esse problema, um serviço de watchdog chamado WATCHFRR.

Ele é responsável por iniciar o servidor zebra, testar o socket, e então iniciar os aplicativos zclients (os que você configurou como yes no arquivo /etc/frr/daemons).



Dessa forma, se o servidor zebra travar todos os processos serão assassinados pelo WATCHFRR e iniciados na ordem correta. Se algum aplicativo individual travar ele é exterminado e iniciado, sem prejuízo dos demais processos saudáveis.


Agora que você já sabe que FRR é o conjunto da obra, vamos reinicia-lo manualmente para subir as aplicações que ativamos


# - Ativar servico
    systemctl enable frr.service
    
# - Parar servico:
    service frr stop
    
# - Iniciar servico:
    service frr start


Observe se os processos estão em execução:


    ps ax | grep frr

 39213 ?   S<s    0:00 /usr/lib/frr/watchfrr -d zebra bgpd ospfd ospf6d babeld staticd
 39238 ?   S<sl   0:00 /usr/lib/frr/zebra -d -A 127.0.0.1 -s 90000000
 39243 ?   S<sl   0:00 /usr/lib/frr/bgpd -d -A 127.0.0.1
 39252 ?   S<s    0:00 /usr/lib/frr/ospfd -d -A 127.0.0.1
 39259 ?   S<s    0:00 /usr/lib/frr/ospf6d -d -A ::1
 39266 ?   S<s    0:00 /usr/lib/frr/babeld -d -A 127.0.0.1
 39272 ?   S<s    0:00 /usr/lib/frr/staticd -d -A 127.0.0.1


Analisando status:


    service frr status

 frr.service - FRRouting
   Loaded: loaded (/lib/systemd/system/frr.service; enabled; vendor preset: enabled)
   Active: active (running) since Tue 2020-08-11 04:24:53 -03; 3min 17s ago
     Docs: https://frrouting.readthedocs.io/en/latest/setup.html
  Process: 39204 ExecStart=/usr/lib/frr/frrinit.sh start (code=exited, status=0/SUCCESS)
    Tasks: 15 (limit: 2330)
   Memory: 16.3M
   CGroup: /system.slice/frr.service
           ├─39213 /usr/lib/frr/watchfrr -d zebra bgpd ospfd ospf6d babeld staticd
           ├─39238 /usr/lib/frr/zebra -d -A 127.0.0.1 -s 90000000
           ├─39243 /usr/lib/frr/bgpd -d -A 127.0.0.1
           ├─39252 /usr/lib/frr/ospfd -d -A 127.0.0.1
           ├─39259 /usr/lib/frr/ospf6d -d -A ::1
           ├─39266 /usr/lib/frr/babeld -d -A 127.0.0.1
           └─39272 /usr/lib/frr/staticd -d -A 127.0.0.1

Aug 11 04:24:53 labserver watchfrr[39213]: zebra state -> up : connect succeeded
Aug 11 04:24:53 labserver watchfrr[39213]: bgpd state -> up : connect succeeded
Aug 11 04:24:53 labserver watchfrr[39213]: ospfd state -> up : connect succeeded
Aug 11 04:24:53 labserver watchfrr[39213]: ospf6d state -> up : connect succeeded
Aug 11 04:24:53 labserver watchfrr[39213]: babeld state -> up : connect succeeded
Aug 11 04:24:53 labserver watchfrr[39213]: staticd state -> up : connect succeeded
Aug 11 04:24:53 labserver watchfrr[39213]: all daemons up, doing startup-complete notify
Aug 11 04:24:53 labserver frrinit.sh[39204]: Started watchfrr.
Aug 11 04:24:53 labserver systemd[1]: Started FRRouting.
Aug 11 04:25:07 labserver watchfrr[39213]: configuration write completed with exit code 0







frr_zebra


Configurandao ZEBRA

O Zebra, alem de ser um framework de protocolos de rede, ele também se propõe a ser um shell independente.

Esse shell é implementado pelo VTYSH, que segue o modelo Cisco de comandos (show, configure terminal, quit, end, write, etc...).

O comando "vtysh" é, internamente, um loop interpretador de palavras utilizando a biblioteca GNU Readline.

Ao contrário do shell Bash, onde cada palavra é um arquivo a ser procurado na variavel $PATH, o VTYSH é mais simplório.

O Zebra registra os comandos e respectivas funções em uma tabela interna. Quando um ZClient é iniciado ele informa ao Zebra seus próprios comandos.

Quando uma nova sessão do VTYSH é iniciada, a primeira palavra digitada é procurada na lista de comandos, se encontrada, a função associada é invocada.

Uma grande vantagem desse shell é possibilidade de criar um Linux básico com apenas o FRR, orientado a funções de rede, onde ao acessar via terminal, telnet ou ssh, o shell padrão do usuário aponta para o VTYSH.

Exemplo (entrando, exibindo a versão (show version), saindo (exit):


    vtysh


Hello, this is FRRouting (version 6.0.2).
Copyright 1996-2005 Kunihiro Ishiguro, et al.

labserver# 
labserver# show version
FRRouting 6.0.2 (labserver).
Copyright 1996-2005 Kunihiro Ishiguro, et al.
configured with:
    ...

labserver# exit

Uma outra forma de acessar o shell do zebra é via TELNET.

Por padrão o FRR não abre portas telnet, se você desejar experimentar o acesso a essas portas, será necessário atribuir a senha de acesso e a senha e enable (acesso privilegiado).


    vtysh


Hello, this is FRRouting (version 6.0.2).
Copyright 1996-2005 Kunihiro Ishiguro, et al.

labserver# configure terminal
labserver(config)# password tulipa
labserver(config)# enable password javali
labserver(config)# service password-encryption
labserver(config)# line vty
labserver(config-line)# login
labserver(config)# end
labserver# write
Note: this version of vtysh never writes vtysh.conf
Building Configuration...
Integrated configuration saved to /etc/frr/frr.conf
[OK]

labserver# exit


Para abrir as portas de TELNET, edite o arquivo /etc/frr/daemons e encontre as variáveis abaixo, e complete-as com o argumento -P

# Arquivo /etc/frr/daemons

zebra_options="  -A 127.0.0.1 -s 90000000 -P 2300"
bgpd_options="   -A 127.0.0.1"
ospfd_options="  -A 127.0.0.1"
ospf6d_options=" -A ::1"

Reinicie o FRR:


    service frr stop
    service frr start

Acessando Zebra via TELNET:


    telnet  localhost  2300

Trying ::1...
Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.

Hello, this is FRRouting (version 6.0.2).
Copyright 1996-2005 Kunihiro Ishiguro, et al.


User Access Verification

Password: digite: tulipa
labserver> 
labserver> 
labserver> enable
Password:  digite: javali
labserver# 
labserver# 
labserver# exit

Embora não seja seguro utilizar telnet, uma das aplicações para esse tipo de acesso é a confecção de servidores Looking Glass, bastando remover a senha comum para que todos os usuários tenham acesso livre a parte comum (somente leitura e consulta).

Exemplo:


    vtysh


Hello, this is FRRouting (version 6.0.2).
Copyright 1996-2005 Kunihiro Ishiguro, et al.

labserver# configure terminal
labserver(config)# no password
Please be aware that removing the password is a security risk and you should think twice about this command.
labserver(config)# line vty
labserver(config-line)# no login
labserver(config)# end
labserver# write
Note: this version of vtysh never writes vtysh.conf
Building Configuration...
Integrated configuration saved to /etc/frr/frr.conf
[OK]

labserver# exit

Acredito que você ja tenha entendido como funciona o VTYSH, como entrar e sair dele.

De agora em diante vou exibir apenas os comandos digitados nas telas pretas, assim ficará mais fácil para você copiar do artigo e colar no terminal.

Antigamente a pilha zebra mantinha a configuração de cada aplicação em seu respectivo arquivo (zebra.conf, ospfd.conf, bgpd.conf, etc...)

Agora por padrão, todas as configurações ficam centralizadas em um único arquivo: /etc/frr/frr.conf, e o que diz respeito a cada aplicação fica em seu respectivo arquivo, difere que ao ser iniciado apenas o frr.conf é relevante. Esse comportamento padrão é determinado pela configuração "service integrated-vtysh-config".

Desativando o service integrated-vtysh-config:


config t
    no service integrated-vtysh-config
    end
write

# Note: this version of vtysh never writes vtysh.conf
# Building Configuration...
# Configuration saved to /etc/frr/zebra.conf
# Configuration saved to /etc/frr/ospfd.conf
# Configuration saved to /etc/frr/ospf6d.conf
# Configuration saved to /etc/frr/bgpd.conf
# Configuration saved to /etc/frr/babeld.conf
# Configuration saved to /etc/frr/staticd.conf
# [OK]

Ativando o service integrated-vtysh-config, configuração padrão desejável:


config t
    service integrated-vtysh-config
    end
write

# Note: this version of vtysh never writes vtysh.conf
# Building Configuration...
# Integrated configuration saved to /etc/frr/frr.conf
# [OK]

Nota: até a versão corrente, independente do que se fazia, ao reiniciar o FRR ele sempre pinava com o service integrated-vtysh-config ativado.


Concluímos até aqui as operações básicas no framework Zebra. Vamos operar alguns protocolos.





frr_ospfv2


Configurandao OSPFv2 (OSPF para IPv4)

O OSPFv2 é um protocolo relativamente simples. Principais regras:

  • As interfaces de um roteador ligada ao outro devem estar na mesma área;
  • As interfaces envolvidas devem ter o mesmo MTU (isso pode ser ignorado);
  • As interfaces envolvidas devem ter o mesmo tipo de adjacência (P2P, BROADCAST, NBMA ou PTMP), padrão BROADCAST;
  • As interfaces envolvidas devem ter a mesma autenticação e senha (ou ambas sem senha);
  • As interfaces devem possuir a mesma máscara de rede;
  • Cada roteador deve ter seu Router-ID (número único de identificação, tipo um CPF);
  • Um roteador NÃO PODEM TER O MESMO ROUTER-ID de outro;
  • A área BACKBONE (area-id 0.0.0.0) deve existir e ser o centro da rede;
  • Todas as áreas devem estar conectadas à área BACKBONE;
  • Áreas atras de áreas devem possuir um mecanismo para não violar a regra acima (virtual-link).

O roteador (nosso Linux) irá enviar um HELLO nas interfaces cadastradas na área, se houver resposta de roteadores vizinhos com os mesmos parâmetros eles iniciam a adjacência (troca de informações).

Para cadastrar uma interface na área, o padrão Cisco requer que você informe uma WILDCARD (prefixo IP e máscara invertida, para deixar bem claro que se trata de uma ACL e não uma REDE). O FRR adotou o uso de prefixo IP normal (IP + número de bits da máscara) para criar esse filtro classificador.

Vou repetir: o NETWORK do OSPF não é uma rede a ser anunciada, é uma ACL para determinar pelo IP da interface se ela participa ou não de alguma área.

A área padrão em uma rede OSPF é a área BACKBONE, representada pelos 32 bits em zero (0.0.0.0).

Observe o diagrama abaixo:


# Roteador BGP
config t
    router ospf
        network 10.90.0.0/30 area 0.0.0.0
        default-information originate always
    end
write

# Roteador CORE
config t
    router ospf
        network 10.90.0.0/30 area 0.0.0.0
        network 10.0.0.0/30  area 0.0.0.0
    end
write

# Roteador BNG
config t
    router ospf
        network 10.0.0.0/30  area 0.0.0.0
    end
write

Comandos explicados:

  • router ospf: ativa o software de OSPF
  • network PREFIXO area AREAID: cria um filtro, toda interface que possuir um IP dentro do PREFIXO passará a participar da área AREAID
  • default-information originate always: origina gateway padrão, informa para os demais roteadores o caminho para a Internet. Somente o roteador de borda (ligado ao link de Internet) pode ter essa opção ativa.

Dado os fatos, a configuração abaixo é igualmente eficiente:

# Roteador BGP
config t
    router ospf
        network 10.0.0.0/8 area 0.0.0.0
        default-information originate always
    end
write

# Roteador CORE
config t
    router ospf
        network 10.0.0.0/8 area 0.0.0.0
    end
write

# Roteador BNG
config t
    router ospf
        network 10.0.0.0/8 area 0.0.0.0
    end
write

Se você observou bem, nada foi mencionado na configuração do OSPF a respeito do servidor Zabbix na rede 172.16.0.0/24, o que significa que apenas o roteador BNG conseguirá se comunicar com ele (por estar na mesma subrede - rota conectada).
Temos 3 opções aqui:

  • 1 - Declarar a rede 172.16.0.0/24 no OSPF (permite adjacências nessa rede);
  • 2 - Declarar a rede 172.16.0.0/24 no OSPF e colocar a eth0 do roteador BNG como passiva (NÃO permite adjacências nessa rede);
  • 3 - Informar ao roteador BNG que propague rotas conectadas para os demais roteadores OSPF.

# Roteador BNG - Opção 1
config t
    router ospf
        network 10.0.0.0/8 area 0.0.0.0
        network 172.16.0.0/24 area 0.0.0.0
    end
write

# Roteador BNG - Opção 2
config t
    interface 
    router ospf
        network 10.0.0.0/8 area 0.0.0.0
        network 172.16.0.0/24 area 0.0.0.0
        passive-interface eth0
    end
write

# Roteador BNG - Opção 3
config t
    interface 
    router ospf
        network 10.0.0.0/8 area 0.0.0.0
        redistribute connected
    end
write

Principais comandos de analise:


show run ospfd

show ip ospf interface

show ip ospf interface json

show ip ospf interface eth0

show ip ospf route

show ip ospf neighbor

show ip ospf neighbor all

show ip ospf neighbor detail

show ip ospf database 

As adjacências (ato de dois ou mais roteadores estabelecerem troca de informações) no OSPF é por padrão do tipo BROADCAST.

Vale ressaltar que estamos falando de um tipo de adjacência, e não um tipo de pacote (rede OSPF tipo Broadcast não tem a ver com pacotes broadcast ip ou mac). E o OSPF não usa pacotes broadcast, apenas multicast.

As regras de uma rede local com adjacência BROADCAST são:

  • Os roteadores que participam da sub-rede devem enviar um HELLO periódico;
  • Apenas os roteadores com o mesmo HELLO INTERVAL devem ser considerados vizinhos aptos;
  • Após completar 1 ciclo de Hello-Interval, o roteador com maior PRIORITY vence a eleição e se forna o DR (presidente);
  • No empate de PRIORITY, o desempate se dá pelo Router-ID, o maior vence;
  • O roteador com a segunda maior PRIORITY se torna o DR-BACKUP (BDR, vice-presidente);
  • Os demais roteadores se toram DR-OTHER (servos);
  • Todas as atualizações numa sub-rede BROADCAST devem ser enviadas somente para o DR e BDR, o DR fica responsável por replicar aos demais;
  • Na queda do DR, o BDR se torna o novo DR e um DR-OTHER de maior PRIORITY/Router-ID assume como novo BDR;
  • Se o DR antigo retornar, ele se torna DR-OTHER até que os novos DR e DRB sofram quedas;
  • Nos pacotes HELLO de todos os participantes de uma sub-rede devem constar quem é o DR e BDR. Assim se um novo roteador for configurado com maior PRIORITY e ingressar na sub-rede, ele não quebra a hierarquia vigente (ele precisa esperar a próxima queda do DR/BDR para ser eleito).

Outro tipo comum de adjacência é o POINT-TO-POINT (P2P ou PTP).

Trata-se de uma sub-rede utilizada em um enlace com apenas um roteador em cada ponta, quando você liga um roteador direto em outro, ou o OSPF é feito dentro de um Tunnel/VPN L3.

Nesse tipo de adjacência basta que um dos lados envie um HELLO para que a adjacência suba imediatamente. Não há eleição de DR e BDR.

Nossa rede exemplo ficaria melhor configurado dessa forma:



Há uma pegadinha no diagrama acima.

Como nós não determinamos o Router-ID, o OSPF utiliza um dos IPs locais como Router-ID, como também não determinamos o PRIORITY das interfaces, todas elas subiram com PRIORITY 1 (valor padrão). O roteador BNG pode ter o Router-ID 10.90.0.2 ou 172.16.0.1, independente disso, se ele participar da rede 172.16.0.0/24 em adjacência BROADCAST, ele perderá para o servidor Zabbix na eleição, e se tornará BDR. Isso não faz nenhum sentido pra mim.
Se futuramente subirmos mais um servidor nessa subrede com ip 172.16.0.3/24 e ele participar do OSPF, ele será o futuro DR, o Servidor Zabbix BDR e o roteador BNG um Dr-Other.

Portanto, segue a configuração dos 3 roteadores corretamente configurados:

# Roteador BGP
config t
    interface eth0
        ip ospf network point-to-point

    router ospf
        network 10.0.0.0/8 area 0.0.0.0
        default-information originate always
    end
write

# Roteador CORE
config t
    interface eth0
        ip ospf network point-to-point

    interface eth2
        ip ospf network point-to-point

    router ospf
        network 10.0.0.0/8 area 0.0.0.0
    end
write

# Roteador BNG
config t
    interface eth0
        ip ospf priority 255
        ip ospf network broadcast

    interface eth2
        ip ospf network point-to-point

    router ospf
        network 10.0.0.0/8 area 0.0.0.0
        network 172.16.0.0/24 area 0.0.0.0
        redistribute connected
    end
write

Deixei por último a configuração da LOOPBACK e do Router-ID. Eu ouço em muitos cursos e videos de OSPF que a loopback e o Router-ID são vitais para a rede OSPF, e sem eles a rede não funciona. ERRADO.

O RouterID é auto-configurado, e se obviamente você não repetir IP na rede, cada roteador usará um dos seus próprios IPs, que são únicos e inequívocos, logo não há problema algum em deixar o RouterID automático se você não cometeu erros grosseiros na alocação de prefixos IP.

Ja o caso da loopback, é importante que seu roteador tenha um IP que não dependa de cabos para ficar sempre ativo. Se você configura seu SNMP ou qualquer outro protocolo para acessar um roteador, e a interface onde está esse IP perde linha (cabo retirado, fibra rompida), o IP é desativado e você perde contato, tendo que usar um IP de outra interface.

Configurando uma Loopback, independe de qual abordagem ao roteador rompeu, a rota para alcançar a loopback continua lá na rede.

Juntando esses dados, podemos dar um IP único para a loopback de cada roteador, e usamos esse ip como base de tudo: monitoramento, Router-ID do OSPF/LDP/BGP, etc...

Rede com Loopback e Router-ID manual:


# Roteador BGP
config t
    interface lo
        ip address 10.255.255.1/32

    interface eth0
        ip ospf network point-to-point

    router ospf
        ospf router-id 10.255.255.1
        network 10.0.0.0/8 area 0.0.0.0
        default-information originate always
    end
write

# Roteador CORE
config t
    interface lo
        ip address 10.255.255.2/32

    interface eth0
        ip ospf network point-to-point

    interface eth2
        ip ospf network point-to-point

    router ospf
        ospf router-id 10.255.255.2
        network 10.0.0.0/8 area 0.0.0.0
    end
write

# Roteador BNG
config t
    interface lo
        ip address 10.255.255.3/32

    interface eth0
        ip ospf priority 255
        ip ospf network broadcast

    interface eth2
        ip ospf network point-to-point

    router ospf
        ospf router-id 10.255.255.3
        network 10.0.0.0/8 area 0.0.0.0
        network 172.16.0.0/24 area 0.0.0.0
        redistribute connected
    end
write

Para encerrar a matéria de OSPFv2, vamos implementar o tratamento de rotas conectadas de usuários PPPoE. Fonte das principais demandas do uso de OSPF e onde acontecem uma quantidade enorme de deselegâncias na configuração.

Considere o diagrama abaixo, onde no roteador BNG temos um PPPoE Server (Accel-ppp ou RP-PPPoE, ...).


  • Os clientes PPPoE por padrão recebem IPs no prefixo CGNAT 100.80.0.0/19 e sofrem CGNAT no mesmo roteador para o prefixo 45.255.130.0/25;
  • Os clientes PPPoE bloqueados recebem IPs no prefixo de bloqueio 172.22.0.0/22, e não sofrem CGNAT, acesso limitado ao backbone apenas;
  • Alguns clientes irão receber IPs públicos determinados pelo RADIUS, assim, qualquer ip da faixa 45.255.128.0/22 (entre 45.255.128.0 e 45.255.131.255) pode contar como rota conectado no roteador BNG.

Missão:
É necessário que o roteador BGP e o roteador CORE tenham conhecimento das rotas utilizadas no roteador BNG via clientes PPPoE.

Existem algumas formas de resolver esse problema, a saber:

Opção 1 - Colocar os prefixos 100.80.0.0/19, 172.22.0.0/22 na área backbone.
Essa é a pior técnica de todas.

Sempre que você declarar uma rede no OSPF, você está criando um filtro que determina quais interfaces participam da área, e incluir o POOL de clientes PPPoE nesse filtro é uma violência à rede. Cada interface PPP será classificada como uma interface OSPF assim que receber um endereço IP dentro dos filtros de OSPF Network, tal interface aparecerá no comando "show ip ospf interface", e pior de tudo, um LSA (Link-state advertisement) será enviado para cada evento up/down de cada interface, 1000 usuários representariam 2000 LSA que irão inundar todo o backbone.

Se houver LDP na rede, cada atualização de rota IP resultará no provisionamento de um LABEL MPLS para ela.
O endereço IP do cliente PPPoE (/32) será propagado por todo backbone, 1 rota por conexão PPPoE. Num provedor com 16 mil usuários, isso seria um completo inferno astral para o backbone.

Para piorar, cada interface classificada na área será uma possivel adjacência, o OSPF enviará HELLO padrão periódio para cada interface PPP, com 1000 clientes online isso significa 1 hello a cada 10 segundos, 6 hellos por interface PPP a cada minuto, 6000 pacotes por minuto sendo injetados na rede de clientes PPPoE. Isso numa rede rádio é um desastre.
    router ospf
        # ...

        network 100.80.0.0/19 area 0.0.0.0
        network 172.22.0.0/22 area 0.0.0.0
        network 45.255.128.0/22 area 0.0.0.0

        # ...
    end

Opção 2 - colocar as interfaces OSPF como padrão passivo.
Para resolver os problemas da opção 1, cujo sintoma é estouro de CPU dos roteadores do backbone, algumas pessoas classificam todas as interfaces por padrão como passivas, ou seja, ainda serão classificadas como interfaces na área, gerando LSA abusivo, mas não haverá possibilidade de adjacência com os clientes PPPoE pela supressão do envio de hello. Se a opção 1 era extremamente horrível, essa é apenas muito ruim.

O endereço IP do cliente PPPoE (/32) ainda será propagado por todo backbone, 1 rota por conexão PPPoE.
    router ospf
        # ...

        network 100.80.0.0/19 area 0.0.0.0
        network 172.22.0.0/22 area 0.0.0.0
        network 45.255.128.0/22 area 0.0.0.0

        passive-interface default
        no passive-interface eth0
        no passive-interface eth1

        # ...
    end

Opção 3 - Criar uma sumarização de rotas de uma área periférica
A sumarização de rotas de uma área é um mecanismo que, ao especificar um prefixo sumarizado, a presença de apenas 1 prefixo especifico dentro do prefixo sumarizado dispara o anuncio da rota sumarizada, e não as rotas especificas.

Essa técnica sozinha é ineficiente em concentradores PPPoE pois ainda há o registro de cada interface PPP no banco de dados de interfaces OSPF dentro da área, se na mesma área houver outras redes, elas serão inundadas de LSA.
Para evitar que os clientes sejam inundados com hello, combina-se com o uso de interfaces passivas.

Posso classificar essa técnica como não muito ruim.
    router ospf
        # ...

        network 100.80.0.0/19 area 0.0.0.99
        network 172.22.0.0/22 area 0.0.0.99
        network 45.255.128.0/22 area 0.0.0.99

        area 0.0.0.99 range 100.80.0.0/19
        area 0.0.0.99 range 172.22.0.0/22

        passive-interface default
        no passive-interface eth0
        no passive-interface eth1

        # ...
    end

Opção 4 - Importar rotas conectadas
Em vez de torrar o banco de dados do OSPF com milhares de dados e cálculos de interfaces, adjacências em PPP, sumarização, podemos simplesmente não incluir os usuários PPPoE diretamente no OSPF e obter as rotas conectadas importando-as do kernel para dentro do banco de dados de rotas OSPF.

Não haverá inundação de LSA e teremos apenas atualização de rotas, estressando menos o algoritmo Dijkstra’s.

Essa técnica é a mais comum, mas ainda tem um efeito desagradável. A rede é inundada com muitas rotas /32, uma para cada usuário conectado. O que tem efeitos colaterais desastrosos no LDP/MPLS e na CPU de todos os roteadores do backbone.

Eu classifico essa técnica como ruim, preguiçosa.
    router ospf
        # ...

        redistribute connected

        # ...
    end

Opção 5 - Importar rota estática do prefixo blackhole
Quando eu informo para algum aluno ou cliente que uma rota blackhole destrui os pacotes com destino nela, a primeira reação é sempre de repulsa, porque deletar os pacotes que vão para os IPs dos clientes?

Observe a configuração:
    ip route 100.80.0.0/19 blackhole 1
    ip route 172.22.0.0/22 blackhole 1

    router ospf
        # ...

        redistribute static

        # ...
    end

Embora os prefixos estejam em blackhole, quando um cliente PPPoE se conectar uma nova rota /32 surgirá, e por ser mais específica a rota /32 vence a decisão, e em vez do pacote ser deletado ele é enviado ao cliente.

Isso é o que acontece no roteador BNG, mas os demais roteadores não irão receber rotas conectadas nesse caso. Somente as rotas estáticas, e rotas blackhole são rotas estáticas.

Essa técnica provê um efeito de sumarização simples e elegante, não haverá notificações aos roteadores do backbone OSPF independente se estiverem conectados 1 ou 10 mil usuários.

Opção 6 - Importar rotas estáticas e conectadas com política de importação
Se você observou bem, não tratamos do prefixo público do CGNAT em nenhum momento, o prefixo 45.255.130.0/25.

Existem 4 formas de guiar a rota do prefixo público até o equipamento CGNAT (Roteador BNG no nosso caso).
  • 1 - Criam uma rota estática no roteador acima (o Roteador CORE aponta o prefixo para o roteador BNG). Não vou nem comentar pois considero que toda rota estática que não seja blackhole uma BOMBA RELÓGIO a explodir na cara do suporte nível 3;
  • 2 - Colocar todos os IPs do prefixo público de CGNAT como /32 na interface loopback, uma grosseria (um monte de IPs respondendo a ping, um monte de rotas /32 enchendo a rede, um monte de linhas na configuração);
  • 3 - Colocar o primeiro IP do prefixo com a máscara correta na interface Loopback ou Null. Pena que alguns roteadores não aceitam IPs na loopback que não seja /32, nem atribuição de IPs na interface Null (dummy). Essa é uma boa opção, mas infelizmente não é universal;
  • 4 - Criar uma rota blackhole do prefixo público de CGNAT. Acredite: isso não vai impedir o funcionamento do CGNAT pois quando o pacote retorna da Internet o IP de destino público é revertido para o IP privado do cliente antes da etapa de roteamento (estágio PREROUTING). A rota passa a ser uma simples rota estática.

Outra coisa que não foi abordada ainda é o uso de IPs públicos delegado aos clientes via RADIUS. Algumas redes colocam todo a faixa de IPs público numa área OSPF, o que nos retorna ao mesmo problema da opção 1.

Devido o fato de que uma rota /32 de IP público é uma rota do tipo diretamente conectada, importar rotas conectadas resolveria esse problema, se não fosse o fato de que todas os demais /32 de IPs privados no CGNAT se enquadram na mesma categoria.

Vamos resolver os problemas dos IPs públicos e blackholes de uma mesma forma: fazendo o controle de rotas que iremos importar para dentro do OSPF.

Veja a configuração completa:
    interface lo
        ip address 10.255.255.3/32

    interface eth0
        ip ospf priority 255
        ip ospf network broadcast

    interface eth2
        ip ospf network point-to-point


    # Blackholes:
    ip route 100.80.0.0/19 blackhole 1
    ip route 172.22.0.0/22 blackhole 1
    ip route 45.255.130.0/25 blackhole 1

    # Lista de prefixos permitidos
    ip prefix-list BNG-Routes-IPv4 seq 10 permit 100.80.0.0/19
    ip prefix-list BNG-Routes-IPv4 seq 20 permit 172.22.0.0/22
    ip prefix-list BNG-Routes-IPv4 seq 30 permit 45.255.130.0/25
    ip prefix-list BNG-Routes-IPv4 seq 40 permit 45.255.128.0/22 ge 25 le 32

    # Politica para permitir apenas prefixos da lista acima
    route-map BNG-OSPF-Import-IPv4 permit 1
        match ip address prefix-list BNG-Routes-IPv4
    #

    router ospf
        ospf router-id 10.255.255.3
        network 10.0.0.0/8 area 0.0.0.0
        network 172.16.0.0/24 area 0.0.0.0

        redistribute static     route-map  BNG-OSPF-Import-IPv4
        redistribute connected  route-map  BNG-OSPF-Import-IPv4

    end

Explicando:
  • A - Colocamos os 3 prefixos utilizados localmente (Pool Cliente, Pool bloqueados e Prefixo público CGNAT) no blackhole (rota estática);
  • B - Dentro do OSPF informamos que iremos importar rotas estáticas e rotas conectadas, mas somente se a política BNG-OSPF-Import-IPv4 permitir;
  • C - Na política BNG-OSPF-Import-IPv4 informamos que iremos permitir apenas prefixos cadastrados na lista BNG-Routes-IPv4;
  • D - Na lista BNG-Routes-IPv4 colocamos os 3 prefixos utilizados localmente (regra 10, 20 e 30), e qualquer IP público dentro do prefixo principal (45.255.128.0/22) na regra 40.

Dessa forma, o OSPF manterá o máximo de silêncio após anunciar os 3 prefixos no blackhole, e quebrará o silêncio apenas quando algum cliente se conectar com algum IP público (enviado pelo RADIUS).






frr_ospfv3


Configurandao OSPFv3 (OSPF para IPv6)

Embora o OSPFv3 tenha sido construído para fazer no IPv6 o que o OSPFv2 faz no IPv4, ele é muito mais do que isso. Ele veio com suporte a famílias de endereços, assim, no futuro o OSPFv3 pode assumir o roteamento de qualquer família de protocolos, principalmente IPv4.

O OSPFv3 é mais simples de operar que o OSPFv2, a primeira diferença facilitadora é que ele é objetivo em relação às interfaces de redes e as áreas, a segunda é que ele NÃO PRECISA DE ENDEREÇOS CONFIGURADOS NA INTERFACE PARA FUNCIONAR.

Isso mesmo, uma rede sem nenhum IPv6 configurado funciona só de você rodar OSPFv3 no backbone, mesmo que entre as interfaces dos roteadores do backbone não hajam endereços IPv6 configurados.

Isso de deve a natureza LINK-LOCAL (fe80::) das comunicações IPv6.


Considerando o diagrama acima, a configuração fica assim:

# Roteador BGP
config t
    interface lo
        ipv6 address 2804:cafe:ffff:ffff::1/128

    interface eth0
        ipv6 ospf6 network point-to-point

    ipv6 route 2000::/3 blackhole 250

    ipv6 prefix-list GLOBAL-SUMMARY-IPV6 permit 2000::/3
    ipv6 prefix-list GATEWAY-IPV6 permit ::/0

    route-map OSPFV3-IMPORT-STATIC permit 10
        match ipv6 address prefix-list GLOBAL-SUMMARY-IPV6
    route-map OSPFV3-IMPORT-STATIC permit 20
        match ipv6 address prefix-list GATEWAY-IPV6

    router ospf6
        ospf6 router-id 10.255.255.1
        interface eth0 area 0.0.0.0
        interface lo area 0.0.0.0
        redistribute static route-map OSPFV3-IMPORT-STATIC
    end

write

# Roteador CORE
config t

    interface lo
        ipv6 address 2804:cafe:ffff:ffff::2/128

    interface eth0
        ipv6 ospf6 network point-to-point

    interface eth2
        ipv6 ospf6 network point-to-point

    router ospf6
        ospf6 router-id 10.255.255.2
        interface eth0 area 0.0.0.0
        interface eth2 area 0.0.0.0
        interface lo area 0.0.0.0
    end
write

# Roteador BNG
config t
    interface lo
        ipv6 address 2804:cafe:ffff:ffff::3/128

    interface eth0
        ipv6 ospf6 network point-to-point

    interface eth2
        ipv6 ospf6 network point-to-point

    ipv6 route 2804:CAFE:D100::/48 blackhole 1
    ipv6 route 2804:CAFE:D200::/48 blackhole 1
    ipv6 route 2001:DB8:FADA::/48  blackhole 1

    router ospf6
        ospf6 router-id 10.255.255.3
        interface eth0 area 0.0.0.0
        interface eth2 area 0.0.0.0
        interface lo area 0.0.0.0
        redistribute static

    end
write





frr_babel


Configurandao BABEL





frr_bgp


Configurandao BGP





Configurandao BGP para RouterReflector





Configurandao BGP para RouterServer















CONTINUA... (ainda estou escrevendo!)
CONTATO