aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorRusty Russell <rusty@rustcorp.com.au>2007-07-27 03:16:56 -0400
committerAvi Kivity <avi@qumranet.com>2007-10-13 04:18:20 -0400
commitfb3f0f51d92d1496f9628ca6f0fb06a48dc9ed2a (patch)
tree38da1073dae5f30fd8f162669bb5a86959f8ace5 /drivers
parenta2fa3e9f52d875f7d4ca98434603b8756be71ba8 (diff)
KVM: Dynamically allocate vcpus
This patch converts the vcpus array in "struct kvm" to a pointer array, and changes the "vcpu_create" and "vcpu_setup" hooks into one "vcpu_create" call which does the allocation and initialization of the vcpu (calling back into the kvm_vcpu_init core helper). Signed-off-by: Rusty Russell <rusty@rustcorp.com.au> Signed-off-by: Avi Kivity <avi@qumranet.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/kvm/kvm.h12
-rw-r--r--drivers/kvm/kvm_main.c198
-rw-r--r--drivers/kvm/kvm_svm.h2
-rw-r--r--drivers/kvm/svm.c177
-rw-r--r--drivers/kvm/vmx.c65
5 files changed, 236 insertions, 218 deletions
diff --git a/drivers/kvm/kvm.h b/drivers/kvm/kvm.h
index 954a14089605..e92c84b04c1f 100644
--- a/drivers/kvm/kvm.h
+++ b/drivers/kvm/kvm.h
@@ -300,10 +300,8 @@ void kvm_io_bus_register_dev(struct kvm_io_bus *bus,
300 struct kvm_io_device *dev); 300 struct kvm_io_device *dev);
301 301
302struct kvm_vcpu { 302struct kvm_vcpu {
303 int valid;
304 struct kvm *kvm; 303 struct kvm *kvm;
305 int vcpu_id; 304 int vcpu_id;
306 void *_priv;
307 struct mutex mutex; 305 struct mutex mutex;
308 int cpu; 306 int cpu;
309 u64 host_tsc; 307 u64 host_tsc;
@@ -404,8 +402,7 @@ struct kvm {
404 struct list_head active_mmu_pages; 402 struct list_head active_mmu_pages;
405 int n_free_mmu_pages; 403 int n_free_mmu_pages;
406 struct hlist_head mmu_page_hash[KVM_NUM_MMU_PAGES]; 404 struct hlist_head mmu_page_hash[KVM_NUM_MMU_PAGES];
407 int nvcpus; 405 struct kvm_vcpu *vcpus[KVM_MAX_VCPUS];
408 struct kvm_vcpu vcpus[KVM_MAX_VCPUS];
409 int memory_config_version; 406 int memory_config_version;
410 int busy; 407 int busy;
411 unsigned long rmap_overflow; 408 unsigned long rmap_overflow;
@@ -428,7 +425,8 @@ struct kvm_arch_ops {
428 int (*hardware_setup)(void); /* __init */ 425 int (*hardware_setup)(void); /* __init */
429 void (*hardware_unsetup)(void); /* __exit */ 426 void (*hardware_unsetup)(void); /* __exit */
430 427
431 int (*vcpu_create)(struct kvm_vcpu *vcpu); 428 /* Create, but do not attach this VCPU */
429 struct kvm_vcpu *(*vcpu_create)(struct kvm *kvm, unsigned id);
432 void (*vcpu_free)(struct kvm_vcpu *vcpu); 430 void (*vcpu_free)(struct kvm_vcpu *vcpu);
433 431
434 void (*vcpu_load)(struct kvm_vcpu *vcpu); 432 void (*vcpu_load)(struct kvm_vcpu *vcpu);
@@ -470,7 +468,6 @@ struct kvm_arch_ops {
470 void (*inject_gp)(struct kvm_vcpu *vcpu, unsigned err_code); 468 void (*inject_gp)(struct kvm_vcpu *vcpu, unsigned err_code);
471 469
472 int (*run)(struct kvm_vcpu *vcpu, struct kvm_run *run); 470 int (*run)(struct kvm_vcpu *vcpu, struct kvm_run *run);
473 int (*vcpu_setup)(struct kvm_vcpu *vcpu);
474 void (*skip_emulated_instruction)(struct kvm_vcpu *vcpu); 471 void (*skip_emulated_instruction)(struct kvm_vcpu *vcpu);
475 void (*patch_hypercall)(struct kvm_vcpu *vcpu, 472 void (*patch_hypercall)(struct kvm_vcpu *vcpu,
476 unsigned char *hypercall_addr); 473 unsigned char *hypercall_addr);
@@ -481,6 +478,9 @@ extern struct kvm_arch_ops *kvm_arch_ops;
481#define kvm_printf(kvm, fmt ...) printk(KERN_DEBUG fmt) 478#define kvm_printf(kvm, fmt ...) printk(KERN_DEBUG fmt)
482#define vcpu_printf(vcpu, fmt...) kvm_printf(vcpu->kvm, fmt) 479#define vcpu_printf(vcpu, fmt...) kvm_printf(vcpu->kvm, fmt)
483 480
481int kvm_vcpu_init(struct kvm_vcpu *vcpu, struct kvm *kvm, unsigned id);
482void kvm_vcpu_uninit(struct kvm_vcpu *vcpu);
483
484int kvm_init_arch(struct kvm_arch_ops *ops, struct module *module); 484int kvm_init_arch(struct kvm_arch_ops *ops, struct module *module);
485void kvm_exit_arch(void); 485void kvm_exit_arch(void);
486 486
diff --git a/drivers/kvm/kvm_main.c b/drivers/kvm/kvm_main.c
index bf8b8f030192..69d9ab4e7cb4 100644
--- a/drivers/kvm/kvm_main.c
+++ b/drivers/kvm/kvm_main.c
@@ -266,8 +266,10 @@ void kvm_flush_remote_tlbs(struct kvm *kvm)
266 atomic_set(&completed, 0); 266 atomic_set(&completed, 0);
267 cpus_clear(cpus); 267 cpus_clear(cpus);
268 needed = 0; 268 needed = 0;
269 for (i = 0; i < kvm->nvcpus; ++i) { 269 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
270 vcpu = &kvm->vcpus[i]; 270 vcpu = kvm->vcpus[i];
271 if (!vcpu)
272 continue;
271 if (test_and_set_bit(KVM_TLB_FLUSH, &vcpu->requests)) 273 if (test_and_set_bit(KVM_TLB_FLUSH, &vcpu->requests))
272 continue; 274 continue;
273 cpu = vcpu->cpu; 275 cpu = vcpu->cpu;
@@ -291,10 +293,61 @@ void kvm_flush_remote_tlbs(struct kvm *kvm)
291 } 293 }
292} 294}
293 295
296int kvm_vcpu_init(struct kvm_vcpu *vcpu, struct kvm *kvm, unsigned id)
297{
298 struct page *page;
299 int r;
300
301 mutex_init(&vcpu->mutex);
302 vcpu->cpu = -1;
303 vcpu->mmu.root_hpa = INVALID_PAGE;
304 vcpu->kvm = kvm;
305 vcpu->vcpu_id = id;
306
307 page = alloc_page(GFP_KERNEL | __GFP_ZERO);
308 if (!page) {
309 r = -ENOMEM;
310 goto fail;
311 }
312 vcpu->run = page_address(page);
313
314 page = alloc_page(GFP_KERNEL | __GFP_ZERO);
315 if (!page) {
316 r = -ENOMEM;
317 goto fail_free_run;
318 }
319 vcpu->pio_data = page_address(page);
320
321 vcpu->host_fx_image = (char*)ALIGN((hva_t)vcpu->fx_buf,
322 FX_IMAGE_ALIGN);
323 vcpu->guest_fx_image = vcpu->host_fx_image + FX_IMAGE_SIZE;
324
325 r = kvm_mmu_create(vcpu);
326 if (r < 0)
327 goto fail_free_pio_data;
328
329 return 0;
330
331fail_free_pio_data:
332 free_page((unsigned long)vcpu->pio_data);
333fail_free_run:
334 free_page((unsigned long)vcpu->run);
335fail:
336 return -ENOMEM;
337}
338EXPORT_SYMBOL_GPL(kvm_vcpu_init);
339
340void kvm_vcpu_uninit(struct kvm_vcpu *vcpu)
341{
342 kvm_mmu_destroy(vcpu);
343 free_page((unsigned long)vcpu->pio_data);
344 free_page((unsigned long)vcpu->run);
345}
346EXPORT_SYMBOL_GPL(kvm_vcpu_uninit);
347
294static struct kvm *kvm_create_vm(void) 348static struct kvm *kvm_create_vm(void)
295{ 349{
296 struct kvm *kvm = kzalloc(sizeof(struct kvm), GFP_KERNEL); 350 struct kvm *kvm = kzalloc(sizeof(struct kvm), GFP_KERNEL);
297 int i;
298 351
299 if (!kvm) 352 if (!kvm)
300 return ERR_PTR(-ENOMEM); 353 return ERR_PTR(-ENOMEM);
@@ -303,14 +356,6 @@ static struct kvm *kvm_create_vm(void)
303 spin_lock_init(&kvm->lock); 356 spin_lock_init(&kvm->lock);
304 INIT_LIST_HEAD(&kvm->active_mmu_pages); 357 INIT_LIST_HEAD(&kvm->active_mmu_pages);
305 kvm_io_bus_init(&kvm->mmio_bus); 358 kvm_io_bus_init(&kvm->mmio_bus);
306 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
307 struct kvm_vcpu *vcpu = &kvm->vcpus[i];
308
309 mutex_init(&vcpu->mutex);
310 vcpu->cpu = -1;
311 vcpu->kvm = kvm;
312 vcpu->mmu.root_hpa = INVALID_PAGE;
313 }
314 spin_lock(&kvm_lock); 359 spin_lock(&kvm_lock);
315 list_add(&kvm->vm_list, &vm_list); 360 list_add(&kvm->vm_list, &vm_list);
316 spin_unlock(&kvm_lock); 361 spin_unlock(&kvm_lock);
@@ -367,30 +412,11 @@ static void free_pio_guest_pages(struct kvm_vcpu *vcpu)
367 412
368static void kvm_unload_vcpu_mmu(struct kvm_vcpu *vcpu) 413static void kvm_unload_vcpu_mmu(struct kvm_vcpu *vcpu)
369{ 414{
370 if (!vcpu->valid)
371 return;
372
373 vcpu_load(vcpu); 415 vcpu_load(vcpu);
374 kvm_mmu_unload(vcpu); 416 kvm_mmu_unload(vcpu);
375 vcpu_put(vcpu); 417 vcpu_put(vcpu);
376} 418}
377 419
378static void kvm_free_vcpu(struct kvm_vcpu *vcpu)
379{
380 if (!vcpu->valid)
381 return;
382
383 vcpu_load(vcpu);
384 kvm_mmu_destroy(vcpu);
385 vcpu_put(vcpu);
386 kvm_arch_ops->vcpu_free(vcpu);
387 free_page((unsigned long)vcpu->run);
388 vcpu->run = NULL;
389 free_page((unsigned long)vcpu->pio_data);
390 vcpu->pio_data = NULL;
391 free_pio_guest_pages(vcpu);
392}
393
394static void kvm_free_vcpus(struct kvm *kvm) 420static void kvm_free_vcpus(struct kvm *kvm)
395{ 421{
396 unsigned int i; 422 unsigned int i;
@@ -399,9 +425,15 @@ static void kvm_free_vcpus(struct kvm *kvm)
399 * Unpin any mmu pages first. 425 * Unpin any mmu pages first.
400 */ 426 */
401 for (i = 0; i < KVM_MAX_VCPUS; ++i) 427 for (i = 0; i < KVM_MAX_VCPUS; ++i)
402 kvm_unload_vcpu_mmu(&kvm->vcpus[i]); 428 if (kvm->vcpus[i])
403 for (i = 0; i < KVM_MAX_VCPUS; ++i) 429 kvm_unload_vcpu_mmu(kvm->vcpus[i]);
404 kvm_free_vcpu(&kvm->vcpus[i]); 430 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
431 if (kvm->vcpus[i]) {
432 kvm_arch_ops->vcpu_free(kvm->vcpus[i]);
433 kvm->vcpus[i] = NULL;
434 }
435 }
436
405} 437}
406 438
407static int kvm_dev_release(struct inode *inode, struct file *filp) 439static int kvm_dev_release(struct inode *inode, struct file *filp)
@@ -2372,77 +2404,47 @@ static int kvm_vm_ioctl_create_vcpu(struct kvm *kvm, int n)
2372{ 2404{
2373 int r; 2405 int r;
2374 struct kvm_vcpu *vcpu; 2406 struct kvm_vcpu *vcpu;
2375 struct page *page;
2376 2407
2377 r = -EINVAL;
2378 if (!valid_vcpu(n)) 2408 if (!valid_vcpu(n))
2379 goto out; 2409 return -EINVAL;
2380
2381 vcpu = &kvm->vcpus[n];
2382 vcpu->vcpu_id = n;
2383
2384 mutex_lock(&vcpu->mutex);
2385
2386 if (vcpu->valid) {
2387 mutex_unlock(&vcpu->mutex);
2388 return -EEXIST;
2389 }
2390
2391 page = alloc_page(GFP_KERNEL | __GFP_ZERO);
2392 r = -ENOMEM;
2393 if (!page)
2394 goto out_unlock;
2395 vcpu->run = page_address(page);
2396
2397 page = alloc_page(GFP_KERNEL | __GFP_ZERO);
2398 r = -ENOMEM;
2399 if (!page)
2400 goto out_free_run;
2401 vcpu->pio_data = page_address(page);
2402
2403 vcpu->host_fx_image = (char*)ALIGN((hva_t)vcpu->fx_buf,
2404 FX_IMAGE_ALIGN);
2405 vcpu->guest_fx_image = vcpu->host_fx_image + FX_IMAGE_SIZE;
2406 vcpu->cr0 = 0x10;
2407
2408 r = kvm_arch_ops->vcpu_create(vcpu);
2409 if (r < 0)
2410 goto out_free_vcpus;
2411 2410
2412 r = kvm_mmu_create(vcpu); 2411 vcpu = kvm_arch_ops->vcpu_create(kvm, n);
2413 if (r < 0) 2412 if (IS_ERR(vcpu))
2414 goto out_free_vcpus; 2413 return PTR_ERR(vcpu);
2415 2414
2416 kvm_arch_ops->vcpu_load(vcpu); 2415 vcpu_load(vcpu);
2417 r = kvm_mmu_setup(vcpu); 2416 r = kvm_mmu_setup(vcpu);
2418 if (r >= 0)
2419 r = kvm_arch_ops->vcpu_setup(vcpu);
2420 vcpu_put(vcpu); 2417 vcpu_put(vcpu);
2421
2422 if (r < 0) 2418 if (r < 0)
2423 goto out_free_vcpus; 2419 goto free_vcpu;
2424 2420
2421 spin_lock(&kvm->lock);
2422 if (kvm->vcpus[n]) {
2423 r = -EEXIST;
2424 spin_unlock(&kvm->lock);
2425 goto mmu_unload;
2426 }
2427 kvm->vcpus[n] = vcpu;
2428 spin_unlock(&kvm->lock);
2429
2430 /* Now it's all set up, let userspace reach it */
2425 r = create_vcpu_fd(vcpu); 2431 r = create_vcpu_fd(vcpu);
2426 if (r < 0) 2432 if (r < 0)
2427 goto out_free_vcpus; 2433 goto unlink;
2428 2434 return r;
2429 spin_lock(&kvm_lock);
2430 if (n >= kvm->nvcpus)
2431 kvm->nvcpus = n + 1;
2432 spin_unlock(&kvm_lock);
2433 2435
2434 vcpu->valid = 1; 2436unlink:
2437 spin_lock(&kvm->lock);
2438 kvm->vcpus[n] = NULL;
2439 spin_unlock(&kvm->lock);
2435 2440
2436 return r; 2441mmu_unload:
2442 vcpu_load(vcpu);
2443 kvm_mmu_unload(vcpu);
2444 vcpu_put(vcpu);
2437 2445
2438out_free_vcpus: 2446free_vcpu:
2439 kvm_free_vcpu(vcpu); 2447 kvm_arch_ops->vcpu_free(vcpu);
2440out_free_run:
2441 free_page((unsigned long)vcpu->run);
2442 vcpu->run = NULL;
2443out_unlock:
2444 mutex_unlock(&vcpu->mutex);
2445out:
2446 return r; 2448 return r;
2447} 2449}
2448 2450
@@ -2935,9 +2937,12 @@ static void decache_vcpus_on_cpu(int cpu)
2935 int i; 2937 int i;
2936 2938
2937 spin_lock(&kvm_lock); 2939 spin_lock(&kvm_lock);
2938 list_for_each_entry(vm, &vm_list, vm_list) 2940 list_for_each_entry(vm, &vm_list, vm_list) {
2941 spin_lock(&vm->lock);
2939 for (i = 0; i < KVM_MAX_VCPUS; ++i) { 2942 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
2940 vcpu = &vm->vcpus[i]; 2943 vcpu = vm->vcpus[i];
2944 if (!vcpu)
2945 continue;
2941 /* 2946 /*
2942 * If the vcpu is locked, then it is running on some 2947 * If the vcpu is locked, then it is running on some
2943 * other cpu and therefore it is not cached on the 2948 * other cpu and therefore it is not cached on the
@@ -2954,6 +2959,8 @@ static void decache_vcpus_on_cpu(int cpu)
2954 mutex_unlock(&vcpu->mutex); 2959 mutex_unlock(&vcpu->mutex);
2955 } 2960 }
2956 } 2961 }
2962 spin_unlock(&vm->lock);
2963 }
2957 spin_unlock(&kvm_lock); 2964 spin_unlock(&kvm_lock);
2958} 2965}
2959 2966
@@ -3078,8 +3085,9 @@ static u64 stat_get(void *_offset)
3078 spin_lock(&kvm_lock); 3085 spin_lock(&kvm_lock);
3079 list_for_each_entry(kvm, &vm_list, vm_list) 3086 list_for_each_entry(kvm, &vm_list, vm_list)
3080 for (i = 0; i < KVM_MAX_VCPUS; ++i) { 3087 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
3081 vcpu = &kvm->vcpus[i]; 3088 vcpu = kvm->vcpus[i];
3082 total += *(u32 *)((void *)vcpu + offset); 3089 if (vcpu)
3090 total += *(u32 *)((void *)vcpu + offset);
3083 } 3091 }
3084 spin_unlock(&kvm_lock); 3092 spin_unlock(&kvm_lock);
3085 return total; 3093 return total;
diff --git a/drivers/kvm/kvm_svm.h b/drivers/kvm/kvm_svm.h
index 82e5d77acbba..a0e415daef5b 100644
--- a/drivers/kvm/kvm_svm.h
+++ b/drivers/kvm/kvm_svm.h
@@ -23,7 +23,7 @@ static const u32 host_save_user_msrs[] = {
23struct kvm_vcpu; 23struct kvm_vcpu;
24 24
25struct vcpu_svm { 25struct vcpu_svm {
26 struct kvm_vcpu *vcpu; 26 struct kvm_vcpu vcpu;
27 struct vmcb *vmcb; 27 struct vmcb *vmcb;
28 unsigned long vmcb_pa; 28 unsigned long vmcb_pa;
29 struct svm_cpu_data *svm_data; 29 struct svm_cpu_data *svm_data;
diff --git a/drivers/kvm/svm.c b/drivers/kvm/svm.c
index 32481876d98b..0feec8558599 100644
--- a/drivers/kvm/svm.c
+++ b/drivers/kvm/svm.c
@@ -51,7 +51,7 @@ MODULE_LICENSE("GPL");
51 51
52static inline struct vcpu_svm *to_svm(struct kvm_vcpu *vcpu) 52static inline struct vcpu_svm *to_svm(struct kvm_vcpu *vcpu)
53{ 53{
54 return (struct vcpu_svm*)vcpu->_priv; 54 return container_of(vcpu, struct vcpu_svm, vcpu);
55} 55}
56 56
57unsigned long iopm_base; 57unsigned long iopm_base;
@@ -466,11 +466,6 @@ static void init_sys_seg(struct vmcb_seg *seg, uint32_t type)
466 seg->base = 0; 466 seg->base = 0;
467} 467}
468 468
469static int svm_vcpu_setup(struct kvm_vcpu *vcpu)
470{
471 return 0;
472}
473
474static void init_vmcb(struct vmcb *vmcb) 469static void init_vmcb(struct vmcb *vmcb)
475{ 470{
476 struct vmcb_control_area *control = &vmcb->control; 471 struct vmcb_control_area *control = &vmcb->control;
@@ -576,19 +571,27 @@ static void init_vmcb(struct vmcb *vmcb)
576 /* rdx = ?? */ 571 /* rdx = ?? */
577} 572}
578 573
579static int svm_create_vcpu(struct kvm_vcpu *vcpu) 574static struct kvm_vcpu *svm_create_vcpu(struct kvm *kvm, unsigned int id)
580{ 575{
581 struct vcpu_svm *svm; 576 struct vcpu_svm *svm;
582 struct page *page; 577 struct page *page;
583 int r; 578 int err;
584 579
585 r = -ENOMEM;
586 svm = kzalloc(sizeof *svm, GFP_KERNEL); 580 svm = kzalloc(sizeof *svm, GFP_KERNEL);
587 if (!svm) 581 if (!svm) {
588 goto out1; 582 err = -ENOMEM;
583 goto out;
584 }
585
586 err = kvm_vcpu_init(&svm->vcpu, kvm, id);
587 if (err)
588 goto free_svm;
589
589 page = alloc_page(GFP_KERNEL); 590 page = alloc_page(GFP_KERNEL);
590 if (!page) 591 if (!page) {
591 goto out2; 592 err = -ENOMEM;
593 goto uninit;
594 }
592 595
593 svm->vmcb = page_address(page); 596 svm->vmcb = page_address(page);
594 clear_page(svm->vmcb); 597 clear_page(svm->vmcb);
@@ -597,33 +600,29 @@ static int svm_create_vcpu(struct kvm_vcpu *vcpu)
597 memset(svm->db_regs, 0, sizeof(svm->db_regs)); 600 memset(svm->db_regs, 0, sizeof(svm->db_regs));
598 init_vmcb(svm->vmcb); 601 init_vmcb(svm->vmcb);
599 602
600 svm->vcpu = vcpu; 603 fx_init(&svm->vcpu);
601 vcpu->_priv = svm; 604 svm->vcpu.fpu_active = 1;
605 svm->vcpu.apic_base = 0xfee00000 | MSR_IA32_APICBASE_ENABLE;
606 if (svm->vcpu.vcpu_id == 0)
607 svm->vcpu.apic_base |= MSR_IA32_APICBASE_BSP;
602 608
603 fx_init(vcpu); 609 return &svm->vcpu;
604 vcpu->fpu_active = 1;
605 vcpu->apic_base = 0xfee00000 | MSR_IA32_APICBASE_ENABLE;
606 if (vcpu->vcpu_id == 0)
607 vcpu->apic_base |= MSR_IA32_APICBASE_BSP;
608 610
609 return 0; 611uninit:
610 612 kvm_vcpu_uninit(&svm->vcpu);
611out2: 613free_svm:
612 kfree(svm); 614 kfree(svm);
613out1: 615out:
614 return r; 616 return ERR_PTR(err);
615} 617}
616 618
617static void svm_free_vcpu(struct kvm_vcpu *vcpu) 619static void svm_free_vcpu(struct kvm_vcpu *vcpu)
618{ 620{
619 struct vcpu_svm *svm = to_svm(vcpu); 621 struct vcpu_svm *svm = to_svm(vcpu);
620 622
621 if (!svm) 623 __free_page(pfn_to_page(svm->vmcb_pa >> PAGE_SHIFT));
622 return; 624 kvm_vcpu_uninit(vcpu);
623 if (svm->vmcb)
624 __free_page(pfn_to_page(svm->vmcb_pa >> PAGE_SHIFT));
625 kfree(svm); 625 kfree(svm);
626 vcpu->_priv = NULL;
627} 626}
628 627
629static void svm_vcpu_load(struct kvm_vcpu *vcpu) 628static void svm_vcpu_load(struct kvm_vcpu *vcpu)
@@ -1591,34 +1590,33 @@ again:
1591#endif 1590#endif
1592 1591
1593#ifdef CONFIG_X86_64 1592#ifdef CONFIG_X86_64
1594 "mov %c[rbx](%[vcpu]), %%rbx \n\t" 1593 "mov %c[rbx](%[svm]), %%rbx \n\t"
1595 "mov %c[rcx](%[vcpu]), %%rcx \n\t" 1594 "mov %c[rcx](%[svm]), %%rcx \n\t"
1596 "mov %c[rdx](%[vcpu]), %%rdx \n\t" 1595 "mov %c[rdx](%[svm]), %%rdx \n\t"
1597 "mov %c[rsi](%[vcpu]), %%rsi \n\t" 1596 "mov %c[rsi](%[svm]), %%rsi \n\t"
1598 "mov %c[rdi](%[vcpu]), %%rdi \n\t" 1597 "mov %c[rdi](%[svm]), %%rdi \n\t"
1599 "mov %c[rbp](%[vcpu]), %%rbp \n\t" 1598 "mov %c[rbp](%[svm]), %%rbp \n\t"
1600 "mov %c[r8](%[vcpu]), %%r8 \n\t" 1599 "mov %c[r8](%[svm]), %%r8 \n\t"
1601 "mov %c[r9](%[vcpu]), %%r9 \n\t" 1600 "mov %c[r9](%[svm]), %%r9 \n\t"
1602 "mov %c[r10](%[vcpu]), %%r10 \n\t" 1601 "mov %c[r10](%[svm]), %%r10 \n\t"
1603 "mov %c[r11](%[vcpu]), %%r11 \n\t" 1602 "mov %c[r11](%[svm]), %%r11 \n\t"
1604 "mov %c[r12](%[vcpu]), %%r12 \n\t" 1603 "mov %c[r12](%[svm]), %%r12 \n\t"
1605 "mov %c[r13](%[vcpu]), %%r13 \n\t" 1604 "mov %c[r13](%[svm]), %%r13 \n\t"
1606 "mov %c[r14](%[vcpu]), %%r14 \n\t" 1605 "mov %c[r14](%[svm]), %%r14 \n\t"
1607 "mov %c[r15](%[vcpu]), %%r15 \n\t" 1606 "mov %c[r15](%[svm]), %%r15 \n\t"
1608#else 1607#else
1609 "mov %c[rbx](%[vcpu]), %%ebx \n\t" 1608 "mov %c[rbx](%[svm]), %%ebx \n\t"
1610 "mov %c[rcx](%[vcpu]), %%ecx \n\t" 1609 "mov %c[rcx](%[svm]), %%ecx \n\t"
1611 "mov %c[rdx](%[vcpu]), %%edx \n\t" 1610 "mov %c[rdx](%[svm]), %%edx \n\t"
1612 "mov %c[rsi](%[vcpu]), %%esi \n\t" 1611 "mov %c[rsi](%[svm]), %%esi \n\t"
1613 "mov %c[rdi](%[vcpu]), %%edi \n\t" 1612 "mov %c[rdi](%[svm]), %%edi \n\t"
1614 "mov %c[rbp](%[vcpu]), %%ebp \n\t" 1613 "mov %c[rbp](%[svm]), %%ebp \n\t"
1615#endif 1614#endif
1616 1615
1617#ifdef CONFIG_X86_64 1616#ifdef CONFIG_X86_64
1618 /* Enter guest mode */ 1617 /* Enter guest mode */
1619 "push %%rax \n\t" 1618 "push %%rax \n\t"
1620 "mov %c[svm](%[vcpu]), %%rax \n\t" 1619 "mov %c[vmcb](%[svm]), %%rax \n\t"
1621 "mov %c[vmcb](%%rax), %%rax \n\t"
1622 SVM_VMLOAD "\n\t" 1620 SVM_VMLOAD "\n\t"
1623 SVM_VMRUN "\n\t" 1621 SVM_VMRUN "\n\t"
1624 SVM_VMSAVE "\n\t" 1622 SVM_VMSAVE "\n\t"
@@ -1626,8 +1624,7 @@ again:
1626#else 1624#else
1627 /* Enter guest mode */ 1625 /* Enter guest mode */
1628 "push %%eax \n\t" 1626 "push %%eax \n\t"
1629 "mov %c[svm](%[vcpu]), %%eax \n\t" 1627 "mov %c[vmcb](%[svm]), %%eax \n\t"
1630 "mov %c[vmcb](%%eax), %%eax \n\t"
1631 SVM_VMLOAD "\n\t" 1628 SVM_VMLOAD "\n\t"
1632 SVM_VMRUN "\n\t" 1629 SVM_VMRUN "\n\t"
1633 SVM_VMSAVE "\n\t" 1630 SVM_VMSAVE "\n\t"
@@ -1636,55 +1633,54 @@ again:
1636 1633
1637 /* Save guest registers, load host registers */ 1634 /* Save guest registers, load host registers */
1638#ifdef CONFIG_X86_64 1635#ifdef CONFIG_X86_64
1639 "mov %%rbx, %c[rbx](%[vcpu]) \n\t" 1636 "mov %%rbx, %c[rbx](%[svm]) \n\t"
1640 "mov %%rcx, %c[rcx](%[vcpu]) \n\t" 1637 "mov %%rcx, %c[rcx](%[svm]) \n\t"
1641 "mov %%rdx, %c[rdx](%[vcpu]) \n\t" 1638 "mov %%rdx, %c[rdx](%[svm]) \n\t"
1642 "mov %%rsi, %c[rsi](%[vcpu]) \n\t" 1639 "mov %%rsi, %c[rsi](%[svm]) \n\t"
1643 "mov %%rdi, %c[rdi](%[vcpu]) \n\t" 1640 "mov %%rdi, %c[rdi](%[svm]) \n\t"
1644 "mov %%rbp, %c[rbp](%[vcpu]) \n\t" 1641 "mov %%rbp, %c[rbp](%[svm]) \n\t"
1645 "mov %%r8, %c[r8](%[vcpu]) \n\t" 1642 "mov %%r8, %c[r8](%[svm]) \n\t"
1646 "mov %%r9, %c[r9](%[vcpu]) \n\t" 1643 "mov %%r9, %c[r9](%[svm]) \n\t"
1647 "mov %%r10, %c[r10](%[vcpu]) \n\t" 1644 "mov %%r10, %c[r10](%[svm]) \n\t"
1648 "mov %%r11, %c[r11](%[vcpu]) \n\t" 1645 "mov %%r11, %c[r11](%[svm]) \n\t"
1649 "mov %%r12, %c[r12](%[vcpu]) \n\t" 1646 "mov %%r12, %c[r12](%[svm]) \n\t"
1650 "mov %%r13, %c[r13](%[vcpu]) \n\t" 1647 "mov %%r13, %c[r13](%[svm]) \n\t"
1651 "mov %%r14, %c[r14](%[vcpu]) \n\t" 1648 "mov %%r14, %c[r14](%[svm]) \n\t"
1652 "mov %%r15, %c[r15](%[vcpu]) \n\t" 1649 "mov %%r15, %c[r15](%[svm]) \n\t"
1653 1650
1654 "pop %%r15; pop %%r14; pop %%r13; pop %%r12;" 1651 "pop %%r15; pop %%r14; pop %%r13; pop %%r12;"
1655 "pop %%r11; pop %%r10; pop %%r9; pop %%r8;" 1652 "pop %%r11; pop %%r10; pop %%r9; pop %%r8;"
1656 "pop %%rbp; pop %%rdi; pop %%rsi;" 1653 "pop %%rbp; pop %%rdi; pop %%rsi;"
1657 "pop %%rdx; pop %%rcx; pop %%rbx; \n\t" 1654 "pop %%rdx; pop %%rcx; pop %%rbx; \n\t"
1658#else 1655#else
1659 "mov %%ebx, %c[rbx](%[vcpu]) \n\t" 1656 "mov %%ebx, %c[rbx](%[svm]) \n\t"
1660 "mov %%ecx, %c[rcx](%[vcpu]) \n\t" 1657 "mov %%ecx, %c[rcx](%[svm]) \n\t"
1661 "mov %%edx, %c[rdx](%[vcpu]) \n\t" 1658 "mov %%edx, %c[rdx](%[svm]) \n\t"
1662 "mov %%esi, %c[rsi](%[vcpu]) \n\t" 1659 "mov %%esi, %c[rsi](%[svm]) \n\t"
1663 "mov %%edi, %c[rdi](%[vcpu]) \n\t" 1660 "mov %%edi, %c[rdi](%[svm]) \n\t"
1664 "mov %%ebp, %c[rbp](%[vcpu]) \n\t" 1661 "mov %%ebp, %c[rbp](%[svm]) \n\t"
1665 1662
1666 "pop %%ebp; pop %%edi; pop %%esi;" 1663 "pop %%ebp; pop %%edi; pop %%esi;"
1667 "pop %%edx; pop %%ecx; pop %%ebx; \n\t" 1664 "pop %%edx; pop %%ecx; pop %%ebx; \n\t"
1668#endif 1665#endif
1669 : 1666 :
1670 : [vcpu]"a"(vcpu), 1667 : [svm]"a"(svm),
1671 [svm]"i"(offsetof(struct kvm_vcpu, _priv)),
1672 [vmcb]"i"(offsetof(struct vcpu_svm, vmcb_pa)), 1668 [vmcb]"i"(offsetof(struct vcpu_svm, vmcb_pa)),
1673 [rbx]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_RBX])), 1669 [rbx]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_RBX])),
1674 [rcx]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_RCX])), 1670 [rcx]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_RCX])),
1675 [rdx]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_RDX])), 1671 [rdx]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_RDX])),
1676 [rsi]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_RSI])), 1672 [rsi]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_RSI])),
1677 [rdi]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_RDI])), 1673 [rdi]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_RDI])),
1678 [rbp]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_RBP])) 1674 [rbp]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_RBP]))
1679#ifdef CONFIG_X86_64 1675#ifdef CONFIG_X86_64
1680 ,[r8 ]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R8 ])), 1676 ,[r8 ]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R8])),
1681 [r9 ]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R9 ])), 1677 [r9 ]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R9 ])),
1682 [r10]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R10])), 1678 [r10]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R10])),
1683 [r11]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R11])), 1679 [r11]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R11])),
1684 [r12]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R12])), 1680 [r12]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R12])),
1685 [r13]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R13])), 1681 [r13]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R13])),
1686 [r14]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R14])), 1682 [r14]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R14])),
1687 [r15]"i"(offsetof(struct kvm_vcpu, regs[VCPU_REGS_R15])) 1683 [r15]"i"(offsetof(struct vcpu_svm,vcpu.regs[VCPU_REGS_R15]))
1688#endif 1684#endif
1689 : "cc", "memory" ); 1685 : "cc", "memory" );
1690 1686
@@ -1865,7 +1861,6 @@ static struct kvm_arch_ops svm_arch_ops = {
1865 1861
1866 .run = svm_vcpu_run, 1862 .run = svm_vcpu_run,
1867 .skip_emulated_instruction = skip_emulated_instruction, 1863 .skip_emulated_instruction = skip_emulated_instruction,
1868 .vcpu_setup = svm_vcpu_setup,
1869 .patch_hypercall = svm_patch_hypercall, 1864 .patch_hypercall = svm_patch_hypercall,
1870}; 1865};
1871 1866
diff --git a/drivers/kvm/vmx.c b/drivers/kvm/vmx.c
index 96837d6ed50b..df5787823309 100644
--- a/drivers/kvm/vmx.c
+++ b/drivers/kvm/vmx.c
@@ -39,7 +39,7 @@ struct vmcs {
39}; 39};
40 40
41struct vcpu_vmx { 41struct vcpu_vmx {
42 struct kvm_vcpu *vcpu; 42 struct kvm_vcpu vcpu;
43 int launched; 43 int launched;
44 struct kvm_msr_entry *guest_msrs; 44 struct kvm_msr_entry *guest_msrs;
45 struct kvm_msr_entry *host_msrs; 45 struct kvm_msr_entry *host_msrs;
@@ -60,7 +60,7 @@ struct vcpu_vmx {
60 60
61static inline struct vcpu_vmx *to_vmx(struct kvm_vcpu *vcpu) 61static inline struct vcpu_vmx *to_vmx(struct kvm_vcpu *vcpu)
62{ 62{
63 return (struct vcpu_vmx*)vcpu->_priv; 63 return container_of(vcpu, struct vcpu_vmx, vcpu);
64} 64}
65 65
66static int init_rmode_tss(struct kvm *kvm); 66static int init_rmode_tss(struct kvm *kvm);
@@ -2302,46 +2302,62 @@ static void vmx_free_vmcs(struct kvm_vcpu *vcpu)
2302 2302
2303static void vmx_free_vcpu(struct kvm_vcpu *vcpu) 2303static void vmx_free_vcpu(struct kvm_vcpu *vcpu)
2304{ 2304{
2305 struct vcpu_vmx *vmx = to_vmx(vcpu);
2306
2305 vmx_free_vmcs(vcpu); 2307 vmx_free_vmcs(vcpu);
2308 kfree(vmx->host_msrs);
2309 kfree(vmx->guest_msrs);
2310 kvm_vcpu_uninit(vcpu);
2311 kfree(vmx);
2306} 2312}
2307 2313
2308static int vmx_create_vcpu(struct kvm_vcpu *vcpu) 2314static struct kvm_vcpu *vmx_create_vcpu(struct kvm *kvm, unsigned int id)
2309{ 2315{
2310 struct vcpu_vmx *vmx; 2316 int err;
2317 struct vcpu_vmx *vmx = kzalloc(sizeof(*vmx), GFP_KERNEL);
2311 2318
2312 vmx = kzalloc(sizeof(*vmx), GFP_KERNEL);
2313 if (!vmx) 2319 if (!vmx)
2314 return -ENOMEM; 2320 return ERR_PTR(-ENOMEM);
2321
2322 err = kvm_vcpu_init(&vmx->vcpu, kvm, id);
2323 if (err)
2324 goto free_vcpu;
2315 2325
2316 vmx->guest_msrs = kmalloc(PAGE_SIZE, GFP_KERNEL); 2326 vmx->guest_msrs = kmalloc(PAGE_SIZE, GFP_KERNEL);
2317 if (!vmx->guest_msrs) 2327 if (!vmx->guest_msrs) {
2318 goto out_free; 2328 err = -ENOMEM;
2329 goto uninit_vcpu;
2330 }
2319 2331
2320 vmx->host_msrs = kmalloc(PAGE_SIZE, GFP_KERNEL); 2332 vmx->host_msrs = kmalloc(PAGE_SIZE, GFP_KERNEL);
2321 if (!vmx->host_msrs) 2333 if (!vmx->host_msrs)
2322 goto out_free; 2334 goto free_guest_msrs;
2323 2335
2324 vmx->vmcs = alloc_vmcs(); 2336 vmx->vmcs = alloc_vmcs();
2325 if (!vmx->vmcs) 2337 if (!vmx->vmcs)
2326 goto out_free; 2338 goto free_msrs;
2327 2339
2328 vmcs_clear(vmx->vmcs); 2340 vmcs_clear(vmx->vmcs);
2329 2341
2330 vmx->vcpu = vcpu; 2342 vmx_vcpu_load(&vmx->vcpu);
2331 vcpu->_priv = vmx; 2343 err = vmx_vcpu_setup(&vmx->vcpu);
2332 2344 vmx_vcpu_put(&vmx->vcpu);
2333 return 0; 2345 if (err)
2334 2346 goto free_vmcs;
2335out_free: 2347
2336 if (vmx->host_msrs) 2348 return &vmx->vcpu;
2337 kfree(vmx->host_msrs); 2349
2338 2350free_vmcs:
2339 if (vmx->guest_msrs) 2351 free_vmcs(vmx->vmcs);
2340 kfree(vmx->guest_msrs); 2352free_msrs:
2341 2353 kfree(vmx->host_msrs);
2354free_guest_msrs:
2355 kfree(vmx->guest_msrs);
2356uninit_vcpu:
2357 kvm_vcpu_uninit(&vmx->vcpu);
2358free_vcpu:
2342 kfree(vmx); 2359 kfree(vmx);
2343 2360 return ERR_PTR(err);
2344 return -ENOMEM;
2345} 2361}
2346 2362
2347static struct kvm_arch_ops vmx_arch_ops = { 2363static struct kvm_arch_ops vmx_arch_ops = {
@@ -2389,7 +2405,6 @@ static struct kvm_arch_ops vmx_arch_ops = {
2389 2405
2390 .run = vmx_vcpu_run, 2406 .run = vmx_vcpu_run,
2391 .skip_emulated_instruction = skip_emulated_instruction, 2407 .skip_emulated_instruction = skip_emulated_instruction,
2392 .vcpu_setup = vmx_vcpu_setup,
2393 .patch_hypercall = vmx_patch_hypercall, 2408 .patch_hypercall = vmx_patch_hypercall,
2394}; 2409};
2395 2410