a positive test proves Ze does what the requirement demands and a negative one proves it refuses what the requirement forbids
RFC 7999 - BLACKHOLE Community
Every requirement this repository extracted from RFC 7999, the tests bound to it, and what a reader has verified about them. This summary is enrolled and gated by ./le rfc check.
Overview
Positive
what Ze has
the requirement admits no counter-case, so one polarity plus a recorded reason is the whole proof available for it
one direction is tested, the other is neither tested nor excused, and nothing states which
scoped tests exist; the remaining obligation is unmet or unproven, with zero whole-requirement credit
no test carries the requirement id, whether or not a gap states why
a red was observed once under a recorded procedure, and the unit, the claim and the producer it rested on still hash to what was recorded. The break is not re-run. A test pair is not a proof until one has been observed
Neutral
measures that are neither good news nor bad
MUST-level requirements the gate HOLDS. A population, not a result: the shares beside it are what says how Ze stands
an obligation that does not bind Ze. A {not-applicable} annotation says it never bound; a {feature-declined} annotation says its condition is an optional feature Ze does not offer, and quotes the RFC sentence that makes it optional. Scope, not coverage: it stays in the denominator every share on this page is taken over
a {not-applicable} annotation says the obligation does not bind Ze, so no test is owed for it. It stays in the denominator every share here is taken over
a {lower-layer} annotation says a layer under Ze performs the behavior, on state Ze installs into that layer, and names the producer that installs it. The obligation binds Ze and is met; Ze proves none of it, because its own boundary carries no value the behavior reads
a {feature-declined} annotation says the obligation is conditional on a feature the RFC makes optional and Ze does not offer, and it quotes the sentence that makes it optional. The condition is false, so nothing is owed and nothing is missing. It stays in the denominator every share here is taken over
Negative
what Ze owes
1 weak, wrong or unimplemented, 2 no longer current. Each is named below under its own requirement id
The 8 shares marked as a part above are the whole of the 4 gated MUSTs: they add to 100%. Proven by a recorded break is a share of TAGGED UNITS, a different population, so it is not one of them.
How to read the colors
A color names what the measure MEANS, not how well Ze scores on it. Green is a good outcome at any value, red is a bad one, and neither a population nor a scope count is an outcome, so both take no color. The number under the label is what says how far Ze has got.
| Card | Tone here | Why that color |
|---|---|---|
| Gated MUSTs | neutral | no color: a population is a scale, and a larger one is neither good news nor bad. It is the accounting total |
| Out of scope | neutral | no color: an obligation that never bound Ze is neither an achievement nor a failure, and counting it either way would be a claim |
| Tested both ways | ok | green at every value: a test pair is the outcome this gate exists to produce, and the share under the label is what says how far Ze has got |
| One polarity plus reason | ok | green at every value: where no counter-case exists, one polarity IS the complete answer, and a recorded reason is what the gate demands beside it |
| One polarity, unexcused | ok | green at zero, RED above it: half a proof with no reason for the other half |
| Partial proof; remaining gap | ok | green at zero, RED above it: a tested clause cannot prove the whole requirement |
| No test at all | ok | green at zero, RED above it: a binding obligation nothing exercises is a claim with nothing behind it, whether or not a reason is stated |
| Not applicable | neutral | no color: an obligation that never bound Ze is neither an achievement nor a failure, and counting it either way would be a claim |
| Met below Ze | neutral | no color: an obligation met below Ze is neither a test Ze wrote nor work Ze owes, and the two green shares above are what says how much Ze proves itself |
| Optional feature declined | neutral | no color: an obligation whose condition Ze never meets is neither an achievement nor a failure. The absent FEATURE is disclosed on the RFC's own status row, as an implementation gap a later scope decision can revisit |
| Proven by a recorded break | ok | green at every value: an observed break is the outcome the discrimination gate exists to produce. The denominator is TAGGED UNITS, not obligations, so this share is not one of the parts above |
| Audit verdicts | bad | RED on the first weak, wrong or unimplemented verdict, amber while a verdict is no longer current or a gated MUST is unjudged, green when every one is judged sound and current |
At a glance
| Field | Value |
|---|---|
| Public status | Partial |
| Enrolment | Enrolled |
| Requirements | 16 |
| Gated MUST-level | 4 |
| Not applicable, so out of scope | 0 |
| Declared gaps | 0 |
| Declared gaps a test demonstrates | 0 |
| Gated with no test | 0 |
| Nightly-only evidence | 0 |
| Test tags | 36 |
| Tagged units | 36 |
| Recorded audit verdicts | 7 |
| Discrimination records | 14 |
| Summary | rfc/short/rfc7999.md |
| Requirement shard | rfc/requirements/rfc7999.md |
| RFC text | rfc/full/rfc7999.txt |
Enrolment
Enrolled: BLACKHOLE Community (65535:666, 0xFFFF029A): four MUST-level requirements, every one of them proven in both polarities. RFC7999-3.3-1 and RFC7999-3.3-2 are the two bullet conditions of the single MUST sentence of section 3.3. Each carries unit evidence over the RIB honoring path (internal/component/bgp/plugins/rib/rfc7999_rib_blackhole_wiring_test.go) and interop evidence at nightly tier. That interop scenario, test/interop/scenarios/bgp-rfc7999-blackhole-frr, reads `ip route show` inside the ze container, so its assertion is a Linux FIB discard route rather than a Ze table. Its three outcomes differ in configuration alone. FRR announces a covered prefix on an agreed session and the kernel holds `blackhole 10.100.0.1`. FRR announces an uncovered prefix on the same session and the kernel forwards it, which is the 3.3-1 negative. BIRD announces a covered prefix on a session that agreed NO community and the kernel forwards it, which is the 3.3-2 negative: the authorization IS present on that peer, so the negative isolates the session agreement instead of an absent config block. RFC7999-3.3-4 is the operator obligation that origin validation must not block a legitimate blackhole, proven over the RPKI decision path (internal/component/bgp/plugins/rpki/rfc7999_blackhole_decision_test.go). RFC7999-3.1-2 binds the SEND side and carried a {not-applicable} annotation until 2026-08-13, on the reading that the obligation binds "the two networks" and no daemon can verify an out-of-band agreement. The owner replaced that reading the same day: configuring the community on a peer IS Ze's half of the agreement, so the obligation has a machine-checkable predicate after all and the annotation is withdrawn. Ze originates BLACKHOLE-tagged announcements through send bgp <selector> blackhole and through send bgp <selector> unicast community 65535:666, and both now narrow the fan-out to the sessions that named the community (agreedSelector, internal/component/bgp/plugins/cmd/announce/blackhole_agreement.go). A peer that agreed is announced to; a peer that did not is left out entirely rather than being sent the prefix untagged, because an ordinary announcement of a host route under attack attracts the traffic the operator asked to have discarded. Both polarities are proven at unit tier over the command handler. The other 12 rows are 6 SHOULD, 1 SHOULD NOT, 1 RECOMMENDED and 4 MAY. The section-by-section walk is recorded in rfc/extraction/rfc7999.json at register prose, with 1 of 4 sites excluded. Enrolled 2026-08-13.
What the public ledger says
Status: Partial
What the ledger says is covered
- The BLACKHOLE community (65535:666) is recognized on receive, and Ze honors it per BGP session. Section 3.3 states two conditions in one MUST sentence, and Ze enforces both. The peer must have agreed on that session by naming the community it honors (
blackhole communities), which accepts the well-known value under either spelling and an operator's own value, because operators run RTBH on their own community far more often than on 65535:666. The announced prefix must be covered by an equal or shorter prefix that peer is authorized to advertise (blackhole prefixes). Coverage is not prefix-list membership: a /24 authorization covers the /32 inside it (coveredByAuthorized,internal/component/bgp/plugins/rib/rib_blackhole.go). A honored route becomes a discard route in the Linux FIB (RTN_BLACKHOLE) and a drop path in VPP. Section 4's default holds: ablackholecontainer with neither leaf-list, and a peer with no container, discard nothing. Statingprefixesalone is itself the explicit configuration directive Section 4 asks for, so it resolves the community to the well-known value - a stated
communitieslist is taken exactly and the well-known value is never added to it. Section 3.1's send-side obligation is met on the origination path.send bgp <selector> blackhole, andsend bgp <selector> unicast community 65535:666, advertise the community only to the sessions that named it, and a peer that named none is left out of the fan-out rather than being sent the prefix untagged (agreedSelector,internal/component/bgp/plugins/cmd/announce/blackhole_agreement.go). Section 3.3's origin-validation obligation is met byblackhole-exemptunder an RPKI peer. It keeps a BLACKHOLE-tagged route that RFC 6811 makes Invalid on prefix length alone, and only when a covering VRP names the origin AS and the session named the community the route carries (internal/component/bgp/plugins/rpki/blackhole.go). All three consumers read one per-peer answer from one place (internal/component/bgp/blackholecfg). Section 3.2's receiver obligations and the own-Global-Administrator scrub are tracked under RFC 1997 and RFC 7454. Tests bound per requirement inrfc/requirements/rfc7999.md, and the FRR and BIRD interop scenariotest/interop/scenarios/bgp-rfc7999-blackhole-frrasserts the discard route in a real kernel. Both Section 3.3 conditions carry interop evidence as well as unit evidence. That scenario tagsRFC7999-3.3-1andRFC7999-3.3-2in both polarities. Neither can afterwards fall back to a unit test alone. Enrolled on 2026-08-13, so the ratchets now hold every requirement here. The walk behind that claim is recorded inrfc/extraction/rfc7999.json, at registerprose, with 1 of 4 sites excluded.
What the ledger says remains
No tracked gap. Every MUST-level row is proven in both polarities.RFC7999-3.1-2 carried a {not-applicable} annotation until 2026-08-13, on the reading that Section 3.1 binds "the two networks" where Section 3.3 binds "BGP speakers", and that no daemon can verify an out-of-band agreement. The owner replaced that reading the same day: configuring the community on a peer is Ze's half of the agreement, the peer sending it is the other half, so the obligation is machine-checkable on the send side. The annotation is withdrawn and the requirement is tested. Four advisory rows carry no test. RFC7999-3.1-3 and RFC7999-3.1-5 bind the sender. RFC7999-3.3-3 asks a multilateral speaker to apply both Section 3.3 conditions. RFC7999-6-1 asks for strict filtering. None is gated, so none is ratcheted. Two are worth stating plainly. The authorization Section 3.3 and Section 6 turn on is operator-supplied. blackhole prefixes is a configured leaf-list, not a view derived from IRR or RPKI. The honoring machinery is bilateral, so a route server does not apply the two conditions to its clients.
Coverage
| Bucket | Count | What it counts |
|---|---|---|
| Positive and negative tests | 4 | one part of the gated population |
| Annotated (including scoped evidence) | 0 | one part of the gated population |
| One polarity only | 0 | one part of the gated population |
| No test and no annotation | 0 | one part of the gated population |
| Partial proof; remaining gap (subset of annotated; zero whole-requirement credit) | 0 | an overlay: each of these is also counted by the part it falls in |
| Evidence that runs nightly only | 0 | an overlay: each of these is also counted by the part it falls in |
| Derived from other rows | 0 | outside the gated population: each asserts nothing and derives its state from the rows it names, which the parts above already count |
| Gated MUST-level requirements | 4 | every gated MUST falls in exactly one bucket above |
Positive and negative tests (4): RFC7999-3.1-2, RFC7999-3.3-1, RFC7999-3.3-2, RFC7999-3.3-4
Requirements
| Requirement | Level | Section | Tests |
|---|---|---|---|
RFC7999-3.1-2 | In a bilateral peering relationship, use of the BLACKHOLE community MUST be agreed upon by the two networks before advertising it. (§3.1) | ||
| MUST | 3.1 - IP Prefix Announcements with BLACKHOLE Community Attached | ||
RFC7999-3.3-1 | BGP speakers in a bilateral peering relationship using the BLACKHOLE community MUST only accept and honor BGP announcements carrying the BLACKHOLE community under the two following conditions: o The announced prefix is covered by an equal or shorter prefix that the neighboring network is authorized to advertise. (§3.3) | ||
| MUST | 3.3 - Accepting Blackholed IP Prefixes | ||
RFC7999-3.3-2 | BGP speakers in a bilateral peering relationship using the BLACKHOLE community MUST only accept and honor BGP announcements carrying the BLACKHOLE community under the two following conditions: o The announced prefix is covered by an equal or shorter prefix that the neighboring network is authorized to advertise. o The receiving party agreed to honor the BLACKHOLE community on the particular BGP session. (§3.3) | ||
| MUST | 3.3 - Accepting Blackholed IP Prefixes | ||
RFC7999-3.3-4 | An operator MUST ensure that origin validation techniques (such as the one described in [RFC6811]) do not inadvertently block legitimate announcements carrying the BLACKHOLE community. (§3.3) | ||
| MUST | 3.3 - Accepting Blackholed IP Prefixes | ||
RFC7999-3.1-3 | The community SHOULD be ignored, if it is received by a network that it not using it. (§3.1) | ||
| SHOULD | 3.1 - IP Prefix Announcements with BLACKHOLE Community Attached | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-3.1-5 | When a network is under DDoS duress, it MAY announce an IP prefix covering the victim's IP address(es) for the purpose of signaling to neighboring networks that any traffic destined for these IP address(es) should be discarded. In such a scenario, the network operator SHOULD attach the BLACKHOLE community. (§3.1) | ||
| SHOULD | 3.1 - IP Prefix Announcements with BLACKHOLE Community Attached | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-3.2-1 | A BGP speaker receiving an announcement tagged with the BLACKHOLE community SHOULD add the NO_ADVERTISE or NO_EXPORT community as defined in [RFC1997], or a similar community, to prevent propagation of the prefix outside the local AS. (§3.2) | ||
| SHOULD | 3.2 - Local Scope of Blackholes | ||
RFC7999-3.2-2 | The community to prevent propagation SHOULD be chosen according to the operator's routing policy. (§3.2) | ||
| SHOULD | 3.2 - Local Scope of Blackholes | ||
RFC7999-3.3-3 | In topologies with a route server or other multilateral peering relationships, BGP speakers SHOULD accept and honor BGP announcements under the same conditions. (§3.3) | ||
| SHOULD | 3.3 - Accepting Blackholed IP Prefixes | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-4-1 | Without an explicit configuration directive set by the operator, network elements SHOULD NOT discard traffic destined towards IP prefixes that are tagged with the BLACKHOLE community. (§4) | ||
| SHOULD NOT | 4 - Vendor Implementation Recommendations | ||
RFC7999-6-1 | In order to further limit the impact of unauthorized BGP announcements carrying the BLACKHOLE community, the receiving BGP speaker SHOULD verify by applying strict filtering (see Section 6.2.1.1.2 of [RFC7454]) that the peer announcing the prefix is authorized to do so. (§6) | ||
| SHOULD | 6 - Security Considerations | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-6-2 | It is RECOMMENDED that operators use best common practices to protect their BGP sessions, such as the ones in [RFC7454]. (§6) | ||
| RECOMMENDED | 6 - Security Considerations | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-3.1-1 | This community MAY be used in all bilateral and multilateral BGP deployment scenarios. (§3.1) | ||
| MAY | 3.1 - IP Prefix Announcements with BLACKHOLE Community Attached | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-3.1-4 | When a network is under DDoS duress, it MAY announce an IP prefix covering the victim's IP address(es) for the purpose of signaling to neighboring networks that any traffic destined for these IP address(es) should be discarded. (§3.1) | ||
| MAY | 3.1 - IP Prefix Announcements with BLACKHOLE Community Attached | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-3.1-6 | The BLACKHOLE community MAY also be used as one of the trigger communities in a destination-based Remote Triggered Blackhole (RTBH) [RFC5635] configuration. (§3.1) | ||
| MAY | 3.1 - IP Prefix Announcements with BLACKHOLE Community Attached | positive
no testno positive testnegative
no testno negative test |
|
RFC7999-4-2 | Vendors MAY provide a shorthand keyword in their configuration language to reference the well-known BLACKHOLE community attribute value. The suggested string to be used is "blackhole". (§4) | ||
| MAY | 4 - Vendor Implementation Recommendations | positive
no testno positive testnegative
no testno negative test |
|
Gaps and untested MUSTs
RFC 7999 declares no gap, and every gated MUST it carries has a test bound to it.
Proof state
A tagged unit reads unproven where no discrimination record exists for it: nothing in this tree has been observed to break it, so the claim its tag makes is unproven.
RFC7999-3.1-2
In a bilateral peering relationship, use of the BLACKHOLE community MUST be agreed upon by the two networks before advertising it. (§3.1)
Audit verdict: weak (the tests pass over code that does not enforce the requirement), fresh. Re-judged 2026-10-14 (independent auditor, D5, owner Q-D5 (a1)). RFC 7999 Section 3.1: "In a bilateral peering relationship, use of the BLACKHOLE community MUST be agreed upon by the two networks before advertising it." Re-advertisement is now covered: TestRFC7999ReadvertiseWithheldWithoutAgreement asserts filter_community egressFilter refuses a BLACKHOLE-tagged route to an eBGP peer that agreed another value, one with no container, an address that only names a group, and any destination with no agreement cache; TestRFC7999ReadvertiseReachesAgreedAndExemptDestinations asserts the agreed peer, a container-only peer, a dynamic member, iBGP, an rs-client and an untagged route pass. Origination by send bgp blackhole is covered by the four announce units over handleAnnounceBlackhole. Remaining gap (question 4): the second originating path, send bgp unicast ... community 65535:666, gates through its own agreedSelector call (cmd/announce/announce.go, handleAnnounceUnicast), and the only unit asserting that call, TestAnnounceUnicastWithBlackholeCommunityMeetsTheSameGate, carries no tag; deleting that call leaves every tagged unit green. Tagging that unit as a positive would answer it.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestAnnounceBlackholeIsWithheldFromAPeerThatDidNotAgree |
unit/verify | unproven |
| negative | TestAnnounceBlackholeIsWithheldFromASessionOutsideTheGroup |
unit/verify | unproven |
| negative | TestRFC7999ReadvertiseReachesAgreedAndExemptDestinations |
unit/verify | revert, verified |
| positive | TestAnnounceBlackholeReachesAMemberOfADynamicGroup |
unit/verify | unproven |
| positive | TestAnnounceBlackholeReachesAnAgreedPeer |
unit/verify | unproven |
| positive | TestRFC7999ReadvertiseWithheldWithoutAgreement |
unit/verify | revert, verified |
RFC7999-3.3-1
BGP speakers in a bilateral peering relationship using the BLACKHOLE community MUST only accept and honor BGP announcements carrying the BLACKHOLE community under the two following conditions: o The announced prefix is covered by an equal or shorter prefix that the neighboring network is authorized to advertise. (§3.3)
Audit verdict: enforced (the tests do what the requirement demands), shifted: internal/le/interoplab/bgp/check_rfc.go::checkRFC7999Blackhole, internal/le/interoplab/bgp/check_rfc.go::checkRFC7999Blackhole#2 moved. Independent source rejudgment of every current cover including checkRFC7999Blackhole. RFC 7999 Section 3.3: BGP speakers in a bilateral peering relationship using the BLACKHOLE community MUST only accept and honor BGP announcements carrying the BLACKHOLE community under the two following conditions: The announced prefix is covered by an equal or shorter prefix that the neighboring network is authorized to advertise. The receiving party agreed to honor the BLACKHOLE community on the particular BGP session. Equal-/24 and covered-/32 positives require exact Blackhole on best-change and Loc-RIB; longer-/25 authorization and outside-prefix negatives require exact type 0. Dynamic group tests require the matching group rule, peer override precedence, and event-carried group identity reaching Loc-RIB. coveredByAuthorized, blackholeRouteTypeForBest and checkBestPathChange produce the type consumed by sysrib and the kernel discard builder. checkRFC7999Blackhole assertion 4 requires a real kernel discard and assertion 5 positively requires forwarding for the unauthorized prefix, after both foreign sessions and all destination routes exist. Q1-Q4 pass for the authorization clause with agreement held true; the dynamic fixture is consumer-boundary rather than eBGP-admission evidence. Stored panic records establish reachability only. No checks were run; live FRR/BIRD/Linux and VPP acceptance and changed-unit proof maintenance remain pending.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestRFC7999BlackholeRefusedUnderALongerAuthorizedPrefix |
unit/verify | revert, verified |
| negative | TestBlackholeNotStampedOutsideAuthorization |
unit/verify | unproven |
| negative | checkRFC7606MixedUpdate |
interop/nightly | unproven |
| positive | TestRFC7999BlackholeHonoredOnAnEqualAuthorizedPrefix |
unit/verify | revert, verified |
| positive | TestBlackholeGroupIdentityArrivesOnAStructuredEvent |
unit/verify | revert, verified |
| positive | TestBlackholeRouteTypeStampedOnBestPath |
unit/verify | unproven |
| positive | TestBlackholeRuleForDynamicGroup |
unit/verify | unproven |
| positive | checkRFC7606MixedUpdate |
interop/nightly | unproven |
RFC7999-3.3-2
BGP speakers in a bilateral peering relationship using the BLACKHOLE community MUST only accept and honor BGP announcements carrying the BLACKHOLE community under the two following conditions: o The announced prefix is covered by an equal or shorter prefix that the neighboring network is authorized to advertise. o The receiving party agreed to honor the BLACKHOLE community on the particular BGP session. (§3.3)
Audit verdict: enforced (the tests do what the requirement demands), shifted: internal/le/interoplab/bgp/check_rfc.go::checkRFC7999Blackhole, internal/le/interoplab/bgp/check_rfc.go::checkRFC7999Blackhole#2 moved. Independent source rejudgment of every current cover including checkRFC7999Blackhole. RFC 7999 Section 3.3: BGP speakers in a bilateral peering relationship using the BLACKHOLE community MUST only accept and honor BGP announcements carrying the BLACKHOLE community under the two following conditions: The announced prefix is covered by an equal or shorter prefix that the neighboring network is authorized to advertise. The receiving party agreed to honor the BLACKHOLE community on the particular BGP session. The row includes both bullets: equal/covered positives require exact Blackhole; outside and too-short announced-prefix negatives require type 0 despite agreement. Authorized/no-community internal config requires type 0; dynamic group membership and peer-rule precedence have distinct outcomes, and the structured consumer must retain ix and install Blackhole. The synthetic empty-community map is not user config-parser proof: prefixes-only defaults agreement. The interop scenario instead explicitly agrees only 65001:666 for BIRD sending 65535:666; assertion 6 requires a gateway route, while assertion 4 requires discard for the authorized/agreed FRR route and assertion 5 isolates authorization. blackholeRouteTypeForBest scopes the decision to the winning session and blackholeRouteType requires both conditions before sysrib/FIB consumption. Q1-Q4 pass over the combined population; group-membership negative alone is not agreement-isolated. Stored coveredByAuthorized HALTs prove reachability only. No checks ran; current live foreign/Linux/VPP acceptance and changed-unit proof maintenance remain pending.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestRFC7999BlackholeNotHonoredOutsideTheAuthorizedPrefix |
unit/verify | revert, verified |
| negative | TestBlackholeNotStampedWhenNoCommunityAgreedButAuthorizationExists |
unit/verify | unproven |
| negative | TestBlackholeRuleForDynamicGroup |
unit/verify | unproven |
| negative | checkRFC7606TypedNLRIDiscard |
interop/nightly | unproven |
| positive | TestRFC7999BlackholeHonoredForTheEqualAuthorizedPrefix |
unit/verify | revert, verified |
| positive | TestBlackholeGroupIdentityArrivesOnAStructuredEvent |
unit/verify | revert, verified |
| positive | TestBlackholeRouteTypeStampedOnBestPath |
unit/verify | unproven |
| positive | TestBlackholeRuleForDynamicGroup |
unit/verify | unproven |
| positive | check_rfc.go |
interop/nightly | unproven |
RFC7999-3.3-4
An operator MUST ensure that origin validation techniques (such as the one described in [RFC6811]) do not inadvertently block legitimate announcements carrying the BLACKHOLE community. (§3.3)
Audit verdict: enforced (the tests do what the requirement demands), fresh. Forbidden: origin validation rejecting a legitimate BLACKHOLE announcement. internal/component/bgp/plugins/rpki/blackhole_decision_test.go::TestBlackholeSurvivesLengthOnlyInvalid: a /32 Invalid only by maxLength with BLACKHOLE must be Accept (Error if not). Negative ::TestBlackholeDoesNotSurviveAWrongOrigin keeps a wrong-origin BLACKHOLE rejected, delimiting 'legitimate'. The exemption is operator opt-in (blackholeDecisionPlugin(t, true)), matching the sentence binding the operator.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestBlackholeDoesNotSurviveAWrongOrigin |
unit/verify | unproven |
| positive | TestBlackholeSurvivesLengthOnlyInvalid |
unit/verify | unproven |
RFC7999-3.2-1
A BGP speaker receiving an announcement tagged with the BLACKHOLE community SHOULD add the NO_ADVERTISE or NO_EXPORT community as defined in [RFC1997], or a similar community, to prevent propagation of the prefix outside the local AS. (§3.2)
Audit verdict: enforced (the tests do what the requirement demands), fresh. Positive TestRFC7999ReceivedBlackholeRouteGainsThePropagationCommunity: config leaf parsed, [BLACKHOLE 64496:1] leaves applyIngressFilter with NO_EXPORT (or NO_ADVERTISE) appended and the other community kept. Negative TestRFC7999RouteWithoutBlackholeGainsNoPropagationCommunity: with the guard on, no COMMUNITY, 65535:665 (one below BLACKHOLE) and 64496:1 pass unchanged, so the trigger is BLACKHOLE alone. Both carry revert records on blackholePropagationGuard. SHOULD: the add is operator-enabled (no leaf: unchanged), which 3.2-2 permits.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestRFC7999RouteWithoutBlackholeGainsNoPropagationCommunity |
unit/verify | revert, verified |
| positive | TestRFC7999BlackholeFieldHasReader |
unit/verify | unproven |
| positive | TestRFC7999ReceivedBlackholeRouteGainsThePropagationCommunity |
unit/verify | revert, verified |
| positive | community-blackhole-noexport.ci |
functional/verify | unproven |
RFC7999-3.2-2
The community to prevent propagation SHOULD be chosen according to the operator's routing policy. (§3.2)
Audit verdict: enforced (the tests do what the requirement demands), fresh. Positive TestRFC7999PropagationCommunityFollowsTheOperatorLeaf: each leaf value puts exactly its community on a received BLACKHOLE route. Negative TestRFC7999PropagationCommunityIsNeverForced: the unchosen community is absent under each value, and leaf none or unset leaves the route unchanged, so no fixed default is forced. Revert records on blackholeGuardCommunity for both.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestRFC7999PropagationCommunityIsNeverForced |
unit/verify | revert, verified |
| positive | TestBlackholeGuardNoAdvertise |
unit/verify | unproven |
| positive | TestRFC7999PropagationCommunityFollowsTheOperatorLeaf |
unit/verify | revert, verified |
RFC7999-4-1
Without an explicit configuration directive set by the operator, network elements SHOULD NOT discard traffic destined towards IP prefixes that are tagged with the BLACKHOLE community. (§4)
Audit verdict: enforced (the tests do what the requirement demands), fresh. SHOULD NOT discard without an operator directive. Positive (conforming) TestBlackholeCommunityLeavesNextHopAloneWithoutAgreement: a modify naming only 65001:100 accepts the 65535:666 route with no change; rib TestBlackholeNotStampedWithoutAgreement / ...WhenNoCommunityAgreedButAuthorizationExists: RouteType 0 on both rails. Negative TestBlackholeCommunityRewritesNextHopWhenAgreed is the directive-present counter-case (next-hop rewritten to the named discard address). Accepted as the negative: it shows the no-discard outcome is caused by the absent directive, so a filter that never rewrote anything cannot pass the pair. Revert records on (matchCond).matches for both filter_modify units; the rib positives have none.
| Polarity | Test | Kind and tier | Proof state |
|---|---|---|---|
| negative | TestBlackholeCommunityRewritesNextHopWhenAgreed |
unit/verify | revert, verified |
| positive | TestBlackholeCommunityLeavesNextHopAloneWithoutAgreement |
unit/verify | revert, verified |
| positive | TestBlackholeNotStampedWhenNoCommunityAgreedButAuthorizationExists |
unit/verify | unproven |
| positive | TestBlackholeNotStampedWithoutAgreement |
unit/verify | unproven |
Extraction sign-off
| Field | Value |
|---|---|
| Reviewer | ze-implement agent, spec-bcp194-6-blackhole enrolment step |
| Signed off | 2026-08-13 |
| Register | prose |
| Source | rfc/full/rfc7999.txt |
| Source fingerprint | f9768bb1d175830a |
| Record | rfc/extraction/rfc7999.json |
| Mapped sentences | 3 |
| Declined as scope | 1 |
| Relocated to a spec, which Ze OWES | 0 |
| Unclassified | 0 |
Sections
| Section | Name | Sites | Disposition | Reason |
|---|---|---|---|---|
front |
not stated | 1 | walked | Title block, Abstract, Status of This Memo, Copyright Notice and Table of Contents. Walked because the site scan attributes one site here. That site is the IETF Trust Legal Provisions boilerplate and is excluded below. |
1 |
Introduction | 0 | walked | Introduction. States the operational problem: each network triggers blackholing by a different mechanism, so an operator must learn the mechanism of every neighbor. Gives the reason for one well-known community. No sentence directs a speaker. |
1.1 |
Requirements Language | 0 | walked | Requirements Language. Restricts the RFC 2119 key words to their upper-case form and states that the lower-case forms are English words without normative meaning. It binds how the document is read and states no obligation of its own. The summary records the restriction, because sections 3.2, 3.3 and 6 each carry a lower-case 'should' that must not be read as a requirement. |
2 |
BLACKHOLE Community | 0 | walked | BLACKHOLE Community. Defines the community as well-known, transitive and advisory, and states its semantics: the presence of the community asks the receiver to drop traffic sent toward the prefix. Every sentence is declarative. The registered value is stated in section 5. |
3 |
Operational Recommendations | 0 | walked | Operational Recommendations. Section heading only. The three subsections carry all of the text. |
3.1 |
IP Prefix Announcements with BLACKHOLE Community Attached | 1 | walked | IP Prefix Announcements with BLACKHOLE Community Attached. One MUST-level site, mapped below. The section also states that accepting and honoring the community or ignoring it is each operator's choice, and carries one MAY on deployment scenarios, one SHOULD on ignoring the community, one MAY and one SHOULD on announcing under DDoS duress, and one MAY on RTBH trigger communities. Captured as RFC7999-3.1-1 through RFC7999-3.1-6. The multilateral sentence states that the decision follows the operator's routing policy and is recorded as guidance without a keyword. |
3.2 |
Local Scope of Blackholes | 0 | walked | Local Scope of Blackholes. No MUST-level site: both obligations are SHOULD. The receiver adds NO_ADVERTISE, NO_EXPORT or a similar community to prevent propagation outside the local AS, and chooses which one by routing policy. Captured as RFC7999-3.2-1 and RFC7999-3.2-2. The closing caution about propagating a tagged prefix outside the local routing domain uses a lower-case 'should' and is recorded as guidance without a keyword. |
3.3 |
Accepting Blackholed IP Prefixes | 2 | walked | Accepting Blackholed IP Prefixes. Two MUST-level sites, both mapped below. The first states one obligation with two bullet conditions, and the summary captures each bullet as its own requirement because each is independently violable: a speaker can honor an uncovered prefix while the session agreement holds, and can honor a covered prefix on a session that agreed to nothing. The site scan sees the lead-in sentence alone, so the second bullet has no site of its own and RFC7999-3.3-2 is recorded as unsourced here. The section also carries one SHOULD extending both conditions to multilateral topologies (RFC7999-3.3-3), the RFC 7606 pointer that makes a malformed community treat-as-withdraw, and four lower-case statements recorded as guidance without a keyword. |
4 |
Vendor Implementation Recommendations | 0 | walked | Vendor Implementation Recommendations. No MUST-level site. One SHOULD NOT states that a network element does not discard traffic toward a tagged prefix without an explicit configuration directive, and one MAY offers a configuration shorthand whose suggested string is 'blackhole'. Captured as RFC7999-4-1 and RFC7999-4-2. |
5 |
IANA Considerations | 0 | skipped (iana) | IANA Considerations. Records that IANA has registered BLACKHOLE as 0xFFFF029A in the 'BGP Well-known Communities' registry, and that the low-order two octets are 666 in decimal. The sentence reports a completed registry action and binds IANA. The value it records is carried in the summary's Constants and Encoding tables, which state a codepoint rather than an obligation. |
6 |
Security Considerations | 0 | walked | Security Considerations. No MUST-level site. One SHOULD asks the receiving speaker to verify by strict filtering that the announcing peer is authorized for the prefix, and one RECOMMENDED asks operators to protect their BGP sessions. Captured as RFC7999-6-1 and RFC7999-6-2. The rest is threat analysis: a forwarding agent can alter, add or remove communities, recipients cannot detect the change, and BGPsec does not resolve it. Two lower-case sentences, on filtering an unauthorized announcement and on the validation method following routing policy, are recorded as guidance without a keyword. |
7 |
References heading | 0 | skipped (references) | References heading. |
7.1 |
not stated | 0 | skipped (references) | Normative References: RFC 1997, RFC 2119, RFC 4271 and RFC 7606. |
7.2 |
not stated | 0 | skipped (references) | Informative References: the BGPsec protocol draft, RFC 3882, RFC 5575, RFC 5635, RFC 6811 and RFC 7454. |
Excluded sentences
| Site | Excluded kind | Reason | Quote |
|---|---|---|---|
front:1 |
not-a-requirementnever bound Ze the sentence states a fact or describes another document, and directs no implementation |
The IETF Trust Legal Provisions boilerplate of the Copyright Notice. Its 'must' is lower case, which section 1.1 puts outside the normative set, and it binds a party that extracts Code Components from the document rather than a BGP speaker. RFC 7999 contains no code component: it defines one codepoint and no syntax. | Code Components extracted from this document must include Simplified BSD License text as described in Section 4.e of the Trust Legal Provisions and are provided without warranty as described in the Simplified BSD License. |
Superseded
No document obsoletes RFC 7999, so its obligations are stated where they were written.