Skip to content

Commit

Permalink
feat(mdns): add option to disable either IPv4 or IPv6 stack
Browse files Browse the repository at this point in the history
allow the user to disable v4 or v6 if needed. This solves the issue when
a user is using discover option but having only one IP stack
  • Loading branch information
badrabubker committed Jul 2, 2024
1 parent 0eb1b84 commit 6719786
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 20 deletions.
10 changes: 9 additions & 1 deletion cmd/serf/command/agent/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,8 @@ func (c *Command) readConfig() *Config {
cmdFlags.StringVar(&cmdConfig.Discover, "discover", "", "mDNS discovery name")
cmdFlags.StringVar(&cmdConfig.Interface, "iface", "", "interface to bind to")
cmdFlags.StringVar(&cmdConfig.MDNS.Interface, "mdns-iface", "", "interface to use for mDNS")
cmdFlags.BoolVar(&cmdConfig.MDNS.DisableIPv4, "mdns-disable-ipv4", false, "disable IPv4 for mDNS")
cmdFlags.BoolVar(&cmdConfig.MDNS.DisableIPv6, "mdns-disable-ipv6", false, "disable IPv6 for mDNS")
cmdFlags.StringVar(&cmdConfig.TagsFile, "tags-file", "", "tag persistence file")
cmdFlags.BoolVar(&cmdConfig.EnableSyslog, "syslog", false,
"enable logging to syslog facility")
Expand Down Expand Up @@ -182,6 +184,12 @@ func (c *Command) readConfig() *Config {
c.Ui.Error(fmt.Sprintf("Invalid mDNS network interface: %s", err))
return nil
}

// Check for a valid mdns ip mode
if config.MDNS.DisableIPv4 && config.MDNS.DisableIPv6 {
c.Ui.Error("Invalid mDNS configuration: both IPv4 and IPv6 are disabled")
return nil
}
}

// Backward compatibility hack for 'Role'
Expand Down Expand Up @@ -445,7 +453,7 @@ func (c *Command) startAgent(config *Config, agent *Agent,
c.logger.Printf("[INFO] agent: Starting mDNS listener on interface %s", iface.Name)

_, err := NewAgentMDNS(agent, logOutput, config.ReplayOnJoin,
config.NodeName, config.Discover, iface, local.Addr, int(local.Port))
config.NodeName, config.Discover, iface, local.Addr, int(local.Port), config.MDNS)
if err != nil {
c.Ui.Error(fmt.Sprintf("Error starting mDNS listener: %s", err))
return nil
Expand Down
12 changes: 11 additions & 1 deletion cmd/serf/command/agent/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,9 @@ type dirEnts []os.FileInfo
type MDNSConfig struct {
// Interface is used to provide a binding interface to use for mDNS.
// if not set, iface will be used.
Interface string `mapstructure:"interface"`
Interface string `mapstructure:"interface"`
DisableIPv4 bool `mapstructure:"disable_ipv4"`
DisableIPv6 bool `mapstructure:"disable_ipv6"`
}

// Config is the configuration that can be set for an Agent. Some of these
Expand Down Expand Up @@ -459,6 +461,14 @@ func MergeConfig(a, b *Config) *Config {
result.MDNS.Interface = b.MDNS.Interface
}

if b.MDNS.DisableIPv4 == true {
result.MDNS.DisableIPv4 = true
}

if b.MDNS.DisableIPv6 == true {
result.MDNS.DisableIPv6 = true
}

if b.ReconnectInterval != 0 {
result.ReconnectInterval = b.ReconnectInterval
}
Expand Down
43 changes: 25 additions & 18 deletions cmd/serf/command/agent/mdns.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,18 +21,21 @@ const (
// AgentMDNS is used to advertise ourself using mDNS and to
// attempt to join peers periodically using mDNS queries.
type AgentMDNS struct {
agent *Agent
discover string
logger *log.Logger
seen map[string]struct{}
server *mdns.Server
replay bool
iface *net.Interface
agent *Agent
discover string
logger *log.Logger
seen map[string]struct{}
server *mdns.Server
replay bool
iface *net.Interface
ipModes []string
disableIPv4 bool
disableIPv6 bool
}

// NewAgentMDNS is used to create a new AgentMDNS
func NewAgentMDNS(agent *Agent, logOutput io.Writer, replay bool,
node, discover string, iface *net.Interface, bind net.IP, port int) (*AgentMDNS, error) {
node, discover string, iface *net.Interface, bind net.IP, port int, MDNSConfig MDNSConfig) (*AgentMDNS, error) {
// Create the service
service, err := mdns.NewMDNSService(
node,
Expand Down Expand Up @@ -60,13 +63,15 @@ func NewAgentMDNS(agent *Agent, logOutput io.Writer, replay bool,

// Initialize the AgentMDNS
m := &AgentMDNS{
agent: agent,
discover: discover,
logger: log.New(logOutput, "", log.LstdFlags),
seen: make(map[string]struct{}),
server: server,
replay: replay,
iface: iface,
agent: agent,
discover: discover,
logger: log.New(logOutput, "", log.LstdFlags),
seen: make(map[string]struct{}),
server: server,
replay: replay,
iface: iface,
disableIPv4: MDNSConfig.DisableIPv4,
disableIPv6: MDNSConfig.DisableIPv6,
}

// Start the background workers
Expand Down Expand Up @@ -123,9 +128,11 @@ func (m *AgentMDNS) run() {
// poll is invoked periodically to check for new hosts
func (m *AgentMDNS) poll(hosts chan *mdns.ServiceEntry) {
params := mdns.QueryParam{
Service: mdnsName(m.discover),
Interface: m.iface,
Entries: hosts,
Service: mdnsName(m.discover),
Interface: m.iface,
Entries: hosts,
DisableIPv4: m.disableIPv4,
DisableIPv6: m.disableIPv6,
}
if err := mdns.Query(&params); err != nil {
m.logger.Printf("[ERR] agent.mdns: Failed to poll for new hosts: %v", err)
Expand Down

0 comments on commit 6719786

Please sign in to comment.