全站域名化改造时撞上了一个意料之中的墙:这套引擎只认点分 IP。配置里把服务器地址从 120.53.236.19 换成 datanger.cn,客户端直接连不上——没有任何报错,就是静默失败。
根因:inet_addr 的 INADDR_NONE
两处连接点(登录网关与更新检测)都走同一条路径:
sockaddr_in addr;
addr.sin_addr.s_addr = inet_addr(host); // 域名 → INADDR_NONE (0xFFFFFFFF)
// 0xFFFFFFFF 恰好等于 255.255.255.255,connect 直接失败
inet_addr 解析失败返回 INADDR_NONE,而老代码从不检查这个返回值——静默失败的经典来源。补法很直接,在 CPipeState_Connecting 里加一层兜底:
u_long ip = inet_addr(host);
if (ip == INADDR_NONE) {
HOSTENT* he = gethostbyname(host);
if (he && he->h_addr_list[0])
ip = *(u_long*)he->h_addr_list[0];
else
return ConnectFailed(); // 明确失败,别静默
}
阻塞与线程边界
gethostbyname 是阻塞调用,风险在连接线程里的语义。这套引擎的连接状态机跑在独立线程里,卡几百毫秒可以接受;如果状态机在主循环里,就得换成异步解析或先解析后连接。改造前先确认线程模型,别盲抄。
改完的验收标准很朴素:netstat 里客户端只持有 datanger.cn 解析出的地址,ESTABLISHED 到 6000 端口,配置文件里再也找不到一个裸 IP。