package config import "fmt" type ConntrackAction string const ( ConntrackNoTrack ConntrackAction = "notrack" ConntrackHelper ConntrackAction = "helper" ConntrackDrop ConntrackAction = "drop" ConntrackLog ConntrackAction = "log" ) type ConntrackChain string const ( ConntrackPrerouting ConntrackChain = "prerouting" ConntrackOutput ConntrackChain = "output" ConntrackBoth ConntrackChain = "both" ) type ConntrackRule struct { // Action: notrack (bypass conntrack), helper (assign CT helper), drop (raw table drop), log. Action ConntrackAction `yaml:"action"` // Source zone spec. Supports zone, zone:interface, zone:interface:address. Source string `yaml:"source,omitempty"` // Dest zone spec. Same syntax as Source. Dest string `yaml:"dest,omitempty"` Proto string `yaml:"proto,omitempty"` DPort PortSpec `yaml:"dport,omitempty"` SPort PortSpec `yaml:"sport,omitempty"` // Chain to install the rule in: prerouting, output, or both. Default: prerouting. Chain ConntrackChain `yaml:"chain,omitempty"` // CT helper name (for helper action): ftp, sip, tftp, irc, pptp, amanda, snmp, etc. Helper string `yaml:"helper,omitempty"` // User/group match (only valid for output chain). User string `yaml:"user,omitempty"` Comment string `yaml:"comment,omitempty"` } var validConntrackActions = map[ConntrackAction]bool{ ConntrackNoTrack: true, ConntrackHelper: true, ConntrackDrop: true, ConntrackLog: true, } var validConntrackChains = map[ConntrackChain]bool{ ConntrackPrerouting: true, ConntrackOutput: true, ConntrackBoth: true, "": true, } func (c *Config) validateConntrack() error { for i, ct := range c.Conntrack { if !validConntrackActions[ct.Action] { return fmt.Errorf("conntrack[%d]: unknown action %q", i, ct.Action) } if !validConntrackChains[ct.Chain] { return fmt.Errorf("conntrack[%d]: chain must be prerouting, output, or both", i) } if ct.Action == ConntrackHelper && ct.Helper == "" { return fmt.Errorf("conntrack[%d]: helper name required for helper action", i) } if ct.Source == "" && ct.Dest == "" && ct.Action != ConntrackHelper { return fmt.Errorf("conntrack[%d]: source or dest required", i) } if ct.User != "" { chain := ct.Chain if chain == "" { chain = ConntrackPrerouting } if chain == ConntrackPrerouting { return fmt.Errorf("conntrack[%d]: user match only valid for output chain", i) } } } return nil }