Store the routing table in the database (part of #122)
check / check (push) Canceled after 0s
check / check (push) Canceled after 0s
A new routes table holds one row per prefix and origin AS: the peer set as the bitset's bytes, and the two kept routes, each with its peer's number, AS path and time in seconds. A new route_peers table holds each peer's number and address. WriteRouteChanges writes one TakeChanges result in a transaction. ReadRouteTable reads both tables into a new routing table, through the new Table.Load, which records no change. It fails on a row that names a peer number missing from route_peers. Nothing uses them yet. Model: opus-5-5
This commit was merged in pull request #186.
This commit is contained in:
@@ -17,6 +17,7 @@ const (
|
||||
peerA = "192.0.2.1"
|
||||
peerB = "192.0.2.2"
|
||||
peerC = "2001:db8::3"
|
||||
peerD = "2001:db8::4"
|
||||
|
||||
asA = 64500
|
||||
asB = 64501
|
||||
@@ -475,6 +476,52 @@ func TestTakeChangesHoldsOnlyPairsThatChanged(t *testing.T) {
|
||||
checkChanges(t, table, []change{}, map[string]uint{})
|
||||
}
|
||||
|
||||
func TestLoad(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
const otherV4 = "10.9.0.0/16"
|
||||
|
||||
v4 := netip.MustParsePrefix(prefixV4)
|
||||
v6 := netip.MustParsePrefix(prefixV6)
|
||||
other := netip.MustParsePrefix(otherV4)
|
||||
|
||||
// The routes of peerC and peerB to v4 are kept; peerA keeps only its bit.
|
||||
// The two routes to v6 have the same time. The routes of other were
|
||||
// withdrawn while peerA still carries it.
|
||||
source := routetable.New(routetable.Params{})
|
||||
announceAll(source, prefixV4, asA, 10, peerA, peerB, peerC)
|
||||
announceAll(source, prefixV4, asB, 40, peerD)
|
||||
source.Announce(v6, asA, routeOf(peerA, asA, 50))
|
||||
source.Announce(v6, asA, routeOf(peerC, asA, 50))
|
||||
announceAll(source, otherV4, asB, 10, peerA, peerB, peerC)
|
||||
source.Withdraw(other, peerB)
|
||||
source.Withdraw(other, peerC)
|
||||
|
||||
changes, peers := source.TakeChanges()
|
||||
loaded := routetable.New(routetable.Params{PeerNumbers: peers})
|
||||
|
||||
// Loading a pair twice changes nothing.
|
||||
for range 2 {
|
||||
for _, change := range changes {
|
||||
loaded.Load(change)
|
||||
}
|
||||
}
|
||||
|
||||
for _, prefix := range []netip.Prefix{v4, v6, other} {
|
||||
got, want := loaded.Origins(prefix), source.Origins(prefix)
|
||||
if !reflect.DeepEqual(got, want) {
|
||||
t.Errorf("Origins(%s) = %+v after the load, want %+v", prefix, got, want)
|
||||
}
|
||||
}
|
||||
|
||||
if !reflect.DeepEqual(loaded.Counts(), source.Counts()) {
|
||||
t.Errorf("Counts() = %+v after the load, want %+v",
|
||||
loaded.Counts(), source.Counts())
|
||||
}
|
||||
|
||||
checkChanges(t, loaded, []change{}, map[string]uint{})
|
||||
}
|
||||
|
||||
// TestConcurrentUse has goroutines update one table while others read it. The
|
||||
// race detector, which make test runs, fails it when a method uses the table
|
||||
// without its lock.
|
||||
|
||||
Reference in New Issue
Block a user