package notify import ( "errors" "net" "time" ) const defaultPeerAttachReplayCapacity = 4096 type PeerAttachChannelBindingRole string const ( PeerAttachChannelBindingRoleClient PeerAttachChannelBindingRole = "client" PeerAttachChannelBindingRoleServer PeerAttachChannelBindingRole = "server" ) type PeerAttachChannelBindingContext struct { Role PeerAttachChannelBindingRole PeerID string Conn net.Conn } type PeerAttachChannelBindingProvider func(PeerAttachChannelBindingContext) ([]byte, error) type PeerAttachSecurityConfig struct { RequireExplicitAuth bool RequireChannelBinding bool ReplayWindow time.Duration ReplayCapacity int ChannelBinding PeerAttachChannelBindingProvider } type peerAttachSecurityState struct { requireExplicitAuth bool requireChannelBinding bool replayWindow time.Duration replayCapacity int channelBinding PeerAttachChannelBindingProvider } var errPeerAttachChannelBindingProviderNil = errors.New("peer attach channel binding provider is nil") func DefaultPeerAttachSecurityConfig() PeerAttachSecurityConfig { return PeerAttachSecurityConfig{ ReplayWindow: peerAttachReplayTTL, ReplayCapacity: defaultPeerAttachReplayCapacity, } } func normalizePeerAttachSecurityConfig(cfg PeerAttachSecurityConfig) (peerAttachSecurityState, error) { if cfg.ReplayWindow <= 0 { cfg.ReplayWindow = peerAttachReplayTTL } if cfg.ReplayCapacity <= 0 { cfg.ReplayCapacity = defaultPeerAttachReplayCapacity } if cfg.RequireChannelBinding { cfg.RequireExplicitAuth = true if cfg.ChannelBinding == nil { return peerAttachSecurityState{}, errPeerAttachChannelBindingProviderNil } } return peerAttachSecurityState{ requireExplicitAuth: cfg.RequireExplicitAuth, requireChannelBinding: cfg.RequireChannelBinding, replayWindow: cfg.ReplayWindow, replayCapacity: cfg.ReplayCapacity, channelBinding: cfg.ChannelBinding, }, nil } func peerAttachSecurityConfigFromState(state *peerAttachSecurityState) PeerAttachSecurityConfig { if state == nil { return DefaultPeerAttachSecurityConfig() } return PeerAttachSecurityConfig{ RequireExplicitAuth: state.requireExplicitAuth, RequireChannelBinding: state.requireChannelBinding, ReplayWindow: state.replayWindow, ReplayCapacity: state.replayCapacity, ChannelBinding: state.channelBinding, } } func defaultPeerAttachSecurityState() *peerAttachSecurityState { cfg, _ := normalizePeerAttachSecurityConfig(DefaultPeerAttachSecurityConfig()) return &cfg } func (c *ClientCommon) peerAttachSecuritySnapshot() peerAttachSecurityState { if c == nil { cfg, _ := normalizePeerAttachSecurityConfig(DefaultPeerAttachSecurityConfig()) return cfg } if state := c.peerAttachSecurity.Load(); state != nil { return *state } cfg, _ := normalizePeerAttachSecurityConfig(DefaultPeerAttachSecurityConfig()) return cfg } func (s *ServerCommon) peerAttachSecuritySnapshot() peerAttachSecurityState { if s == nil { cfg, _ := normalizePeerAttachSecurityConfig(DefaultPeerAttachSecurityConfig()) return cfg } if state := s.peerAttachSecurity.Load(); state != nil { return *state } cfg, _ := normalizePeerAttachSecurityConfig(DefaultPeerAttachSecurityConfig()) return cfg } func (c *ClientCommon) SetPeerAttachSecurityConfig(cfg PeerAttachSecurityConfig) error { state, err := normalizePeerAttachSecurityConfig(cfg) if err != nil { return err } c.peerAttachSecurity.Store(&state) return nil } func (c *ClientCommon) PeerAttachSecurityConfig() PeerAttachSecurityConfig { return peerAttachSecurityConfigFromState(c.peerAttachSecurity.Load()) } func (s *ServerCommon) SetPeerAttachSecurityConfig(cfg PeerAttachSecurityConfig) error { state, err := normalizePeerAttachSecurityConfig(cfg) if err != nil { return err } s.peerAttachSecurity.Store(&state) return nil } func (s *ServerCommon) PeerAttachSecurityConfig() PeerAttachSecurityConfig { return peerAttachSecurityConfigFromState(s.peerAttachSecurity.Load()) }