Cơ Chế Bảo Mật Trong Container: Namespace, Cgroups, Seccomp, AppArmor và SELinux

Trong vài năm gần đây, container (như Docker, Kubernetes) đã trở thành một phần không thể thiếu trong quy trình phát triển và triển khai phần mềm hiện đại. Tuy nhiên, nhiều người chỉ dừng lại ở việc sử dụng container mà chưa thật sự hiểu rõ cách thức hoạt động và cơ chế bảo mật bên trong chúng.

Vậy container bảo vệ ứng dụng và hệ thống như thế nào? Bài viết này sẽ giúp bạn hiểu được 4 trụ cột bảo mật quan trọng của container: namespace, cgroups, seccomp, và AppArmor/SELinux — cùng các ví dụ thực tế khi triển khai bằng Docker.


1. Bối Cảnh: Tại Sao Container Xuất Hiện?

Trước Khi Có Máy Ảo

Trước đây, ứng dụng được triển khai bằng cách cài đặt mỗi ứng dụng trên một máy chủ riêng biệt vì các lý do:

  • Bảo mật: Tránh ảnh hưởng chéo giữa các ứng dụng khi có sự cố(bị tấn công, máy chủ sập kéo theo tất cả ứng dụng khác sập theo).
  • Quản lý tài nguyên: Tránh chiếm dụng lẫn nhau.
  • Xung đột thư viện: Các ứng dụng khác nhau cần các phiên bản khác nhau của cùng một thư viện. Nếu cài trên cùng một máy chủ có thể gây xung đột

Nhược điểm là:

  • Chi phí cao: khi có ứng dụng mới cần phải mua thêm một máy chủ mới
  • Lãng phí tài nguyên nếu ứng dụng không sử dụng hết công suất máy chủ

Máy Ảo (Virtual Machine)

Máy ảo giải quyết một phần vấn đề trên bằng cách cho phép nhiều hệ điều hành chạy song song trên cùng một máy chủ thông qua hypervisor như VMWare, Hyper-V, XenServer...

  • Ưu điểm
    - Tăng hiệu suất sử dụng phần cứng, cách ly tốt
  • Nhược điểm
    - Mỗi máy ảo cần hệ điều hành riêng → tốn RAM, CPU
    - Khởi động chậm: máy ảo phải khởi động hệ điều hành như một máy tính thật sự
    - Chi phí: mỗi một hệ điều hành trong máy ảo cần giấy phép (license) để sử dụng

Container

Container xuất hiện như một giải pháp nhẹ hơn, sử dụng chung kernel của máy chủ và chỉ đóng gói các thư viện, mã nguồn cần thiết.

https://cloudzy.com/blog/virtual-machine-vm-what-why-when
  • Ưu điểm
    - Nhẹ, nhanh: không giả lập hệ điều hành và kernel vì dùng chung kernel với máy chủ
    - Khởi động nhanh
    - Cài được nhiều ứng dụng trên một máy chủ vì mỗi container nhẹ hơn một máy ảo nhiều
    - Dễ triển khai ở nhiều môi trường
    - Không tốn chi phí giấy phép
  • Nhược điểm
    - Không cách ly hoàn toàn như máy ảo
    - Dùng chung kernel với máy chủ → dễ bị khai thác nếu không bảo vệ đúng cách

2. Cơ Chế Bảo Mật Chính Trong Container

Namespace – Cách Ly Tài Nguyên Hệ Thống

Namespace là cơ chế của Linux để tách biệt không gian tài nguyên giữa các tiến trình. Mỗi loại namespace sẽ cách ly một khía cạnh khác nhau:

Namespace Cách Ly Ví dụ
pid Tiến trình PID trong container bắt đầu từ 1, không thấy được tiến trình bên ngoài
net Mạng Container có IP riêng, bảng định tuyến riêng
mnt Hệ thống tập tin File system riêng biệt cho mỗi container
uts Hostname/domain Container có hostname riêng
ipc Giao tiếp tiến trình Tách biệt vùng nhớ chia sẻ (shared memory)
user UID/GID Root trong container khác root trên máy chủ

Máy chủ tạo và quản lý namespace cho các container.
Nếu không có namespace, một tiến trình ở container này có thể thấy và tương tác với tiến trình ở container khác.

https://blog.nginx.org/blog/what-are-namespaces-cgroups-how-do-they-work

Ví dụ với Docker:

docker run -it --name test-container --hostname mycontainer ubuntu bash

Cgroups – Giới Hạn và Theo Dõi Tài Nguyên

Cgroup (Control Group) giúp giới hạn tài nguyên mà container sử dụng.

Khi chạy container, các tiến trình của container sẽ được đặt bên trong một cgroup.
Cgroup cung cấp các khả năng sau:

  • Giới hạn tài nguyên của tiến trình
  • Thiết lập ưu tiên tài nguyên khi có nhiều tiến trình sử dụng
  • Theo dõi: giới hạn tài nguyên được theo dõi và báo cáo ở cấp độ cgroup
  • Điều khiển: thay đổi trạng thái (đóng băng, dừng và tái khởi động) của mọi tiến trình trong một cgroup
https://blog.nginx.org/blog/what-are-namespaces-cgroups-how-do-they-work

Ví dụ giới hạn tài nguyên trong Docker:

docker run -it --cpus=".5" --memory="256m" ubuntu

Seccomp – Chặn Gọi Hệ Thống Nguy Hiểm

Seccomp (Secure Computing Mode) là một tính năng của kernel cho phép chặn các syscall nguy hiểm — vốn là cửa ngõ để ứng dụng giao tiếp với hệ điều hành.

Một số ví dụ về syscall:

  • Clone cho phép sao chép  namespace
  • iopl cho phép thay đổi cấp độ quyền hạn I/O của kernel

Nếu kẻ xấu tấn công ứng dụng, chúng có thể lợi dụng syscall để tương tác với máy chủ.
Seccomp ngăn chặn các syscall nguy hiểm, giảm thiểu đáng kể cơ hội bị tấn công.
Seccomp trong docker mặc định ngăn chặn 44 syscall trong tổng số hơn 300 syscall.

Ví dụ Docker với seccomp profile:

Tạo profile cho phép 4 quyền read, write, exit, sigreturn:

{
  "defaultAction": "SCMP_ACT_ERRNO",
  "archMap": [
    {
      "architecture": "SCMP_ARCH_X86_64",
      "subArchitectures": [
        "SCMP_ARCH_X86",
        "SCMP_ARCH_X32"
      ]
    }
  ],
  "syscalls": [
    {
      "names": [
        "read",
        "write",
        "exit",
        "sigreturn"
      ],
      "action": "SCMP_ACT_ALLOW"
    }
  ]
}
docker run --security-opt seccomp=/path/to/custom-seccomp.json ubuntu

AppArmor & SELinux – Quản Lý Truy Cập Hệ Thống

Cả AppArmor và SELinux đều là Mandatory Access Control (MAC) — cơ chế bảo vệ cấp kernel nhằm kiểm soát quyền truy cập của ứng dụng lên file, thư mục và tài nguyên hệ thống.

Điểm khác nhau giữa chúng nằm ở cách thức thực hiện và độ phức tạp trong thiết lập quản lý.

Đặc điểm AppArmor SELinux
Dựa trên Đường dẫn Nhãn (label)
Tính dễ sử dụng Dễ cho người mới Phức tạp hơn, chuyên sâu
Phân phối chính Ubuntu, Debian CentOS, Fedora, RHEL
Hiệu suất Nhẹ, nhanh Tối ưu cho môi trường lớn

Ví dụ dùng AppArmor với Docker:

docker run --security-opt apparmor=docker-default nginx

3. So Sánh Mức Độ Cách Ly Giữa Container Và Máy Ảo

Container có tốc độ và hiệu quả tài nguyên cao hơn máy ảo, nhưng mức độ cách ly thấp hơn vì:

  • Máy ảo có kernel riêng, không thể truy cập kernel của máy chủ.
  • Container dùng chung kernel với máy chủ, nếu container bị tấn công thì có thể truy cập kernel, từ đó ảnh hưởng hệ thống.

Để thực hiện tấn công lên máy chủ từ máy ảo, kẻ tấn công cần vượt qua 3 rào cản sau:

  • Kernel máy ảo: tấn công và vượt qua kernel trong máy ảo
  • Hypervisor: từ kernel của máy ảo tấn công/vượt qua hypervisor
  • Hệ thống máy chủ: từ hypervisor tấn công lên máy chủ

Xét đến container, do sử dụng chung kernel với máy chủ nên bước thứ 2 đã được bỏ qua hoàn toàn.

Dữ liệu thống kê thực tế cho thấy container gặp nhiều sự cố bảo mật hơn máy ảo:


4. Biện Pháp Cải Thiện Bảo Mật Container

Để nâng mức độ bảo mật của container cho giống máy ảo, chúng ta có thể sử dụng các biện pháp sau:

  • gVisor: lớp kernel user-space giúp ngăn container truy cập kernel thật
  • Kata Containers: container chạy bên trong một máy ảo nhẹ
  • Rootless containers: container chạy với user không phải root
  • AppArmor/SELinux read-only: cấu hình container không thể ghi vào vùng dữ liệu nhạy cảm
https://gvisor.dev

✅ Tổng Kết

Container là công cụ mạnh mẽ giúp đơn giản hóa việc đóng gói và triển khai ứng dụng, nhưng đi kèm đó là thách thức về bảo mật. Việc hiểu rõ các cơ chế như namespace, cgroups, seccomp, AppArmor và SELinux sẽ giúp chúng ta:

  • Nâng cao khả năng phòng thủ cho hệ thống
  • Hạn chế tối đa thiệt hại nếu container bị khai thác
  • Tự tin hơn khi đưa container vào các môi trường production quan trọng

📚 Tham Khảo

  1. selinux vs apparmor
  2. vmware vs container
  3. docker image vs container
  4. What Are Namespaces and cgroups, and How Do They Work?
  5. Seccomp security profiles for Docker
  6. What Is Container Escape?
  7. Virtual Machine (VM): Why and When Do You Need One?
  8. Virtual machine escapes
  9. Container escapes
  10. gVisor