Dagbog-bloggen

Software-router del 4: Border Network Gateway

Sommeren er over os, og selv om temperaturen i skyggen om dagen nærmer sig 30 grader, og stranden med de blå bølger frister, er det blevet tid til at kigge lidt mere på software-routing.

Jeg har tidligere betegnet en Linux-server som netværkets svar på en schweizerkniv - et alsidigt stykke værktøj, der kan bruges til rigtig mange ting.

Sammenligningen er ikke helt fair, for modsat en schweizerkniv, der både er en halvdårlig skruetrækker og en halvdårlig kniv, men kan bruges i en nødsituation, er en Linux-server et udmærket valg, hvis man skal bygge en billig, stabil og frem for alt fleksibel software-router, der kan anvendes i et netværk hos en mindre internetudbyder.

Der er dog en opgave, vi hos Kviknet endnu ikke har fået Linux til at håndtere med success: Opgaven som Border Network Gateway, også kaldet BNG.

En BNG er det punkt, hvor den enkelte kundes trafik overgår fra layer 2 til layer 3, og dermed er det også den enkelte kundes default gateway.

Aggregering af VLANs

Hvis man som udbyder har DSL- eller fiberkunder på TDC's netværk, udveksler man trafikken med TDC gennem en eller flere såkaldte POI-porte (Point of Interconnect). En POI-port er typisk på 1 eller 10 Gbit/s, og antallet af mulige kunder på en POI-port dikterer derfor antallet af VLANs, der bliver overført på porten, da hver enkelt kunde har sit eget VLAN.

En POI-port er typisk en QinQ-trunk, hvilket betyder at hver eneste ethernet-pakke både indeholder et outer og et inner VLAN tag (802.1q header). Det giver plads til lidt over 16 mio. unikke VLAN-kombinationer pr. POI-port.

Illustration: Luca Ghio / Wikipedia

Det er mere end rigeligt til vores brug, men alternativet havde været et enkelt VLAN-tag, som kun giver 4096 unikke kombinationer, og det er lige i underkanten.

På Kviknets hardware-routere, der i dag agerer BNG, definerer vi en liste over VLAN ranges, de enkelte interfaces skal kommunikere på.

vlan-configuration
  interface xgei-0/0/0/2.3
    qinq range internal-vlan-range 201-206 external-vlan-range 30
    qinq range internal-vlan-range 208-209 external-vlan-range 30
    qinq range internal-vlan-range 216 external-vlan-range 30
    qinq range internal-vlan-range 218 external-vlan-range 30
    qinq range internal-vlan-range 221 external-vlan-range 30
    qinq range internal-vlan-range 226-229 external-vlan-range 30
    qinq range internal-vlan-range 231-233 external-vlan-range 30
    qinq range internal-vlan-range 235-236 external-vlan-range 30
    qinq range internal-vlan-range 239-241 external-vlan-range 30

På det enkelte interface sætter vi også en IP-adresse, der skal være default gateway for de kunder, der er tilknyttet de VLANs, vi har defineret.

interface xgei-0/0/0/2.3
  description "POI-port Nyborg"
  ip vrf forwarding kviknet
  ip address 185.107.15.1 255.255.255.192
  ip address 100.64.128.1 255.255.255.192 secondary
  ip address 100.64.128.65 255.255.255.192 secondary

På den måde kan vi lade den enkelte kunde indgå i et større netværk på fx 64 IP-adresser (/26). Det holder spildet af IP-adresser nede, da hvert netværk koster os 4 IP-adresser: En til netværket selv, en til default gateway, en til backup-gateway og en til broadcast.

Vi ønsker at holde vores kunder isoleret fra hinanden på layer 2-niveau. Det skyldes dels et hensyn til sikkerheden, dels et hensyn til stabiliteten af netværket, da det ellers ville være nemt for kunder at forstyrre hinandens adgang til internettet ved simple uheld.

Vores interface på BNG'en fungerer som et router-interface og ikke som en switchport. Det betyder, at kunderne som udgangspunkt ikke kan kommunikere med hinanden, da ARP-forespørgsler, broadcasts m.v. ikke sendes videre fra et VLAN til et andet - det er kun IP-trafik, der sendes fra kunden til BNG'ens egen MAC-adresse, der routes.

BNG'en vedligeholder en ARP cache, der mapper kundernes IP-adresser til MAC-adresser. I forvejen vedligeholder routeren en MAC-adressetabel, som mapper den enkelte kundes MAC-adresse til et specifikt VLAN.

Så længe begge tabeller er up to date, fungerer systemet fint, men hvis en IP-adresse er gledet ud af ARP-tabellen pga. inaktivitet, er BNG'en nødt til at sende en ARP-forespørgsel til samtlige VLANs for at finde den rigtige modtager af pakkerne.

Det giver et potentielt stabilitetsproblem - hvis en kunde har konfigureret en anden kundes IP-adresse statisk, vil der opstå en IP-konflikt, hvor begge kunder vil opleve, at forbindelsen med jævne mellemrum er væk.

Det problem kan løses vha. DHCP snooping, hvor BNG'en kun tillader en kunde at anvende en IP-adresse, som er uddelt af en af vores DHCP-servere. Det har dog den bi-effekt, at alle kunder uden undtagelse er nødt til at anvende DHCP, og samtidig umuliggør det, at vi kan tildele mere end 1 IP-adresse pr. kunde.

I den ideelle verden kunne vi fortælle BNG'en, at en specifik IP-adresse hørte til et specifikt VLAN. Firmwaren på BNG'en tillader os dog kun at låse specifikke MAC-adresser til specifikke VLANs, og det skalerer ikke specielt godt.

Software-router som BNG

En hardware-router i den kaliber, vi anvender som BNG, koster langt over 100.000 kr., mens en Linux-server kan bygges for under 10.000 kr.

Hvis vi kan øge antallet af BNG'er, får vi et mere robust netværk, da nedbrud og fejl på den enkelte BNG vil kunne begrænses til færre berørte kunder.

Kan vi bruge en Linux-server som BNG?

Både og. Det altoverskyggende problem, vi støder på, er den måde, Linux håndterer VLANs på.

Hvis man skal modtage trafik på et VLAN i Linux, skal man definere et VLAN-interface, som hægtes på et fysisk interface.

Et VLAN-interface kan kun håndtere 1 VLAN. Skal man bruge QinQ, skal man definere et VLAN-interface (inner VLAN), der er hægtet på et andet VLAN-interface (outer VLAN), som til sidst er hægtet på et fysisk interface.

Illustration: Yoel Caspersen

Hvis man vil have flere VLANs til at dele samme IP-adresserum, skal man melde sine VLAN-interfaces ind i en bridge, som er en slags virtuel switch. På bridge-interfacet definerer man så den IP-adresse, der skal være default gateway for de tilmeldte VLANs.

Illustration: Yoel Caspersen

Vil man på en Linux-baseret BNG håndtere 200 kunder på hver sit VLAN, vil man således skulle have lidt over 200 VLAN-interfaces. Vil man håndtere 4.000 kunder, skal man have lidt over 4.000 VLAN-interfaces.

Det skalerer ikke særlig godt - ud over det åbenlyse problem i at overskue opsætningen på en Linux-server med 4.000 VLAN-interfaces, er der mange ting, der holder op med at virke, når antallet af interfaces overstiger 1024, herunder en lang række programmer, hvor enumerering af samtlige interfaces på serveren indgår.

Vi har derfor brug for en mere elegant håndtering af VLANs i Linux. Læs med næste gang, hvor vi kigger på en mulig løsning.

Relateret indhold

Kommentarer (10)
Yoel Caspersen Blogger

Har du set på Open vSwitch, https://www.openvswitch.org/
Det kan muligvis løse dit problem.

Det rækker en smule ind i næste blogindlæg, men skåret helt ind til benet ser vores behov således ud:

Når vi modtager trafik fra en kundes VLAN (QinQ), skal vi dels kunne anvende en fælles default gateway for et større antal kunde-VLANs, dels skal vi kunne filtrere trafikken fra kunden, så vi undgår, at kunden anvender en forkert IP-adresse, enten med vilje eller ved et uheld.

Første udfordring ser det ud til, at Open vSwitch kan løse - QinQ-support blev tilføjet i 2017, og det ser endda ud til at performe hæderligt med hardware-acceleration:

https://developers.redhat.com/blog/2017/06/27/open-vswitch-qinq-performa...

Den sidste udfordring, filtrering af trafikken, er dog noget sværere at få hul på. En del af problemet er, at vi gerne vil filtrere på IP-adresser, men på layer 2-niveau skal vi håndtere en del trafik, der ikke indeholder IP-adresser (bl.a. DHCP discover-forespørgsler).

Det er derfor essentielt for vores filtrering, at vi har viden om både inner- og outer VLAN tag idet den enkelte pakke filtreres. Jeg kan ikke på stående fod gennemskue, om det kan lade sig gøre i Open vSwitch.

Klavs Klavsen

Det ser ud til at nogen piller med det i nftables.. (erstatningen for iptables).. og tilbage i 2015 var der oplæg om det på linux con japan: https://events.static.linuxfound.org/sites/events/files/slides/LinuxConJ...

Jeg ville nok prøve at sende en venlig mail til ham der lavede det oplæg på linuxcon, og høre om nftables har fået tilføjet support for at se på "inner vlan" tag'et også.. og ellers kigge i træet hvor de vedligeholde nftables kerne delen: https://git.kernel.org/pub/scm/linux/kernel/git/pablo/nf-next.git/ - clone og git grep :)

Benny Lyne Amorsen

For godt 10 år siden ca. bøvlede jeg med at Red Hat Linux var meget længe om at starte op hvis man havde mere end hundrede interfaces. Det blev fikset. I dag er det ikke et problem at have nogle tusinde... sagde han og prøvede :(

NetworkManager og systemd-udevd forsinker processen en del; det kan ikke anbefales at prøve nedenstående hvis disse to services er slået til. Med dem slået fra får man:

[root@sisyphos ~]# time for i in $(seq 2 7) ; do ip link add link enp0s31f6 name eth0.$i type vlan id $i ; for j in $(seq 2 4000) ; do ip link add link eth0.$i name eth0.$i.$j type vlan id $j ; done ; done

real 0m40,838s
user 0m10,994s
sys 0m30,345s

Knap 40 sekunder for at oprette næsten 24000 VLANs, det er da ok.

[root@sisyphos ~]# time for i in $(seq 2 7) ; do ip link del dev eth0.$i ; done

real 0m7,028s
user 0m0,004s
sys 0m6,694s

7 sekunder om at nedlægge dem. Det er snyd fordi de er spredt på kun 6 yder-VLANs, leg selv med parametrene for at sprede dem på flere.

Men øv, NetworkManager og systemd-udevd kan ikke lide tusindvis af interfaces. På den positive side: de låser kun maskinen i nogle minutter.

Mht. programmer som enummerer samtlige netværksinterfaces. "Doktor, det gør ondt når jeg placerer min fod bag min nakke". "Så lad være med at gøre det..."

Benny Lyne Amorsen

Man kan få en Juniper MX150 til noget under de nævnte 100.000 DKK. Du skal så skrive konfigurationen statisk ligesom du gør i dag. Hvis du vil have den til selv at lave den relevante konfiguration når en ny subscriber kobler til på et tidligere inaktivt QinQ-VLAN, så skal du have subscriber-management-licens, og den er ikke gratis. Men den er som sagt kun nødvendig hvis du vil mere end du har i dag.

MX150 er en vMX i en kasse, så du kan også selv tage en server, installere en passende hypervisor, og installere vMX på den. Det koster så en licens, afhængigt af hvor kraftig den skal være.

Hvis du vil have en hardware-router skal du have en MX204, og den vil jeg også tro kan holde sig under 100.000 inkl. licenser.

Hos Cisco vil jeg tro at en ASR920 kan gøre det, men jeg kender ikke meget til Ciscos løsninger. Det er i al fald billig hardware; jeg ved ikke hvad licenser koster.

Markedet for BNG'er og i det hele taget for ISP-routere er blevet noget mere konkurrencepræget de seneste år... Det var lidt trælst for ikke så mange år siden hvor man skulle have et halvt rack til en router og kun kunne vælge mellem MX480/MX960 og ASR9000.

Jesper Brouer

(version2's CMS system vil ikke lade mig vise bash koden)

Jeg vil lige gøre opmærksom på at Linux ip(8) kommandoen har en -batch option, som lave oprettelsen en del hurtigere.

Jeg prøvet og kunne oprette de ca. 24000 VLANs, med 'ip -batch $FILE', og det tog 6 sekunder.

Jeg tror ikke kernens fast-path har et problem med at håndtere pakke til disse VLAN devices (dog bruger de en del kernel hukommelse).

Det største problem er userspace værktøjer der fx lister interfaces, der kan komme til at tage for lang tid.

'ip link' er stadigvæk meget hurtig med 0.5 sec.
Mens 'ifconfig -a' stoppet jeg selv efter 11 Minutter!

Log ind eller Opret konto for at kommentere