mirror of
https://github.com/rancher/plugins.git
synced 2025-09-07 10:25:10 +00:00
fix(dhcp): can not renew an ip address
The dhcp server is systemd-networkd, and the dhcp plugin can request an ip but can not renew it. The systemd-networkd just ignore the renew request. ``` 2024/09/14 21:46:00 no DHCP packet received within 10s 2024/09/14 21:46:00 retrying in 31.529038 seconds 2024/09/14 21:46:42 no DHCP packet received within 10s 2024/09/14 21:46:42 retrying in 63.150490 seconds 2024/09/14 21:47:45 98184616c91f15419f5cacd012697f85afaa2daeb5d3233e28b0ec21589fb45a/iot/eth1: no more tries 2024/09/14 21:47:45 98184616c91f15419f5cacd012697f85afaa2daeb5d3233e28b0ec21589fb45a/iot/eth1: renewal time expired, rebinding 2024/09/14 21:47:45 Link "eth1" down. Attempting to set up 2024/09/14 21:47:45 98184616c91f15419f5cacd012697f85afaa2daeb5d3233e28b0ec21589fb45a/iot/eth1: lease rebound, expiration is 2024-09-14 22:47:45.309270751 +0800 CST m=+11730.048516519 ``` Follow the https://datatracker.ietf.org/doc/html/rfc2131#section-4.3.6, following options must not be sent in renew - Requested IP Address - Server Identifier Since the upstream code has been inactive for 6 years, we should switch to another dhcpv4 library. The new selected one is https://github.com/insomniacslk/dhcp. Signed-off-by: Songmin Li <lisongmin@protonmail.com>
This commit is contained in:
committed by
Casey Callendrello
parent
e4950728ce
commit
d61e7e5e1f
150
vendor/github.com/mdlayher/socket/netns_linux.go
generated
vendored
Normal file
150
vendor/github.com/mdlayher/socket/netns_linux.go
generated
vendored
Normal file
@@ -0,0 +1,150 @@
|
||||
//go:build linux
|
||||
// +build linux
|
||||
|
||||
package socket
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"runtime"
|
||||
|
||||
"golang.org/x/sync/errgroup"
|
||||
"golang.org/x/sys/unix"
|
||||
)
|
||||
|
||||
// errNetNSDisabled is returned when network namespaces are unavailable on
|
||||
// a given system.
|
||||
var errNetNSDisabled = errors.New("socket: Linux network namespaces are not enabled on this system")
|
||||
|
||||
// withNetNS invokes fn within the context of the network namespace specified by
|
||||
// fd, while also managing the logic required to safely do so by manipulating
|
||||
// thread-local state.
|
||||
func withNetNS(fd int, fn func() (*Conn, error)) (*Conn, error) {
|
||||
var (
|
||||
eg errgroup.Group
|
||||
conn *Conn
|
||||
)
|
||||
|
||||
eg.Go(func() error {
|
||||
// Retrieve and store the calling OS thread's network namespace so the
|
||||
// thread can be reassigned to it after creating a socket in another network
|
||||
// namespace.
|
||||
runtime.LockOSThread()
|
||||
|
||||
ns, err := threadNetNS()
|
||||
if err != nil {
|
||||
// No thread-local manipulation, unlock.
|
||||
runtime.UnlockOSThread()
|
||||
return err
|
||||
}
|
||||
defer ns.Close()
|
||||
|
||||
// Beyond this point, the thread's network namespace is poisoned. Do not
|
||||
// unlock the OS thread until all network namespace manipulation completes
|
||||
// to avoid returning to the caller with altered thread-local state.
|
||||
|
||||
// Assign the current OS thread the goroutine is locked to to the given
|
||||
// network namespace.
|
||||
if err := ns.Set(fd); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Attempt Conn creation and unconditionally restore the original namespace.
|
||||
c, err := fn()
|
||||
if nerr := ns.Restore(); nerr != nil {
|
||||
// Failed to restore original namespace. Return an error and allow the
|
||||
// runtime to terminate the thread.
|
||||
if err == nil {
|
||||
_ = c.Close()
|
||||
}
|
||||
|
||||
return nerr
|
||||
}
|
||||
|
||||
// No more thread-local state manipulation; return the new Conn.
|
||||
runtime.UnlockOSThread()
|
||||
conn = c
|
||||
return nil
|
||||
})
|
||||
|
||||
if err := eg.Wait(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return conn, nil
|
||||
}
|
||||
|
||||
// A netNS is a handle that can manipulate network namespaces.
|
||||
//
|
||||
// Operations performed on a netNS must use runtime.LockOSThread before
|
||||
// manipulating any network namespaces.
|
||||
type netNS struct {
|
||||
// The handle to a network namespace.
|
||||
f *os.File
|
||||
|
||||
// Indicates if network namespaces are disabled on this system, and thus
|
||||
// operations should become a no-op or return errors.
|
||||
disabled bool
|
||||
}
|
||||
|
||||
// threadNetNS constructs a netNS using the network namespace of the calling
|
||||
// thread. If the namespace is not the default namespace, runtime.LockOSThread
|
||||
// should be invoked first.
|
||||
func threadNetNS() (*netNS, error) {
|
||||
return fileNetNS(fmt.Sprintf("/proc/self/task/%d/ns/net", unix.Gettid()))
|
||||
}
|
||||
|
||||
// fileNetNS opens file and creates a netNS. fileNetNS should only be called
|
||||
// directly in tests.
|
||||
func fileNetNS(file string) (*netNS, error) {
|
||||
f, err := os.Open(file)
|
||||
switch {
|
||||
case err == nil:
|
||||
return &netNS{f: f}, nil
|
||||
case os.IsNotExist(err):
|
||||
// Network namespaces are not enabled on this system. Use this signal
|
||||
// to return errors elsewhere if the caller explicitly asks for a
|
||||
// network namespace to be set.
|
||||
return &netNS{disabled: true}, nil
|
||||
default:
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
|
||||
// Close releases the handle to a network namespace.
|
||||
func (n *netNS) Close() error {
|
||||
return n.do(func() error { return n.f.Close() })
|
||||
}
|
||||
|
||||
// FD returns a file descriptor which represents the network namespace.
|
||||
func (n *netNS) FD() int {
|
||||
if n.disabled {
|
||||
// No reasonable file descriptor value in this case, so specify a
|
||||
// non-existent one.
|
||||
return -1
|
||||
}
|
||||
|
||||
return int(n.f.Fd())
|
||||
}
|
||||
|
||||
// Restore restores the original network namespace for the calling thread.
|
||||
func (n *netNS) Restore() error {
|
||||
return n.do(func() error { return n.Set(n.FD()) })
|
||||
}
|
||||
|
||||
// Set sets a new network namespace for the current thread using fd.
|
||||
func (n *netNS) Set(fd int) error {
|
||||
return n.do(func() error {
|
||||
return os.NewSyscallError("setns", unix.Setns(fd, unix.CLONE_NEWNET))
|
||||
})
|
||||
}
|
||||
|
||||
// do runs fn if network namespaces are enabled on this system.
|
||||
func (n *netNS) do(fn func() error) error {
|
||||
if n.disabled {
|
||||
return errNetNSDisabled
|
||||
}
|
||||
|
||||
return fn()
|
||||
}
|
Reference in New Issue
Block a user