OS/Linux

[Linux] 메모리 증가 확인 방법(pmap, ps, /proc/pid/status )

코끼리 개발자 2022. 5. 27. 16:56
728x90
SMALL
728x90

리눅스 환경에서 특정 프로세스의 메모리가 증가하는지 확인하는 방법 입니다.

C언어를 이용해서 모듈을 만들고 프로세스를 모니터링 할 때
메모리 누수가 있는지 확인할 때 사용했던 방법입니다.
RSS값을 통해 메모리 누수를 확인 할 수 있는데, RSS란 Resident Set Size이며 해당 프로세스에 할당되고 RAM에있는 메모리 양을 표시하는 데 사용됩니다.

우선 누수가 발생한 프로세스를 빌드하여 메모리를 모니터링 해 보겠습니다.

#include<stdio.h>
#include<stdlib.h>

void main()
{
        char *a = NULL;

        while(1)
        {
                a = (char *)malloc(sizeof(char)*10);
                sleep(1);
        }

}

코드는 위와 같이 간단히 무한반복문을 돌리며 malloc후 free를 해주지 않고 메모리 누수를 발생시켜보겟습니다.

gcc -o test test.c 커맨드로 빌드를 해 주고
모듈을 실행시켜줍니다.

모듈이 실행 되었다면 ps 커맨드를 이용해서 올라간 실행된 프로세스의 pid를 알아놓습니다.
ps -ef | grep test


메모리 누수를 발생시킬 준비가 끝났다면,
세 가지 방법을 통해 메모리 누수를 확인 해 보겠습니다.

첫번째는 pmap을 이용해서 확인하는 방법 입니다.
pmap 명령어는 프로세스 ID를 기준으로 메모리 맵을 출력하는 명령어 입니다.
간단하게 pmap에서 사용할 수 있는 옵션들을 정리 해 보자면 아래와 같습니다.

-x 확장된 포맷으로 출력합니다
-d 디스크 포맷을 출력합니다.
-q 정보를 간단하게 출력합니다.
-V 버전 정보를 출력합니다

이 중 -x 옵션을 사용해서 메모리 누수를 모니터링 해보도록 하겠습니다.
pmap -x [pid] 커맨드를 입력하면 아래와 같이 메모리 맵을 확인할 수 있는데
맨 아랫줄의 전체 통계 RSS 값을 모니터링하여 메모리가 누수되고있는지 확인 가능합니다.

pmap -x pid | tail -1 명령어를 사용해 원하는 주기로 모니터링 하면 되는데,
매번 커맨드를 치기는 너무 귀찮은 일이니까
while을 사용하여 1초마다 조회해보도록 하겠습니다
커맨드창에
while true; do pmap -x [pid] | tail -1; sleep 1; done
tail -1명령어는 입력한 커맨드 출력결과의 맨 마지막 줄을 출력한다는 명령어입니다.

위의 명령어 모두를 입력하면 1초주기로 같은 커맨드 결과값을 출력할 수 있습니다.

커맨드 결과를 보면 중간부터 RSS값이 472 -> 476으로 증가한 것을 확인할 수 있습니다.
메모리 할당을 할 때 메모리가 증가하는 것은 문제가 되지 않지만
사용하지 않을 때는 free를 해서 메모리를 해제시켜 주어야 하는데,
해제 시켜주지 않아 메모리의 양이
증가 -> 감소 -> 증가 -> 감소 가 아닌 지속적으로 증가가 일어난다면
어디선가 메모리 누수가 발생하고 있다는 것을 확인할 수 있죠..


두번째로는 ps 커맨드를 이용해서 누수를 모니터링 하는 방법이 있습니다.
ps 커맨드는 프로세스의 현재 상태를 출력해주는 커맨드입니다.
간단하게 ps 커맨드에서 사용할 수 있는 옵션들을 몇가지 정리 해 보자면 다음과 같습니다.

-e 커널프로세스를 제외한 모든 프로세스 출력
-f 풀 포맷으로 출력 (UID, PID 등)
-o 사용자가 지정한 포맷대로 출력
-p 특정 PID의 프로세스를 출력
-l 긴 포맷으로 출력
-u 특정 사용자의 프로세스를 출력

이중 -e옵션과 -o옵션을 가지고 메모리 누수를 모니터링 해 보도록 하겠습니다.
ps -eo "pid","rss" | grep [pid]
다음 커맨드에 모니터링 하고자 하는 프로세스의 pid값을 대입하여 모니터링 하면 됩니다
첫번째 방법과 동일하게 while문으로 지속적인 모니터링을 해 보도록 하겠습니다.
테스트 모듈을 실행시키고, pid를 확인합니다.
그 다음 [pid]부분에 대입 해 주시면 됩니다.
while true; do ps -eo "pid","rss" | grep [pid]; sleep 1; done

쭉 해당 커맨드를 실행 시켜 본 결과 다음과 같이 396 -> 660으로 증가 후 감소하지 않는 것을 확인할 수 있습니다.

 

SMALL



세번째 방법으로는 /proc/[pid]/status 파일에 출력된 RSS 값으로 메모리누수를 모니터링 하는 방법이 있습니다.
프로세스가 실행될 떄 마다 /proc/위치에 프로세스 아이디의 폴더가 생기는데, 그 안의 다양한 파일들로 여러가지를 확인할 수 있습니다.
그 중 status 파일로 메모리 누수를 확인할 수 있습니다.
일단 status 파일을 열어보면

다음과 같이 pid 정보, 프로세스의 상태 등 다양한 프로세스의 정보를 확인할 수 있는데 VmRSS을 모니터링하여 메모리 누수를 체크할 수 있습니다.
이 파일을 주기적으로 cat하여 메모리를 확인하면 되는데,
cat /proc/[pid]/status | grep VmRSS 커맨드를 사용하시면 되고,
주기적으로 모니터링하기 위하여 while문으로 1초마다 반복적으로 커맨드를 실행시켜 메모리 누수를 확인 해 보겠습니다.
while true; do cat /proc/[pid]/status | grep VmRSS; sleep 1; done

이번에도 동일하게 메모리가 증가한 후 감소되지 않는 것을 확인할 수 있습니다.

위에서 간단하게 메모리 누수를 발생시킬 프로그램으로 모니터링 했을 경우는 너무 작은경우라 메모리가 증가를 확인하기 까지 조금 시간이 소요되지만, 큰 프로세스에서는 확연하게 차이를 보실 수 도 있습니다.




728x90
LIST