Linux本身不带DNS缓存,偶发超时是因直连上游DNS无缓存导致;nscd是最轻量的libc层缓存方案,需正确配置enable-cache hosts yes等参数,并验证其对getaddrinfo生效。

Linux 本身不带 DNS 缓存,所谓“DNS 解析偶尔超时假死”,大概率是每次请求都直连上游 DNS(比如 114.114.114.114 或 8.8.8.8),遇到网络抖动、上游响应慢或丢包,getaddrinfo() 就卡住几秒甚至更久——这不是 bug,是没缓存的正常表现。加 nscd 是最轻量、侵入性最小的本地缓存方案,但配置不当反而会让问题更隐蔽。
确认 nscd 确实能解决你的问题场景
nscd 缓存的是 gethostbyname()、getaddrinfo() 这类 libc 接口的解析结果,对 curl/wget/浏览器等大多数命令行和应用有效;但它不拦截 /etc/resolv.conf 的 DNS 请求流向,也不影响 systemd-resolved 或 dnsmasq 的行为。如果你的超时发生在容器内、或程序显式调用 resolvconf、或已启用 systemd-resolved,nscd 可能完全不生效。
- 先验证是否真走 libc:运行
strace -e trace=getaddrinfo,gethostbyname curl -I google.com 2>&1 | head -5,看是否有系统调用输出 - 检查是否已有冲突服务:
systemctl is-active systemd-resolved、ps aux | grep dnsmasq -
nscd对负向缓存(域名不存在)也生效,能显著减少 NXDOMAIN 频繁重试导致的假死
安装并启用 hosts 缓存(不是 dns 缓存)
nscd 默认只缓存 hosts 数据库(即 /etc/hosts 和 DNS 解析共用同一缓存开关),它没有独立的 dns 数据库类型——很多文档写的 enable-cache dns yes 是无效配置,会被忽略。真正起作用的是 enable-cache hosts yes,且必须配合 positive-time-to-live hosts 等参数。
Linux系统管理专家,覆盖12大模块:用户权限、SSH、存储、网络、systemd、防火墙、日志监控、备份恢复、TLS证书、Ansible、容器、IaC。提供配置、验证、加固、监控、备份、自动化、故障排查、回滚闭环。关键词:useradd、sudo、sshd_config、chmod、SEL...
- 安装:
sudo apt install nscd(Debian/Ubuntu)或sudo yum install nscd(RHEL/CentOS) - 编辑
/etc/nscd.conf,确保包含:enable-cache hosts yes positive-time-to-live hosts 300 negative-time-to-live hosts 20 suggested-size hosts 211 check-files hosts yes persistent hosts yes
- 不要动
threads或max-threads:默认值足够,调高反而易因锁竞争加剧假死
避免 nscd 自身成为新的单点故障
nscd 进程一旦卡住(如日志文件满、共享内存损坏),所有依赖它的解析都会 hang 住——这比没缓存还糟。必须限制其影响范围,并设法快速恢复。
- 启动前清空旧缓存:
sudo systemctl stop nscd && sudo rm -f /var/cache/nscd/* && sudo systemctl start nscd - 启用日志便于排查:
logfile /var/log/nscd.log+debug-level 1(仅调试时开,上线关) - 加 systemd 超时保护:在
/etc/systemd/system/nscd.service.d/override.conf中写:[Service] Restart=on-failure RestartSec=5 StartLimitIntervalSec=60
- 验证是否生效:
nscd -g查看hosts缓存统计,再用time getent hosts example.com测两次,第二次应明显快于第一次
为什么不用 systemd-resolved 或 dnsmasq?
因为它们解决的是不同层面的问题。systemd-resolved 拦截所有 getaddrinfo() 并接管整个解析链路,但会引入 stub resolver、LLMNR、多接口策略等复杂逻辑,调试困难;dnsmasq 是完整 DNS 服务器,需监听 53 端口、改 /etc/resolv.conf,容易与 NetworkManager 冲突。而 nscd 只做一层 libc 层缓存,不改网络栈、不争端口、不碰 resolv.conf,适合只想“让 getaddrinfo 快一点、稳一点”的运维场景——但前提是,你得接受它只缓存 libc 调用,对 Go/Python 自研 DNS 客户端或容器内 busybox wget 无效。
真正容易被忽略的点是:nscd 不缓存 DNS over TLS/HTTPS 查询,也不影响 dig 或 nslookup 的行为;你用这些工具测不到缓存效果,得用 getent hosts 或真实业务进程验证。

















