commit 7d4443daafee5530ed069e23ff3367877c7ee319 Author: root Date: Mon Apr 20 04:42:25 2020 +0200 initial commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..00896aa --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +icvpn-meta/ diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..80abb6e --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "icvpn-scripts"] + path = icvpn-scripts + url = https://github.com/freifunk/icvpn-scripts.git diff --git a/bird.conf b/bird.conf new file mode 100644 index 0000000..b1d34f7 --- /dev/null +++ b/bird.conf @@ -0,0 +1,28 @@ + +log syslog all; + +router id 172.23.156.14; + +timeformat base iso long; +timeformat log iso long; +timeformat protocol iso long; +timeformat route iso long; + +include "/etc/bird/constants.conf"; +include "/etc/bird/communities.conf"; +include "/etc/bird/tables.conf"; +include "/etc/bird/rpki.conf"; +include "/etc/bird/filters/*.conf"; +include "/etc/bird/protocols/*.conf"; + +protocol device { + +} + +protocol direct { + ipv4; + ipv6; + + interface "virbr*", "wg-*", "sit-*", "idrac", "eno*", "tobi", "manu"; +} + diff --git a/communities.conf b/communities.conf new file mode 100644 index 0000000..061080e --- /dev/null +++ b/communities.conf @@ -0,0 +1,52 @@ +# Well-known: https://www.iana.org/assignments/bgp-well-known-communities/bgp-well-known-communities.xhtml +define wk_graceful_shutdown = (0xffff, 0x0000); # RFC8326 +define wk_accept_own = (0xffff, 0x0001); # RFC7611 +define wk_blackhole = (0xffff, 0x029a); # RFC7999 +define wk_no_export = (0xffff, 0xff01); # RFC1997 +define wk_no_advertise = (0xffff, 0xff02); # RFC1997 +define wk_no_export_subconfed = (0xffff, 0xff03); # RFC1997 +define wk_nopeer = (0xffff, 0xff04); # RFC3765 + +# See https://www.euro-ix.net/en/forixps/large-bgp-communities/ + +# Informational RS:1000-1999:* + +## Informational tags RS:1000-1099:* +define informational_rpki_valid = (my_ripe_asn, 1000, 1); +define informational_rpki_unknown = (my_ripe_asn, 1000, 2); +define informational_rpki_not_checked = (my_ripe_asn, 1000, 3); +define informational_rpki_invalid = (my_ripe_asn, 1000, 4); +define informational_rpki_invalid_origin_as = (my_ripe_asn, 1000, 5); +define informational_rpki_invalid_max_length = (my_ripe_asn, 1000, 6); + +define informational_irrdb_valid = (my_ripe_asn, 1001, 1); +define informational_irrdb_not_checked = (my_ripe_asn, 1001, 2); +define informational_irrdb_more_specific = (my_ripe_asn, 1001, 3); +define informational_irrdb_prefix_not_found_in_as_set = (my_ripe_asn, 1001, 4); +define informational_irrdb_invalid_origin_as = (my_ripe_asn, 1001, 5); +define informational_irrdb_invalid_prefix_for_origin_as = (my_ripe_asn, 1001, 6); + +# Filtered reasons: RS:1100-1199:* + +## Route was filtered on import RS:1101:* +define filtered_import_prefix_too_long = (my_ripe_asn, 1101, 1); +define filtered_import_prefix_too_short = (my_ripe_asn, 1101, 2); +define filtered_import_bogon_prefix = (my_ripe_asn, 1101, 3); +define filtered_import_bogon_as = (my_ripe_asn, 1101, 4); +define filtered_import_as_path_too_long = (my_ripe_asn, 1101, 5); +define filtered_import_as_path_too_short = (my_ripe_asn, 1101, 6); +define filtered_import_first_as_not_peer = (my_ripe_asn, 1101, 7); +define filtered_import_next_hop_not_peer = (my_ripe_asn, 1101, 8); +define filtered_import_irrdb_prefix_not_in_as_set = (my_ripe_asn, 1101, 9); +define filtered_import_origin_as_not_in_peer_as_set = (my_ripe_asn, 1101, 10); +define filtered_import_prefix_not_found_in_origin_as = (my_ripe_asn, 1101, 11); +define filtered_import_prefix_is_rpki_unknown = (my_ripe_asn, 1101, 12); +define filtered_import_prefix_is_rpki_invalid = (my_ripe_asn, 1101, 13); +define filtered_import_transit_free_asn_in_as_path = (my_ripe_asn, 1101, 14); +define filtered_import_too_many_bgp_communities = (my_ripe_asn, 1101, 15); + +# Route was filtered on export RS:1102:* +define filtered_export_advertising_peer_declines_prefix = (my_ripe_asn, 1102, 1); +define filtered_export_declined_from_advertising_peer = (my_ripe_asn, 1102, 2); +define filtered_export_too_many_bgp_communities = (my_ripe_asn, 1102, 3); + diff --git a/constants.conf b/constants.conf new file mode 100644 index 0000000..c3a03b4 --- /dev/null +++ b/constants.conf @@ -0,0 +1,3 @@ +define my_ripe_asn = 207613; +define my_dn42_asn = 4242422428; + diff --git a/filters/chaosvpn.conf b/filters/chaosvpn.conf new file mode 100644 index 0000000..8579655 --- /dev/null +++ b/filters/chaosvpn.conf @@ -0,0 +1,12 @@ +# Source: https://wiki.hamburg.ccc.de/ChaosVPN:IPRanges + +function is_chaosvpn() { + return net ~ [ + 10.4.0.0/16+, + 10.32.0.0/16+, + 10.100.0.0/14+, + 10.104.0.0/14+, + 172.31.0.0/16+ + ]; +} + diff --git a/filters/common.conf b/filters/common.conf new file mode 100644 index 0000000..ba59ef8 --- /dev/null +++ b/filters/common.conf @@ -0,0 +1,210 @@ +# Sources: +# http://www.us.ntt.net/support/policy/routing.cfm#bogon +# http://as2914.net/bogon_asns/configuration_examples.txt +# https://www.de-cix.net/en/locations/germany/frankfurt/routeserver-guide +# https://archive.nanog.org/sites/default/files/Snijders_Everyday_Practical_Bgp.pdf +# http://bgpfilterguide.nlnog.net/ +# https://gitlab.labs.nic.cz/labs/bird/-/wikis/BGP_filtering + +function is_mine_ripe() { + return net ~ [ + 2a09:11c0:200::/44+, + 2a0e:97c7:100::/44+, + 2a09:4c2:1b::/48+ + ]; +} + +function is_mine_dn42() { + return net ~ [ + 172.23.156.0/23, + fd42:4dd0:ff00::/48 + ]; +} + +function is_mine() { + return is_mine_dn42() || is_mine_ripe(); +} + +# Big transit / tier 1 ASNs for "peerlock" +function is_big_asn(int asnum) { + return asnum ~ [ + 174, # Cogent + 209, # Qwest (HE carries this on IXPs IPv6 (Jul 12 2018)) + 701, # UUNET + 702, # UUNET + 1239, # Sprint + 1299, # Telia + 2914, # NTT Communications + 3257, # GTT Backbone + 3320, # Deutsche Telekom AG (DTAG) + 3356, # Level3 + 3549, # Level3 + 3561, # Savvis / CenturyLink + 4134, # Chinanet + 5511, # Orange opentransit + 6453, # Tata Communications + 6461, # Zayo Bandwidth + 6762, # Seabone / Telecom Italia + 7018 # AT&T + ]; +} + +# Source: https://wiki.freifunk.net/AS-Nummern +function is_freifunk_asn(int asnum) { + return asnum ~ [ 64856..65534 ]; +} + +# Source: https://dn42.net/services/Whois +function is_dn42_asn(int asnum) { + return asnum ~ [ 4242420000..4242429999 ]; +} + +function is_bogon_asn(int asnum) { + return asnum ~ [ + 0, # RFC7607: Codification of AS 0 Processing + 23456, # RFC6793: AS_TRANS for 32bit extendend ASN range + 64496..64511, # RFC5398: Reservation for Documentation Use 16bit ASN + 64512..65534, # RFC6996: Reservation for Private Use 16bit ASN + 65535, # RFC7300: Reservation of Last ASNs + 65536..65551, # RFC5398: Reservation for Documentation Use 32bit ASN + 65552..131071, # IANA reserved ASNs https://www.mail-archive.com/uknof@lists.uknof.org.uk/msg03395.html + 4200000000..4294967294, # RFC6996: Reservation for Private Use 32bit ASN + 4294967295 # RFC7300: Reservation of Last ASNs + ]; +} + +# RFC 1918 +function is_private_v4() { + return net ~ [ + 10.0.0.0/8+, + 172.16.0.0/12+, + 192.168.0.0/16+ + ]; +} + +function is_private_v6() { + return net ~ [ + fc00::/7+ # RFC4193: Unique-Local + ]; +} + +function is_peering_lan_v4() { + return net ~ [ + 185.1.119.0/24+, # LocIX Frankfurt + 80.81.192.0/21+, # DE-CIX Frankfurt + 185.1.125.0/24+, # 4IXP / 4b42 + 206.81.104.0/24+, # EVIX + 193.189.82.0/23+ # KleyRex + ]; +} + +function is_peering_lan_v6() { + return net ~ [ + 2a07:1c44:61f0::/64+, # LocIX Frankfurt + 2001:7f8::/64+, # DE-CIX Frankfurt + 2001:7f8:d0:b901::/64+, # 4IXP / 4b42 + 2001:7f8:d0:4b42::/64+, # 4IXP / 4b42 + 2602:fed2:fff:ffff::/64, # EVIX + 2001:7f8:33::/48+ # KleyRex + ]; +} + +function is_martian_v4() { + # See RFC6890 + + return is_private_v4() || + net ~ [ + 0.0.0.0/8+, # RFC1122: This host on this network + 100.64.0.0/10+, # RFC6598: IANA-Reserved IPv4 Prefix for Shared Address Space + 127.0.0.0/8+, # RFC1122: Loopback + 192.18.0.0/15+, # RFC2544: Benchmarking Methodology for Network Interconnect Devices + 169.254.0.0/16+, # RFC3927: Dynamic Configuration of IPv4 Link-Local Addresses + 192.0.0.0/24+, # RFC6890: IETF Protocol Assignments + 192.0.0.0/29+, # RFC6333: DS-Lite + 192.0.2.0/24+, # RFC5737: IPv4 Address Blocks Reserved for Documentation (TEST-NET-1) + 198.51.100.0/24+, # RFC5737: IPv4 Address Blocks Reserved for Documentation (TEST-NET-2) + 192.88.99.0/24+, # RFC3068: 6to4 Relay Anycast + 203.0.113.0/24+, # RFC5737: IPv4 Address Blocks Reserved for Documentation (TEST-NET-3) + 224.0.0.0/4+, # RFC5771: IPv4 Multicast + 240.0.0.0/4+, # RFC1112: Reserved for Future Use + 255.255.255.255/32 # RFC0919: Limited Broadcast + ]; +} + +function is_martian_v6() { + # See RFC6890 + + return is_private_v6() || + net ~ [ + ::ffff:0:0/96+, # RFC4291: IPv4-mapped Address + ::ffff:0:0:0/96+, # IPv4 translated + ::/128, # RFC4291: Unspecified Address + ::1/128, # RFC4291: Loopback Address + 64:ff9b::/96+, # RFC6052: IPv4-IPv6 Translated (NAT64) + 100::/64+, # RFC6666: Discard-Only Address Block + 2001::/23+, # RFC2928: IETF Protocol Assignments + 2001::/32+, # RFC4380: TEREDO + 2001:2::/48+, # RFC5180: Benchmarking + 2001:10::/28+, # RFC4843: ORCHID + 2001:db8::/32+, # RFC3849: Documentation + 2002::/16+, # RFC3056: 6to4 + fe80::/10+, # RFC4291: Linked-Scoped Unicast + ff00::/8+ # RFC2373/3306: IPv6 Multicast + ]; +} + +function is_default_v4() { + return net = 0.0.0.0/0; +} + +function is_default_v6() { + return net ~ ::/0; +} + + +function is_bogon_ebgp_v4() { + if net.len > 24 then # RFC7454 + return true; + + if is_martian_v4() then + return true; + + if is_peering_lan_v4() then + return true; + + if bgp_path.first != my_ripe_asn then + return true; + + if bgp_path.len > 32 then + return true; + + if net.len < 8 then # RFC7454 + return true; + + return false; +} + +function is_bogon_ebgp_v6() { + if net.len > 48 then # RFC7454 + return true; + + if is_martian_v6() then + return true; + + if is_peering_lan_v6() then + return true; + + #if is_bogon_asn() then + # return true; + + if bgp_path.first != my_ripe_asn then + return true; + + if bgp_path.len > 32 then + return true; + + if net.len < 19 then # RFC7454 + return true; + + return false; +} diff --git a/filters/dn42.conf b/filters/dn42.conf new file mode 100644 index 0000000..7d93ccb --- /dev/null +++ b/filters/dn42.conf @@ -0,0 +1,64 @@ +function is_dn42() { + return net ~ [ + 172.20.0.0/14{21,29}, + 172.20.0.0/24{28,32}, # Anycast + 172.21.0.0/24{28,32}, # Anycast + 172.22.0.0/24{28,32}, # Anycast + 172.23.0.0/24{28,32}, # Anycast + fd00::/8{44,64} + ]; +} + +filter dn42_import_v4 + bool rej; +{ + accept; + + rej = false; + + if ! is_dn42() then + rej = true; + + if is_rpki_invalid_dn42_v6() then + rej = true; + + # We delay the final decission until all communities are added + if rej then + reject; + + accept; +} + +filter dn42_import_v6 + bool rej; +{ + accept; + + rej = false; + + if ! is_dn42() then + rej = true; + + if is_rpki_invalid_dn42_v6() then + rej = true; + + # We delay the final decission until all communities are added + if rej then + reject; + + accept; +} + +filter dn42_export_v4 { + if ! is_mine_dn42() then + reject; + + accept; +} + +filter dn42_export_v6 { + if ! is_mine_dn42() then + reject; + + accept; +} diff --git a/filters/ebgp.conf b/filters/ebgp.conf new file mode 100644 index 0000000..dbb307b --- /dev/null +++ b/filters/ebgp.conf @@ -0,0 +1,37 @@ +filter ebgp_import_v4 { + reject; +} + +filter ebgp_import_v6 + bool rej; +{ + rej = false; + + if is_rpki_invalid_v6() then + rej = true; + + if net.len > 48 then { + filter_reason(filtered_import_prefix_too_long); + rej = true; + } + + if bgp_path.len > 64 then { + filter_reason(filtered_import_as_path_too_long); + rej = true; + } + + # We delay the final decission until all communities are added + if rej then reject; else accept; +} + +filter ebgp_export_v4 { + reject; +} + +filter ebgp_export_v6 + prefix set mynets; +{ + if is_mine_ripe() then accept; + + reject; +} diff --git a/filters/freifunk.conf b/filters/freifunk.conf new file mode 100644 index 0000000..1966109 --- /dev/null +++ b/filters/freifunk.conf @@ -0,0 +1,6 @@ +function is_freifunk() { + return net ~ [ + 10.0.0.0/8{15,24} + ]; +} + diff --git a/filters/ibgp.conf b/filters/ibgp.conf new file mode 100644 index 0000000..8b86275 --- /dev/null +++ b/filters/ibgp.conf @@ -0,0 +1,23 @@ +filter ibgp_export_v4 { + if net.len = 32 then + reject; + + accept; +} + +filter ibgp_export_v6 { + if net.len = 128 then + reject; + + accept; +} + +filter ibgp_import_v4 { + if net = 0.0.0.0/0 then reject; + + accept; +} + +filter ibgp_import_v6 { + accept; +} diff --git a/filters/rwth.conf b/filters/rwth.conf new file mode 100644 index 0000000..2cad18a --- /dev/null +++ b/filters/rwth.conf @@ -0,0 +1,12 @@ +# https://noc-portal.rz.rwth-aachen.de/networks-view/ +function is_rwth() { + return net ~ [ + 134.61.0.0/16+, + 134.130.0.0/16+, + 137.226.0.0/16+, + 192.35.229.0/24+, + 194.35.108.0/22+, + 2a00:8a60::/29+ + ]; +} + diff --git a/icvpn-scripts b/icvpn-scripts new file mode 160000 index 0000000..898eb44 --- /dev/null +++ b/icvpn-scripts @@ -0,0 +1 @@ +Subproject commit 898eb449091db4029f1bf3ab6bb478a0f3cf4b4d diff --git a/protocols/4ixp.conf b/protocols/4ixp.conf new file mode 100644 index 0000000..2f09915 --- /dev/null +++ b/protocols/4ixp.conf @@ -0,0 +1,30 @@ +template bgp ixp_ch { + local 2001:7f8:d0:4b42::45 as my_ripe_asn; + neighbor as 35708; + + ipv6 { + table ebgp_v6; + + #import keep filtered; + import filter ebgp_import_v6; + export filter ebgp_export_v6; + }; +} + +protocol bgp ixp_ch_rs1 from ixp_ch { + description "4IXP Routeserver 1"; + + neighbor 2001:7f8:d0:b901::7d01; +} + +protocol bgp ixp_ch_rs2 from ixp_ch { + description "4IXP Routeserver 2"; + + neighbor 2001:7f8:d0:b901::7d02; +} + +protocol bgp ixp_ch_transit1 from ixp_ch { + description "4b42 transit at 4IXP"; + + neighbor 2001:7f8:d0:b901::7dfe as 60474; +} diff --git a/protocols/cymru.conf_ b/protocols/cymru.conf_ new file mode 100644 index 0000000..be4c7a7 --- /dev/null +++ b/protocols/cymru.conf_ @@ -0,0 +1,53 @@ +filter cymru_bogons_import { + bgp_community.add((65332,888)); + dest = RTD_BLACKHOLE; + accept; +} + +filter cymru_bogons_export { + reject; +} + +protocol bgp bgp_cymru_v4_1 { + description "Cymru Bogons RS1"; + import filter cymru_bogons_import; + export filter cymru_bogons_export; + multihop 255; + password "pass_here"; + local as my_asn; + neighbor 38.229.66.20 as 65332; + source address IPv4_here; +} + +protocol bgp bgp_cymru_v4_2 { + description "Cymru Bogons RS2"; + import filter cymru_bogons_import; + export filter cymru_bogons_export; + multihop 255; + password "pass_here"; + local as my_ripe_asn; + neighbor 193.231.140.82 as 65332; + source address IPv4_here; +} + +protocol bgp bgp_cymru_v6_1 { + description "Cymru Bogons RS1 v6"; + import filter cymru_bogons_import; + export filter cymru_bogons_export; + multihop 255; + password "pass_here"; + local as my_ripe_asn; + neighbor 2620:0:6B0::26E5:4207 as 65332; + source address IPv6_here; +} + +protocol bgp bgp_cymru_v6_2 { + description "Cymru Bogons RS2 v6"; + import filter cymru_bogons_import; + export filter cymru_bogons_export; + multihop 255; + password "pass_here"; + local as my_asn; + neighbor 2001:B30:1000:19::2 as 65332; + source address IPv6_here; +} diff --git a/protocols/decix.conf b/protocols/decix.conf new file mode 100644 index 0000000..0b3002b --- /dev/null +++ b/protocols/decix.conf @@ -0,0 +1,57 @@ +template bgp decix_fra_v6 { + local 2001:7f8::3:2afd:0:1 as my_ripe_asn; + neighbor as 6695; + + ipv6 { + table ebgp_v6; + + import keep filtered; + import filter ebgp_import_v6; + export filter ebgp_export_v6; + }; + + graceful restart on; +} + +template bgp decix_fra_v4 { + local 80.81.196.155 as my_ripe_asn; + neighbor as 6695; + + ipv4 { + table ebgp_v4; + + import keep filtered; + import filter ebgp_import_v4; + export filter ebgp_export_v4; + }; + + graceful restart on; +} + +protocol bgp decix_fra_rs1_v4 from decix_fra_v4 { + description "DE-CIX Frankfurt RS1 (IPv4)"; + + neighbor 80.81.192.157; +} + +protocol bgp decix_fra_rs1_v6 from decix_fra_v6 { + description "DE-CIX Frankfurt RS1"; + + neighbor 2001:7f8::1a27:5051:c09d; +} + +protocol bgp decix_fra_rs2_v6 from decix_fra_v6 { + description "DE-CIX Frankfurt RS2"; + + neighbor 2001:7f8::1a27:5051:c19d; +} + +protocol bgp decix_fra_bh_v6 from decix_fra_v6 { + description "DE-CIX Frankfurt Blackholing"; + + neighbor 2001:7f8::1a27:5051:c09e; + + ipv6 { + table ebgp_v6_bh; + }; +} diff --git a/protocols/dn42.conf b/protocols/dn42.conf new file mode 100644 index 0000000..b1f2b0f --- /dev/null +++ b/protocols/dn42.conf @@ -0,0 +1,45 @@ +# ROA tables +protocol static static_roa_dn42_v4 { + roa4 { + table roa_dn42_v4; + }; + + include "/var/lib/bird/bird_roa_dn42_v4.conf"; +} + +protocol static static_roa_dn42_v6 { + roa6 { + table roa_dn42_v6; + }; + + include "/var/lib/bird/bird_roa_dn42_v6.conf"; +} + +# Template +template bgp dn42_peer { + local as my_dn42_asn; + + graceful restart on; +} + +template bgp dn42_peer_v4 from dn42_peer { + ipv4 { + table dn42_v4; + + import keep filtered; + import filter dn42_import_v4; + export filter dn42_export_v4; + }; +} + +template bgp dn42_peer_v6 from dn42_peer { + ipv6 { + table dn42_v6; + + import keep filtered; + import filter dn42_import_v6; + export filter dn42_export_v6; + }; +} + +include "/etc/bird/protocols/dn42/*.conf"; diff --git a/protocols/dn42/doxz.conf b/protocols/dn42/doxz.conf new file mode 100644 index 0000000..36ecf7c --- /dev/null +++ b/protocols/dn42/doxz.conf @@ -0,0 +1,17 @@ +protocol bgp dn42_doxz_v4 from dn42_peer_v4 { + description "dn42 doxz IPv4"; + + interface "wg-doxz"; + + local 172.23.156.66; + neighbor 172.22.159.62 as 4242422904; +} + +protocol bgp dn42_doxz_v6 from dn42_peer_v6 { + description "dn42 doxz IPv6"; + + interface "wg-doxz"; + + local fd42:4dd0:ff00::1; + neighbor fdfc:694e:234f::1 as 4242422904; +} diff --git a/protocols/dn42/tbspace.conf b/protocols/dn42/tbspace.conf new file mode 100644 index 0000000..02357d4 --- /dev/null +++ b/protocols/dn42/tbspace.conf @@ -0,0 +1,17 @@ +protocol bgp dn42_tbspace_v4 from dn42_peer_v4 { + description "dn42 tbspace IPv4"; + + interface "wg-tbspace"; + + local 172.23.156.65; + neighbor 172.23.235.1 as 76190; +} + +protocol bgp dn42_tbspace_v6 from dn42_peer_v6 { + description "dn42 tbspace IPv6"; + + interface "wg-tbspace"; + + local fe80::1337; + neighbor fe80::1299:e as 76190; +} diff --git a/protocols/ibgp.conf b/protocols/ibgp.conf new file mode 100644 index 0000000..c77c730 --- /dev/null +++ b/protocols/ibgp.conf @@ -0,0 +1,34 @@ +template bgp rr_clients { + local as my_ripe_asn; + neighbor as my_ripe_asn; + rr client; + rr cluster id 172.23.156.3; + + ipv4 { + import keep filtered; + import filter ibgp_import_v4; + export filter ibgp_export_v4; + next hop self; + }; + + ipv6 { + import keep filtered; + import filter ibgp_import_v6; + export filter ibgp_export_v6; + next hop self; + }; +} + +protocol bgp lian from rr_clients { + description "iBGP: lian.0l.de"; + + local 2a09:11c0:200::14; + neighbor 2a09:11c0:200::2; +} + +protocol bgp acs from rr_clients { + description "iBGP: acs.0l.de"; + + local 2a09:11c0:200::7; + neighbor 2a09:11c0:200::6; +} diff --git a/protocols/k8s.conf b/protocols/k8s.conf new file mode 100644 index 0000000..4a73d92 --- /dev/null +++ b/protocols/k8s.conf @@ -0,0 +1,21 @@ +protocol bgp k8s_0_v4 from rr_clients { + description "iBGP: k8s-0.edgy.vms.0l.de"; + + local 172.23.156.14; + neighbor 172.23.156.183; + + ipv4 { + export none; + }; +} + +protocol bgp k8s_0_v6 from rr_clients { + description "iBGP: k8s-0.edgy.vms.0l.de"; + + local 2a09:11c0:200::14; + neighbor 2a09:11c0:200:101:5054:ff:fe3e:5017; + + ipv6 { + export none; + }; +} diff --git a/protocols/kernel.conf b/protocols/kernel.conf new file mode 100644 index 0000000..09cc8b5 --- /dev/null +++ b/protocols/kernel.conf @@ -0,0 +1,65 @@ +protocol kernel kernel_v4 { + ipv4 { + import none; + export where source != RTS_DEVICE && net.len > 0 && dest != RTD_UNREACHABLE; + }; + + metric 0; +} + +protocol kernel kernel_v6 { + ipv6 { + import none; + export where source != RTS_DEVICE && net.len > 0 && dest != RTD_UNREACHABLE; + }; + + metric 0; +} + +protocol kernel kernel_dn42_v4 { + kernel table krt_dn42; + + ipv4 { + table dn42_v4; + + import none; + export all; + }; +} + +protocol kernel kernel_dn42_v6 { + kernel table krt_dn42; + + ipv6 { + table dn42_v6; + + import none; + export all; + }; +} + +protocol kernel kernel_ebgp_v6 { + kernel table krt_ebgp; + + ipv6 { + table ebgp_v6; + + export where source != RTS_DEVICE; + import none; + }; + + metric 0; +} + +protocol kernel kernel_ebgp_v4 { + kernel table krt_ebgp; + + ipv4 { + table ebgp_v4; + + export where source != RTS_DEVICE; + import none; + }; + + metric 0; +} diff --git a/protocols/kleyrex.conf b/protocols/kleyrex.conf new file mode 100644 index 0000000..76a0190 --- /dev/null +++ b/protocols/kleyrex.conf @@ -0,0 +1,44 @@ +template bgp kleyrex_fra { + local 2001:7f8:33::A120:7613:1 as my_ripe_asn; + neighbor as 31142; + + ipv6 { + table ebgp_v6; + + #import keep filtered; + import all; + export filter ebgp_export_v6; + }; + + graceful restart on; +} + +protocol bgp kleyrex_fra_rs1 from kleyrex_fra { + description "KleyRex FRA RS1"; + + neighbor 2001:7f8:33::a103:1142:1; +} + +protocol bgp kleyrex_fra_rs2 from kleyrex_fra { + description "KleyRex FRA RS2"; + + neighbor 2001:7f8:33::a103:1142:2; +} + +protocol bgp kleyrex_fra_rs3 from kleyrex_fra { + description "KleyRex FRA RS3"; + + neighbor 2001:7f8:33::a103:1142:3; +} + +protocol bgp kleyrex_fra_42b4 from kleyrex_fra { + description "KleyRex FRA 42b4"; + + neighbor 2001:7f8:33::a106:474:1 as 60474; +} + +protocol bgp kleyrex_fra_ifog from kleyrex_fra { + description "KleyRex FRA iFog"; + + neighbor 2001:7f8:33::a103:4927:1 as 34927; +} diff --git a/protocols/layerbridge.conf b/protocols/layerbridge.conf new file mode 100644 index 0000000..3a33591 --- /dev/null +++ b/protocols/layerbridge.conf @@ -0,0 +1,17 @@ +# Layerbridge +protocol bgp tb_lb1 { + description "LayerBridge / Hetnix"; + + local fc00:0:6::2 as my_ripe_asn; + neighbor fc00:0:6::1 as 3280; + + ipv6 { + table ebgp_v6; + + import keep filtered; + import filter ebgp_import_v6; + export filter ebgp_export_v6; + }; + + multihop 10; +} diff --git a/protocols/locix.conf b/protocols/locix.conf new file mode 100644 index 0000000..9dcc6c8 --- /dev/null +++ b/protocols/locix.conf @@ -0,0 +1,43 @@ +template bgp locix_fra { + local 2a07:1c44:61f0::a520:7613:1 as my_ripe_asn; + neighbor as 202409; + + ipv6 { + table ebgp_v6; + + #import keep filtered; + import all; + export filter ebgp_export_v6; + }; + + graceful restart on; +} + +protocol bgp locix_fra_rs1 from locix_fra { + description "LocIX FRA RS1"; + + neighbor 2a07:1c44:61f0::babe:1; +} + +protocol bgp locix_fra_rs2 from locix_fra { + description "LocIX FRA RS2"; + + neighbor 2a07:1c44:61f0::dead:1; +} + +protocol bgp locix_fra_rs3 from locix_fra { + description "LocIX FRA RS3"; + + neighbor 2a07:1c44:61f0::be5a; +} + +protocol bgp locix_fra_ifog from locix_fra { + description "LocIX FRA iFog"; + + neighbor 2a07:1c44:61f0::a120:4927:1 as 34927; + + ipv6 { + preference 80; + }; +} + diff --git a/protocols/meerfarbig.conf b/protocols/meerfarbig.conf new file mode 100644 index 0000000..de794cc --- /dev/null +++ b/protocols/meerfarbig.conf @@ -0,0 +1,15 @@ +protocol bgp meerfarbig { + description "meerfarbig"; + + local 2a00:f820:457::2 as my_ripe_asn; + neighbor 2a00:f820:457::1 as 34549; + + ipv6 { + table ebgp_v6; + + import keep filtered; + import filter ebgp_import_v6; + export filter ebgp_export_v6; + next hop self; + }; +} diff --git a/protocols/static.conf b/protocols/static.conf new file mode 100644 index 0000000..0adee07 --- /dev/null +++ b/protocols/static.conf @@ -0,0 +1,85 @@ +protocol static static_v4 { + ipv4 { + table master4; + }; + + # mail.0l.de + route 31.47.232.67/32 + via "virbr1"; + + # hap.0l.de + route 31.47.232.68/32 + via "virbr1"; + + # k8s.0l.de + route 31.47.232.69/32 + via "virbr1"; + + # tor.edgy.vms.0l.de + route 31.47.232.70/32 + via "virbr1"; + + # Internal Transport + route 172.23.156.0/27 + reject; + + route 172.20.0.0/14 + reject; + + # Marienstrasse + route 192.168.178.0/24 + via 172.23.156.9; + + route 0.0.0.0/0 + via 31.47.232.65; +} + +protocol static static_v6 { + ipv6 { + table master6; + }; + + # NAT64 + route 2a09:11c0:201::/96 reject; + + route ::/0 reject; +} + +protocol static static_ebgp_v6 { + ipv6 { + table ebgp_v6; + }; + + # My own prefixes for eBGP announcement + route 2a0e:97c7:100::/44 reject; + route 2a09:11c0:200::/44 reject; + route 2a09:4c2:1b::/48 reject; +} + +protocol static static_ebgp_v4 { + ipv4 { + table ebgp_v4; + }; + + # For wireguard + route 31.47.232.64/29 via "eno1"; + route 0.0.0.0/0 via 31.47.232.65; +} + +protocol static static_dn42_v4 { + ipv4 { + table dn42_v4; + }; + + route 172.23.156.0/23 + reject; +} + +protocol static static_dn42_v6 { + ipv6 { + table dn42_v6; + }; + + route fd42:4dd0:ff00::/48 + reject; +} diff --git a/protocols/tunnelbroker_net.conf b/protocols/tunnelbroker_net.conf new file mode 100644 index 0000000..7544d1a --- /dev/null +++ b/protocols/tunnelbroker_net.conf @@ -0,0 +1,17 @@ +protocol bgp tb_he1 { + description "tunnelserver.net (Hurricane Electric)"; + + local 2001:470:12:1ab::2 as my_ripe_asn; + neighbor 2001:470:12:1ab::1 as 6939; + + ipv6 { + table ebgp_v6; + preference 80; + + import keep filtered; + import filter ebgp_import_v6; + export filter ebgp_export_v6; + }; + + multihop 10; +} diff --git a/rpki.conf b/rpki.conf new file mode 100644 index 0000000..f17165a --- /dev/null +++ b/rpki.conf @@ -0,0 +1,65 @@ +protocol rpki { + roa6 { + table roa_v6; + }; + + remote "10.43.141.166" port 3323; + + retry keep 90; + refresh keep 900; + expire keep 172800; +} + +function filter_reason(lc rsn) { + bgp_large_community.add(rsn); +} + +# RPKI tests +function is_rpki_invalid_v6() { + if roa_check(roa_v6, net, bgp_path.last_nonaggregated) = ROA_VALID then + bgp_large_community.add(informational_rpki_valid); + else if roa_check(roa_v6, net, bgp_path.last_nonaggregated) = ROA_UNKNOWN then + bgp_large_community.add(informational_rpki_unknown); + else if roa_check(roa_v6, net, bgp_path.last_nonaggregated) = ROA_INVALID then { + print "Ignore RPKI invalid ", net, " for ASN ", bgp_path.last; + bgp_large_community.add(informational_rpki_invalid); + return true; + } + else + bgp_large_community.add(informational_rpki_not_checked); + + return false; +} + +function is_rpki_invalid_dn42_v4() { + if roa_check(roa_dn42_v4, net, bgp_path.last_nonaggregated) = ROA_VALID then + bgp_large_community.add(informational_rpki_valid); + else if roa_check(roa_dn42_v4, net, bgp_path.last_nonaggregated) = ROA_UNKNOWN then + bgp_large_community.add(informational_rpki_unknown); + else if roa_check(roa_dn42_v4, net, bgp_path.last_nonaggregated) = ROA_INVALID then { + print "Ignore RPKI invalid ", net, " for ASN ", bgp_path.last; + bgp_large_community.add(informational_rpki_invalid); + return true; + } + else + bgp_large_community.add(informational_rpki_not_checked); + + return false; +} + +function is_rpki_invalid_dn42_v6() { + if roa_check(roa_dn42_v6, net, bgp_path.last_nonaggregated) = ROA_VALID then + bgp_large_community.add(informational_rpki_valid); + else if roa_check(roa_dn42_v6, net, bgp_path.last_nonaggregated) = ROA_UNKNOWN then + bgp_large_community.add(informational_rpki_unknown); + else if roa_check(roa_dn42_v6, net, bgp_path.last_nonaggregated) = ROA_INVALID then { + print "Ignore RPKI invalid ", net, " for ASN ", bgp_path.last; + bgp_large_community.add(informational_rpki_invalid); + return true; + } + else + bgp_large_community.add(informational_rpki_not_checked); + + return false; +} + diff --git a/tables.conf b/tables.conf new file mode 100644 index 0000000..1619ee7 --- /dev/null +++ b/tables.conf @@ -0,0 +1,20 @@ +# Kernel routing tables +define krt_main = 254; +define krt_local = 255; +define krt_default = 253; +define krt_ebgp = 100; +define krt_dn42 = 101; + +# Bird tables +ipv4 table ebgp_v4; + +ipv6 table ebgp_v6_bh; # Blackholing +ipv6 table ebgp_v6; +roa6 table roa_v6; + +ipv4 table dn42_v4; +roa4 table roa_dn42_v4; + +ipv6 table dn42_v6; +roa6 table roa_dn42_v6; + diff --git a/update.sh b/update.sh new file mode 100644 index 0000000..75b1f2f --- /dev/null +++ b/update.sh @@ -0,0 +1,13 @@ +#!/bin/bash + +git -C icvpn-meta/ pull + +cd /etc/bird + +icvpn-scripts/mkroa -s icvpn-meta > /var/lib/bird/icvpn_roa.conf + +curl -sfSLR {-o,-z}/var/lib/bird/bird_roa_dn42_v4.conf https://dn42.burble.com/roa/dn42_roa_bird2_4.conf +curl -sfSLR {-o,-z}/var/lib/bird/bird_roa_dn42_v6.conf https://dn42.burble.com/roa/dn42_roa_bird2_6.conf + +# Maybe do a 'birdc configure check' before? +birdc configure