가장 큰 열린 파일을 찾는 방법은 무엇입니까?

가장 큰 열린 파일을 찾는 방법은 무엇입니까?

프로세스에서 연 모든 파일 중에서 가장 큰 파일을 찾습니다. lsof이미 열려 있는 파일과 크기가 있습니다. 올바른 매개변수를 전달 lsof하고 출력을 처리할 수 있습니다.

답변1

정교한 방법은 다음과 같습니다.

lsof \
| grep REG \
| grep -v "stat: No such file or directory" \
| grep -v DEL \
| awk '{if ($NF=="(deleted)") {x=3;y=1} else {x=2;y=0}; {print $(NF-x) "  " $(NF-y) } }'  \
| sort -n -u  \
| numfmt  --field=1 --to=iec

산출

...
....
129M  /var/log/maillog
166M  /var/log/nginx/access_log
172M  /var/log/metrics/kubernetes/kubelet.log
185M  /var/log/metrics/kubernetes/etcd.log
257M  /var/log/metrics/kubernetes/etcd.log.1
335M  /var/log/metrics/kubernetes/kubelet.log.1

나는 그것이 완벽하지 않다는 것을 안다. 예를 들어, 파일 이름에 "DEL"이 포함되어 있으면 출력 목록에서 파일이 지워집니다. 에 설명된 옵션 lsof도 있습니다 .-F다른 프로그램의 출력부분. 사용하는 것이 더 간단할 수도 있습니다.

세부 사항

lsof다음과 같이 인쇄하십시오.

COMMAND      PID    TID           USER   FD      TYPE             DEVICE  SIZE/OFF       NODE NAME
systemd        1                  root  cwd       DIR              253,0      4096        128 /
tuned       2975                  root    7u      REG              253,0      4096  805307770 /tmp/ffiKkVeXD (deleted)
python2    49888  49890           root  DEL       REG               0,18            196039884 /dev/shm/sem.NXPFow
systemd        1                  root  mem       REG              253,0     90664      10063 /usr/lib64/libz.so.1.2.7
java      149435 175229            box   69r      REG              253,0 350872273  808108999 /box/var/log/metrics/kubernetes/kubelet.log.1
java      149435 149580            box  107w     FIFO                0,8       0t0  272526226 pipe
prometheu 147867 148211           root  mem       REG              253,6             31457463 /lib64/ld-2.12.so (stat: No such file or directory)

grep REG일반 파일 보관


grep -v "stat: No such file or directory"통계 오류가 있는 파일을 삭제합니다. (왜 이런 일이 발생하는지 모르겠습니다)


grep -v DEL삭제된 Linux 매핑 파일을 삭제합니다.

lsof에서문서:

'DEL''은 삭제된 Linux 매핑 파일을 나타냅니다.


이 처리 후에는 다음과 같은 결과를 얻습니다.

tuned       2975                  root    7u      REG              253,0      4096  805307770 /tmp/ffiKkVeXD (deleted)
systemd        1                  root  mem       REG              253,0     90664      10063 /usr/lib64/libz.so.1.2.7
java      149435 175229            box   69r      REG              253,0 350872273  808108999 /box/var/log/metrics/kubernetes/kubelet.log.1

크기는 마지막 열의 값에 따라 아래쪽에서 세 번째 또는 두 번째 열입니다. 마지막 열이 (deleted)마지막에서 세 번째 열을 선택하는 경우 그렇지 않으면 두 번째 열을 선택합니다.

awk '{if ($NF=="(deleted)") {x=3;y=1} else {x=2;y=0}; {print $(NF-x) " " $(NF-y) } }'


sort -n -u | numfmt --field=1 --to=iec

바이트 수를 정렬, 고유화 및 사람이 읽을 수 있도록 설정

답변2

-F옵션을 사용하여 lsof얻을 수 있습니다 .중간 정도의 통증만 있는 기계로 구문 분석할 수 있는 거의 명확한 출력. lsof파일 이름의 줄 바꿈 이 \n.

출력에는 lsof한 줄에 하나의 필드가 포함됩니다. 각 이름의 첫 번째 문자는 필드 유형을 나타내고 줄의 나머지 부분은 필드 값을 나타냅니다. 필드는 p=PID(주어진 프로세스의 첫 번째 설명자에만 적용됨), f=descriptor, t=type( REG일반 파일의 경우 크기가 있는 유일한 유형), s=size(사용 가능한 경우에만), n=name입니다. 다음 awk 코드는 크기가 있는 항목을 수집하고 크기와 파일 이름을 인쇄합니다. 나머지 파이프라인은 출력을 정렬하고 가장 큰 크기의 항목을 유지합니다.

lsof -Fnst | awk '
    { field = substr($0,1,1); sub(/^./,""); }
    field == "p" { pid = $0; }
    field == "t" { if ($0 == "REG") size = 0; else next; }
    field == "s" { size = $0; }
    field == "n" && size != 0 { print size, $0; }
' | sort -k1n -u | tail -n42 | sed 's/^[0-9]* //'

답변3

다음을 수행할 수 있습니다.

lsof | grep REG | awk '{ print $1,$7,$9 }' | sort -t ' ' -k 2 -V

awk를 사용하여 명령, 크기 및 파일 이름을 포함하도록 출력을 필터링하고 두 번째 열인 크기를 기준으로 정렬합니다. -티구분자를 지정하고,-V"자연스러운" 순서 - 따라서 1, 10, 2가 아닌 1, 2, 10이 이런 방식으로 정렬됩니다.-케이정렬할 키(정렬하려는 열)입니다.

관련 정보