f-28: refactor dhcp config to use VPCRoute and DefaultGateway

Signed-off-by: GnomeZworc <nicolas.boufidjeline@g3e.fr>
This commit is contained in:
GnomeZworc 2026-05-18 22:50:39 +02:00
commit 1b56a42627
Signed by: nicolas.boufideline
GPG key ID: 4406BBBF8845D632
4 changed files with 61 additions and 24 deletions

View file

@ -51,10 +51,13 @@ func TestIncrementIP_Carry(t *testing.T) {
func newConf(t *testing.T, cidr string) Config { func newConf(t *testing.T, cidr string) Config {
t.Helper() t.Helper()
_, network, _ := net.ParseCIDR(cidr) _, network, _ := net.ParseCIDR(cidr)
_, vpcNet, _ := net.ParseCIDR("10.0.0.0/16")
gw := net.ParseIP("192.168.1.1").To4()
return Config{ return Config{
Network: network, Network: network,
Gateway: net.ParseIP("192.168.1.1").To4(), VPCGateway: gw,
DefaultRoute: true, VPCRoute: vpcNet,
DefaultGateway: gw,
Name: "test", Name: "test",
ConfDir: t.TempDir(), ConfDir: t.TempDir(),
} }
@ -85,24 +88,45 @@ func TestGenerateConfig_FilenameMatchesName(t *testing.T) {
} }
} }
func TestGenerateConfig_ContainsGateway(t *testing.T) { func TestGenerateConfig_ContainsDefaultGateway(t *testing.T) {
conf := newConf(t, "192.168.1.0/29") conf := newConf(t, "192.168.1.0/29")
path, _, _ := GenerateConfig(conf) path, _, _ := GenerateConfig(conf)
content, _ := os.ReadFile(path) content, _ := os.ReadFile(path)
if !strings.Contains(string(content), "dhcp-option=3,192.168.1.1") { if !strings.Contains(string(content), "dhcp-option=3,192.168.1.1") {
t.Errorf("gateway absente du fichier généré :\n%s", content) t.Errorf("dhcp-option=3 absente du fichier généré :\n%s", content)
} }
} }
func TestGenerateConfig_NoDefaultRoute(t *testing.T) { func TestGenerateConfig_NoDefaultGateway(t *testing.T) {
conf := newConf(t, "192.168.1.0/29") conf := newConf(t, "192.168.1.0/29")
conf.DefaultRoute = false conf.DefaultGateway = nil
path, _, _ := GenerateConfig(conf) path, _, _ := GenerateConfig(conf)
content, _ := os.ReadFile(path) content, _ := os.ReadFile(path)
if strings.Contains(string(content), "dhcp-option=3,") { if strings.Contains(string(content), "dhcp-option=3,") {
t.Errorf("dhcp-option=3 présente alors que DefaultRoute=false :\n%s", content) t.Errorf("dhcp-option=3 présente alors que DefaultGateway=nil :\n%s", content)
}
}
func TestGenerateConfig_ContainsVPCRoute(t *testing.T) {
conf := newConf(t, "192.168.1.0/29")
path, _, _ := GenerateConfig(conf)
content, _ := os.ReadFile(path)
if !strings.Contains(string(content), "dhcp-option=121,10.0.0.0/16,192.168.1.1") {
t.Errorf("dhcp-option=121 absente ou incorrecte :\n%s", content)
}
}
func TestGenerateConfig_NoVPCRoute(t *testing.T) {
conf := newConf(t, "192.168.1.0/29")
conf.VPCRoute = nil
path, _, _ := GenerateConfig(conf)
content, _ := os.ReadFile(path)
if strings.Contains(string(content), "dhcp-option=121,") {
t.Errorf("dhcp-option=121 présente alors que VPCRoute=nil :\n%s", content)
} }
} }
@ -110,7 +134,6 @@ func TestGenerateConfig_ContainsDhcpRange(t *testing.T) {
_, network, _ := net.ParseCIDR("10.10.0.0/24") _, network, _ := net.ParseCIDR("10.10.0.0/24")
conf := Config{ conf := Config{
Network: network, Network: network,
Gateway: net.ParseIP("10.10.0.1").To4(),
Name: "vpc1", Name: "vpc1",
ConfDir: t.TempDir(), ConfDir: t.TempDir(),
} }
@ -156,7 +179,6 @@ func TestGenerateConfig_CreatesConfDir(t *testing.T) {
_, network, _ := net.ParseCIDR("10.0.0.0/30") _, network, _ := net.ParseCIDR("10.0.0.0/30")
conf := Config{ conf := Config{
Network: network, Network: network,
Gateway: net.ParseIP("10.0.0.1").To4(),
Name: "net", Name: "net",
ConfDir: dir, ConfDir: dir,
} }

View file

@ -14,8 +14,11 @@ func GenerateConfig(c Config) (string, map[string]string, error) {
var sb strings.Builder var sb strings.Builder
fmt.Fprintf(&sb, "no-resolv\n") fmt.Fprintf(&sb, "no-resolv\n")
fmt.Fprintf(&sb, "dhcp-range=%s,static,%s,12h\n", c.Network.IP.String(), mask) fmt.Fprintf(&sb, "dhcp-range=%s,static,%s,12h\n", c.Network.IP.String(), mask)
if c.DefaultRoute { if c.VPCRoute != nil {
fmt.Fprintf(&sb, "dhcp-option=3,%s\n", c.Gateway.String()) fmt.Fprintf(&sb, "dhcp-option=121,%s,%s\n", c.VPCRoute.String(), c.VPCGateway.String())
}
if c.DefaultGateway != nil {
fmt.Fprintf(&sb, "dhcp-option=3,%s\n", c.DefaultGateway.String())
} }
fmt.Fprintf(&sb, "dhcp-option=6,1.1.1.1,8.8.8.8\n\n") fmt.Fprintf(&sb, "dhcp-option=6,1.1.1.1,8.8.8.8\n\n")

View file

@ -6,8 +6,9 @@ import (
type Config struct { type Config struct {
Network *net.IPNet Network *net.IPNet
Gateway net.IP VPCGateway net.IP // next-hop for VPCRoute (option 121)
DefaultRoute bool VPCRoute *net.IPNet // if non-nil, emit dhcp-option=121,VPCRoute,VPCGateway
DefaultGateway net.IP // if non-nil, emit dhcp-option=3,DefaultGateway
Name string Name string
ConfDir string ConfDir string
} }

View file

@ -137,11 +137,22 @@ func setupVxlanHost(d subnetData, vethE string) error {
func startDHCP(db *badger.DB, subnetName string, d subnetData) error { func startDHCP(db *badger.DB, subnetName string, d subnetData) error {
conf := dhcp.Config{ conf := dhcp.Config{
Network: d.cidr, Network: d.cidr,
Gateway: d.interfaceIP,
DefaultRoute: d.mode == "vxlan",
Name: d.vpc + "_" + d.bridge, Name: d.vpc + "_" + d.bridge,
ConfDir: "/etc/dnsmasq.d", ConfDir: "/etc/dnsmasq.d",
} }
switch d.mode {
case "vxlan":
conf.VPCGateway = d.interfaceIP
conf.VPCRoute = d.vpcCIDR
case "bridge":
if d.defaultRoute {
gw, err := netif.GetDefaultGateway()
if err != nil {
return fmt.Errorf("get default gateway: %w", err)
}
conf.DefaultGateway = gw
}
}
_, entries, err := dhcp.GenerateConfig(conf) _, entries, err := dhcp.GenerateConfig(conf)
if err != nil { if err != nil {
return fmt.Errorf("generate dhcp config: %w", err) return fmt.Errorf("generate dhcp config: %w", err)