VyOSXXVI · BGP AttributesAttributes
BGP communities — well-known, extended, and large
What you'll learn
- Configure `set community` and `set large-community` on a route-map using the 1.4+ node shape
- Use the well-known communities (no-export, no-advertise, no-export-subconfed) for selective advertisement
- Apply route-map matching by community-list, and read the community-list value as the regular expression it is
- Diagnose community propagation, send-community, and well-known community enforcement
Prerequisites
Verified against VyOS 1.5.x LTS (circinus) · VyOS 1.4.x (sagitta) — legacy · FRRouting 10.x (VyOS 1.5) · Linux kernel 6.6 LTS (VyOS 1.5 base) · strongSwan 5.9.x (IPsec) · WireGuard 1.0.x (kernel module + userspace tooling) · 2026-08-19
BGP communities are tags attached to routes. They are the
operator’s tool for signalling policy decisions across ASes:
“this route is a customer route”, “this route is a backbone
route”, “do not advertise this outside this AS”. On VyOS 1.5
LTS / FRR 10.x, communities are set by a route-map, matched
through a community-list, and read back with the
show bgp ipv4 unicast family of commands.
This lesson is the operator’s reference for communities: the three community formats (standard, extended, large), the well-known communities and which of them are actually enforced, route-map matching and setting on the 1.4+ configuration tree, and how the whole mechanism fails in production.
What communities do
A community is a tag carried in BGP UPDATE messages. The tag is opaque to BGP itself — BGP does not interpret the community’s value. The operator (or the peer’s operator) uses the community to apply policy.
flowchart LR
R1["R1<br/>advertises 192.0.2.0/24<br/>community: 64512:100"]
R2["R2<br/>matches community-list on 64512:100<br/>applies policy (e.g. prepend)"]
R1 --> R2
The community 64512:100 is just a tag. R2’s configuration
says: “if a route arrives with community 64512:100, apply
this policy”. R2’s policy might be “prepend 3x on export”
or “set local-preference 50” or “deny the route”.
The community is optional transitive in RFC 4271’s classification:
- Optional — BGP implementations are not required to recognise it (every modern implementation does).
- Transitive — a speaker that does not recognise the attribute must still pass it on unchanged, marking it partial.
The transitive property is what makes communities a signalling mechanism between ASes rather than a local note. It is also the property most often defeated by configuration, which is the subject of the first failure mode below.
Community formats
Three formats are in use.
Standard communities (RFC 1997)
A 32-bit value, conventionally written as AS:value (for
example 64512:100):
ASis a 16-bit AS number (1-65535).valueis a 16-bit tag (0-65535).
Total: 32 bits = 4 octets. The split into AS:value is a
convention for readability, not a protocol field — the wire
format is one opaque 32-bit number, which is why the same
community can also be written as 4227858532 in decimal.
set policy route-map SET-COMMUNITY rule 10 action 'permit'
set policy route-map SET-COMMUNITY rule 10 set community add '64512:100'
Extended communities (RFC 4360)
A 64-bit value with structure the protocol does interpret:
- The first 16 bits are a type/sub-type pair (
route-target,route-origin,link-bandwidth, and others). - The remaining 48 bits are the value.
Extended communities are what MPLS/VPN deployments are built on — a VRF’s import and export policy is expressed as route-targets.
set policy route-map SET-EXT-COMMUNITY rule 10 action 'permit'
set policy route-map SET-EXT-COMMUNITY rule 10 set extcommunity rt '64512:100'
On VyOS 1.3 these were flat leaves (set extcommunity-rt,
set extcommunity-soo); 1.4 nested them under an
extcommunity node, the same reshaping that turned
set as-path-prepend into set as-path prepend.
Large communities (RFC 8092)
A 96-bit value, written as three colon-separated 32-bit
fields, global:value1:value2:
- The first field holds a 32-bit AS number, so a 4-byte ASN fits.
value1andvalue2are 32-bit tags.
set policy route-map SET-LARGE-COMMUNITY rule 10 action 'permit'
set policy route-map SET-LARGE-COMMUNITY rule 10 set large-community add '64512:100:200'
Large communities exist because a 4-byte ASN does not fit in the 16 bits a standard community gives you. Before RFC 8092 the workaround was to burn a 16-bit private ASN as the community’s first field and lose the ability to say unambiguously which AS set the tag.
Well-known communities
RFC 1997 defines three well-known communities that every conforming BGP implementation honours automatically. Two later RFCs add widely-deployed values that are honoured by convention rather than by the protocol — the difference matters enormously in production.
| Community | Hex | AS:value | Defined by | Honoured how |
|---|---|---|---|---|
no-export | 0xFFFFFF01 | 65535:65281 | RFC 1997 | Automatically, by every implementation |
no-advertise | 0xFFFFFF02 | 65535:65282 | RFC 1997 | Automatically, by every implementation |
no-export-subconfed | 0xFFFFFF03 | 65535:65283 | RFC 1997 | Automatically, by every implementation |
no-peer (NOPEER) | 0xFFFFFF04 | 65535:65284 | RFC 3765 | By local policy only — nothing enforces it |
blackhole | — | 65535:666 | RFC 7999 | By the receiving operator’s policy |
graceful-shutdown | — | 65535:0 | RFC 8326 | By the receiving operator’s policy |
The three RFC 1997 semantics:
no-export— advertise to iBGP peers, but not to eBGP peers. The route stays inside the AS (or inside the confederation, if there is one).no-advertise— do not advertise to any peer at all. The route stops at the router that received it.no-export-subconfed— do not advertise outside the local confederation sub-AS. Only meaningful inside a confederation.
flowchart TB
R1["R1<br/>originates 192.0.2.0/24<br/>community: no-export"]
R2["R2 (iBGP)<br/>receives the route<br/>sees no-export<br/>does not advertise to eBGP"]
R3["R3 (eBGP peer)<br/>never sees the route"]
R1 --> R2 --> R3
set policy route-map SET-NO-EXPORT rule 10 action 'permit'
set policy route-map SET-NO-EXPORT rule 10 set community add 'no-export'
The VyOS configuration
Communities are set by a route-map and matched through a community-list.
Setting a community
set policy route-map SET-CUSTOMER-COMMUNITY rule 10 action 'permit'
set policy route-map SET-CUSTOMER-COMMUNITY rule 10 match ip address prefix-list 'CUSTOMER-NETWORKS'
set policy route-map SET-CUSTOMER-COMMUNITY rule 10 set community add '64512:100'
set policy route-map SET-CUSTOMER-COMMUNITY rule 20 action 'permit'
add appends to whatever communities the route already
carries; replace discards them and installs only what you
name; none removes the attribute entirely. Rule 20 is the
catch-all — an FRR route-map ends with an implicit deny, so
without it every prefix that does not match the prefix-list
is dropped by the map.
Setting a large community
set policy route-map SET-LARGE-COMMUNITY rule 10 action 'permit'
set policy route-map SET-LARGE-COMMUNITY rule 10 set large-community add '64512:100:200'
Standard and large communities are separate attributes on the
wire and separate nodes in the configuration. Setting one
does not touch the other, and a community-list that matches
standard communities will never match a large community —
that needs policy large-community-list.
Matching by community
set policy community-list MY-CUSTOMERS rule 10 action 'permit'
set policy community-list MY-CUSTOMERS rule 10 regex '64512:100'
set policy route-map PROCESS-CUSTOMERS rule 10 action 'permit'
set policy route-map PROCESS-CUSTOMERS rule 10 match community community-list 'MY-CUSTOMERS'
set policy route-map PROCESS-CUSTOMERS rule 10 set local-preference '200'
set policy route-map PROCESS-CUSTOMERS rule 20 action 'permit'
Two things in that block regularly surprise people.
The leaf is regex, and it means it: the value is a regular
expression evaluated against the route’s community string,
not an equality test. 64512:100 therefore also matches a
route carrying 64512:1000. Choose community values that are
not prefixes of one another, or the classifier will quietly
widen as the scheme grows.
The match clause is match community community-list <name> —
community is a node with community-list and exact-match
underneath it, not a leaf that takes a name directly. By
default the match succeeds if the route carries any of the
communities the list permits; match community exact-match
requires the route’s community set to be exactly the list.
Applying the route-map
set protocols bgp system-as 64512
set protocols bgp neighbor 10.0.0.1 remote-as '64513'
set protocols bgp neighbor 10.0.0.1 address-family ipv4-unicast route-map import 'FROM-PROVIDER-A'
set protocols bgp neighbor 10.0.0.1 address-family ipv4-unicast route-map export 'PROCESS-CUSTOMERS'
The binding lives inside the address family, and the
direction keyword is import or export — it comes before
the map name, not after it. There is no ASN in the path from
1.4 onward, and no route-map NAME in leaf hanging off the
neighbour: set protocols bgp 64512 neighbor 10.0.0.1 route-map FROM-PROVIDER-A import is rejected at the set,
not at commit.
Import route-maps typically set communities — the local router tags the route according to which peer it arrived from. Export route-maps typically match them — the local router filters or rewrites according to tags applied earlier.
Validation
1 — Is the community on the route? The one-line-per-prefix table does not show communities; you need the per-prefix detail view.
vyos@r1:~$ show bgp ipv4 unicast 192.0.2.0/24BGP routing table entry for 192.0.2.0/24
Paths: (1 available, best #1, table default)
Advertised to non peer-group peers:
10.0.0.5
64513 15169
10.0.0.1 from 10.0.0.1 (10.0.0.1)
Origin IGP, valid, external, best (First path received)
Community: 64512:100 64513:7000
Last update: Tue Aug 19 09:14:02 2026Illustrative output
2 — Which routes carry a community?
show bgp ipv4 unicast community 64512:100
show bgp ipv4 unicast community no-export
show bgp ipv4 unicast large-community 64512:100:200
3 — Does the classifier resolve, and to what?
show configuration commands | match 'community-list MY-CUSTOMERS'
vyos@r1:~$ vtysh -c 'show bgp community-list MY-CUSTOMERS'Reading both is the point. VyOS holds the intent and FRR
holds what is running; a community-list that exists in
show configuration and not in FRR means the commit that was
supposed to render it did not.
4 — Is the route-map firing?
vyos@r1:~$ vtysh -c 'show route-map PROCESS-CUSTOMERS'5 — Did the change apply to routes already in the table? It did not. A policy edit affects routes received after the edit. Force a re-evaluation without bouncing the session:
vyos@r1:~$ clear bgp ipv4 unicast 10.0.0.1 soft inFailure modes
The community is set but the peer never sees it
This is the first thing to check and the last thing people
think of. Communities are only transmitted to a neighbour if
the router is configured to send them. FRR sends standard and
extended communities by default, and VyOS exposes the switch
that turns them off per neighbour and per address family
(disable-send-community, with standard and extended
underneath it). A neighbour where that has been set — often
years earlier, often for a reason nobody recorded — will
receive routes with every community you configured stripped
on transmission.
The signature: show bgp ipv4 unicast <prefix> on your
router shows the community; the peer says there is none.
Nothing about your route-map is wrong.
The community is not on the route at all
The route-map that should have set it is not running, or is not reaching the rule that sets it:
- The map is bound in the wrong direction (
exportwhereimportwas meant), or bound outside the address family and therefore not bound at all. - An earlier rule matched first. Route-map evaluation stops at the first matching rule, so a catch-all at rule 10 makes rule 20 dead configuration.
- The match clause never succeeds — a prefix-list that does not cover the prefix, or a community-list name with a typo in it. FRR treats an unresolvable community-list as a match that never succeeds, so the rule fails silently rather than erroring.
vtysh -c 'show route-map <name>' and its per-clause
counters separate “not running” from “running and wrong” in
one command.
The route replaced the peer’s communities instead of adding to them
The route arrives carrying the upstream’s tags, and after
your import map it carries only yours. That is replace
behaviour, and it is what you get from the 1.3-era
set community '64512:200' with no additive keyword and
from the 1.4+ set community replace. On 1.4+ the additive
form is set community add.
Discarding an upstream’s communities is occasionally what you want — it is a defensible ingress hygiene policy — but it should be a decision, not a node-shape accident.
The community-list matches more than intended
regex '64512:10' matches 64512:100, 64512:101 and
64512:1000. The policy works correctly for months and
misbehaves on the day someone adds a value to the scheme.
Verify the classifier against the real table with
show bgp ipv4 unicast community-list <name> rather than
trusting the expression.
The well-known community is ignored
The operator set no-export, but an eBGP peer still receives
the route. In practice this is almost never the protocol
failing to honour it:
- The map that sets it is bound to the wrong session, so the route reaching the eBGP peer never got tagged.
- A later route-map stripped it —
set community replaceorset community noneon the export path towards that peer. - The community was never set at all, because the rule that sets it did not match.
Confirm on the advertising router with
show bgp ipv4 unicast community no-export before assuming
the peer is at fault.
Rollback
delete policy route-map SET-CUSTOMER-COMMUNITY rule 10 set community
commit
delete protocols bgp neighbor 10.0.0.1 address-family ipv4-unicast route-map import
commit
Removing a policy stops it applying to routes received from now on. It does not rewrite the routes already in the BGP table, so the sequence for a community change that caused a routing problem is:
- Capture the before state —
show bgp ipv4 unicast <prefix>andshow bgp ipv4 unicast community <community>. - Remove the offending clause or binding, and
commit. clear bgp ipv4 unicast <peer> soft in(orsoft out) so the table is rebuilt under the new policy.- Verify the after state on both sides of the session, and confirm the peers have re-converged.
Step 3 is the one people skip, and skipping it produces the most confusing possible symptom: correct configuration and unchanged behaviour.
Production discipline
Cross-course references
- Part XXV (
XXV-VyOS-BGPAdvertise) covers the origination primitives that produce routes; communities are tags applied to these routes. - Part XXVI-01 (
XXVI-VyOS-BGPAttributes/ local-preference) is the higher-precedence attribute that communities often influence. - Part XXVIII (
XXVIII-VyOS-BGPPrefixFilter) covers the outbound filtering that uses communities as match criteria. - Part XXIX (
XXIX-VyOS-BGPCommunities) builds the full tag-on-import, act-on-export policy pattern on top of this reference. - Part XXX (
XXX-VyOS-BGPReflector) covers the route reflector use case where communities control client-to-client reflection. - Part LXII (
LXII-VyOS-VPNServices) covers the extended-community use case for MPLS/VPN route-targets.
Quiz
Knowledge check · 4 questions
Q1. An operator sets the community `no-export` on a route via route-map. What is the effect when the route is advertised?
Q2. BGP communities are transitive: they propagate across ASes even if the receiving AS does not recognise the specific community value.
Q3. R1 receives 192.0.2.0/24 from Provider A carrying community `64513:100`. R1's import route-map adds `64512:200`. After the change the route carries only `64512:200` — the provider's tag is gone. What happened, and how is it fixed?
R1's import route-map is: set policy route-map FROM-PROVIDER-A rule 10 action 'permit' set policy route-map FROM-PROVIDER-A rule 10 set community replace '64512:200' The operator expected the route to end up with both 64513:100 and 64512:200. `show bgp ipv4 unicast 192.0.2.0/24` on R1 shows a Community line with 64512:200 only.
Q4. R1 is in AS 200000, a 4-byte ASN, and wants to tag routes with `200000:100`. `set community add '200000:100'` is rejected. What is the fix, and what does it cost?
The standard community format is one opaque 32-bit value conventionally read as a 16-bit AS number and a 16-bit tag. 200000 does not fit in 16 bits, so the value is invalid as a standard community and the configuration is rejected.
Passing score: 75%. Answers are checked in this browser.