Merge branch 'ipv6'

This commit is contained in:
Christian Goll
2022-03-18 09:24:35 +01:00
12 changed files with 93 additions and 17 deletions

View File

@@ -1,6 +1,9 @@
package add
import (
"fmt"
"net"
"github.com/hpcng/warewulf/internal/pkg/node"
"github.com/hpcng/warewulf/internal/pkg/util"
"github.com/hpcng/warewulf/internal/pkg/warewulfd"
@@ -123,7 +126,19 @@ func CobraRunE(cmd *cobra.Command, args []string) error {
n.NetDevs[SetNetName].Type.Set(SetType)
}
if SetIpaddr6 != "" {
if SetNetName == "" {
return errors.New("you must include the '--netname' option")
}
if _, ok := n.NetDevs[SetNetName]; !ok {
return errors.New("network device does not exist: " + SetNetName)
}
// just check if address is a valid ipv6 CIDR address
if _, _, err := net.ParseCIDR(SetIpaddr6); err != nil {
return errors.New(fmt.Sprintf("%s is not a valid ipv6 address in CIDR notation\n", SetIpaddr6))
}
}
if SetDiscoverable {
wwlog.Printf(wwlog.VERBOSE, "Node: %s, Setting node to discoverable\n", n.Id.Get())

View File

@@ -5,16 +5,17 @@ import "github.com/spf13/cobra"
var (
baseCmd = &cobra.Command{
DisableFlagsInUseLine: true,
Use: "add [OPTIONS] NODENAME",
Short: "Add new node to Warewulf",
Long: "This command will add a new node named NODENAME to Warewulf.",
RunE: CobraRunE,
Args: cobra.MinimumNArgs(1),
Use: "add [OPTIONS] NODENAME",
Short: "Add new node to Warewulf",
Long: "This command will add a new node named NODENAME to Warewulf.",
RunE: CobraRunE,
Args: cobra.MinimumNArgs(1),
}
SetClusterName string
SetNetName string
SetNetDev string
SetIpaddr string
SetIpaddr6 string
SetNetmask string
SetGateway string
SetHwaddr string
@@ -27,6 +28,7 @@ func init() {
baseCmd.PersistentFlags().StringVarP(&SetNetName, "netname", "n", "default", "Define the network name to configure")
baseCmd.PersistentFlags().StringVarP(&SetNetDev, "netdev", "N", "", "Define the network device to configure")
baseCmd.PersistentFlags().StringVarP(&SetIpaddr, "ipaddr", "I", "", "Set the node's network device IP address")
baseCmd.PersistentFlags().StringVarP(&SetIpaddr6, "ipaddr6", "6", "", "Set the node's network device IPv6 address")
baseCmd.PersistentFlags().StringVarP(&SetNetmask, "netmask", "M", "", "Set the node's network device netmask")
baseCmd.PersistentFlags().StringVarP(&SetGateway, "gateway", "G", "", "Set the node's network device gateway")
baseCmd.PersistentFlags().StringVarP(&SetHwaddr, "hwaddr", "H", "", "Set the node's network device HW address")

View File

@@ -65,6 +65,7 @@ func CobraRunE(cmd *cobra.Command, args []string) error {
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":DEVICE", netdev.Device.Source(), netdev.Device.Print())
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":HWADDR", netdev.Hwaddr.Source(), netdev.Hwaddr.Print())
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":IPADDR", netdev.Ipaddr.Source(), netdev.Ipaddr.Print())
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":IPADDR6", netdev.Ipaddr.Source(), netdev.Ipaddr6.Print())
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":NETMASK", netdev.Netmask.Source(), netdev.Netmask.Print())
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":GATEWAY", netdev.Gateway.Source(), netdev.Gateway.Print())
fmt.Printf("%-20s %-18s %-12s %s\n", node.Id.Get(), name+":TYPE", netdev.Type.Source(), netdev.Type.Print())
@@ -75,16 +76,17 @@ func CobraRunE(cmd *cobra.Command, args []string) error {
}
} else if ShowNet {
fmt.Printf("%-22s %-6s %-18s %-15s %-15s\n", "NODE NAME", "DEVICE", "HWADDR", "IPADDR", "GATEWAY")
fmt.Printf("%-22s %-6s %-18s %-15s %-15s %-15s\n", "NODE NAME", "DEVICE", "HWADDR", "IPADDR", "GATEWAY", "IPADDR6")
fmt.Println(strings.Repeat("=", 80))
for _, node := range node.FilterByName(nodes, args) {
if len(node.NetDevs) > 0 {
for name, dev := range node.NetDevs {
fmt.Printf("%-22s %-6s %-18s %-15s %-15s\n", node.Id.Get(), name, dev.Hwaddr.Print(), dev.Ipaddr.Print(), dev.Gateway.Print())
fmt.Printf("%-22s %-6s %-18s %-15s %-15s %-15s\n",
node.Id.Get(), name, dev.Hwaddr.Print(), dev.Ipaddr.Print(), dev.Gateway.Print(), dev.Ipaddr6.Print())
}
} else {
fmt.Printf("%-22s %-6s %-18s %-15s %-15s\n", node.Id.Get(), "--", "--", "--", "--")
fmt.Printf("%-22s %-6s %-18s %-15s %-15s %-15s\n", node.Id.Get(), "--", "--", "--", "--", "--")
}
}

View File

@@ -2,12 +2,15 @@ package node
import (
"errors"
"fmt"
"io/ioutil"
"net"
"path"
"sort"
"strings"
"github.com/hpcng/warewulf/internal/pkg/buildconfig"
"github.com/hpcng/warewulf/internal/pkg/warewulfconf"
"github.com/hpcng/warewulf/internal/pkg/wwlog"
"gopkg.in/yaml.v2"
@@ -43,7 +46,10 @@ func New() (nodeYaml, error) {
func (config *nodeYaml) FindAllNodes() ([]NodeInfo, error) {
var ret []NodeInfo
wwconfig, err := warewulfconf.New()
if err != nil {
return ret, err
}
wwlog.Printf(wwlog.DEBUG, "Finding all nodes...\n")
for nodename, node := range config.Nodes {
var n NodeInfo
@@ -103,13 +109,28 @@ func (config *nodeYaml) FindAllNodes() ([]NodeInfo, error) {
}
n.NetDevs[devname].Device.Set(netdev.Device)
n.NetDevs[devname].Ipaddr.Set(netdev.Ipaddr)
n.NetDevs[devname].Ipaddr6.Set(netdev.Ipaddr6)
// Derive value of ipv6 address from ipv4 if not explicitly set
if wwconfig.Ipaddr6 != "" {
ipv4Arr := strings.Split(netdev.Ipaddr, ".")
// error can be ignored as check was done at init
_, ipv6Net, _ := net.ParseCIDR(wwconfig.Ipaddr6)
mSize, _ := ipv6Net.Mask.Size()
ipv6str := fmt.Sprintf("%s%s:%s:%s:%s/%v",
ipv6Net.IP.String(), ipv4Arr[0], ipv4Arr[1], ipv4Arr[2], ipv4Arr[3], mSize)
if strings.Count(ipv6Net.IP.String(), ":") == 5 {
ipv6str = strings.Replace(ipv6str, "::", ":", -1)
}
n.NetDevs[devname].Ipaddr6.SetDefault(ipv6str)
}
n.NetDevs[devname].Netmask.Set(netdev.Netmask)
n.NetDevs[devname].Hwaddr.Set(netdev.Hwaddr)
n.NetDevs[devname].Gateway.Set(netdev.Gateway)
n.NetDevs[devname].Type.Set(netdev.Type)
n.NetDevs[devname].OnBoot.Set(netdev.OnBoot)
n.NetDevs[devname].Default.Set(netdev.Default)
// for just one netdeve, it is always the default
// for just one netdev, it is always the default
if len(node.NetDevs) == 1 {
n.NetDevs[devname].Default.Set("true")
}
@@ -174,7 +195,7 @@ func (config *nodeYaml) FindAllNodes() ([]NodeInfo, error) {
wwlog.Printf(wwlog.DEBUG, "Updating profile (%s) netdev: %s\n", p, devname)
n.NetDevs[devname].Device.SetAlt(netdev.Device, p)
n.NetDevs[devname].Ipaddr.SetAlt(netdev.Ipaddr, p)
//n.NetDevs[devname].Ipaddr.SetAlt(netdev.Ipaddr, p) <- Ipaddr must be uniq
n.NetDevs[devname].Netmask.SetAlt(netdev.Netmask, p)
n.NetDevs[devname].Hwaddr.SetAlt(netdev.Hwaddr, p)
n.NetDevs[devname].Gateway.SetAlt(netdev.Gateway, p)

View File

@@ -49,6 +49,7 @@ type NetDevs struct {
Hwaddr string `yaml:"hwaddr,omitempty"`
Ipaddr string `yaml:"ipaddr,omitempty"`
IpCIDR string `yaml:"ipcidr,omitempty"`
Ipaddr6 string `yaml:"ip6addr,omitempty"`
Prefix string `yaml:"prefix,omitempty"`
Netmask string `yaml:"netmask,omitempty"`
Gateway string `yaml:"gateway,omitempty"`
@@ -101,6 +102,7 @@ type NetDevEntry struct {
Device Entry
Hwaddr Entry
Ipaddr Entry
Ipaddr6 Entry
IpCIDR Entry
Prefix Entry
Netmask Entry

View File

@@ -33,8 +33,10 @@ type TemplateStruct struct {
BuildTime string
BuildSource string
Ipaddr string
Ipaddr6 string
Netmask string
Network string
Ipv6 bool
Dhcp warewulfconf.DhcpConf
Nfs warewulfconf.NfsConf
Warewulf warewulfconf.WarewulfConf

View File

@@ -253,7 +253,7 @@ func BuildOverlayIndir(nodeInfo node.NodeInfo, overlayNames []string, outputDir
netPrefix, _ := net.IPMask(net.ParseIP(netdev.Netmask.Get()).To4()).Size()
tstruct.NetDevs[devname].Prefix = strconv.Itoa(netPrefix)
tstruct.NetDevs[devname].IpCIDR = netaddr.String()
tstruct.NetDevs[devname].Ipaddr6 = netdev.Ipaddr6.Get()
}
// Backwards compatibility for templates using "Keys"
for keyname, key := range nodeInfo.Tags {
@@ -267,8 +267,14 @@ func BuildOverlayIndir(nodeInfo node.NodeInfo, overlayNames []string, outputDir
tstruct.Dhcp = *controller.Dhcp
tstruct.Warewulf = *controller.Warewulf
tstruct.Ipaddr = controller.Ipaddr
tstruct.Ipaddr6 = controller.Ipaddr6
tstruct.Netmask = controller.Netmask
tstruct.Network = controller.Network
if controller.Ipaddr6 != "" {
tstruct.Ipv6 = true
} else {
tstruct.Ipv6 = false
}
hostname, _ := os.Hostname()
tstruct.BuildHost = hostname
dt := time.Now()

View File

@@ -62,7 +62,18 @@ func New() (ControllerConf, error) {
ret.Network = sub.GetNetworkPortion()
}
// check validity of ipv6 net
if ret.Ipaddr6 != "" {
_, ipv6net, err := net.ParseCIDR(ret.Ipaddr6)
if err != nil {
wwlog.Printf(wwlog.ERROR, "Invalid ipv6 address specified, mut be CIDR notation: %s\n", ret.Ipaddr6)
return ret, errors.New("invalid ipv6 network")
}
if msize, _ := ipv6net.Mask.Size(); msize > 64 {
wwlog.Printf(wwlog.ERROR, "ipv6 mask size must be smaller than 64\n")
return ret, errors.New("invalid ipv6 network size")
}
}
if ret.Warewulf.Port == 0 {
ret.Warewulf.Port = defaultPort
}

View File

@@ -9,8 +9,10 @@ import (
type ControllerConf struct {
Comment string `yaml:"comment,omitempty"`
Ipaddr string `yaml:"ipaddr"`
Ipaddr6 string `yaml:"ipaddr6,omitempty"`
Netmask string `yaml:"netmask"`
Network string `yaml:"network,omitempty"`
Ipv6net string `yaml:"ipv6net,omitempty"`
Fqdn string `yaml:"fqdn,omitempty"`
Warewulf *WarewulfConf `yaml:"warewulf"`
Dhcp *DhcpConf `yaml:"dhcp"`

View File

@@ -7,7 +7,6 @@ Network:
{{- range $devname, $netdev := .NetDevs}}
{{$devname}}: {{$netdev.Device}}
{{$devname}}: {{$netdev.IpCIDR}}
{{if $netdev.Hwaddr }}
{{$devname}}: {{$netdev.Hwaddr}}
{{ end -}}
{{end}}
{{if $netdev.Ipaddr6 }} {{$devname}}: {{$netdev.Ipaddr6}}{{ end }}
{{if $netdev.Hwaddr }} {{$devname}}: {{$netdev.Hwaddr}}{{ end }}
{{end}}

View File

@@ -21,4 +21,11 @@ GATEWAY={{ $netdev.Gateway }}
HWADDR={{ $netdev.Hwaddr }}
{{ end -}}
ONBOOT=yes
IPV6INIT=yes
IPV6_AUTOCONF=yes
IPV6_DEFROUTE=yes
IPV6_FAILURE_FATAL=no
{{ if $.NetDevs.default.Ipaddr6 -}}
IPV6ADDR="{{ $.NetDevs.default.Ipaddr6 }}"
{{ end -}}
{{ end -}}

View File

@@ -38,5 +38,12 @@ Source: {{ $source }}
<privacy>prefer-public</privacy>
<accept-redirects>false</accept-redirects>
</ipv6>
{{ if $.NetDevs.default.Ipaddr6 -}}
<ipv6:static>
<address>
<local>{{ $.NetDevs.default.Ipaddr6 }}</local>
</address>
</ipv6:static>
{{ end -}}
</interface>
{{ end -}}