On Sun, 2008-11-16 at 05:26 -0800, Avi Kivity wrote: > Kamble, Nitin A wrote: > >> The capability itself can return the count; for example > >> > >> case KVM_CAP_NR_CPUID_LEAVES: > >> return KVM_MAX_CPUID_ENTRIES; > >> > >> which is simpler to use and shorter. > >> > > > > Avi, > > Yes, it is simpler and shorter, but is returning a constant. It will be > > wasting space for the unused entries. Also it put's a restriction that the > > list count can not go more than that. > > The dynamic size finding, the patch I sent, is not complicated or long > > to be an issue. Would you like to give another consideration for the same > > patch (patch-3) I sent earlier? > > > > > > Oh, I confused the sizing code with something else. > > We can add this, but older kernels will still miss the code so we have > to work around it. I guess userspace can start with a large number, and > double it each time the ioctl fails.
Avi, You mean older kernels which does not support the KVM_CAP_CPUID_SIZER ioctl. Two ways to handle it: 1. qemu giving error that "-cpu host" option is not supported on this kernel. 2. or as per your suggestion guess it in userland. Either way it is code for kvm-userspace.git tree. I am attaching the patch again. Please apply. BTW I did not get your opinion for the patch for the kvm-userspace.git tree. Would you comment on it please? -- Thanks & Regards, Nitin Open Source Technology Center, Intel Corporation ----------------------------------------------------------------- The mind is like a parachute; it works much better when it's open
commit 70e4e65bc591eb9cf25c1cbc0d16b2cbdb089a6f Author: Nitin A Kamble <[EMAIL PROTECTED]> Date: Wed Nov 5 16:17:46 2008 -0800 Change the ioctl KVM_GET_SUPPORTED_CPUID, such that it will return the no of entries in the list when requested no of entries (nent) is 0. Also add another KVM_CHECK_EXTENSION, KVM_CAP_CPUID_SIZER to determine if the running kernel supports the above changed ABI. Signed-Off-By: Nitin A Kamble <[EMAIL PROTECTED]> diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h index 09e6c56..e50db11 100644 --- a/arch/x86/include/asm/kvm_host.h +++ b/arch/x86/include/asm/kvm_host.h @@ -86,7 +86,7 @@ #define KVM_NUM_MMU_PAGES (1 << KVM_MMU_HASH_SHIFT) #define KVM_MIN_FREE_MMU_PAGES 5 #define KVM_REFILL_PAGES 25 -#define KVM_MAX_CPUID_ENTRIES 40 +#define KVM_MAX_CPUID_ENTRIES 100 #define KVM_NR_FIXED_MTRR_REGION 88 #define KVM_NR_VAR_MTRR 8 diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index bf7461b..52e6207 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -969,6 +969,7 @@ int kvm_dev_ioctl_check_extension(long ext) case KVM_CAP_NOP_IO_DELAY: case KVM_CAP_MP_STATE: case KVM_CAP_SYNC_MMU: + case KVM_CAP_CPUID_SIZER: r = 1; break; case KVM_CAP_COALESCED_MMIO: @@ -1303,10 +1304,14 @@ static int kvm_dev_ioctl_get_supported_cpuid(struct kvm_cpuid2 *cpuid, { struct kvm_cpuid_entry2 *cpuid_entries; int limit, nent = 0, r = -E2BIG; + int sizer = 0; u32 func; - if (cpuid->nent < 1) - goto out; + if (cpuid->nent == 0) { + sizer = 1; + cpuid->nent = KVM_MAX_CPUID_ENTRIES; + } + r = -ENOMEM; cpuid_entries = vmalloc(sizeof(struct kvm_cpuid_entry2) * cpuid->nent); if (!cpuid_entries) @@ -1327,9 +1332,11 @@ static int kvm_dev_ioctl_get_supported_cpuid(struct kvm_cpuid2 *cpuid, do_cpuid_ent(&cpuid_entries[nent], func, 0, &nent, cpuid->nent); r = -EFAULT; - if (copy_to_user(entries, cpuid_entries, + if (!sizer) { + if (copy_to_user(entries, cpuid_entries, nent * sizeof(struct kvm_cpuid_entry2))) - goto out_free; + goto out_free; + } cpuid->nent = nent; r = 0; diff --git a/include/linux/kvm.h b/include/linux/kvm.h index 44fd7fa..d4cb8b1 100644 --- a/include/linux/kvm.h +++ b/include/linux/kvm.h @@ -392,6 +392,9 @@ struct kvm_trace_rec { #endif #define KVM_CAP_IOMMU 18 #define KVM_CAP_NMI 19 +#define KVM_CAP_CPUID_SIZER 20 /* return of 1 means the KVM_GET_SUPPORTED_CPUID */ + /* ioctl will return the size of list when input */ + /* list size (nent) is 0 */ /* * ioctls for VM fds