Pull request: aghnet: fix ipset init errors
Updates #4027. Squashed commit of the following: commit 9ac0cc27ca94e630cc321c90b60b271499af4d9b Author: Ainar Garipov <A.Garipov@AdGuard.COM> Date: Mon Dec 27 20:26:22 2021 +0300 aghnet: fix ipset init errors
This commit is contained in:
parent
dea8a585f8
commit
2ed1f939b5
|
@ -29,6 +29,7 @@ and this project adheres to
|
|||
|
||||
### Fixed
|
||||
|
||||
- `ipset` initialization bugs ([#4027]).
|
||||
- Legacy DNS rewrites from a wildcard pattern to a subdomain ([#4016]).
|
||||
- Service not being stopped before running the `uninstall` service action
|
||||
([#3868]).
|
||||
|
@ -46,6 +47,7 @@ and this project adheres to
|
|||
[#3987]: https://github.com/AdguardTeam/AdGuardHome/issues/3987
|
||||
[#4008]: https://github.com/AdguardTeam/AdGuardHome/issues/4008
|
||||
[#4016]: https://github.com/AdguardTeam/AdGuardHome/issues/4016
|
||||
[#4027]: https://github.com/AdguardTeam/AdGuardHome/issues/4027
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -20,7 +20,12 @@ type IpsetManager interface {
|
|||
//
|
||||
// DOMAIN[,DOMAIN].../IPSET_NAME[,IPSET_NAME]...
|
||||
//
|
||||
// The error is of type *aghos.UnsupportedError if the OS is not supported.
|
||||
// If ipsetConf is empty, msg and err are nil. The error is of type
|
||||
// *aghos.UnsupportedError if the OS is not supported.
|
||||
func NewIpsetManager(ipsetConf []string) (mgr IpsetManager, err error) {
|
||||
if len(ipsetConf) == 0 {
|
||||
return nil, nil
|
||||
}
|
||||
|
||||
return newIpsetMgr(ipsetConf)
|
||||
}
|
||||
|
|
|
@ -14,6 +14,7 @@ import (
|
|||
"github.com/digineo/go-ipset/v2"
|
||||
"github.com/mdlayher/netlink"
|
||||
"github.com/ti-mo/netfilter"
|
||||
"golang.org/x/sys/unix"
|
||||
)
|
||||
|
||||
// How to test on a real Linux machine:
|
||||
|
@ -42,11 +43,17 @@ import (
|
|||
|
||||
// newIpsetMgr returns a new Linux ipset manager.
|
||||
func newIpsetMgr(ipsetConf []string) (set IpsetManager, err error) {
|
||||
dial := func(pf netfilter.ProtoFamily, conf *netlink.Config) (conn ipsetConn, err error) {
|
||||
return ipset.Dial(pf, conf)
|
||||
return newIpsetMgrWithDialer(ipsetConf, defaultDial)
|
||||
}
|
||||
|
||||
return newIpsetMgrWithDialer(ipsetConf, dial)
|
||||
// defaultDial is the default netfilter dialing function.
|
||||
func defaultDial(pf netfilter.ProtoFamily, conf *netlink.Config) (conn ipsetConn, err error) {
|
||||
conn, err = ipset.Dial(pf, conf)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return conn, nil
|
||||
}
|
||||
|
||||
// ipsetConn is the ipset conn interface.
|
||||
|
@ -103,8 +110,8 @@ func (m *ipsetMgr) dialNetfilter(conf *netlink.Config) (err error) {
|
|||
// The kernel API does not actually require two sockets but package
|
||||
// github.com/digineo/go-ipset does.
|
||||
//
|
||||
// TODO(a.garipov): Perhaps we can ditch package ipset altogether and
|
||||
// just use packages netfilter and netlink.
|
||||
// TODO(a.garipov): Perhaps we can ditch package ipset altogether and just
|
||||
// use packages netfilter and netlink.
|
||||
m.ipv4Conn, err = m.dial(netfilter.ProtoIPv4, conf)
|
||||
if err != nil {
|
||||
return fmt.Errorf("dialing v4: %w", err)
|
||||
|
@ -214,6 +221,14 @@ func newIpsetMgrWithDialer(ipsetConf []string, dial ipsetDialer) (mgr IpsetManag
|
|||
|
||||
err = m.dialNetfilter(&netlink.Config{})
|
||||
if err != nil {
|
||||
if errors.Is(err, unix.EPROTONOSUPPORT) {
|
||||
// The implementation doesn't support this protocol version. Just
|
||||
// issue a warning.
|
||||
log.Info("ipset: dialing netfilter: warning: %s", err)
|
||||
|
||||
return nil, nil
|
||||
}
|
||||
|
||||
return nil, fmt.Errorf("dialing netfilter: %w", err)
|
||||
}
|
||||
|
||||
|
|
|
@ -24,20 +24,19 @@ type ipsetCtx struct {
|
|||
func (c *ipsetCtx) init(ipsetConf []string) (err error) {
|
||||
c.ipsetMgr, err = aghnet.NewIpsetManager(ipsetConf)
|
||||
if errors.Is(err, os.ErrInvalid) || errors.Is(err, os.ErrPermission) {
|
||||
// ipset cannot currently be initialized if the server was
|
||||
// installed from Snap or when the user or the binary doesn't
|
||||
// have the required permissions, or when the kernel doesn't
|
||||
// support netfilter.
|
||||
// ipset cannot currently be initialized if the server was installed
|
||||
// from Snap or when the user or the binary doesn't have the required
|
||||
// permissions, or when the kernel doesn't support netfilter.
|
||||
//
|
||||
// Log and go on.
|
||||
//
|
||||
// TODO(a.garipov): The Snap problem can probably be solved if
|
||||
// we add the netlink-connector interface plug.
|
||||
log.Info("warning: cannot initialize ipset: %s", err)
|
||||
// TODO(a.garipov): The Snap problem can probably be solved if we add
|
||||
// the netlink-connector interface plug.
|
||||
log.Info("ipset: warning: cannot initialize: %s", err)
|
||||
|
||||
return nil
|
||||
} else if unsupErr := (&aghos.UnsupportedError{}); errors.As(err, &unsupErr) {
|
||||
log.Info("warning: %s", err)
|
||||
log.Info("ipset: warning: %s", err)
|
||||
|
||||
return nil
|
||||
} else if err != nil {
|
||||
|
|
Loading…
Reference in New Issue