KVM ve QEMU ile Donanım Destekli Sanallaştırma

2021-04-27



Donanım destekli sanallaştırmada CPU'lar sanallaştırma işlemlerini yapmaktadırlar. Donanım destekli sanallaştırma, yazılım sanallaştırmaya göre çok daha hızlı çalışmaktadır. Intel VT-X veya AMD-V buna örnek olarak verilebilir. Bir çok hypervisor da donanım desteklerinden faydalanmaktadır.

Bu yazıda Qemu/KVM kullanılarak basit bir örnek de yapacağız.

Qemu Mimarisi

QEMU (Quick Emulator) ihtiyaç duyulan donanımları hızlı bir şekilde taklit edebilecek bir emülatördür. QEMU farklı CPU çeşitlerini (x86, PowerPC, ARM vb.) farklı mimarilerde (x86, PowerPC, ARM, Sparc, MIPS vb.) kullanmaya izin vermektedir. Aynı zamanda donanım ile sanallaştırmayı da desteklemektedir.

Örnek kod parçaları

kvmq->kvm_fd = open("/dev/kvm", O_RDWR | O_CLOEXEC); // KVM'in açılması

uint8_t ver = ioctl(kvmq->kvm_fd, KVM_GET_API_VERSION, 0); // Basit bir KVM ioctl'in oluşturulması 

if (ver != 12){
    fprintf(stderr, "KVM_GET_API_VERSION %d, expected 12",ver);
    return NULL;
}

Qemu ve KVM arasındaki genel şemayı da bu şekilde çizebiliriz. (KVM kernel seviyesinde (ring 0) QEMU ise userspace'de (ring 3) de çalışmaktadır. )

Qemu ve KVM arasındaki en önemli işlemlerden birisi ise KVM_RUN ioctl'inin çalıştırılması. Bu işlemi de basit bir döngü üzerinde açıklamak gerekirse:

while (!kvm_exit)
{
    ret = ioctl(kvm->vcpu->vcpu_fd, KVM_RUN, NULL);
    switch (kvm->vcpu->kvm_run->exit_reason)
    {
        case KVM_EXIT_IO:
        {
        }
        case KVM_EXIT_HLT:
        {
        }
        default:
        {

        }
    }
}

KVM_RUN ioctl'i çalıştıktan sonra QEMU bloklanıyor ve kontrol KVM'e geçiyor. Burada KVM işlemlerini bitirdikten sonra file descriptor üzerinden çıkış nedenini belirtiyor. Bu şekilde KVM'in işlemlerimizi yerine getirip getiremediğini anlayabilmekteyiz. Sanallaştırma işlemlerine devam ederken iki önemli konu karşımıza çıkmaktadır. Bunlar:

  1. Bellek Sanallaştırması
  2. I/O Sanallaştırması

VT-x ve VMX

VT-x sayesinde x86 sistemlerde sanallaştırma yapabilmek mümkündür. Bunu kontrol etmek için cat /proc/cpuinfo | grep "vmx" yazabiliriz.

VMX Mode

Bu komutlar kullanıldıkları zaman base OS ile sananallaştırılan OS arasında veri alışverişi olmaktadır. Burada sanallaştırılan cihazının page-tableları, registerları base OS'e aktarılmaktadır. Ancak bu verilerin OS'de tutulamaz bunun için VMCS (VM control structure) bulunmaktadır. Burada VMCS KVM ve CPU arasındaki iletişimi sağlamaktadır.

Ayrıca vmcs hakkında daha detaylı bilgi edinebilmek için https://www.intel.com/content/dam/www/public/us/en/documents/white-papers/intel-vmcs-shadowing-paper.pdf kaynağına göz atmakta fayda var.