{"id":"IL-0048","org":"unknown","date":"2025-08-12","docs":["https://cep.dev/posts/eks-dns-timeouts-sudo-hostname-lookups/"],"title":{"en":"DNS lookups timed out in a large EKS cluster when CoreDNS hit the 1024 packets-per-second link-local limit, driven by sudo hostname lookups","ko":"대형 EKS 클러스터에서 CoreDNS 가 VPC DNS 리졸버로 보내는 질의가 링크 로컬 트래픽의 초당 1024 패킷 한도에 걸려 DNS 조회가 간헐적으로 타임아웃됐다."},"domain":["kubernetes","aws","networking"],"impact":{"scope":"DNS resolution in a very large EKS cluster, seen as intermittent CI failures","users":"unknown","region":"us-east-2, per the hostnames quoted in the post"},"review":{"written_by":"session","reviewed_at":null,"reviewed_by":null},"lessons":{"en":"Traffic from CoreDNS to the VPC DNS resolver is limited to 1024 packets per second per interface, and drops show up only as UDP timeouts; the linklocal_allowance_exceeded counter in ethtool shows them. Names that are not fully qualified are multiplied by the search domains under ndots:5, and AAAA lookups double them again. sudo looks up the host's own name on every call unless 'Defaults !fqdn' is set.","ko":"EC2 에서 링크 로컬 주소로 가는 VPC DNS 질의에는 초당 1024 패킷의 한도가 있다. 한도를 넘은 UDP 패킷은 버려지는데, 보낸 쪽은 이를 알 수 없다. 노드에서 ethtool -S eth0 | grep linklocal_allowance_exceeded 로 이 한도에 걸렸는지 볼 수 있다. ndots:5 와 검색 도메인 때문에 FQDN 이 아닌 이름 하나가 질의 다섯 번이 되고, AAAA 까지 물으면 열 번이 된다. sudo 는 기본 설정에서 실행할 때마다 호스트 이름을 조회하므로, sudo 를 자주 부르는 파드는 DNS 트래픽을 많이 만든다."},"related":[],"sources":[{"url":"https://medium.com/@cep21/my-process-to-debug-dns-timeouts-in-a-large-eks-cluster-9f731bd5617d","kind":"blog","license":"unknown","archived":"https://web.archive.org/web/20250821234026/https://medium.com/@cep21/my-process-to-debug-dns-timeouts-in-a-large-eks-cluster-9f731bd5617d"}],"summary":{"en":"Jack Lindamood describes an investigation in a very large AWS EKS cluster. Intermittent DNS failures in CI were traced to CoreDNS forwarding too many uncached queries to the VPC's Route 53 Resolver. Traffic to that resolver goes to a link-local address, and EC2 drops packets above 1024 per second on such traffic per network interface; the linklocal_allowance_exceeded counter in ethtool confirmed the drops.\n\nPacket captures showed that most of the uncached traffic was for EC2-style hostnames, each queried five times. Pods get a resolv.conf with ndots:5 and four search domains (app-namespace.svc.cluster.local, svc.cluster.local, cluster.local, us-east-2.compute.internal), so any name with fewer than five dots is first tried with every search domain appended. The query pattern revealed the namespace and that the source pod used host networking, which led to one administrative pod that issued A and AAAA queries for its node's hostname every few seconds.\n\nBy cutting parts of the pod's main loop, the author narrowed the traffic down to a few subprocess calls that ran commands with sudo. Running the same commands without sudo produced no DNS traffic. An ltrace of sudo showed libsudo_util.so calling gethostname and sudoers.so calling getaddrinfo on the node's hostname, so sudo itself made the lookups because of its fqdn default. Adding 'Defaults !fqdn' to the container image stopped the lookups, and uncached DNS queries to the VPC resolver almost disappeared.","ko":"글쓴이의 팀은 아주 큰 AWS EKS 클러스터를 운영한다. CI 가 간헐적으로 실패한다는 보고를 따라가 보니 DNS 조회 실패였다. CoreDNS 로그에는 VPC 의 Route 53 리졸버로 보낸 UDP 질의가 i/o timeout 으로 끝난 기록이 남아 있었다.\n\nAWS 지원 케이스로 첫 번째 원인을 찾았다. 링크 로컬 주소를 쓰는 서비스에는 ENI 마다 초당 1024 패킷의 한도가 있다. CoreDNS 는 UDP 로 질의를 링크 로컬 주소의 Route 53 리졸버에 보낸다. 한도를 넘은 패킷은 버려지고, UDP 는 연결이 없는 프로토콜이라 보낸 쪽은 패킷이 버려진 줄 모른 채 타임아웃을 맞는다. 영향을 받은 노드에서 linklocal_allowance_exceeded 값이 0 이 아니었다.\n\nCoreDNS 가 도는 노드에서 tcpdump 로 DNS 트래픽을 잡아 많이 나온 이름을 세어 보니, 호스트 이름처럼 생긴 질의가 롱테일을 이루고 있었다. 이름마다 검색 도메인이 붙은 질의가 다섯 번씩 나왔다. 파드의 /etc/resolv.conf 에는 검색 도메인 네 개와 options ndots:5 가 있었다. 점이 다섯 개보다 적은 이름은 FQDN 이 아닌 것으로 보고 검색 도메인을 하나씩 붙여 물어보므로, 질의 하나가 다섯 번이 되고 A 와 AAAA 를 합치면 열 번이 된다. 이런 질의는 CoreDNS 캐시에 걸리지 않아 그대로 VPC DNS 리졸버로 나갔다.\n\n질의에 붙은 검색 도메인으로 요청한 파드의 네임스페이스가 app-namespace 라는 것을 알았다. EC2 호스트 이름을 묻는 것으로 보아 호스트 네트워크를 쓰는 파드라고 짐작했다. 그 파드에서 tcpdump 를 돌리자 몇 초마다 노드 자신의 호스트 이름을 묻는 A 와 AAAA 질의가 나왔다. 파드의 주 루프 코드를 절반씩 잘라 내는 이진 탐색으로 원인을 sudo 호출 몇 개로 좁혔다. 같은 명령을 sudo 없이 실행하면 DNS 트래픽이 없었다. ltrace 로 보니 sudoers.so 가 getaddrinfo 로 호스트 이름을 조회하고 있었다. DNS 질의를 만든 쪽은 실행된 명령이 아니라 sudo 자신이었다.\n\n컨테이너 이미지에 Defaults !fqdn 을 넣어 sudo 의 호스트 이름 조회를 껐다. 그 뒤 캐시에 걸리지 않는 DNS 질의가 거의 모두 사라졌다."},"trigger":{"en":"An administrative pod running with host networking called sudo in a loop. Each sudo call looked up the node's own hostname, and with ndots:5 and four search domains every lookup became five queries, for both A and AAAA records.","ko":"호스트 네트워크를 쓰는 시스템 관리용 파드가 몇 초마다 sudo 명령을 실행했다. sudo 는 기본 설정에서 실행할 때마다 노드 자신의 호스트 이름을 조회했다. 파드의 resolv.conf 에 있는 ndots:5 와 검색 도메인 네 개 때문에 이 조회 하나가 A 와 AAAA 를 합쳐 질의 열 번이 됐고, CoreDNS 캐시에 걸리지 않은 질의가 VPC DNS 리졸버로 몰렸다."},"severity":"unknown","symptoms":["dns-resolution-failures","intermittent-timeouts"],"timeline":{"detected_after":null,"resolved_after":null},"date_kind":"published","detection":{"en":"Reports of flaky CI jobs that could not resolve an S3 bucket hostname, followed by i/o timeout errors in the CoreDNS logs.","ko":"CI 가 간헐적으로 실패한다는 보고가 시작이었다. tensorstore 가 company-bucket.s3.amazonaws.com 의 DNS 조회에 실패했다는 오류를 냈다. 글쓴이는 kubectl logs 로 CoreDNS 파드 로그를 뒤져 i/o timeout 오류를 찾았다."},"components":["coredns","dns-resolver","vpc-dns-resolver"],"root_cause":"capacity","remediation":[{"text":{"en":"added 'Defaults !fqdn' in /etc/sudoers.d/00-no-fqdn (mode 440) to the container image so sudo stopped looking up the hostname","ko":"컨테이너 이미지에 /etc/sudoers.d/00-no-fqdn 파일로 Defaults !fqdn 을 넣어 sudo 가 호스트 이름을 조회하지 않게 했다."}}],"action_items":[],"contributing":["limit-unknown","default-config-unchanged"],"recurrence_of":null,"symptoms_text":{"en":"CI jobs failed now and then because a hostname could not be resolved. The failures came from tensorstore, appeared on several different instances and did not repeat consistently. The error read: \"./tensorstore/util/result.h:420: Status not ok: status(): UNAVAILABLE: CURL error Could not resolve hostname: Could not resolve host: company-bucket.s3.amazonaws.com\".\n\nThe CoreDNS logs (kubectl logs -n kube-system deployment/coredns --tail=1000 | grep -i error) showed upstream queries timing out on the way to the VPC's Route 53 Resolver at the VPC+2 address, for example \"[ERROR] plugin/errors: 2 company-bucket.s3.amazonaws.com. A: read udp 10.1.2.3:44211->10.0.0.2:53: i/o timeout\". Most failing lookups were for internal hostnames such as ip-10-8-1-3.us-east-2.compute.internal, and many were AAAA queries, so every name was being looked up twice.\n\nAWS support pointed to a hard limit of 1024 packets per second for traffic to link-local services, which includes the VPC DNS resolver. Running ethtool -S eth0 | grep linklocal_allowance_exceeded on an affected node returned a non-zero count. Because DNS runs over UDP, CoreDNS never learned that packets were dropped; it only saw timeouts.\n\nA tcpdump of port 53 on a CoreDNS node showed, after the expected traffic, a long tail of host-name-like queries, each repeated with every search domain appended: ip-10-0-1-10.us-east-2.compute.internal.app-namespace.svc.cluster.local, ...svc.cluster.local, ...cluster.local, ...us-east-2.compute.internal.us-east-2.compute.internal, and finally the name itself. These were cache misses that CoreDNS forwarded to the VPC resolver.","ko":"처음 들어온 보고는 CI 가 간헐적으로 실패한다는 것이었다. 실패는 tensorstore 안에서 났고, 오류는 ./tensorstore/util/result.h:420: Status not ok: status(): UNAVAILABLE: CURL error Could not resolve hostname: Could not resolve host: company-bucket.s3.amazonaws.com 이었다.\n\n실패는 여러 인스턴스에서 일정하지 않게 났다. curl 의 CURLE_COULDNT_RESOLVE_HOST 는 너무 일반적인 오류여서 DNS 조회 로그를 직접 봐야 했다.\n\nCoreDNS 파드 로그에는 [ERROR] plugin/errors: 2 company-bucket.s3.amazonaws.com. A: read udp 10.1.2.3:44211->10.0.0.2:53: i/o timeout 같은 오류가 있었다. 10.1.2.3 은 CoreDNS 파드이고 10.0.0.2 는 VPC 의 Route 53 리졸버다. 실패한 조회는 대부분 ip-10-8-1-3.us-east-2.compute.internal 같은 내부 호스트 이름이었고, IPv6 주소를 묻는 AAAA 질의가 많았다. 보통은 IPv4 응답만 필요한데 A 와 AAAA 를 둘 다 물어서 트래픽이 두 배가 됐다.\n\nAWS 지원 케이스에서 링크 로컬 주소를 쓰는 서비스에는 초당 1024 패킷의 한도가 있고 이 한도는 올릴 수 없다는 답을 받았다. 영향을 받은 노드에서 AWS 가 알려 준 명령 ethtool -S eth0 | grep linklocal_allowance_exceeded 를 돌리자 0 이 아닌 값이 나왔다."},"updated_at":"2026-11-08T19:10:30.194994Z","url":"https://benchlet.com/incidentlib/app/cases/IL-0048","org_slug":"unknown"}