Control communities: session groups, prepends, and only ours to give
Control communities could say which peers a route goes to, by AS. Now
they can also name sessions by group, and ask for prepends:
L:11:P .. L:13:P our AS once to three times more towards AS P
(P 0: towards every peer in another AS)
L:20:G / L:21:G not to / only to the sessions of group G
L:31:G .. L:33:G our AS once to three times more towards group G
A group is a number given to sessions in the configuration (`groups` of
a peer): those at one exchange, or those over one link. The same network
at two exchanges is one AS but two sessions, which is what steering
inbound traffic between exchanges needs. Of several prepends that apply
the most counts, on top of the session's own as_path_prepend. Functions
2 to 9, as the documentation already promised, and 100 and up stay
informational; 10 to 99 are kept for actions to come.
They are acted on where a route leaves our AS, and taken off there; our
informational communities are not. To a peer in our own AS a route goes
with them, unchanged, so that a mark put on at one router is acted on at
another. Before, they were acted on and taken off on internal sessions
too, so a route marked "to nobody" did not even reach our own routers.
And they are ours to give: the communities of our own AS (L:n, L:n:m,
and 0:n where control communities are on) are taken off every route
from a peer in another AS as it comes in, before import marks are put
on. A peer at an exchange could otherwise decide where its routes go
from us, and set our informational marks. A customer that is to steer
its own routes is given import.accept_control_communities. An UPDATE
without any of ours is still taken as it came, without being written
out again.
This changes what a customer that set control communities gets: it now
needs accept_control_communities. The transit example and the interop
lab say so; the lab also has FRR, as a customer, ask for a prepend
towards BIRD's group, and BIRD, as a provider, have its "not to" taken
off.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
3609451bdc
commit
72444c2706
25 files changed
+833
-120
No files matched your search
@@ -235,8 +235,7 @@ set their local preference:
|
||||
peers {
|
||||
name: "ixp-a-rs"
|
||||
import {
|
||||
remove_communities: "64500:2:*"
|
||||
remove_communities: "64500:3:*"
|
||||
remove_communities: "64496:*"
|
||||
add_large_communities: "64500:2:1001"
|
||||
local_pref: 150
|
||||
}
|
||||
@@ -246,7 +245,9 @@ peers {
|
||||
The statements have the following effect:
|
||||
|
||||
- `remove_communities` removes matching communities. Ferrix applies it
|
||||
before adding communities. A pattern has two fields for a standard
|
||||
after it removes the communities of the local AS (see
|
||||
[Communities of the Local AS](#communities-of-the-local-as)), and before
|
||||
adding communities. A pattern has two fields for a standard
|
||||
community and three for a large community; each field is a number or `*`.
|
||||
Examples: `64500:100`, `64500:*`, `64500:2:*`, `*:*`.
|
||||
- `add_communities` and `add_large_communities` add communities to every
|
||||
@@ -257,17 +258,52 @@ The statements have the following effect:
|
||||
value is preferred. Default: 100.
|
||||
|
||||
> [!TIP]
|
||||
> Remove the local AS's informational communities from received routes, so
|
||||
> that a neighbor cannot set them. A common local preference scheme assigns
|
||||
> 200 to customer routes, 150 to peer and route server routes, and 100 to
|
||||
> transit routes.
|
||||
> A common local preference scheme assigns 200 to customer routes, 150 to
|
||||
> peer and route server routes, and 100 to transit routes.
|
||||
|
||||
The examples in this documentation use large communities `64500:2:x` to
|
||||
record where a route was learned and `64500:3:r` to record the router that
|
||||
advertised it. These values do not overlap the
|
||||
[control communities](@/docs/guides/passing-routes-on.md#control-communities),
|
||||
which use `64500:0:*` and `64500:1:*`, or the standard communities
|
||||
`64500:n`, which control communities interpret as "advertise to AS n".
|
||||
or the standard communities `64500:n`, which control communities interpret
|
||||
as "advertise to AS n".
|
||||
|
||||
## Communities of the Local AS
|
||||
|
||||
By default, Ferrix removes the local AS's communities from every route that
|
||||
it receives from an EBGP neighbor, before `add_communities` and
|
||||
`add_large_communities` are applied. The following communities are
|
||||
removed, where `L` is the local AS number:
|
||||
|
||||
- Standard communities `L:n`, if `L` is 65535 or lower.
|
||||
- Large communities `L:n:m`.
|
||||
- Standard communities `0:n`, if `control_communities` is enabled.
|
||||
|
||||
These communities are instructions and records of the local AS: control
|
||||
communities decide where Ferrix advertises a route, and informational
|
||||
communities record where a route was learned. A neighbor at an Internet
|
||||
exchange must not be able to set them. Ferrix retains them on routes from
|
||||
IBGP neighbors.
|
||||
|
||||
A customer that sets control communities on its own routes requires the
|
||||
following statement:
|
||||
|
||||
```textproto
|
||||
peers {
|
||||
name: "customer-a"
|
||||
role: CUSTOMER
|
||||
import { accept_control_communities: true }
|
||||
}
|
||||
```
|
||||
|
||||
Ferrix then retains all communities of the local AS on the customer's
|
||||
routes. The customer can affect only its own routes. Use
|
||||
`remove_communities` to remove informational communities that the
|
||||
customer must not set, for example `64500:2:*`.
|
||||
|
||||
Ferrix examines the communities of every UPDATE message from an EBGP
|
||||
neighbor. A message without communities of the local AS is accepted
|
||||
unchanged.
|
||||
|
||||
## Performance
|
||||
|
||||
|
||||
@@ -111,52 +111,130 @@ export {
|
||||
## Control Communities
|
||||
|
||||
Control communities allow a route's communities to restrict the neighbors
|
||||
to which Ferrix advertises it. The format is the one used by Internet
|
||||
exchange route servers. To enable control communities, configure the
|
||||
following top-level statement:
|
||||
to which Ferrix advertises it, and to prepend the local AS number to its AS
|
||||
path on its way to them. The formats are the ones used by Internet exchange
|
||||
route servers and transit providers. To enable control communities,
|
||||
configure the following top-level statement:
|
||||
|
||||
```textproto
|
||||
control_communities: true
|
||||
```
|
||||
|
||||
Table 2 lists the control communities, where `L` is the local AS number and
|
||||
`P` is a neighbor's AS number.
|
||||
Table 2 lists the control communities, where `L` is the local AS number,
|
||||
`P` is a neighbor's AS number, and `G` is a session group (see
|
||||
[Session Groups](#session-groups)).
|
||||
|
||||
| Standard community | Large community | Action |
|
||||
|---|---|---|
|
||||
| `0:P` | `L:0:P` | Do not advertise to the neighbor with AS `P`. |
|
||||
| `L:P` | `L:1:P` | Advertise to the neighbor with AS `P`. If present, advertise only to neighbors named in such communities. |
|
||||
| `0:L` | `L:0:0` | Do not advertise to any neighbor. |
|
||||
| | `L:11:P`, `L:12:P`, `L:13:P` | Prepend the local AS number once, twice, or three times when advertising to the neighbor with AS `P`. If `P` is 0, prepend to every EBGP neighbor. |
|
||||
| | `L:20:G` | Do not advertise to the sessions in group `G`. |
|
||||
| | `L:21:G` | Advertise to the sessions in group `G`. If present, advertise only to sessions named in such communities, by group or by AS. |
|
||||
| | `L:31:G`, `L:32:G`, `L:33:G` | Prepend the local AS number once, twice, or three times when advertising to the sessions in group `G`. |
|
||||
|
||||
Control communities are evaluated as follows:
|
||||
|
||||
- "Do not advertise" takes precedence over "advertise".
|
||||
- A route without control communities is advertised as the other rules
|
||||
permit.
|
||||
- If several prepend communities apply to a session, the largest number of
|
||||
prepends applies. It is added to the session's `as_path_prepend`.
|
||||
- Standard communities can express AS numbers up to 65535 only. Use the
|
||||
large community forms for four-octet AS numbers.
|
||||
- Ferrix removes control communities from a route when it advertises the
|
||||
route.
|
||||
- Control communities apply to originated routes and to communities added
|
||||
by the import policy.
|
||||
|
||||
The following example prevents the advertisement of an originated route to
|
||||
AS 64496:
|
||||
### Where Control Communities Apply
|
||||
|
||||
Ferrix acts on control communities when it advertises a route to an EBGP
|
||||
neighbor, and removes them from the route at that point. Informational
|
||||
communities of the local AS are not removed. To an IBGP neighbor, Ferrix
|
||||
advertises the route with its control communities, and without acting on
|
||||
them: the other router acts on them when it advertises the route outside
|
||||
the local AS. A control community can therefore be set on one router and
|
||||
take effect on another.
|
||||
|
||||
Ferrix acts on control communities that come from the following sources:
|
||||
|
||||
- The `communities` and `large_communities` statements of an originated
|
||||
route.
|
||||
- The `add_communities` and `add_large_communities` statements of an
|
||||
import policy.
|
||||
- Routes from IBGP neighbors.
|
||||
- Routes from EBGP neighbors with `accept_control_communities`, usually
|
||||
customers that steer their own routes.
|
||||
|
||||
Ferrix removes the local AS's communities from routes from all other
|
||||
neighbors when it receives them. See
|
||||
[Communities of the Local AS](@/docs/guides/import-policy.md#communities-of-the-local-as).
|
||||
|
||||
### Session Groups
|
||||
|
||||
A control community can name sessions by group instead of by AS. A group
|
||||
is a number that the configuration assigns to sessions, for example the
|
||||
sessions at one Internet exchange. A neighbor present at two exchanges has
|
||||
the same AS number at both, but its sessions are in different groups. A
|
||||
session can be in several groups:
|
||||
|
||||
```textproto
|
||||
control_communities: true
|
||||
originate {
|
||||
prefix: "198.51.100.0/24"
|
||||
large_communities: "64500:0:64496"
|
||||
peers {
|
||||
name: "exchange-b-rs1"
|
||||
role: ROUTE_SERVER
|
||||
groups: 2
|
||||
groups: 10
|
||||
}
|
||||
```
|
||||
|
||||
Use the same group numbers on all routers in the local AS, because a
|
||||
control community set on one router can take effect on another.
|
||||
|
||||
### Example: Inbound Traffic Engineering
|
||||
|
||||
In the following example, the router is connected to exchange A over a
|
||||
fast link and to exchange B over a slow one. Routes of the customer are to
|
||||
reach networks at exchange B with a longer AS path, so that networks
|
||||
present at both exchanges send traffic for them through exchange A. The
|
||||
originated anycast prefix is advertised at both exchanges unchanged.
|
||||
|
||||
```textproto
|
||||
local_asn: 64500
|
||||
control_communities: true
|
||||
originate { prefix: "198.51.100.0/24" }
|
||||
|
||||
peers {
|
||||
name: "customer-a"
|
||||
role: CUSTOMER
|
||||
import {
|
||||
add_large_communities: "64500:31:2"
|
||||
accept_control_communities: true
|
||||
}
|
||||
}
|
||||
|
||||
peers {
|
||||
name: "exchange-a-rs1"
|
||||
role: ROUTE_SERVER
|
||||
groups: 1
|
||||
}
|
||||
|
||||
peers {
|
||||
name: "exchange-b-rs1"
|
||||
role: ROUTE_SERVER
|
||||
groups: 2
|
||||
}
|
||||
```
|
||||
|
||||
Ferrix adds `64500:31:2` to every route of the customer, and prepends the
|
||||
local AS number once to those routes on the sessions in group 2. With
|
||||
`accept_control_communities`, the customer can also set control
|
||||
communities on individual prefixes, for example `64500:20:2` to withdraw a
|
||||
prefix from exchange B.
|
||||
|
||||
> [!IMPORTANT]
|
||||
> When control communities are enabled, Ferrix interprets the standard
|
||||
> community `L:n` as "advertise to AS n", and the large communities `L:0:n`
|
||||
> and `L:1:n` as listed in Table 2. Use large communities `L:2:n` and higher
|
||||
> for informational communities. Do not remove customers' control
|
||||
> communities with `remove_communities`.
|
||||
> community `L:n` as "advertise to AS n", and the large communities of
|
||||
> Table 2 as listed. Use large communities with a second field of 2
|
||||
> through 9, or 100 and higher, for informational communities. Values 10
|
||||
> through 99 are reserved for control communities.
|
||||
|
||||
## Update Generation
|
||||
|
||||
|
||||
@@ -54,7 +54,7 @@ Top-level statements.
|
||||
| `rpki` <span class="type">[Rpki](#rpki)</span> | Disabled | Enables RPKI route origin validation and ASPA verification. |
|
||||
| `kernel` <span class="type">[Kernel](#kernel)</span> | Disabled | Enables kernel route installation (Linux only). |
|
||||
| `export` <span class="type">[ExportPolicy](#exportpolicy)</span> | Originated routes only | Specifies the export policy for neighbors that have no `export` statement. |
|
||||
| `control_communities` <span class="type">bool</span> | `false` | Enables control communities, which restrict the neighbors to which a route is advertised. See [Control Communities](@/docs/guides/passing-routes-on.md#control-communities). |
|
||||
| `control_communities` <span class="type">bool</span> | `false` | Enables control communities, which restrict the neighbors to which a route is advertised and prepend the local AS number on its way to them. See [Control Communities](@/docs/guides/passing-routes-on.md#control-communities). |
|
||||
| `graceful_restart` <span class="type">[GracefulRestart](#gracefulrestart)</span> | Enabled | Specifies graceful restart for neighbors that have no `graceful_restart` statement. Its `restart_time_seconds` also limits how long Ferrix waits at startup for neighbors to send their routes. |
|
||||
|
||||
## Peer
|
||||
@@ -75,6 +75,7 @@ Statements for a BGP neighbor.
|
||||
| `require_role` <span class="type">bool</span> | `false` | Rejects the session if the neighbor does not advertise a BGP role. Requires `role`. |
|
||||
| `export` <span class="type">[ExportPolicy](#exportpolicy)</span> | Top-level `export` | Specifies the export policy for the neighbor. Replaces the top-level `export` statement. |
|
||||
| `graceful_restart` <span class="type">[GracefulRestart](#gracefulrestart)</span> | Top-level `graceful_restart` | Specifies graceful restart for the neighbor. Each statement that is set replaces the corresponding top-level statement. |
|
||||
| `groups` <span class="type">uint32, repeated</span> | None | Specifies the groups of the session, by number, for control communities that name sessions by group. Use the same numbers on all routers in the local AS. Range: 1 through 4,294,967,295. See [Session Groups](@/docs/guides/passing-routes-on.md#session-groups). |
|
||||
|
||||
## TcpEndpoint
|
||||
|
||||
@@ -110,6 +111,7 @@ accepted. See [Import Policy](@/docs/guides/import-policy.md).
|
||||
| `add_large_communities` <span class="type">string, repeated</span> | None | Specifies large communities added to accepted routes, for example `64500:2:1`. |
|
||||
| `remove_communities` <span class="type">string, repeated</span> | None | Specifies patterns of communities removed from accepted routes, for example `64500:100`, `64500:*`, or `64500:2:*`. Applied before communities are added. |
|
||||
| `local_pref` <span class="type">uint32, optional</span> | 100 | Specifies the local preference of accepted routes. |
|
||||
| `accept_control_communities` <span class="type">bool</span> | `false` | Retains the local AS's communities on routes from an EBGP neighbor, so that the neighbor can set control communities on its own routes. By default, Ferrix removes them. Has no effect for an IBGP neighbor. See [Communities of the Local AS](@/docs/guides/import-policy.md#communities-of-the-local-as). |
|
||||
|
||||
## PrefixRange
|
||||
|
||||
|
||||
@@ -10,7 +10,9 @@ export { learned_routes: true }
|
||||
# Customers can restrict the advertisement of their routes with the large
|
||||
# communities 64500:0:P (not to AS P), 64500:1:P (only to AS P), and
|
||||
# 64500:0:0 (to no neighbor), or the standard communities 0:P, 64500:P, and
|
||||
# 0:64500.
|
||||
# 0:64500, and prepend 64500 towards AS P with 64500:11:P to 64500:13:P.
|
||||
# Ferrix removes the communities of AS 64500 from the routes of other
|
||||
# neighbors, such as the providers below.
|
||||
control_communities: true
|
||||
|
||||
peers {
|
||||
@@ -20,7 +22,6 @@ peers {
|
||||
role: PROVIDER
|
||||
import {
|
||||
max_prefixes: 1500000
|
||||
remove_communities: "64500:2:*"
|
||||
add_large_communities: "64500:2:100"
|
||||
}
|
||||
}
|
||||
@@ -32,7 +33,6 @@ peers {
|
||||
role: PROVIDER
|
||||
import {
|
||||
max_prefixes: 1500000
|
||||
remove_communities: "64500:2:*"
|
||||
add_large_communities: "64500:2:200"
|
||||
}
|
||||
# Prepend to make the path through transit-b less preferred. This
|
||||
@@ -43,6 +43,8 @@ peers {
|
||||
# Customer with a four-octet AS number. The prefix and origin AS lists
|
||||
# restrict its routes to its registered address space. Local preference
|
||||
# 200 makes its routes preferred over the same prefixes from providers.
|
||||
# The customer may set control communities; the informational communities
|
||||
# 64500:2:* are removed, so that it cannot set those.
|
||||
peers {
|
||||
name: "customer-65536"
|
||||
endpoint { address: "203.0.113.5" }
|
||||
@@ -54,6 +56,7 @@ peers {
|
||||
prefixes { prefix: "192.0.2.0/24" }
|
||||
prefixes { prefix: "2001:db8:a00::/40" max_length: 48 }
|
||||
origin_asns: 65536
|
||||
accept_control_communities: true
|
||||
remove_communities: "64500:2:*"
|
||||
add_large_communities: "64500:2:300"
|
||||
local_pref: 200
|
||||
|
||||
Reference in new issue
Block a user