Skip to content

Commit

Permalink
Move the res_search function to runtime package while linking in net
Browse files Browse the repository at this point in the history
Signed-off-by: grant <[email protected]>
  • Loading branch information
grantseltzer committed Mar 9, 2019
1 parent 8f42cff commit 45ca41c
Show file tree
Hide file tree
Showing 2 changed files with 74 additions and 72 deletions.
73 changes: 73 additions & 0 deletions src/net/lookup_darwin.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@ package net

import (
"context"
"errors"
"internal/bytealg"
"strings"
"sync"
"syscall"

Expand Down Expand Up @@ -372,3 +374,74 @@ func concurrentThreadsLimit() int {
}
return r
}

// resolverSearch will make a call to the 'res_search' routine in libSystem
// and parse the output as a slice of IPAddr's
func resolverSearch(ctx context.Context, hostname string, rtype, class int32) ([]string, error) {

var byteHostname = []byte(hostname)
var responseBuffer = [512]byte{}

retcode := res_search(&byteHostname[0], class, rtype, &responseBuffer[0], 512)
if retcode < 0 {
return nil, errors.New("could not complete domain resolution")
}

msg := &dnsmessage.Message{}
err := msg.Unpack(responseBuffer[:])
if err != nil {
return nil, fmt.Errorf("could not parse dns response: %s", err.Error())
}

// parse received answers
var dnsParser dnsmessage.Parser

if _, err := dnsParser.Start(responseBuffer); err != nil {
return nil, err
}

var answers []string
for {
h, err := dnsParser.AnswerHeader()
if err == dnsmessage.ErrSectionDone {
break
}
if err != nil {
return nil, err
}

if !strings.EqualFold(h.Name.String(), hostname) {
if err := dnsParser.SkipAnswer(); err != nil {
return nil, err
}
continue
}

switch h.Type {
case dnsmessage.TypeA:
r, err := dnsParser.AResource()
if err != nil {
return nil, err
}
answers = append(answers, fmt.Stringf("%s", r.A))
case dnsmessage.TypeAAAA:
r, err := dnsParser.AAAAResource()
if err != nil {
return nil, err
}
answers = append(answers, fmt.Stringf("%s", r.AAAA))

case dnsmessage.TypeCNAME:
r, err := dnsParser.CNAMEResource()
if err != nil {
return nil, err
}
answers = append(answers, fmt.Stringf("%s", r.Name))
}
}
return answers, nil
}

// res_search is defined in runtimne/lookup_darwin.go

func res_search(name *byte, class int32, rtype int32, answer *byte, anslen int32) int32
73 changes: 1 addition & 72 deletions src/runtime/lookup_darwin.go
Original file line number Diff line number Diff line change
@@ -1,81 +1,10 @@
package runtime

import (
"context"
"errors"
"strings"
"unsafe"

"internal/x/net/dns/dnsmessage"
)

// ResolverSearch is a darwin specific function. It will make a call to the 'res_search' routine in libSystem
// and parse the output as a slice of IPAddr's
func ResolverSearch(ctx context.Context, hostname string, rtype, class int32) ([]string, error) {

var byteHostname = []byte(hostname)
var responseBuffer = [512]byte{}

retcode := res_search(&byteHostname[0], class, rtype, &responseBuffer[0], 512)
if retcode < 0 {
return nil, errors.New("could not complete domain resolution")
}

msg := &dnsmessage.Message{}
err := msg.Unpack(responseBuffer[:])
if err != nil {
return nil, fmt.Errorf("could not parse dns response: %s", err.Error())
}

// parse received answers
var dnsParser dnsmessage.Parser

if _, err := dnsParser.Start(responseBuffer); err != nil {
return nil, err
}

var answers []string
for {
h, err := dnsParser.AnswerHeader()
if err == dnsmessage.ErrSectionDone {
break
}
if err != nil {
return nil, err
}

if !strings.EqualFold(h.Name.String(), hostname) {
if err := dnsParser.SkipAnswer(); err != nil {
return nil, err
}
continue
}

switch h.Type {
case dnsmessage.TypeA:
r, err := dnsParser.AResource()
if err != nil {
return nil, err
}
answers = append(answers, fmt.Stringf("%s", r.A))
case dnsmessage.TypeAAAA:
r, err := dnsParser.AAAAResource()
if err != nil {
return nil, err
}
answers = append(answers, fmt.Stringf("%s", r.AAAA))

case dnsmessage.TypeCNAME:
r, err := dnsParser.CNAMEResource()
if err != nil {
return nil, err
}
answers = append(answers, fmt.Stringf("%s", r.Name))
}
}
return answers, nil
}

//go:linkname res_search net.res_search
//go:nosplit
//go:cgo_unsafe_args
func res_search(name *byte, class int32, rtype int32, answer *byte, anslen int32) int32 {
Expand Down

0 comments on commit 45ca41c

Please sign in to comment.