Skip to content

Commit

Permalink
HostResolver shouldn't return IPv6 addresses by default
Browse files Browse the repository at this point in the history
They don't work over the SLIRP interface, and sometimes don't
even work over a bridged vmnet interface.

Signed-off-by: Jan Dubois <[email protected]>
  • Loading branch information
jandubois committed Jan 13, 2022
1 parent 356988d commit eaeee31
Show file tree
Hide file tree
Showing 9 changed files with 79 additions and 25 deletions.
9 changes: 7 additions & 2 deletions cmd/limactl/debug.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,22 +27,27 @@ func newDebugDNSCommand() *cobra.Command {
Args: cobra.RangeArgs(1, 2),
RunE: debugDNSAction,
}
cmd.Flags().BoolP("ipv6", "6", false, "lookup IPv6 addresses too")
return cmd
}

func debugDNSAction(cmd *cobra.Command, args []string) error {
ipv6, err := cmd.Flags().GetBool("ipv6")
if err != nil {
return err
}
udpLocalPort, err := strconv.Atoi(args[0])
if err != nil {
return err
}
tcpLocalPort := 0
if len(args) > 2 {
if len(args) > 1 {
tcpLocalPort, err = strconv.Atoi(args[1])
if err != nil {
return err
}
}
srv, err := dns.Start(udpLocalPort, tcpLocalPort)
srv, err := dns.Start(udpLocalPort, tcpLocalPort, ipv6)
if err != nil {
return err
}
Expand Down
2 changes: 1 addition & 1 deletion pkg/cidata/cidata.go
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,7 @@ func GenerateISO9660(instDir, name string, y *limayaml.LimaYAML, udpDNSLocalPort
if err != nil {
return err
}
if *y.UseHostResolver {
if *y.HostResolver.Enabled {
args.UDPDNSLocalPort = udpDNSLocalPort
args.TCPDNSLocalPort = tcpDNSLocalPort
args.DNSAddresses = append(args.DNSAddresses, qemu.SlirpDNS)
Expand Down
15 changes: 11 additions & 4 deletions pkg/hostagent/dns/dns.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ const truncateSize = 512
type Handler struct {
clientConfig *dns.ClientConfig
clients []*dns.Client
IPv6 bool
}

type Server struct {
Expand All @@ -43,7 +44,7 @@ func newStaticClientConfig(ips []net.IP) (*dns.ClientConfig, error) {
return dns.ClientConfigFromReader(r)
}

func newHandler() (dns.Handler, error) {
func newHandler(IPv6 bool) (dns.Handler, error) {
cc, err := dns.ClientConfigFromFile("/etc/resolv.conf")
if err != nil {
fallbackIPs := []net.IP{net.ParseIP("8.8.8.8"), net.ParseIP("1.1.1.1")}
Expand All @@ -60,6 +61,7 @@ func newHandler() (dns.Handler, error) {
h := &Handler{
clientConfig: cc,
clients: clients,
IPv6: IPv6,
}
return h, nil
}
Expand All @@ -78,7 +80,12 @@ func (h *Handler) handleQuery(w dns.ResponseWriter, req *dns.Msg) {
Ttl: 5,
}
switch q.Qtype {
case dns.TypeCNAME, dns.TypeA, dns.TypeAAAA:
case dns.TypeAAAA:
if !h.IPv6 {
break
}
fallthrough
case dns.TypeCNAME, dns.TypeA:
cname, err := net.LookupCNAME(q.Name)
if err != nil {
break
Expand Down Expand Up @@ -212,8 +219,8 @@ func (h *Handler) ServeDNS(w dns.ResponseWriter, req *dns.Msg) {
}
}

func Start(udpLocalPort, tcpLocalPort int) (*Server, error) {
h, err := newHandler()
func Start(udpLocalPort, tcpLocalPort int, IPv6 bool) (*Server, error) {
h, err := newHandler(IPv6)
if err != nil {
return nil, err
}
Expand Down
6 changes: 3 additions & 3 deletions pkg/hostagent/hostagent.go
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ func New(instName string, stdout io.Writer, sigintCh chan os.Signal, opts ...Opt
}

var udpDNSLocalPort, tcpDNSLocalPort int
if *y.UseHostResolver {
if *y.HostResolver.Enabled {
udpDNSLocalPort, err = findFreeUDPLocalPort()
if err != nil {
return nil, err
Expand Down Expand Up @@ -248,8 +248,8 @@ func (a *HostAgent) Run(ctx context.Context) error {
a.emitEvent(ctx, exitingEv)
}()

if *a.y.UseHostResolver {
dnsServer, err := dns.Start(a.udpDNSLocalPort, a.tcpDNSLocalPort)
if *a.y.HostResolver.Enabled {
dnsServer, err := dns.Start(a.udpDNSLocalPort, a.tcpDNSLocalPort, *a.y.HostResolver.IPv6)
if err != nil {
return fmt.Errorf("cannot start DNS server: %w", err)
}
Expand Down
11 changes: 8 additions & 3 deletions pkg/limayaml/default.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -236,9 +236,14 @@ propagateProxyEnv: null
# The host agent implements a DNS server that looks up host names on the host
# using the local system resolver. This means changing VPN and network settings
# are reflected automatically into the guest, including conditional forward,
# and mDNS lookup:
# Default: true
useHostResolver: null
# and mDNS lookup. By default only IPv4 addresses will be returned. IPv6 addresses
# can only work when using a vmnet network interface and the host has working
# IPv6 configured as well.
hostResolver:
# Default: true
enabled: null
# Default: false
ipv6: null

# If useHostResolver is false, then the following rules apply for configuring dns:
# Explicitly set DNS addresses for qemu user-mode networking. By default qemu picks *one*
Expand Down
34 changes: 28 additions & 6 deletions pkg/limayaml/defaults.go
Original file line number Diff line number Diff line change
Expand Up @@ -217,14 +217,36 @@ func FillDefault(y, d, o *LimaYAML, filePath string) {
// After defaults processing the singular HostPort and GuestPort values should not be used again.
}

if y.UseHostResolver == nil {
y.UseHostResolver = d.UseHostResolver
// If both `useHostResolved` and `HostResolver.Enabled` are defined in the same config,
// then the deprecated `useHostResolved` setting is silently ignored.
if y.HostResolver.Enabled == nil {
y.HostResolver.Enabled = y.UseHostResolver
}
if o.UseHostResolver != nil {
y.UseHostResolver = o.UseHostResolver
if d.HostResolver.Enabled == nil {
d.HostResolver.Enabled = d.UseHostResolver
}
if y.UseHostResolver == nil {
y.UseHostResolver = pointer.Bool(true)
if o.HostResolver.Enabled == nil {
o.HostResolver.Enabled = o.UseHostResolver
}

if y.HostResolver.Enabled == nil {
y.HostResolver.Enabled = d.HostResolver.Enabled
}
if o.HostResolver.Enabled != nil {
y.HostResolver.Enabled = o.HostResolver.Enabled
}
if y.HostResolver.Enabled == nil {
y.HostResolver.Enabled = pointer.Bool(true)
}

if y.HostResolver.IPv6 == nil {
y.HostResolver.IPv6 = d.HostResolver.IPv6
}
if o.HostResolver.IPv6 != nil {
y.HostResolver.IPv6 = o.HostResolver.IPv6
}
if y.HostResolver.IPv6 == nil {
y.HostResolver.IPv6 = pointer.Bool(false)
}

if y.PropagateProxyEnv == nil {
Expand Down
15 changes: 12 additions & 3 deletions pkg/limayaml/defaults_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,10 @@ func TestFillDefault(t *testing.T) {
Video: Video{
Display: pointer.String("none"),
},
UseHostResolver: pointer.Bool(true),
HostResolver: HostResolver{
Enabled: pointer.Bool(true),
IPv6: pointer.Bool(false),
},
PropagateProxyEnv: pointer.Bool(true),
}

Expand Down Expand Up @@ -186,7 +189,10 @@ func TestFillDefault(t *testing.T) {
Video: Video{
Display: pointer.String("cocoa"),
},
UseHostResolver: pointer.Bool(false),
HostResolver: HostResolver{
Enabled: pointer.Bool(false),
IPv6: pointer.Bool(true),
},
PropagateProxyEnv: pointer.Bool(false),

Mounts: []Mount{
Expand Down Expand Up @@ -298,7 +304,10 @@ func TestFillDefault(t *testing.T) {
Video: Video{
Display: pointer.String("cocoa"),
},
UseHostResolver: pointer.Bool(false),
HostResolver: HostResolver{
Enabled: pointer.Bool(false),
IPv6: pointer.Bool(false),
},
PropagateProxyEnv: pointer.Bool(false),

Mounts: []Mount{
Expand Down
8 changes: 7 additions & 1 deletion pkg/limayaml/limayaml.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,8 @@ type LimaYAML struct {
Network NetworkDeprecated `yaml:"network,omitempty" json:"network,omitempty"` // DEPRECATED, use `networks` instead
Env map[string]string `yaml:"env,omitempty" json:"env,omitempty"`
DNS []net.IP `yaml:"dns,omitempty" json:"dns,omitempty"`
UseHostResolver *bool `yaml:"useHostResolver,omitempty" json:"useHostResolver,omitempty"`
HostResolver HostResolver `yaml:"hostResolver,omitempty" json:"hostResolver,omitempty"`
UseHostResolver *bool `yaml:"useHostResolver,omitempty" json:"useHostResolver,omitempty"` // DEPRECATED, use `HostResolver.Enabled` instead
PropagateProxyEnv *bool `yaml:"propagateProxyEnv,omitempty" json:"propagateProxyEnv,omitempty"`
}

Expand Down Expand Up @@ -132,6 +133,11 @@ type Network struct {
Interface string `yaml:"interface,omitempty" json:"interface,omitempty"`
}

type HostResolver struct {
Enabled *bool `yaml:"enabled,omitempty" json:"enabled,omitempty"`
IPv6 *bool `yaml:"ipv6,omitempty" json:"ipv6,omitempty"`
}

// DEPRECATED types below

// Types have been renamed to turn all references to the old names into compiler errors,
Expand Down
4 changes: 2 additions & 2 deletions pkg/limayaml/validate.go
Original file line number Diff line number Diff line change
Expand Up @@ -194,8 +194,8 @@ func Validate(y LimaYAML, warn bool) error {
// processed sequentially and the first matching rule for a guest port determines forwarding behavior.
}

if y.UseHostResolver != nil && *y.UseHostResolver && len(y.DNS) > 0 {
return fmt.Errorf("field `dns` must be empty when field `useHostResolver` is true")
if y.HostResolver.Enabled != nil && *y.HostResolver.Enabled && len(y.DNS) > 0 {
return fmt.Errorf("field `dns` must be empty when field `HostResolver.Enabled` is true")
}

if err := validateNetwork(y, warn); err != nil {
Expand Down

0 comments on commit eaeee31

Please sign in to comment.