🔌 第一章 浏览器生成消息
📄 一句话概括

解析器发出查询后原地等回信——应用程序整个【睡过去】;DNS 服务器回信写进解析器的内存,IP 从这里交回应用程序。

📝 本节和前面几节的关系

1.2.4 看了消息怎么发;本篇补上最后一块——等待期间程序内部发生了什么。

一、控制流的走法

应用程序调 gethostbyname 后,控制权交给解析器; 解析器发完查询就【停在那儿】等回信—— 对应用程序来说,就是这一行代码卡了一会儿。

二、回信放在哪

DNS 服务器把 IP 写进响应消息送回来, 解析器把它写进自己的内存区,再交回应用程序。

三、一个容易被忽略的点

解析器也是一段程序,它发消息同样要走协议栈—— 【翻译官自己也要寄信】,这是分层世界里常见的嵌套。

四、动手 Demo:解析器原地等回信

一条时间线看清谁在等、谁在跑:

for t, ev in [('t0','应用程序 -> gethostbyname(...)'),
             ('t1','解析器组查询消息,交协议栈发 UDP'),
             ('t2','解析器停在这里等回信'),
             ('t3','DNS 服务器回信,IP 写进内存'),
             ('t4','gethostbyname 返回,应用程序继续')]:
    print('%-4s %s' % (t, ev))

实跑输出:

--------------------------------------------------------------------
解析器原地等回信
--------------------------------------------------------------------
  控制流从应用程序一路交下去,谁在等、谁在跑:

    t0  应用程序 -> gethostbyname('www.lab.glb.com')
    t1  解析器组好查询消息,交协议栈发 UDP
    t2  解析器【停在这里】——控制权交还应用程序?不,
        是应用程序整个【睡过去】,等解析器带答案回来
    t3  DNS 服务器回信,IP 写进解析器的内存
    t4  gethostbyname 返回,应用程序醒来继续

  一句话:解析器替你跑腿,但你得等它——查 IP 这件事
  在应用程序看来就是【一行代码卡了一会儿才往下走】。

在 2026 年的系统里,这个等待通常还有超时与多服务器轮询: 第一台 DNS 不答就换下一台——教材限于篇幅没展开。

30 秒实验

  1. 写一行 Python,分别对存在和不存在的域名调 getaddrinfo,对比耗时。
  2. 把首选 DNS 改成一个不存在的地址,体验等待与切换。
  3. 想想:解析器等待期间,浏览器窗口是不是也【卡着】?为什么?

常见误区

  1. 以为解析器会【异步通知】——经典同步接口就是原地等。
  2. 以为解析器直接和 DNS 服务器说话——它也得经协议栈。
自测三问(点开对答案) 1. 解析器发出查询后在做什么? —— 原地等回信。 2. 回信里的 IP 先放在哪里? —— 解析器自己的内存区。 3. 应用程序视角下,查 IP 是什么体验? —— 一行代码卡一会儿才往下走。

相关笔记