diff --git a/app/commander/commander.go b/app/commander/commander.go index 67a0b89b7..e1e408a97 100644 --- a/app/commander/commander.go +++ b/app/commander/commander.go @@ -31,12 +31,16 @@ func NewCommander(ctx context.Context, config *Config) (*Commander, error) { ohm: v.OutboundHandlerManager(), v: v, } - if err := v.RegisterFeature((*core.Commander)(nil), c); err != nil { + if err := v.RegisterFeature((*Commander)(nil), c); err != nil { return nil, err } return c, nil } +func (c *Commander) Type() interface{} { + return (*Commander)(nil) +} + func (c *Commander) Start() error { c.Lock() c.server = grpc.NewServer() diff --git a/commander.go b/commander.go deleted file mode 100644 index eb2d3750d..000000000 --- a/commander.go +++ /dev/null @@ -1,44 +0,0 @@ -package core - -import ( - "sync" -) - -// Commander is a feature that accepts commands from external source. -type Commander interface { - Feature -} - -type syncCommander struct { - sync.RWMutex - Commander -} - -func (c *syncCommander) Start() error { - c.RLock() - defer c.RUnlock() - - if c.Commander == nil { - return nil - } - - return c.Commander.Start() -} - -func (c *syncCommander) Close() error { - c.RLock() - defer c.RUnlock() - - if c.Commander == nil { - return nil - } - - return c.Commander.Close() -} - -func (c *syncCommander) Set(commander Commander) { - c.Lock() - defer c.Unlock() - - c.Commander = commander -} diff --git a/v2ray.go b/v2ray.go index 5538da7ee..aab56fe8d 100644 --- a/v2ray.go +++ b/v2ray.go @@ -28,7 +28,6 @@ type Instance struct { router syncRouter ihm syncInboundHandlerManager ohm syncOutboundHandlerManager - cmd syncCommander access sync.Mutex features []Feature @@ -105,7 +104,7 @@ func (s *Instance) Close() error { defer s.access.Unlock() s.running = false - for _, f := range s.features { + for _, f := range s.allFeatures() { f.Close() } @@ -119,7 +118,7 @@ func (s *Instance) Start() error { defer s.access.Unlock() s.running = true - for _, f := range s.features { + for _, f := range s.allFeatures() { if err := f.Start(); err != nil { return err } @@ -134,6 +133,8 @@ func (s *Instance) Start() error { // If feature is one of the following types, the corressponding feature in this Instance // will be replaced: DNSClient, PolicyManager, Router, Dispatcher, InboundHandlerManager, OutboundHandlerManager. func (s *Instance) RegisterFeature(feature interface{}, instance Feature) error { + running := false + switch feature.(type) { case DNSClient, *DNSClient: s.dnsClient.Set(instance.(DNSClient)) @@ -147,19 +148,23 @@ func (s *Instance) RegisterFeature(feature interface{}, instance Feature) error s.ihm.Set(instance.(InboundHandlerManager)) case OutboundHandlerManager, *OutboundHandlerManager: s.ohm.Set(instance.(OutboundHandlerManager)) - case Commander, *Commander: - s.cmd.Set(instance.(Commander)) + default: + s.access.Lock() + s.features = append(s.features, instance) + running = s.running + s.access.Unlock() } - s.access.Lock() - defer s.access.Unlock() - s.features = append(s.features, instance) - if s.running { + if running { return instance.Start() } return nil } +func (s *Instance) allFeatures() []Feature { + return append([]Feature{s.DNSClient(), s.PolicyManager(), s.Dispatcher(), s.Router(), s.InboundHandlerManager(), s.OutboundHandlerManager()}, s.features...) +} + // GetFeature returns a feature that was registered in this Instance. Nil if not found. // The returned Feature must implement common.HasType and whose type equals the given feature type. func (s *Instance) GetFeature(featureType interface{}) Feature { @@ -202,8 +207,3 @@ func (s *Instance) InboundHandlerManager() InboundHandlerManager { func (s *Instance) OutboundHandlerManager() OutboundHandlerManager { return &(s.ohm) } - -// Commander returns the Commander used by this Instance. The returned Commander is always functional. -func (s *Instance) Commander() Commander { - return &(s.cmd) -}