정말 메모리가 부족해?
linux를 운영할 때, 시스템의 free (여유)메모리가 부족하여 당황한 적이 있으셨을 텐데요,
정말 시스템의 메모리가 부족한 것인지 확인해 보겠습니다.
total used free shared buff/cache available
Mem: 7820 2000 50 200 5700 5800
Swap: 2048 0 2048
리눅스 커널은 여유 메모리 - 즉 놀고 있는 생산성 없는 메모리를 싫어합니다.
따라서 리눅스 커널은 놀고 있는 메모리를 디스크 캐싱에 활용하므로 시스템을 훨씬 더 빠르고 반응성 있게 만듭니다.
위 free -m 명령 출력에서 주목할 점은 7번째 열의 available 항목이 cache/buffer가 포함된 시스템에서 사용 가능 메모리입니다.
따라서 free 항목의 메모리 값이 낮다고 시스템에 메모리가 부족한 것이 아닙니다.
성능향상 목적을 위해 디스크 캐시를 포함한 가용 메모리를 확보하려는 리눅스 커널의 메모리 방식 입니다.
Available memory:
새로운 프로세스가 사용할 수 있는 실제 가용 메모리
free + 일부 buff/cache(회수가능) + 일부 used 의 개념 -> 시스템의 총 가용 메모리
* 일부 used 메모리에서도 회수가 가능한데, 이는 프로세스에게 메모리를 할당했지만 실제 사용중이지 않는 메모리 일부를 회수할 수 있음.
만약 더 많은 애플리케이션을 실행하려면 어떻게 해야 하나요?
만약 이 상태에서 여유메모리가 없다고 애플리케이션이 추가적인 메모리를 요청하면 현재 구동중인 다른 AP에서 메모리를 빼았느냐? 그렇지 않습니다.
이런 경우 커널은 기존에 활용했던 캐시를 자동으로 해제하고 애플리케이션에 메모리를 제공합니다.
즉 디스크 캐싱 명목의 메모리는 남는 메모리를 효율적으로 사용하고 있을 뿐, 애플리케이션이 필요하면 언제든지 해제가 가능합니다.
스왑이 더 필요한가요?
아니요 - 대부분의 경우 그렇지 않습니다.
디스크 캐싱은 주로 애플리케이션이 현재 원하지 않는 메모리를 빌립니다.
애플리케이션이 당장 필요하지 않은 메모리를 "빌려서" 디스크 캐시로 활용되어집니다.
하지만 애플리케이션이 메모리가 필요하면, 커널이 디스크 캐시를 줄여서 메모리를 다시 돌려줍니다.
즉, 캐시는 빌려 쓰는 개념이므로 무작정 스왑 확장을 고려하지 않아도 됩니다.
그렇다면 언제 스왑을 사용해요?
진정으로 메모리가 부족한 경우 커널은 메모리 압력을 감지하고, 이에 따라 스왑 영역을 사용할지를 결정합니다.
스왑 사용의 기준은 평소 성능명목으로 사용되었던 익명의 메모리(anonymous 메모리)중 최근 사용이 뜸했던 비 주류의(inactive memory) anon 메모리를 스왑으로 보낸다는(swap out) 것입니다.
익명의 메모리의 개념을 살펴보겠습니다.
Anonymous memory
스왑 공간으로 swap out 되는 대상은 주로 익명의 메모리 (Anonymous 메모리)라고 합니다.
이는 파일과 연결되지 않은 메모리 영역을 의미합니다. 즉 파일에서 로드된 게 아니라, 프로그램 실행 중에 동적으로 할당된 메모리입니다.
파일과 연결된 게 아니므로, 디스크에서 다시 읽을 방법이 없습니다. 따라서 이 anon memory는 swap 푸시의 대상이 됩니다.
file-backed memory
이와 다른 파일 기반의 캐시메모리는 file-backed 메모리라고 하며, 파일과 연결된 메모리입니다.
쉽게 말해 디스크에서 데이터를 읽어 메모리에 상주시켰다가 사용 빈도가 낮으면 다시 원래 자리였던 디스크로 이동시키는 것이지요.
즉 이 파일 기반의 캐시는 스왑 영역을 소비하지 않습니다.
메모리가 부족하게 될 경우 스왑영역으로 푸시되는 메모리의 절차를 생각해 보았습니다.
1. 가용메모리가(Available memory) 부족하면 커널이 스왑을 고려합니다.
2. 경우에 따라 익명메모리(Anonymous 메모리)가 스왑으로 이동하며 파일 캐시(file-backed 메모리)는 디스크로 바로 drop되어집니다.
3. 스왑으로 이동한 익명의 메모리는 RAM에서 해제됩니다. 나중에 해당 메모리가 필요하면 swap space에서 다시 메모리로 swap in 됩니다.
4. 마찬가지로 디스크로 drop된 파일 기반 캐시 메모리도 RAM에서 버려지게 되며 필요할 때 디스크에서 다시 로드되어 RAM에 적재됩니다.
따라서 덜 중요한 데이터를 스왑 또는 디스크로 내보내게 되면서 성능을 유지할 수 있습니다.
단, 잦은 swap in/out은 디스크 I/O와 CPU Overhead를 발생시켜 성능에 영향을 줄 수 있습니다.
swap을 무조건 사용하는건 좋은 것이 아닙니다.
진정으로 메모리가 부족하여 swap in/out이 자주 발생한다면 물리적인 RAM을 업그레이드 하는것이 권장됩니다.
또는 swappiness 커널 변수를 조절하므로서 swap을 적극적으로 사용할지 말지를 조절할 수 있습니다.
파일 기반 캐시메모리는 주로 "삭제(drop)"되고, 스왑 대상이 아닌 이유는?
파일 캐시는 디스크에 원본이 있기 때문에 스왑으로 보낼 필요가 없습니다.
- 스왑은 "RAM에서만 존재하는 데이터(익명 메모리)"를 보존하기 위해 사용하는 공간이므로, 파일 캐시는 보통 스왑으로 가지 않고 그냥 RAM에서 drop됩니다.
- 하지만, 일부 파일 캐시가 스왑으로 갈 수도 있습니다.
예를 들어 메모리 매핑된 파일(mmap()) 중 쓰기가 발생한 페이지는 dirty page가 되므로, 이 데이터는 디스크에 저장되지 않았다면 스왑으로 이동될 수도 있습니다.
그럼 언제 진정으로 메모리가 부족하다고 걱정해야 하나요?
충분한 메모리가 있는 건강한 리눅스 시스템은 매 실행시간 동안 다음과 같은 무해하고 예상된 동작을 보여줍니다.
1. free 칼럼의 값이 "0"에 가깝다.
2. available 메모리 (or "free + buffers/cache") 가 충분하다. (대략 총 메모리의 20%이상)
3. swap used가 변하지 않았다.
이와 반대로 메모리가 부족한 상황에서 경고하는 신호는 아래와 같습니다.
1. available 메모리 (or "free + buffers/cache") 가 "0"에 가깝다
2. swap used 가 증가하거나 변동되었다.
3. # dmesg | grep oom-killer 명령을 확인하였을떄 OutOfMemory-killer가 작동하는 모습을 보여줍니다.
이번 글에서는 시스템의 메모리의 상태를 확인해보는 방법과 함께, 리눅스의 메모리 관리 방식과 스왑(Swap)사용 여부에 대해 학습해 보았습니다.
OS의 메모리 관리 방식은 매우 복잡하지만, 꾸준한 관심을 가지고 하나씩 이해해 나가 다 보면 좀 더 깊이 있는 지식을 습득 할 수 있을 것이라 생각합니다.
글 작성에 많은 참고가 되었던 사이트입니다.
https://www.linuxatemyram.com/
Help! Linux ate my RAM!
Don't Panic!Your ram is fine! What's going on? Like all modern operating systems, Linux is borrowing unused memory for disk caching. This makes it look like you are low on "free" memory, but you are not! Everything is fine! Why is it doing this? Disk cachi
www.linuxatemyram.com