Files
Rayhaan JaufeerallyandClaude Opus 5.5 9cfd3f67f0 Export limits, and a role for every peer where routes are passed on
What other networks were told of rested on one thing: the Only to
Customer mark that routes from providers, peers and route servers get as
they come in. A route without it, from a session without a role or by a
mistake anywhere along the way, went to every peer, from every router of
ours, and nothing of ours stood in the way.

export_limits are a second check, independent of the roles, the marks
and the export policy. For peers above or beside us (PROVIDER, PEER,
ROUTE_SERVER, and any in another AS without a role):

- prefixes: only routes for these go out, learned or our own. With our
  and our customers' space listed, a leak of anyone else's routes goes
  nowhere above us.
- max_prefixes: if more routes were to go out than this, none of them
  does. The session ends with a Cease / Administrative Shutdown whose
  Shutdown Communication says why (RFC 9003), and the peer is held down
  for its import.hold_down_seconds, so that it is told nothing rather
  than too much. The whole table is counted before any of it is sent.

They are set at the top and hold for every such peer that has none of its
own; unlike `export`, a peer's own export policy does not drop them. A
peer's own export_limits take their place, and an empty one lifts them.
Customers, route server clients and our own routers are not limited.

A configuration in which learned routes are passed on and a peer in
another AS has no role is now refused, as is accept_unconfigured_peers
with learned routes: without a role, a peer's routes go to everyone and
it is told of everything. This used to be a warning.

At startup, a warning for each peer the limits apply to that has none,
and for each originated route the limits leave out. A metric,
bgp_export_limit_exceeded_total, counts the sessions ended for it.

The interop lab has a phase in which a customer leaks: a route outside
its space never reaches BIRD, and when more were to go than the limit,
BIRD's session ends and its log has our reason.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 23:10:43 +02:00

85 lines
2.7 KiB
Protocol Buffer Text Format

# Transit network with two providers and one customer. Customer routes are
# advertised to all neighbors. Provider routes are advertised to the
# customer only. The BGP roles of the neighbors enforce this.
router_id: "198.51.100.1"
local_asn: 64500
# Advertise learned routes to all neighbors, as BGP roles permit.
export { learned_routes: true }
# Advertise to the providers only routes for the address space of the local
# AS and of the customer, and at most 20 routes. If more routes are to be
# advertised, Ferrix advertises none of them and tears down the session.
export_limits {
prefixes { prefix: "198.51.100.0/24" }
prefixes { prefix: "2001:db8:100::/40" max_length: 48 }
prefixes { prefix: "192.0.2.0/24" }
prefixes { prefix: "2001:db8:a00::/40" max_length: 48 }
max_prefixes: 20
}
# 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, 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 {
name: "transit-a"
endpoint { address: "203.0.113.0" }
remote_asn: 64496
role: PROVIDER
import {
max_prefixes: 1500000
add_large_communities: "64500:2:100"
}
}
peers {
name: "transit-b"
endpoint { address: "203.0.113.2" }
remote_asn: 64497
role: PROVIDER
import {
max_prefixes: 1500000
add_large_communities: "64500:2:200"
}
# Prepend to make the path through transit-b less preferred. This
# statement replaces the top-level export statement for this neighbor.
export { learned_routes: true as_path_prepend: 2 }
}
# 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" }
remote_asn: 65536
role: CUSTOMER
require_role: true
import {
max_prefixes: 50
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
}
}
originate { prefix: "198.51.100.0/24" }
originate { prefix: "2001:db8:100::/40" }
rpki { caches { address: "::1" port: 3323 } }
kernel {}
http_endpoint { address: "127.0.0.1" port: 8080 }