]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
kvm: Check vmx capability using cpuid
authorAsias He <asias.hejun@gmail.com>
Mon, 5 Jul 2010 06:01:11 +0000 (14:01 +0800)
committerPekka Enberg <penberg@cs.helsinki.fi>
Mon, 5 Jul 2010 16:07:00 +0000 (19:07 +0300)
[ penberg@cs.helsinki.fi: use host_cpuid(), cleanups ]
Reported-by: Cyrill Gorcunov <gorcunov@gmail.com>
Signed-off-by: Asias He <asias.hejun@gmail.com>
Signed-off-by: Pekka Enberg <penberg@cs.helsinki.fi>
tools/kvm/cpuid.c
tools/kvm/include/kvm/cpufeature.h
tools/kvm/kvm.c

index ee80fe3caef2bcadd234065fc7aee3bff9ae87e3..7fdfb83a84b2b46fb4a0771b17c514c8ac713674 100644 (file)
@@ -7,23 +7,6 @@
 #include <stdlib.h>
 #include <assert.h>
 
-struct cpuid_regs {
-       uint32_t        eax;
-       uint32_t        ebx;
-       uint32_t        ecx;
-       uint32_t        edx;
-};
-
-static inline void host_cpuid(struct cpuid_regs *regs)
-{
-       asm volatile("cpuid"
-               : "=a" (regs->eax),
-                 "=b" (regs->ebx),
-                 "=c" (regs->ecx),
-                 "=d" (regs->edx)
-               : "0" (regs->eax), "2" (regs->ecx));
-}
-
 static struct kvm_cpuid2 *kvm_cpuid__new(unsigned long nent)
 {
        struct kvm_cpuid2 *self;
index 35c55ade91e815e7e9f02a310bf34f877b5169c1..4f566df47d265c118e96a1792ffc9f301df033c7 100644 (file)
 #define cpu_feature_enable(reg, feature)       \
        ((reg) |  (1 << (feature)))
 
+struct cpuid_regs {
+       uint32_t        eax;
+       uint32_t        ebx;
+       uint32_t        ecx;
+       uint32_t        edx;
+};
+
+static inline void host_cpuid(struct cpuid_regs *regs)
+{
+       asm volatile("cpuid"
+               : "=a" (regs->eax),
+                 "=b" (regs->ebx),
+                 "=c" (regs->ecx),
+                 "=d" (regs->edx)
+               : "0" (regs->eax), "2" (regs->ecx));
+}
+
 #endif /* KVM__CPUFEATURE_H */
index 1e0259e063b6897561953656f65718ff9bbdc77a..f290f8ceecf3d6dd36c2fd37a96c047054311315 100644 (file)
@@ -1,6 +1,7 @@
 #include "kvm/kvm.h"
 
 #include "kvm/interrupt.h"
+#include "kvm/cpufeature.h"
 #include "kvm/util.h"
 
 #include <linux/kvm.h>
@@ -133,6 +134,18 @@ void kvm__delete(struct kvm *self)
        free(self);
 }
 
+static bool kvm__cpu_supports_vm(void)
+{
+       struct cpuid_regs regs;
+
+       regs    = (struct cpuid_regs) {
+               .eax            = 1,
+       };
+       host_cpuid(&regs);
+
+       return regs.ecx & (1 << KVM__X86_FEATURE_VMX);
+}
+
 struct kvm *kvm__init(const char *kvm_dev)
 {
        struct kvm_userspace_memory_region mem;
@@ -142,6 +155,9 @@ struct kvm *kvm__init(const char *kvm_dev)
        int mmap_size;
        int ret;
 
+       if (!kvm__cpu_supports_vm())
+               die("Your CPU does not support hardware virtualization");
+
        self = kvm__new();
 
        self->sys_fd = open(kvm_dev, O_RDWR);