- Published on
리눅스 디스크 100%? du 느릴 때 찾는 법
- Authors
- Name
- 스타차일드
- https://x.com/ETFBITX
운영 중인 리눅스 서버에서 갑자기 디스크 사용량이 100%에 가까워지면 보통 가장 먼저 df와 du를 떠올립니다. 그런데 문제는, 정작 원인을 찾으려고 du를 돌리면 너무 느리거나(수십 분~수 시간), I/O를 더 악화시켜 서비스까지 흔들리는 상황이 자주 발생한다는 점입니다.
이 글은 “df는 100%라고 하는데 du가 느리거나 결과가 안 맞는다”는 전형적인 케이스에서, 시간을 아끼면서도 실수를 줄이는 진단 루트를 단계별로 정리합니다. 특히 네트워크 스토리지(EFS/NFS), 컨테이너 런타임, 삭제됐지만 열린 파일, inode 고갈 같은 함정을 함께 다룹니다.
참고: 쿠버네티스/EKS 환경에서 스토리지 마운트 이슈가 의심된다면 EKS에서 Pod는 뜨는데 EFS Mount 타임아웃 해결 글도 같이 보면 원인 분리가 빨라집니다.
1) 먼저 “무엇이 100%인가”를 분리하기
디스크 100%라고 할 때 실제로는 세 가지 중 하나인 경우가 많습니다.
- 블록 사용량(용량) 100%:
df -h - inode 100%:
df -i - I/O가 100%처럼 보임(지연 폭증):
iostat,pidstat등
가장 먼저 아래를 실행해 “용량 문제인지, inode 문제인지”부터 분리하세요.
# 용량(블록) 사용량
df -hT
# inode 사용량
df -i
df -hT에서 특정 마운트가 100%면 그 파일시스템 내부를 추적하면 됩니다.df -i가 100%면 “작은 파일이 너무 많다”가 핵심이고,du -h로는 감이 잘 안 옵니다(용량은 작을 수 있음).
2) df와 du가 안 맞는 1순위: 삭제됐지만 열린 파일
가장 흔한 함정입니다.
- 로그 파일을 지웠는데도
df는 줄지 않는다 du로는 큰 파일이 안 보인다
원인은 프로세스가 파일 핸들을 잡고 있는 상태에서 파일이 삭제(unlink)된 경우입니다. 공간은 여전히 점유되지만 디렉터리 트리에서는 사라져 du가 못 봅니다.
아래로 빠르게 확인합니다.
# 삭제됐지만 열린 파일 찾기
sudo lsof +L1
# 용량 큰 순으로 보고 싶으면(파일 크기 컬럼이 환경마다 다름)
sudo lsof +L1 | head -n 50
자주 나오는 패턴:
java,node,python,nginx,mysqld가 오래 떠 있고 로그 로테이션이 꼬인 경우- 컨테이너 로그가 런타임에 의해 잡혀 있는 경우
해결은 보통 “프로세스 재시작”이 가장 확실합니다(서비스 영향 고려). 로깅 설정을 고치는 것이 근본 해결이고, DB라면 재시작 전 체크리스트가 필요합니다.
3) du를 느리게 만드는 주범: 마운트 경계와 네트워크 파일시스템
du가 느린 이유는 단순합니다. 기본적으로 디렉터리를 전부 순회하며 stat를 때립니다. 파일 수가 많거나, 원격/NFS/EFS처럼 메타데이터 호출이 비싼 스토리지면 폭발적으로 느려집니다.
여기서 핵심은 “내가 보고 싶은 파일시스템만 보게” 제한하는 것입니다.
3-1) 반드시 -x로 파일시스템 경계 고정
# 루트(/) 기준으로 다른 마운트로 넘어가지 않게 제한
sudo du -xhd 1 / | sort -h
-x는 다른 파일시스템으로 넘어가지 않습니다./proc,/sys,/run,/var/lib/kubelet/pods같은 곳에 다른 마운트가 섞여 있으면du가 헛수고를 많이 합니다.
3-2) 깊이를 제한해서 “큰 가지”부터 자르기
# 1단계: 최상위 디렉터리만
sudo du -xhd 1 / | sort -h
# 2단계: 의심 디렉터리만 더 깊게
sudo du -xhd 1 /var | sort -h
sudo du -xhd 1 /var/lib | sort -h
이 방식은 느린 환경에서 특히 효과적입니다. 한 번에 / 전체를 깊게 보지 말고, 큰 디렉터리부터 단계적으로 내려가세요.
4) du가 너무 느릴 때 쓰는 “대체 스캐너”들
du가 느린 상황은 보통 “파일이 너무 많다” 또는 “스토리지가 느리다”입니다. 이때는 목적에 따라 다른 도구가 더 빠릅니다.
4-1) 큰 파일만 빨리 찾기: find로 사이즈 필터
du는 전체를 다 보지만, 우리는 보통 “큰 놈” 몇 개만 잡으면 해결되는 경우가 많습니다.
# 1GB 이상 파일만 찾기(다른 파일시스템 제외)
sudo find / -xdev -type f -size +1G -printf '%s %p\n' 2>/dev/null | sort -n | tail -n 50
-xdev는du -x와 같은 의미로 마운트 경계를 넘지 않습니다.2>/dev/null로 권한 에러를 조용히 넘깁니다.
4-2) inode 문제면: “파일 개수”를 세는 쪽이 빠르다
inode 100%일 때는 용량이 아니라 파일 개수 분포가 중요합니다.
# 디렉터리별 파일 개수(대략) 파악
sudo find /var -xdev -type f 2>/dev/null | awk -F/ '{print "/"$2"/"$3}' | sort | uniq -c | sort -n | tail -n 30
정밀한 리포트가 아니라 “어느 트리가 파일을 쏟아내는지”를 빠르게 보는 용도입니다.
4-3) ext 계열이면 ncdu가 체감상 가장 편하다
터미널 UI로 탐색하며 큰 디렉터리를 바로바로 파고들 수 있습니다.
# 설치(배포판별로 다름)
# Debian/Ubuntu
sudo apt-get update && sudo apt-get install -y ncdu
# RHEL/CentOS/Amazon Linux 계열
sudo yum install -y ncdu
# 마운트 경계 제한해서 실행
sudo ncdu -x /
ncdu도 결국 스캔은 하지만, 사람이 “의심 구간만 더 본다”는 흐름으로 전환하기 좋아서 운영에서 시간을 많이 아낍니다.
5) 디스크 100%인데 du 합계가 작다: 스냅샷/예약/메타데이터/오버레이 확인
5-1) 파일시스템 예약 블록(reserved blocks)
ext4는 루트용으로 일부 블록을 예약합니다. 작은 디스크에서는 이게 크게 체감될 수 있습니다.
# ext4 예약 블록 비율 확인
tune2fs -l /dev/sdXN | grep -E 'Reserved block count|Block count|Reserved block percentage'
예약을 줄이는 건 신중해야 합니다(운영 정책에 따라 다름).
5-2) LVM 스냅샷/Thin pool
LVM thin pool이 가득 차면 갑자기 쓰기 실패가 납니다.
sudo lvs
sudo vgs
sudo pvs
스냅샷이 쌓여 있거나 thin pool이 포화인지 확인하세요.
5-3) 컨테이너 환경: overlay2가 “진짜 범인”인 경우
도커/컨테이너d는 이미지/레이어/로그가 /var/lib 아래에 쌓입니다.
# 도커면
sudo docker system df
sudo docker ps --size
# 컨테이너d/쿠버네티스면(환경에 따라 경로 상이)
sudo du -xhd 1 /var/lib | sort -h
특히 다음이 흔합니다.
- 이미지가 계속 쌓이는데 GC가 안 됨
- 애플리케이션 로그를 파일로 쌓고 로테이션이 없음
/var/log/containers,/var/log/pods가 폭증
6) “느림” 자체가 문제일 때: I/O 병목을 먼저 확인
디스크가 100% 찼다는 것과 별개로, du가 느린 이유가 “디스크가 이미 죽어가고 있음”일 수 있습니다. 이 경우 원인 탐색 커맨드가 오히려 장애를 키웁니다.
아래로 I/O 상태를 먼저 봅니다.
# iostat(없으면 sysstat 설치)
iostat -xz 1 10
# 어떤 프로세스가 I/O를 먹는지
pidstat -d 1 10
await가 높고util이 지속적으로 높으면 스토리지 병목입니다.- 이때는 무턱대고 전체
du스캔을 돌리기보다, 3번의 “깊이 제한” 또는 4-1의 “큰 파일만” 같은 저부하 접근이 안전합니다.
7) 실전 진단 루트(체크리스트)
운영에서 바로 써먹는 순서로 정리하면 다음이 가장 실패가 적습니다.
df -hT로 100%인 마운트 식별df -i로 inode 100% 여부 확인lsof +L1로 삭제됐지만 열린 파일 확인(불일치 문제 최우선)du -xhd 1로 큰 디렉터리부터 단계적으로 좁히기find / -xdev -type f -size +1G로 큰 파일 상위 N개 추출- 컨테이너/런타임(
/var/lib)과 로그(/var/log) 집중 확인 - 여전히 이상하면 LVM 스냅샷/thin, 예약 블록, 파일시스템 오류(필요 시 점검)로 확장
8) 예시: du가 30분 넘게 걸릴 때의 “안전한” 커맨드 세트
아래는 서비스 영향 최소화 관점에서 자주 쓰는 조합입니다.
# 0) 어디가 찼나
df -hT
# 1) inode도 같이
df -i
# 2) du는 깊이 1로만, 파일시스템 경계 고정
sudo du -xhd 1 / | sort -h
# 3) /var가 크면 한 단계 더
sudo du -xhd 1 /var | sort -h
# 4) 큰 파일만 빠르게
sudo find /var -xdev -type f -size +500M -printf '%s %p\n' 2>/dev/null | sort -n | tail -n 30
# 5) df/du 불일치 의심 시(특히 로그 삭제 후)
sudo lsof +L1 | head -n 50
9) 마무리: “빨리 찾는 법”의 핵심은 스캔 범위를 줄이는 것
du는 정직하지만, 운영 환경에서는 너무 정직해서 문제입니다. 느릴 때는 더 강하게 돌리는 게 아니라, -x로 마운트 경계를 고정하고 -d 1로 깊이를 제한해 큰 가지부터 잘라야 합니다. 그리고 df와 du가 안 맞으면 거의 항상 lsof +L1로 해결 실마리가 나옵니다.
스토리지가 네트워크(EFS/NFS)거나 쿠버네티스 마운트가 얽혀 있다면, “용량 문제”와 “마운트/지연 문제”가 함께 나타날 수 있습니다. 그런 경우에는 스토리지/마운트 경로 자체의 장애 신호도 같이 확인하는 것이 전체 복구 시간을 줄입니다.