티스토리 뷰

반응형

Docker를 사용하는 것을 넘어서 Docker의 원리와 엔진에 대한 구조까지 알고 있지만 시간이 지나다보니 기억이 흐릿해졌습니다. 서버나 리눅스 기반 플랫폼 직무면접에 나올 가능성이 많은 개념이기도 해서 오늘은 그래서 컨테이너 기술을 위한 핵심 기술인 리눅스의 namespace와 cgroup에 대해서 알아보도록 할 것인데요. 검색하시면 굉장히 많은 글들이 나오니, 핵심만 찍고 가도록 하겠습니다.  요약하면 독립적인 환경을 만들기 위해 namespace를 사용하고 cgroups(control groups)를 사용하여 자원의 할당 등을 관리합니다.

namespace

하나의 system에서 수행되지만, 각각 별개의 독립된 공간처럼 격리된 환경을 제공하는 lightweight 가상화 기술로, vm에서 쓰이는 hypervior는 hw resource를 가상화 하지만 namespace는 동일한 os, kernel에서 작동합니다. 한 덩어리의 데이터에 이름을 붙여 분할 함으로써 충돌 가능성을 줄이고, 쉽게 참조할 수 있게 하는 개념이며 이름과 연결된 실체는 그 이름이 어떤 이름 공간에 속해 있는 고유하게 정해집니다. 그래서 이름 공간이 다르면 동일한 이름이라도 다른 실체로 처리하게 되지요.

namespace 종류

  • mnt : 마운트 조작 시 namespace에서 격리된 파일 시스템 트리를 만든다.
  • pid : pid와 프로세스를 격리시키고, namespace가 다른 프로세스끼리 서로 엑세스 할 수 없다.
  • net : network 리소스의 관련된 정보를 분할(network interface, iptables 등), 호스트 os 상에서 사용 중인 포트가 있더라도 컨테이너 안에서 동일한 번호의 포트 사용 가능
  • ipc : 프로세스간 독립적인 통신통로 할당, IPC는 공유메모리, 세마포어 또는 메시지큐를 말한다.
  • uts : 독립적인 hostname 할당
  • user : uid, gid 분할 격리

linux namespace 구현 시에 사용되는 systemcall의 경우 clone(), nshare(), setns() 이며 namespace가 생성되면 /proc/<pid>/ns 에 6개의 inode entry가 생성됩니다.

cgroups (control groups)

Linux 커널 기능인 'control groups' 기능을 사용하여 컨테이너 자원 할당 등을 관리하며 프로세스는 하나 이상의 스레드를 가질 수 있습니다. cgroups는 프로세스와 스레드를 그룹화하여 그 그룹 안에 존재하는 프로세스의 스레드 관리를 수행하기 위한 기능입니다.

cgroups의 주요 서브시스템

  • cpu : CPU 사용량을 제한
  • cpuacct : CPU 사용량 통계 정보 제공
  • cpuset : CPU나 메모리 배치를 제어
  • memory : 메모리나 스왑 사용량 제한
  • devices : 디바이스에 대한 엑세스 허가/거부
  • freezer : 그룹에 속한 프로세스 정지/재게
  • net_cls : 네트워크 제어 태그를 부가
  • bikio : 블록 디바이스 입출력량 제어
  • ns : namespace 서브시스템

활용사례

  • runC, YARN(Hadoop), Android 등
  • ex) Android에서는 cgroup을 이용해서 어플리케이션을 foreground / background로 나누고 background의 CPU 점유율을 낮추고 있음
  • ex) 페이스북에서는 워크로드를 core workload, non-core services 등으로 나누고 cgroup을 지정하여 리소스를 관리

cgroup 종류

  • cgroupv1 : control 대상이 되는 리소스들을 기준으로 control 그룹들을 나눔
  • cgroupv2 : control 대상이 되는 워크로드들을 기준으로 control 그룹들을 나눔

cgroups는 계층 구조를 사용하여 프로세스를 그룹화하여 관리할 수 있습니다. 예를 들어 사용자 어플리케이션과 서버와 같은 데몬 프로세스를 나눠, 각각의 그룹에 CPU 사용량을 할당할 수 있습니다. cgroups의 부모 자식 관계에서는 자식이 부모의 제한을 물려받고 자식이 부모의 제한을 초과하는 설정을 하더라도 부모 cgroups의 제한에 걸리게 됩니다.

namespace vs cgroup

  • cgroup은 해당 프로세스가 쓸 수 있는 사용량을 제한한다.
  • namespaces는 해당 프로세스가 볼 수 있는 범위를 제한한다.

lxc, libContainer, runC 등은 cgroups와 namespaces를 표준으로 정의한 OCI(Open Container Initative) 스펙을 구현한 컨테이너 기술의 구현체이며 docker의 경우 1.8이전까지 lxc를 이용했고 현재는 libContainer->runC 로 자체 구현체를 가지고 릴리즈를 하고 있습니다.

반응형
댓글