Skip to content

Commit

Permalink
r1
Browse files Browse the repository at this point in the history
  • Loading branch information
lukedirtwalker committed Jan 7, 2020
1 parent f5f956f commit 1925c9a
Show file tree
Hide file tree
Showing 6 changed files with 36 additions and 43 deletions.
31 changes: 14 additions & 17 deletions doc/BeaconService.md
Original file line number Diff line number Diff line change
Expand Up @@ -162,16 +162,17 @@ type Interface interface {
// necessary, and sets the remote interface id. The return value indicates
// the previous state of the interface.
func Activate(remote common.IFIDType) State
// Expire checks whether the interface has not been activated for a certain
// amount of time. If that is the case and the current state is inactive or
// active, the state changes to Expired. The return value indicates,
// whether the state is expired or revoked when the call returns.
func Expire() bool
// Revoke changes the state of the interface to revoked and updates the
// revocation, unless the current state is active. In that case, the
// interface has been activated in the meantime and should not be revoked.
// Revoke checks whether the interface has not been activated for a certain
// amount of time. If that is the case and the current state is active, the
// state changes to Revoked. The times for last beacon origination and
// propagation are reset to the zero value. The return value indicates, whether
// the state is revoked when the call returns.
func Revoke() bool
// SetRevocation sets the revocation for this interface. This can only be
// invoked when the interface is in revoked state. Otherwise it is assumed that
// the interface has been activated in the meantime and should not be revoked.
// This is indicated through an error.
func Revoke(rev *path_mgmt.SignedRevInfo) error
func SetRevocation(rev *path_mgmt.SignedRevInfo) error
// Revocation returns the revocation.
func Revocation() *path_mgmt.SignedRevInfo
// TopoInfo returns the topology information.
Expand All @@ -184,13 +185,8 @@ type Interface interface {
type State string

const (
// Inactive indicates that the interface has not been activated or
// expired yet.
Inactive State = "Inactive"
// Active indicates that the interface is active.
Active State = "Active"
// Expired indicates that the interface is expired.
Expired State = "Expired"
// Revoked indicates that the interface is revoked.
Revoked State = "Revoked"
)
Expand Down Expand Up @@ -316,14 +312,15 @@ after a stale period.

#### Interface Revocation

*(uses: `Interfaces.All`, `Interface.Expire`, `Interface.Revoke`, `BeaconStore.InsertRevocation`).*
*(uses: `Interfaces.All`, `Interface.Revoke`, `Interface.SetRevocation`,
`BeaconStore.InsertRevocation`).*

Each BS instance keeps track of the interface state in an in-memory structure. When a configurable
amount of keepalive messages for a given interface is not received, the interface is revoked by the
BS.

1. Call `Interface.Expire` on all infos.
1. Revoke all expired interfaces in `InterfaceState`, update the revocation if necessary (certain
1. Call `Interface.Revoke` on all infos.
1. Revoke all revoked interfaces in `InterfaceState`, update the revocation if necessary (certain
amount of previous revocation period has passed).
1. Insert revocation in beacon store.
1. Send revocation to all BRs in the local AS.
Expand Down
26 changes: 11 additions & 15 deletions go/beacon_srv/internal/ifstate/ifstate.go
Original file line number Diff line number Diff line change
Expand Up @@ -152,31 +152,27 @@ func (intf *Interface) Activate(remote common.IFIDType) State {
return prev
}

// Expire checks whether the interface has not been activated for a certain
// amount of time. If that is the case and the current state is inactive or
// active, the state changes to Expired. The times for last beacon origination
// and propagation are reset to the zero value. The return value indicates,
// whether the state is expired or revoked when the call returns.
func (intf *Interface) Expire() bool {
// Revoke checks whether the interface has not been activated for a certain
// amount of time. If that is the case and the current state is active, the
// state changes to Revoked. The times for last beacon origination and
// propagation are reset to the zero value. The return value indicates, whether
// the state is revoked when the call returns.
func (intf *Interface) Revoke() bool {
intf.mu.Lock()
defer intf.mu.Unlock()
if intf.state != Active {
return true
}
if time.Now().Sub(intf.lastActivate) > intf.cfg.KeepaliveTimeout {
intf.lastOriginate = time.Time{}
intf.lastPropagate = time.Time{}
intf.state = Revoked
return true
}
return false
return intf.state == Revoked
}

// Revoke changes the state of the interface to revoked and updates the
// revocation, unless the current state is active. In that case, the
// interface has been activated in the meantime and should not be revoked.
// SetRevocation sets the revocation for this interface. This can only be
// invoked when the interface is in revoked state. Otherwise it is assumed that
// the interface has been activated in the meantime and should not be revoked.
// This is indicated through an error.
func (intf *Interface) Revoke(rev *path_mgmt.SignedRevInfo) error {
func (intf *Interface) SetRevocation(rev *path_mgmt.SignedRevInfo) error {
intf.mu.Lock()
defer intf.mu.Unlock()
if intf.state == Active {
Expand Down
12 changes: 6 additions & 6 deletions go/beacon_srv/internal/ifstate/ifstate_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ func TestInfoActivate(t *testing.T) {
}
}

func TestInfoExpire(t *testing.T) {
func TestInfoRevoke(t *testing.T) {
Convey("Given an interface that has not received a keepalive", t, func() {
testCases := []struct {
PrevState State
Expand All @@ -121,7 +121,7 @@ func TestInfoExpire(t *testing.T) {
lastActivate: time.Now().Add(-DefaultKeepaliveTimeout - time.Second),
}
intf.cfg.InitDefaults()
expired := intf.Expire()
expired := intf.Revoke()
SoMsg("Expired", expired, ShouldBeTrue)
SoMsg("State", intf.State(), ShouldEqual, test.NextState)
SoMsg("LastActivate", time.Now().Sub(intf.lastActivate), ShouldBeGreaterThan,
Expand All @@ -137,15 +137,15 @@ func TestInfoExpire(t *testing.T) {
lastActivate: time.Now().Add(-DefaultKeepaliveTimeout + time.Second),
}
intf.cfg.InitDefaults()
expired := intf.Expire()
expired := intf.Revoke()
SoMsg("Expired", expired, ShouldEqual, test == Revoked)
SoMsg("State", intf.State(), ShouldEqual, test)
})
}
})
}

func TestInfoRevoke(t *testing.T) {
func TestInfoSetRevocation(t *testing.T) {
Convey("Given an interface in a certain state", t, func() {
testCases := []struct {
PrevState State
Expand All @@ -161,7 +161,7 @@ func TestInfoRevoke(t *testing.T) {
state: test.PrevState,
}
intf.cfg.InitDefaults()
err := intf.Revoke(&path_mgmt.SignedRevInfo{})
err := intf.SetRevocation(&path_mgmt.SignedRevInfo{})
SoMsg("State", intf.State(), ShouldEqual, test.NextState)
if test.Error {
SoMsg("err", err, ShouldNotBeNil)
Expand All @@ -184,7 +184,7 @@ func testInterfaces(t *testing.T) *Interfaces {
intfs.Get(1).Activate(11)
intfs.Get(2).topoInfo.RemoteIFID = 22
intfs.Get(2).state = Revoked
err := intfs.Get(2).Revoke(&path_mgmt.SignedRevInfo{})
err := intfs.Get(2).SetRevocation(&path_mgmt.SignedRevInfo{})
require.NoError(t, err)
return intfs
}
4 changes: 2 additions & 2 deletions go/beacon_srv/internal/ifstate/revoker.go
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ func (r *Revoker) Run(ctx context.Context) {
NeighIA: intf.TopoInfo().IA,
}

if intf.Expire() && !r.hasValidRevocation(intf) {
if intf.Revoke() && !r.hasValidRevocation(intf) {
if intf.Revocation() == nil {
labelsIssued.State = metrics.RevNew
logger.Info("[ifstate.Revoker] interface went down", "ifid", ifid)
Expand All @@ -107,7 +107,7 @@ func (r *Revoker) Run(ctx context.Context) {
"ifid", ifid, "err", err)
continue
}
if err := intf.Revoke(srev); err != nil {
if err := intf.SetRevocation(srev); err != nil {
logger.Error("[ifstate.Revoker] Failed to revoke!", "ifid", ifid, "err", err)
continue
}
Expand Down
4 changes: 2 additions & 2 deletions go/beacon_srv/internal/ifstate/revoker_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,7 @@ func TestRevokedInterfaceNotRevokedImmediately(t *testing.T) {
RawTTL: uint32(ttl.Seconds()),
}, infra.NullSigner)
xtest.FailOnErr(t, err)
intfs.Get(101).Revoke(srev)
intfs.Get(101).SetRevocation(srev)
cfg := RevokerConf{
Intfs: intfs,
Msgr: msgr,
Expand Down Expand Up @@ -204,7 +204,7 @@ func TestRevokedInterfaceRevokedAgain(t *testing.T) {
RawTTL: uint32(ttl.Seconds()),
}, infra.NullSigner)
xtest.FailOnErr(t, err)
intfs.Get(101).Revoke(srev)
intfs.Get(101).SetRevocation(srev)
revInserter.EXPECT().InsertRevocations(gomock.Any(), &matchers.SignedRevs{
Verifier: revVerifier(pub),
MatchRevs: []path_mgmt.RevInfo{{
Expand Down
2 changes: 1 addition & 1 deletion go/beacon_srv/internal/keepalive/handler_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@ func TestNewHandler(t *testing.T) {
func testInterfaces(t *testing.T) *ifstate.Interfaces {
infoMap := topology.IfInfoMap{localIF: topology.IFInfo{IA: originIA}}
intfs := ifstate.NewInterfaces(infoMap, ifstate.Config{KeepaliveTimeout: time.Nanosecond})
require.True(t, intfs.Get(localIF).Expire(), "must expire interface")
require.True(t, intfs.Get(localIF).Revoke(), "must revoke interface")
return intfs
}

Expand Down

0 comments on commit 1925c9a

Please sign in to comment.