Docker 的 Seccomp 安全性設定檔

安全運算模式(seccomp)是一種 Linux 核心功能。您可以使用它來限制容器內可執行的動作。seccomp() 系統呼叫會對呼叫進程的 seccomp 狀態進行操作。您可以使用此功能來限制應用程式的存取權限。

此功能僅在 Docker 建置時包含 seccomp 且核心已啟用 CONFIG_SECCOMP 時才可用。若要檢查您的核心是否支援 seccomp

$ grep CONFIG_SECCOMP= /boot/config-$(uname -r)
CONFIG_SECCOMP=y

為容器傳遞設定檔

預設的 seccomp 設定檔為執行容器提供了合理的預設值,並禁用了 300 多個系統呼叫中的約 44 個。它在提供廣泛應用程式相容性的同時,具有中等程度的保護能力。Docker 的預設設定檔可以在這裡找到。

實際上,該設定檔是一個允許清單,預設會拒絕所有系統呼叫,隨後再開放特定的系統呼叫。其運作方式是將 defaultAction 定義為 SCMP_ACT_ERRNO,並僅針對特定系統呼叫覆寫該動作。SCMP_ACT_ERRNO 的效果是產生一個「拒絕存取」(Permission Denied) 錯誤。接著,設定檔定義了一份完全允許的系統呼叫清單,因為它們的 action 被覆寫為 SCMP_ACT_ALLOW。最後,針對某些個別系統呼叫(如 personality 等)設有特定規則,以允許在帶有特定參數的情況下執行這些變體呼叫。

seccomp 對於以最小權限執行 Docker 容器至關重要。不建議更改預設的 seccomp 設定檔。

當您執行容器時,除非您使用 --security-opt 選項覆寫它,否則它會使用預設設定檔。例如,以下明確指定了一個策略:

$ docker run --rm \
             -it \
             --security-opt seccomp=/path/to/seccomp/profile.json \
             hello-world

預設設定檔封鎖的重要系統呼叫

Docker 的預設 seccomp 設定檔是一個指定允許呼叫的清單。下表列出了因未包含在允許清單中而實際上被封鎖的重要(但非全部)系統呼叫。該表包含了每個系統呼叫被封鎖而非加入允許清單的原因。

系統呼叫 (Syscall)描述
acct帳戶統計系統呼叫,可能讓容器停用自身的資源限制或處理程序統計。同時受 CAP_SYS_PACCT 權限控管。
add_key防止容器使用未命名空間化的核心金鑰環。
bpf拒絕將潛在的持續性 BPF 程式載入核心,此操作已受 CAP_SYS_ADMIN 權限控管。
clock_adjtime時間/日期未命名空間化。同時受 CAP_SYS_TIME 權限控管。
clock_settime時間/日期未命名空間化。同時受 CAP_SYS_TIME 權限控管。
clone拒絕複製新的命名空間。除了 CLONE_NEWUSER 旗標外,CLONE_* 旗標皆受 CAP_SYS_ADMIN 權限控管。
create_module拒絕核心模組的操控與功能。已棄用。同時受 CAP_SYS_MODULE 權限控管。
delete_module拒絕核心模組的操控與功能。同時受 CAP_SYS_MODULE 權限控管。
finit_module拒絕核心模組的操控與功能。同時受 CAP_SYS_MODULE 權限控管。
get_kernel_syms拒絕檢索匯出的核心與模組符號。已棄用。
get_mempolicy修改核心記憶體與 NUMA 設定的系統呼叫。已受 CAP_SYS_NICE 權限控管。
init_module拒絕核心模組的操控與功能。同時受 CAP_SYS_MODULE 權限控管。
ioperm防止容器修改核心 I/O 特權等級。已受 CAP_SYS_RAWIO 權限控管。
iopl防止容器修改核心 I/O 特權等級。已受 CAP_SYS_RAWIO 權限控管。
kcmp限制處理程序檢視能力,透過移除 CAP_SYS_PTRACE 已封鎖此功能。
kexec_file_loadkexec_load 的姊妹系統呼叫,功能相同但參數略有不同。同時受 CAP_SYS_BOOT 權限控管。
kexec_load拒絕載入新核心以備後續執行。同時受 CAP_SYS_BOOT 權限控管。
keyctl防止容器使用未命名空間化的核心金鑰環。
lookup_dcookie追蹤/剖析系統呼叫,可能洩漏主機上的大量資訊。同時受 CAP_SYS_ADMIN 權限控管。
mbind修改核心記憶體與 NUMA 設定的系統呼叫。已受 CAP_SYS_NICE 權限控管。
mount拒絕掛載,已受 CAP_SYS_ADMIN 權限控管。
move_pages修改核心記憶體與 NUMA 設定的系統呼叫。
nfsservctl拒絕與核心 NFS 守護程序互動。自 Linux 3.1 起已棄用。
open_by_handle_at曾導致舊版容器逃逸漏洞。同時受 CAP_DAC_READ_SEARCH 權限控管。
perf_event_open追蹤/剖析系統呼叫,可能洩漏主機上的大量資訊。
personality防止容器啟用 BSD 模擬。本身並不危險,但測試不足,存在許多核心漏洞的潛在風險。
pivot_root拒絕 pivot_root,應為特權操作。
process_vm_readv限制處理程序檢視能力,透過移除 CAP_SYS_PTRACE 已封鎖此功能。
process_vm_writev限制處理程序檢視能力,透過移除 CAP_SYS_PTRACE 已封鎖此功能。
ptrace追蹤/剖析系統呼叫。在 Linux 核心 4.8 以前的版本中被封鎖以避免 seccomp 繞過。由於可能洩漏主機上的大量資訊,對任意處理程序進行追蹤/剖析的功能,已透過移除 CAP_SYS_PTRACE 進行封鎖。
query_module拒絕核心模組的操控與功能。已棄用。
quotactl配額系統呼叫,可能讓容器停用自身的資源限制或處理程序統計。同時受 CAP_SYS_ADMIN 權限控管。
reboot不允許容器重新啟動主機。同時受 CAP_SYS_BOOT 權限控管。
request_key防止容器使用未命名空間化的核心金鑰環。
set_mempolicy修改核心記憶體與 NUMA 設定的系統呼叫。已受 CAP_SYS_NICE 權限控管。
setns拒絕將執行緒關聯至命名空間。同時受 CAP_SYS_ADMIN 權限控管。
settimeofday時間/日期未命名空間化。同時受 CAP_SYS_TIME 權限控管。
stime時間/日期未命名空間化。同時受 CAP_SYS_TIME 權限控管。
swapon拒絕啟動/停止檔案或裝置的交換空間 (swapping)。同時受 CAP_SYS_ADMIN 權限控管。
swapoff拒絕啟動/停止檔案或裝置的交換空間 (swapping)。同時受 CAP_SYS_ADMIN 權限控管。
sysfs已棄用的系統呼叫。
_sysctl已棄用,由 /proc/sys 取代。
umount應為特權操作。同時受 CAP_SYS_ADMIN 權限控管。
umount2應為特權操作。同時受 CAP_SYS_ADMIN 權限控管。
unshare拒絕為處理程序複製新的命名空間。除 unshare --user 外,同時受 CAP_SYS_ADMIN 權限控管。
uselib與共用程式庫相關的舊版系統呼叫,已長期未使用。
userfaultfd使用者空間頁面錯誤處理,主要用於處理程序遷移。
ustat已棄用的系統呼叫。
vm86核心內 x86 真實模式虛擬機器。同時受 CAP_SYS_ADMIN 權限控管。
vm86old核心內 x86 真實模式虛擬機器。同時受 CAP_SYS_ADMIN 權限控管。

在不安裝預設 seccomp 設定檔的情況下執行

您可以傳遞 unconfined 來執行不使用預設 seccomp 設定檔的容器。

$ docker run --rm -it --security-opt seccomp=unconfined debian:latest \
    unshare --map-root-user --user sh -c whoami
© . This site is unofficial and not affiliated with Kubernetes or Docker Inc.