Docker 컨테이너 내부에 있는 호스트의 모든 디스크 마운트 지점에 연결해야 합니다. 마운트 정보는 파일에서 확인할 수 있지만 /proc/1/mounts
일부 운영 체제에서는 파일에 액세스할 수 없습니다.
Ubuntu에서 다음 명령을 실행하면 제대로 작동합니다.
docker run -it -v /proc/1/mounts:/tmp/mounts ubuntu:16.04
하지만 SELinux가 활성화된 CentOS에서는 /proc/1/mounts
파일을 마운트할 수 없습니다. 오류가 보고 됩니다 permission denied
.
나도 이것을 시도했지만 /etc/mtab
심볼릭 링크이므로 /proc/self/mounts
내용이 Docker 컨테이너 내부에서 변경됩니다.
호스트의 마운트 정보를 얻는 다른 방법이 있습니까 /proc/1/mounts
? 아니면 특정 SELinux 태그를 사용해야 합니까?
사용해 보았지만 docker run -it --privileged -v /proc/1/mounts:/tmp/mounts ubuntu:16.04
여전히 같은 오류가 발생합니다.
답변1
init 프로세스(pid 1)에 표시되는 설치가 엄격하게 요구되지 않고 docker 데몬에 표시되는 설치이면 충분하다고 가정합니다. 일반적으로 동일한 마운트 네임스페이스를 가져야 합니다.
CentOS 도커 패키지 답변
(CentOS 저장소의 docker 1.13.1 사용)
을 사용하여 문제를 재현할 수 있습니다 /proc/1/mounts
. 그러나 docker 데몬의 마운트 파일을 사용하면 다음을 수행할 수 있습니다.
$ docker run -it -v /proc/$(pidof dockerd-current)/mounts:/tmp/mounts ubuntu:16.04
Docker 컨테이너에서 /tmp/mounts
호스트의 마운트를 나열합니다.
Docker 커뮤니티 에디션 답변
(외부 docker-ce 18.09.5 패키지 사용여기에 명시된 바와 같이)
위에서 설명한 문제 외에도 이 docker-ce
패키지에는 서비스의 SE Linux 컨텍스트와 관련된 문제도 있습니다 containerd
.
# ps xZ | grep containerd
system_u:system_r:unconfined_service_t:s0 5695 ? Ssl 0:00 /usr/bin/containerd
...
우리는 태그 대신에 containerd
유형을 사용하고 싶습니다 . 이렇게 하려면 레이블을 업데이트해야 합니다(container_runtime_t
unconfined_service_t
/usr/bin/containerd
일반 참조):
# ls -Z /usr/bin/dockerd-ce
-rwxr-xr-x. root root system_u:object_r:container_runtime_exec_t:s0 /usr/bin/dockerd-ce
# ls -Z /usr/bin/containerd
-rwxr-xr-x. root root system_u:object_r:bin_t:s0 /usr/bin/containerd
# semanage fcontext -a -t container_runtime_exec_t /usr/bin/containerd
# restorecon /usr/bin/containerd
# ls -Z /usr/bin/containerd
-rwxr-xr-x. root root system_u:object_r:container_runtime_exec_t:s0 /usr/bin/containerd
다음으로 containerd
데몬을 다시 시작합니다.
# systemctl daemon-reload
# systemctl restart containerd
# ps xZ | grep containerd
system_u:system_r:container_runtime_t:s0 6557 ? Ssl 0:00 /usr/bin/containerd
이제 위와 동일한 기술을 사용하여 도커 컨테이너를 시작할 수 있습니다( dockerd
대신 사용 dockerd-current
).
$ docker run -it -v /proc/$(pidof dockerd)/mounts:/tmp/mounts ubuntu:16.04
배경 정보
CentOS Linux 버전 7.6.1810에서 이것을 테스트했습니다.
init 및 docker 데몬이 동일한 마운트 네임스페이스를 가지고 있는지 확인할 수 있습니다(즉, 해당 /proc/[pid]/mounts에 동일한 마운트가 표시됨).
# readlink /proc/1/ns/mnt /proc/$(pidof dockerd-current)/ns/mnt
mnt:[4026531840]
mnt:[4026531840]
또한 SE Linux가 활성화되어 있는지 확인했습니다.
# getenforce
Enforcing
CentOS 패키지를 사용하여 명령을 실행할 때 docker
다음 오류 메시지가 나타납니다.
$ docker run -it -v /proc/1/mounts:/tmp/mounts ubuntu:16.04
/usr/bin/docker-current: Error response from daemon: oci runtime error: container_linux.go:247: starting container process caused "container init exited prematurely".
또한 /var/log/audit/audit.log
다음과 같은 AVC 위반이 표시됩니다.
type=AVC msg=audit(1555530383.707:214): avc: denied { mounton } for pid=5691 comm="runc:[2:INIT]" path="/var/lib/docker/overlay2/8944062749f8ad19c3ff600e1d5286315227378174b95a952e7b0530927f4dcd/merged/tmp/mounts" dev="proc" ino=45422 scontext=system_u:system_r:container_runtime_t:s0 tcontext=system_u:system_r:init_t:s0 tclass=file permissive=0
이는 SE Linux 규칙이 'init_t' 유형의 대상 컨텍스트를 '마운트'하기 위해 'container_runtime_t' 유형의 소스 컨텍스트를 허용하지 않음을 알려줍니다. 이것이 컨텍스트 /proc/1/mounts
이고 컨텍스트가 /proc/$(pidof dockerd-current)/mounts
일치하는지 확인할 수 있습니다.
# ls -Z /proc/1/mounts /proc/$(pidof dockerd-current)/mounts
-r--r--r--. root root system_u:system_r:init_t:s0 /proc/1/mounts
-r--r--r--. root root system_u:system_r:container_runtime_t:s0 /proc/5476/mounts