go (golang) DNS網域名稱解析實現

來源:互聯網
上載者:User
這是一個建立於 的文章,其中的資訊可能已經有所發展或是發生改變。

        之前使用過GO語言寫了一個即時圖片下載程式,主要考慮到GO語言的DNS解析對協程支援友好, 即

DNS解析時不會阻塞執行線程,只會阻塞當前協程,順便研究了一下GO的net.LookupHost/ResolveIPAddr

實現方式。下面一段描述翻譯自go語言的官方文檔 https://golang.org/pkg/net/網域名稱解析:

        網域名稱解析函數,Dial函數會間接調用到,而LokupHost和LookupAddr則會直接調用網域名稱解析函數,不同

的作業系統實現不同,  在Unix系統中有兩種方法進行網域名稱解析:

        1)純GO語言實現的網域名稱解析,從/etc/resolv.conf中取出本地dns server地址清單, 發送DNS請求(UDP

             報文)並獲得結果

         2)  使用cgo方式, 最終會調用到c標準庫的getaddrinfo或getnameinfo函數(不建議使用對GO協程不友好)

關於 cgo dns 解析的坑 參照以下連結

https://jira.mongodb.org/browse/MGO-41

https://github.com/golang/go/issues/8602#issuecomment-66098142

         GO語言預設使用純GO的網域名稱解析,因為這樣一個阻塞的DNS請求只會消耗一個協程, 使 用cgo的方式

則會阻塞一個系統線程, 只有某些特定條件下才會使用系統提供的cgo方式, 例如: 1) 在OS X系統中不允許程式

直接發送DNS請求;  2) LOCALDOMAINH環境變數存在,即使為空白;  3) ES_OPTIONS或HOSTALIASES或ASR

_CONFIG環境變數非空; 4)/etc/resolv.conf或/etc/nsswitch.conf指定的使用方式GO解析器沒有實現;  5) 當要解

析的網域名稱以.local結束, 或者是一個mDNS網域名稱

可以通過GODEBUG環境變數來設定go語言的預設DNS解析方式 純go或cgo,
export GODEBUG=netdns=go    # force pure Go resolver 純go 方式
export GODEBUG=netdns=cgo   # force cgo resolver   cgo 方式
也可以在編譯時間指定netgo或netcgo的編譯tag來設定
在plan 9中 網域名稱解析只能通過 /net/cs和 /net/dns

在windows中 網域名稱解析只能通過windows提供的C標準庫函數GetAddrInfo或DnsQuery

OK 官方說明看完了, 我們寫一個例子試一下

package mainimport ("net""fmt""os")func main() {ns, err := net.LookupHost("www.baidu.com")if err != nil {fmt.Fprintf(os.Stderr, "Err: %s", err.Error())return}for _, n := range ns {fmt.Fprintf(os.Stdout, "--%s\n", n) }}


使用strace命令分析一下, 系統調用過程

openat(AT_FDCWD, "/etc/hosts", O_RDONLY|O_CLOEXEC) = 3read(3, "127.0.0.1   localhost localhost."..., 4096) = 158read(3, "", 3938)                       = 0read(3, "", 4096)                       = 0close(3)                                = 0//讀取本地dns server 配置stat("/etc/resolv.conf", {st_mode=S_IFREG|0644, st_size=104, ...}) = 0//建立UDP socket 發送準備發送DNS請求socket(PF_INET, SOCK_DGRAM|SOCK_CLOEXEC|SOCK_NONBLOCK, IPPROTO_IP) = 3setsockopt(3, SOL_SOCKET, SO_BROADCAST, [1], 4) = 0connect(3, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("172.16.1.3")}, 16) = 0epoll_create1(EPOLL_CLOEXEC)            = 4// 將UDP socket 加入到epoll中epoll_ctl(4, EPOLL_CTL_ADD, 3, {EPOLLIN|EPOLLOUT|EPOLLRDHUP|EPOLLET, {u32=2130514816, u64=140679489328000}}) = 0getsockname(3, {sa_family=AF_INET, sin_port=htons(57587), sin_addr=inet_addr("10.0.2.15")}, [16]) = 0getpeername(3, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("172.16.1.3")}, [16]) = 0//發送DNS請求write(3, "\363}\1\0\0\1\0\0\0\0\0\0\3www\5baidu\3com\0\0\34\0\1", 31) = 31futex(0x645c10, FUTEX_WAIT, 0, NULL)    = 0read(3, 0xc82007c000, 512)              = -1 EAGAIN (Resource temporarily unavailable)epoll_wait(4, {{EPOLLOUT, {u32=2130514816, u64=140679489328000}}, {EPOLLOUT, {u32=2130514624, u64=140679489327808}}}, 128, 0) = 2// epoll等待socket 事件epoll_wait(4, {{EPOLLIN|EPOLLOUT, {u32=2130514624, u64=140679489327808}}}, 128, -1) = 1futex(0x645680, FUTEX_WAKE, 1)          = 1read(5, "g\217\201\200\0\1\0\2\0\r\0\v\3www\5baidu\3com\0\0\1\0\1\300"..., 512) = 474epoll_ctl(4, EPOLL_CTL_DEL, 5, {0, {u32=0, u64=0}}) = 0close(5)                                = 0epoll_wait(4, {}, 128, 0)               = 0epoll_wait(4, {{EPOLLIN|EPOLLOUT, {u32=2130514816, u64=140679489328000}}}, 128, -1) = 1futex(0x645680, FUTEX_WAKE, 1)          = 1// 得到DNS解析結果read(3, "\363}\201\200\0\1\0\1\0\1\0\0\3www\5baidu\3com\0\0\34\0\1\300"..., 512) = 115epoll_ctl(4, EPOLL_CTL_DEL, 3, {0, {u32=0, u64=0}}) = 0close(3)                                = 0

著作權聲明:轉載請註明出處, 多謝 http://blog.csdn.net/mumumuwudi

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.