Hướng dẫn cấu hình KVM Nested Virtualization trên Linux: Kích hoạt ảo hóa lồng nhau cho Lab Proxmox, VMware và OpenStack

Virtualization tutorial - IT technology blog
Virtualization tutorial - IT technology blog

Khi máy ảo từ chối chạy thêm máy ảo

Để luyện tập dựng cụm Proxmox VE 3 node, thử nghiệm VMware ESXi hay lab OpenStack DevStack, lý tưởng nhất là có vài con server vật lý. Thực tế thì ít ai có sẵn ngân sách hàng chục triệu đồng và không gian cho cả dàn bare-metal ở nhà.

Giải pháp phổ biến nhất là tận dụng máy tính Linux cấu hình vừa phải (khoảng 8 core, 32GB RAM) hoặc một server KVM thuê ngoài. Bạn dựng máy ảo cấp 1 (L1 Guest), rồi cài Proxmox hoặc ESXi lên đó. Rắc rối xuất hiện ngay khi bạn bấm nút khởi động máy ảo con (L2) bên trong:

TASK ERROR: KVM acceleration not available, using software emulation
# Hoặc thông báo lỗi từ VMware ESXi:
Hardware Virtualization is not a feature of the CPU, or is not enabled in the BIOS

Trải nghiệm lúc này cực kỳ tệ. Máy ảo chạy giả lập phần mềm (TCG), CPU host vọt lên 100%, một bản Ubuntu Server mất 15-20 phút mới boot xong, hoặc installer của ESXi sẽ chặn đứng quá trình cài đặt.

Trong homelab của mình (chạy chip Ryzen 7 5700X, 64GB RAM), toàn bộ cụm lab test tính năng HA (High Availability) và Ceph storage đều chạy dưới dạng nested VM. Trước đây mình cũng từng mất đứt một buổi tối chỉ vì quên bật cờ ảo hóa từ host.

Vì sao máy ảo L1 không thấy tập lệnh ảo hóa?

Mô hình ảo hóa lồng nhau (Nested Virtualization) chia làm 3 tầng rõ rệt:

  • L0 (Bare-metal Host): Máy chủ vật lý chạy Linux và nạp module KVM.
  • L1 (Guest Hypervisor): Máy ảo chạy trên L0, đóng vai trò hypervisor trung gian (Proxmox, ESXi).
  • L2 (Nested Guest): Máy ảo chạy bên trong L1.

CPU Intel có tập lệnh VMX (VT-x), còn AMD dùng SVM (AMD-V). Hypervisor tầng L0 dùng tập lệnh này để cấp phát tài nguyên trực tiếp cho máy ảo.

Mặc định trên nhiều bản phân phối Linux như RHEL hay Debian, tính năng lồng cờ ảo hóa trong module kvm_intel và kvm_amd bị tắt sẵn để đảm bảo an toàn bộ nhớ. Host L0 sẽ che giấu các cờ phần cứng này, không truyền tiếp cho L1.

Chưa hết. Khi tạo máy ảo L1 qua libvirt với kiểu CPU mặc định qemu64, hệ thống chỉ cấp tập lệnh x86 cơ bản. Máy ảo L1 bị tước sạch cờ VT-x/AMD-V. Không có cờ phần cứng, L1 không thể khởi tạo tiếp máy ảo L2.

Các hướng xử lý: Ưu và nhược điểm

Có 3 cách giải quyết bài toán này, tùy thuộc vào mục đích sử dụng:

1. Giả lập thuần phần mềm (QEMU TCG)

L1 không cần /dev/kvm, xử lý mọi chỉ lệnh CPU hoàn toàn bằng phần mềm.

Đánh đổi: Hiệu năng giảm 80-90% so với ảo hóa phần cứng. Cách này chỉ phù hợp để vọc vạch shell Alpine Linux dung lượng vài chục MB, hoàn toàn không chạy nổi cụm Kubernetes hay Ceph.

2. Thuê cụm server Bare-metal riêng

Thuê 3 máy chủ vật lý độc lập tại các nhà cung cấp như Hetzner hay OVH.

Đánh đổi: Hiệu năng đạt 100%, chuẩn production. Chi phí mỗi tháng dao động từ 150-300 USD, quá tốn kém cho nhu cầu lab cá nhân.

3. Bật KVM Nested Virtualization và Host-Passthrough

Cấu hình host L0 chuyển tiếp nguyên vẹn tập lệnh CPU thực vào máy ảo L1. Đây là chuẩn mực cho môi trường staging, CI/CD và lab thực hành của dân DevOps/Sysadmin. Mức suy hao hiệu năng của L2 so với máy vật lý thường chỉ rơi vào khoảng 5% đến 15%.

Các bước kích hoạt KVM Nested Virtualization

Quy trình triển khai gồm 4 bước: kiểm tra phần cứng, bật module kernel, cấu hình CPU máy ảo và kiểm tra lại từ bên trong.

Bước 1: Kiểm tra phần cứng trên Host L0

Kiểm tra xem CPU vật lý có hỗ trợ ảo hóa hay không:

egrep -c '(vmx|svm)' /proc/cpuinfo

Con số trả về tương ứng số luồng CPU (ví dụ: 8, 16 hoặc 32). Nếu kết quả trả về 0, bạn cần vào BIOS/UEFI của mainboard để bật Intel VT-x hoặc AMD-V (SVM Mode).

Tiếp theo, xem trạng thái tính năng nested trên host:

# Với CPU Intel:
cat /sys/module/kvm_intel/parameters/nested

# Với CPU AMD:
cat /sys/module/kvm_amd/parameters/nested

Kết quả hiển thị N hoặc 0 nghĩa là đang tắt. Nếu trả về Y hoặc 1, bạn có thể bỏ qua Bước 2 và sang thẳng Bước 3.

Bước 2: Kích hoạt module KVM trên Kernel Host

Lưu ý: Tắt hết các VM đang chạy trên L0 trước khi nạp lại module. Nếu VM còn bật, lệnh modprobe -r sẽ báo lỗi Module is in use.

# Áp dụng tạm thời cho chip Intel:
sudo modprobe -r kvm_intel
sudo modprobe kvm_intel nested=1

# Áp dụng tạm thời cho chip AMD:
sudo modprobe -r kvm_amd
sudo modprobe kvm_amd nested=1

Để cấu hình giữ nguyên sau mỗi lần khởi động lại máy, tạo file cấu hình cho modprobe:

# Với chip Intel:
echo "options kvm_intel nested=1" | sudo tee /etc/modprobe.d/kvm.conf

# Với chip AMD:
echo "options kvm_amd nested=1" | sudo tee /etc/modprobe.d/kvm.conf

Đọc lại file /sys/module/kvm_intel/parameters/nested (hoặc kvm_amd). Kết quả xuất hiện Y hoặc 1 là thành công.

Bước 3: Cấu hình CPU Passthrough cho máy ảo L1

Kernel host đã mở đường, bước tiếp theo là cho phép máy ảo L1 nhận diện đúng CPU gốc.

Với các VM quản lý bằng virsh (libvirt), mở file cấu hình XML:

virsh edit <ten-vm-L1>

Tìm khối <cpu> và cập nhật thuộc tính mode='host-passthrough':

<cpu mode='host-passthrough' check='none'>
  <topology sockets='1' dies='1' cores='4' threads='1'/>
</cpu>

Thao tác tương đương trên giao diện đồ họa virt-manager:

  1. Mở cửa sổ chi tiết VM, chọn mục CPUs.
  2. Đánh dấu vào Copy host CPU configuration (hoặc nhập chữ host-passthrough vào ô Model).
  3. Nhấn Apply rồi bật máy ảo.

Bước 4: Xác thực bên trong máy ảo L1

Khởi động máy ảo L1, mở SSH và chạy lệnh kiểm tra:

# Kiểm tra cờ ảo hóa đã xuất hiện chưa
egrep -c '(vmx|svm)' /proc/cpuinfo

# Xác nhận thiết bị tăng tốc phần cứng KVM
ls -l /dev/kvm

Lệnh đếm trả về số lớn hơn 0 và xuất hiện character device /dev/kvm (quyền truy cập nhóm kvm). Máy ảo L1 đã sẵn sàng hoạt động như một máy chủ vật lý.

Từ đây, bạn có thể triển khai cụm Proxmox VE, cấu hình HA 3 node hoặc cài đặt VMware ESXi để tạo máy ảo L2 mượt mà. Toàn bộ hạ tầng lab phức tạp giờ đây nằm gọn gàng trên một máy chủ duy nhất.

Share: