BGP – Route Manipulation via Communities

Laddat upp med en dubbel espresso för nu är det dags att gå över Communities. Vi har i tidigare poster gått igenom hur vi kan påverka routing-beslut i BGP via:

Gemensamt för både AS_PATH Prepending & MED är dock att din peer/ISP måste acceptera att du skickar dessa attribut, något som är långt ifrån varken best practice eller vanligt förekommande. Oftast väljer istället ISP:n att helt enkelt ignorera dessa attribut från dina routing-uppdateringar om du försöker lägga till detta.

dualhomed

Tänk dig följande exempel – du som kund har köpt en dual-homed uppkoppling med en primär länk på 100Mbit & backup på 20Mbit. Hur stor tror du risken är att Telia skulle gå in och manuellt modifiera Weight eller Local Preference för dina länkar (alt. låta dig använda MED)? Med 10,000+ kunder så skulle det bli en del route-maps att hålla reda på för dem.. 😉

Det är istället här användandet av Communities kommer in i bilden. BGP Communitys är ett 32bitars värde, där i det “nya formatet” (ip bgp-community new-format) delas upp i två 16bitars värde. Best practice är att använda sitt AS-nummer i det första 16bitars fältet, och sedan använda det sista fältet enligt eget önskemål för att skapa sina communitys.

Så för en ISP med AS 300 hade dess community-värden exempelvis kunnat vara:

  • 300:1
  • 300:10
  • 300:25000
  • 300:60000

Om du istället skulle vilja använda det “gamla formatet” så skrivs hela värdet ut i en och samma 32bitars sträng. 300:10 hade då blivit:

0000 0001 0010 1100 0000 0000 1010

Vilket omskrivet i decimalt blir – 1,228,810. Så vi kan antingen skicka community-taggen 300:10, eller använda oss av det gamla formatet och skicka taggen 1228810 för att få samma effekt- ganska lätt att se vad som är enklast! 🙂

Vi annonserar sedan community-taggen tillsammans med övriga BGP Attribut som Origin/Next hop/AS-Path etc, Community räknas förövrigt som du kanske kommer ihåg från posten “BGP Key Attributes”  tidigare i veckan som ett “Optional Attribute“. Alla routrar har med andra ord inte stöd för detta!

Genom communitys kan vi som kund “tagga” våra routing-uppdateringar enligt de värden som vår ISP tagit fram. ISPn kan i sin tur sedan använda en default route-map för alla sina kunder där de matchar Community-värden och ifrån det sätter exempelvis ett förutbestämt Weight eller Local Preference värde.

En vanlig lösning verkar vara att ISPn skickar ett excel-blad med alla sina förutbestämda communitys och dess “åtgärder”, något i stil med detta:

Community-excel

Om vi som kund sedan taggar vårat nät 200.0.0.0/24 med community 300:10 kommer då ISPn att ändra Local Preference till 10. Taggar vi med community 300:201 så kommer ISPn istället att använda AS_Path Prepend och lägga till ytterligare ett AS-hopp. Vi kan även kombinera flera communities om vi så önskar, taggar vi samma route med 300:50 OCH 300:202 så ändras både Local Preference & AS_Path Prepending!

Det är ganska lätt att se hur enormt mycket mer skalbart och lättanvänt detta är för vår ISP, alternativet hade ju varit att skapa individuella route-maps för varje kund som önskar någon form av routing-modifiering..

Labbexempel

MED

Vi tar och testar detta i praktiken med ovanstående topologi.

  • Länken mellan R1 & R3 är på 50M
  • Länken mellan R1 & R4 är på 2M
  • Länken mellan R2 & R4 är på 100M

Vi vill således att vår ISP använder länken via R2-R4 primärt för trafik som kommer från “the Internet”. Att modifiera Weight eller AS_Path-Prepending fungerar ej i detta fall, vår ISP måste istället använda Local Preference. Om du inte förstår varför så föreslår jag att du går tillbaka och läser posterna relaterat till detta länkat överst i dedå det är rätt basic vid det här laget. 😉

Vår ISP har skickat följande lista med communities vi kan använda oss av:

Community-excel.2png

Vi börjar med att konfigurera upp vår egen utrustning så kollar vi senare på hur ISPn hanterar detta.

Med ren grundkonfig kan vi se att ISP just nu föredrar den sämre länken via R1 på 50Mbit för att nå nätet 10.0.12.0/24.

bgp-community-default

Vi börjar med att konfigurera R1 – men vad är det vi vill åstadkomma? Kom ihåg att för Local Preference så är högst värde bäst (default 100), vi vill med andra ord att ISP ändrar Local Preference till <100 för länken mellan R1 – R3, och sedan sätter ett ännu lägre värde för länken mellan R1 – R4.  Enligt excel-listan behöver vi då sätta följande communities:

  • Länken mellan R1 – R3 – community 65000:50
  • Länken mellan R1 – R4 – community 65000:10

Vi börjar dock med en access-lista:

access-list 1 permit 10.0.12.0 0.0.0.255

Sedan en route-map:

route-map PeerToR3 permit 10
match ip address 1
 set community 65000:50
route-map PeerToR4 permit 10
match ip address 1
 set community 65000:10

Hur får vi då routern att skicka communities till sina peers? Vi måste först aktivera “bgp-community new format” då vi använt oss av det nya formatet att skriva communities:

ip bgp-community new-format

Vi behöver sedan bara konfigurera följande mot våra peers:

router bgp 500
neighbor 191.0.0.2 route-map PeerToR3 out
neighbor 191.0.0.2 send-community
neighbor 191.0.0.6 route-map PeerToR4 out
neighbor 191.0.0.6 send-community

Vi gör i princip samma sak för R2, men här behöver vi egentligen inte ändra LP då vi sänkt de andra länkarna till <100, men det är ju bra träning om inte annat.. 🙂

access-list 1 permit 10.0.12.0 0.0.0.255
route-map PeerToR4 permit 10
match ip address 1
 set community 65000:110
ip bgp-community new-format
router bgp 500
neighbor 191.0.0.10 route-map PeerToR4 out
neighbor 191.0.0.10 send-community

Svårare än så är det inte!

Hur har då vår ISP konfigurerat sitt nät?

Vi skapar först något som kallas “community-list”, här specificerar vi våra communities så vi sedan kan använda oss av dessa i route-maps:

ip community-list 1 permit 65000:10
ip community-list 2 permit 65000:50
ip community-list 3 permit 65000:110

Dessa fungerar precis som en access-lista och det finns möjlighet att göra både standard & extended-versioner:

R3(config)#ip community-list ?
 <1-99> Community list number (standard)
 <100-500> Community list number (expanded)
 expanded Add an expanded community-list entry
 standard Add a standard community-list entry

Vi skapar sedan en default route-map vi använder till alla våra kunder:

route-map CUSTOMER_DEFAULT permit 10
match community 1
 set local-preference 10
route-map CUSTOMER_DEFAULT permit 20
match community 2
 set local-preference 50
route-map CUSTOMER_DEFAULT permit  30
match community 3
 set local-preference 110
route-map CUSTOMER_DEFAULT permit 40

Inget konstigt direkt, istället för match ip address där vi sedan använt oss av en access-lista använder vi här istället match community, vilket hänvisar till den ip community-list vi tidigare skapat.

ip bgp-community new-format
router bgp 65000
neighbor x.x.x.x route-map CUSTOMER_DEFAULT in

Detta ger följande resultat:

R3

bgp-community-finalr3

R4

bgp-community-finalr4

R5

bgp-community-finalr5

Vackert! Vi behöver givetvis inte begränsa oss till endast ändra Weight/Local Preference, möjligheterna är rätt rejäla 😉

R5(config-route-map)#set ?
 as-path Prepend string for a BGP AS-path attribute
 automatic-tag Automatically compute TAG value
 clns OSI summary address
 comm-list set BGP community list (for deletion)
 community BGP community attribute
 dampening Set BGP route flap dampening parameters
 default Set default information
 extcommunity BGP extended community attribute
 interface Output interface
 ip IP specific information
 ipv6 IPv6 specific information
 level Where to import route
 local-preference BGP local preference path attribute
 metric Metric value for destination routing protocol
 metric-type Type of metric for destination routing protocol
 mpls-label Set MPLS label for prefix
 nlri BGP NLRI type
 origin BGP origin code
 tag Tag value for destination routing protocol
 traffic-index BGP traffic classification number for accounting
 vrf Define VRF name
 weight BGP weight for routing table

Det får avsluta communities för den här gången, nästa post blir troligtvis om Route-Reflectors eller Confederations.

BGP – Path Selection Part II & Weight

Detta blir en fortsättning på inlägget “AS_SEQ Path Attribute & Path Selection” så vi kan gå in lite mer på djupet över hur just BGPs best path selection går till.

För att bestämma vilken route som är bäst används följande kriterier i turordning tills den hittat en avgörande faktor, dvs om alla parametrar är identiska mellan två vägar för en specifik destination så är det tillslut den med lägst Router-ID som vinner. 🙂

  1. Largest Weight (cisco proprietary)
  2. Highest Local Preference
  3. Locally Originated
  4. Shortest AS Path
  5. Lowest Origin Type (i < e < ?)*
  6. Lowest MED (metric)
  7. eBGP over iBGP
  8. Lowest IGP metric to neighbor (Max. paths check – default 1)
  9. Older route
  10. Lowest Router-ID

*i = Injected from an IGP (using network-command), e = Injected from Exterior Gateway Protocol (EGP), ? = Undetermined

Det finns dock ett Steg 0 också, “Next hop: reachable?”, om routern inte kan nå den specificerade next-hop adressen kommer routern räknas som invalid.

För att lättare komma ihåg detta föreslår Cisco följande “ordramsa(?)” – N WLLA OMNI.

Ytterligare något som är bra att känna till är att Cisco särskiljer på rekommenderade metoder beroende på om vi vill modifiera “outbound”-eller “inbound”-routes.

För outbound rekommenderas:

  • Weight
  • Local Preference
  • AS_PATH

Och för inbound:

  • MED (metric)

Låt oss använda följande topologi igen och kontrollera hur valet gått till för exempelvis routen 200.0.3.0/24 i R7:

bgp AS-path

pathselection1

Först har vi weight, men vi kan se att värdet är satt till “0” för båda alternativen, ingen vinnare där med andra ord. Nästa steg är “Highest Local Preference”, men inte heller där finns det något värde satt, Tredje punkten, “Locally Originated” får vi inte heller någon match på då det är en extern route.

För fjärde punkten i listan – “Shortest AS Path”, kan vi dock se skillnad. Routen med next-hop adressen 172.16.47.4 har ett mindre AS-hopp än alternativet som går via AS200- > AS500 -> AS100. Denna route blir därför vald till “best route” och installeras i routerns routing table:

R7#sh ip route 200.0.3.0
Routing entry for 200.0.3.0/24
 Known via "bgp 50", distance 20, metric 0
 Tag 500, type external
 Last update from 172.16.47.4 05:53:45 ago
 Routing Descriptor Blocks:
 * 172.16.47.4, from 172.16.47.4, 05:53:45 ago
 Route metric is 0, traffic share count is 1
 AS Hops 2
 Route tag 500

Hur bär vi då oss åt om vi vill modifiera detta? I CCNP route räknar Cisco med att vi ska ha koll på följande fyra:

  • Weight
  • Local preference
  • AS_Path Lenght
  • MED (metric)

Vi börjar med den enklaste(?)..

Largest Weight

  • Is not a Path Attribute
  • Purpose – Identifies a single router’s best route
  • Scope – Set on inbound route Updates; influences only that one router’s choice
  • Range – 0 through 65-535 (2^16-1)
  • Which is best? – Bigger value is better
  • Default – 0 for learned routes, 32,768 for locally injected routes
  • Defining a new default – Not supported
  • Configuration – neighbor route-map (per prefix), neighbor weight (all routes from this neighbor)

Detta option är “Cisco proprietary” och räknas ej som ett “Path Attribute”. Vi behöver dock inte bry oss i om våra neighbors också använder Cisco’s hårdvara då Weight endast används lokalt! Om vi använder oss av samma topologi återigen, låt oss säga att vi hellre föredrar att trafiken från R7 tar den längre vägen via AS200 -> AS500 -> AS100 (då vi kanske har en snabbare uppkoppling mellan de kontoren). Konfigurationen blir då följande:

R7(config)#router bgp 50
R7(config-router)#neighbor 172.16.76.6 weight ?
 <0-65535> default weight
R7(config-router)#neighbor 172.16.76.6 weight 5
R7(config-router)#end
R7#clear ip bgp *

Kom ihåg att vi behöver starta om BGP-processen!

Detta leder till följande resultat:

pathselection-weight

R7 föredrar nu att gå via R6 trots att det är ett AS-hopp mer än direkt via R4/AS500.

Hur gör vi då om vi endast vill modifiera detta för en/flera specifika routes och inte alla? Route-maps! Vi tar bort ändringen ovan och försöker istället utföra samma sak men endast för routen 200.0.3.0/24.

Som du säkert gissat behöver vi först skapa en access-lista:

access-list 1 permit 200.0.3.0

Och sedan en route-map:

route-map WEIGHT-FILTER permit 10
match ip address 1
set weight 10

Vi applicerar sedan route-map:en i vårat neighbor-statement(!)

router bgp 50
neighbor 172.16.76.6 route-map WEIGHT-FILTER in
do clear ip bgp *

That’s it, detta ger följande resultat:

route-map weight

Fast vänta lite nu.. Jämför detta med det resultat vi fick innan vi applicerade route-mapen ovan. Vi saknar nu de alternativa vägarna för näten 5.5.5.0/24, 6.6.6.0/24 & 200.0.2.0/24! Du kanske redan listat ut varför det blir såhär, om inte föreslår jag att du tar en paus och försöker lösa det på egen hand innan du läser vidare.

I den access-lista vi skapade matchade vi endast nätet 200.0.3.0/24, så det är kanske inte så konstigt att vi endast ser detta nätet nu. Men vi kan ju inte gärna lägga till resterande nät i acl:en då vi endast ville ändra weight för 200.0.3.0?

Svaret ligger i route-map:en! Just nu har vi ju följande konfiguration:

access-list 1 permit 200.0.3.0
!
route-map WEIGHT-FILTER permit 10
match ip address 1
set weight 10

Det finns ju bevisligen inget statement för de övriga näten. Vi fixar detta enkelt med att skapa ett match-any statement som tillåter allt!

route-map WEIGHT-FILTER permit 20

Vi behöver inget match-statement då vi vill tillåta allt som inte redan matchats under sequence 10/ACL 1. Vi kör återigen en clear ip bgp * och håller tummarna..

route-map weight2

Kungligt! Nästa inlägg blir en fortsättning på samma ämne men då kollar vi istället på Local Preference & AS PATH_LENGHT.