Merge commit '60e0df25e415b00cf35c4d214eaba9dc19aaa9e6' into upstream-merge
[qemu/qemu-dev-zwu.git] / qemu-kvm-x86.c
blob6c3a0a9adceb97c3695c2831385f29f62bc39122
1 /*
2 * qemu/kvm integration, x86 specific code
4 * Copyright (C) 2006-2008 Qumranet Technologies
6 * Licensed under the terms of the GNU GPL version 2 or higher.
7 */
9 #include "config.h"
10 #include "config-host.h"
12 #include <string.h>
13 #include "hw/hw.h"
14 #include "gdbstub.h"
15 #include <sys/io.h>
17 #include "qemu-kvm.h"
18 #include <pthread.h>
19 #include <sys/utsname.h>
20 #include <linux/kvm_para.h>
21 #include <sys/ioctl.h>
23 #include "kvm.h"
24 #include "hw/apic.h"
26 static int kvm_create_pit(kvm_context_t kvm)
28 #ifdef KVM_CAP_PIT
29 int r;
31 if (kvm_pit_in_kernel()) {
32 r = kvm_vm_ioctl(kvm_state, KVM_CREATE_PIT);
33 if (r < 0) {
34 fprintf(stderr, "Create kernel PIC irqchip failed\n");
35 return r;
37 if (!kvm_pit_reinject) {
38 r = kvm_reinject_control(kvm_context, 0);
39 if (r < 0) {
40 fprintf(stderr,
41 "failure to disable in-kernel PIT reinjection\n");
42 return r;
46 #endif
47 return 0;
50 #ifdef KVM_EXIT_TPR_ACCESS
52 static int kvm_handle_tpr_access(CPUState *env)
54 struct kvm_run *run = env->kvm_run;
55 kvm_tpr_access_report(env,
56 run->tpr_access.rip,
57 run->tpr_access.is_write);
58 return 0;
62 int kvm_enable_vapic(CPUState *env, uint64_t vapic)
64 struct kvm_vapic_addr va = {
65 .vapic_addr = vapic,
68 return kvm_vcpu_ioctl(env, KVM_SET_VAPIC_ADDR, &va);
71 #endif
73 extern CPUState *kvm_debug_cpu_requested;
75 int kvm_arch_run(CPUState *env)
77 int r = 0;
78 struct kvm_run *run = env->kvm_run;
80 switch (run->exit_reason) {
81 #ifdef KVM_EXIT_SET_TPR
82 case KVM_EXIT_SET_TPR:
83 break;
84 #endif
85 #ifdef KVM_EXIT_TPR_ACCESS
86 case KVM_EXIT_TPR_ACCESS:
87 r = kvm_handle_tpr_access(env);
88 break;
89 #endif
90 #ifdef KVM_CAP_SET_GUEST_DEBUG
91 case KVM_EXIT_DEBUG:
92 DPRINTF("kvm_exit_debug\n");
93 r = kvm_handle_debug(&run->debug.arch);
94 if (r == EXCP_DEBUG) {
95 kvm_debug_cpu_requested = env;
96 env->stopped = 1;
98 break;
99 #endif /* KVM_CAP_SET_GUEST_DEBUG */
100 default:
101 r = -1;
102 break;
105 return r;
108 #ifdef KVM_CAP_IRQCHIP
110 int kvm_get_lapic(CPUState *env, struct kvm_lapic_state *s)
112 int r = 0;
114 if (!kvm_irqchip_in_kernel()) {
115 return r;
118 r = kvm_vcpu_ioctl(env, KVM_GET_LAPIC, s);
119 if (r < 0) {
120 fprintf(stderr, "KVM_GET_LAPIC failed\n");
122 return r;
125 int kvm_set_lapic(CPUState *env, struct kvm_lapic_state *s)
127 int r = 0;
129 if (!kvm_irqchip_in_kernel()) {
130 return 0;
133 r = kvm_vcpu_ioctl(env, KVM_SET_LAPIC, s);
135 if (r < 0) {
136 fprintf(stderr, "KVM_SET_LAPIC failed\n");
138 return r;
141 #endif
143 #ifdef KVM_CAP_PIT
145 int kvm_get_pit(kvm_context_t kvm, struct kvm_pit_state *s)
147 if (!kvm_pit_in_kernel()) {
148 return 0;
150 return kvm_vm_ioctl(kvm_state, KVM_GET_PIT, s);
153 int kvm_set_pit(kvm_context_t kvm, struct kvm_pit_state *s)
155 if (!kvm_pit_in_kernel()) {
156 return 0;
158 return kvm_vm_ioctl(kvm_state, KVM_SET_PIT, s);
161 #ifdef KVM_CAP_PIT_STATE2
162 int kvm_get_pit2(kvm_context_t kvm, struct kvm_pit_state2 *ps2)
164 if (!kvm_pit_in_kernel()) {
165 return 0;
167 return kvm_vm_ioctl(kvm_state, KVM_GET_PIT2, ps2);
170 int kvm_set_pit2(kvm_context_t kvm, struct kvm_pit_state2 *ps2)
172 if (!kvm_pit_in_kernel()) {
173 return 0;
175 return kvm_vm_ioctl(kvm_state, KVM_SET_PIT2, ps2);
178 #endif
179 #endif
181 int kvm_has_pit_state2(kvm_context_t kvm)
183 int r = 0;
185 #ifdef KVM_CAP_PIT_STATE2
186 r = kvm_check_extension(kvm_state, KVM_CAP_PIT_STATE2);
187 #endif
188 return r;
191 static void kvm_set_cr8(CPUState *env, uint64_t cr8)
193 env->kvm_run->cr8 = cr8;
196 #ifdef KVM_CAP_VAPIC
197 static int kvm_enable_tpr_access_reporting(CPUState *env)
199 int r;
200 struct kvm_tpr_access_ctl tac = { .enabled = 1 };
202 r = kvm_ioctl(env->kvm_state, KVM_CHECK_EXTENSION, KVM_CAP_VAPIC);
203 if (r <= 0) {
204 return -ENOSYS;
206 return kvm_vcpu_ioctl(env, KVM_TPR_ACCESS_REPORTING, &tac);
208 #endif
210 static int _kvm_arch_init_vcpu(CPUState *env)
212 kvm_arch_reset_vcpu(env);
214 #ifdef KVM_EXIT_TPR_ACCESS
215 kvm_enable_tpr_access_reporting(env);
216 #endif
217 return 0;
220 int kvm_arch_halt(CPUState *env)
223 if (!((env->interrupt_request & CPU_INTERRUPT_HARD) &&
224 (env->eflags & IF_MASK)) &&
225 !(env->interrupt_request & CPU_INTERRUPT_NMI)) {
226 env->halted = 1;
228 return 1;
231 void kvm_arch_pre_run(CPUState *env, struct kvm_run *run)
233 if (!kvm_irqchip_in_kernel()) {
234 kvm_set_cr8(env, cpu_get_apic_tpr(env->apic_state));
238 int kvm_arch_has_work(CPUState *env)
240 if (((env->interrupt_request & CPU_INTERRUPT_HARD) &&
241 (env->eflags & IF_MASK)) ||
242 (env->interrupt_request & CPU_INTERRUPT_NMI)) {
243 return 1;
245 return 0;
248 int kvm_arch_try_push_interrupts(void *opaque)
250 CPUState *env = cpu_single_env;
251 int r, irq;
253 if (kvm_is_ready_for_interrupt_injection(env) &&
254 (env->interrupt_request & CPU_INTERRUPT_HARD) &&
255 (env->eflags & IF_MASK)) {
256 env->interrupt_request &= ~CPU_INTERRUPT_HARD;
257 irq = cpu_get_pic_interrupt(env);
258 if (irq >= 0) {
259 r = kvm_inject_irq(env, irq);
260 if (r < 0) {
261 printf("cpu %d fail inject %x\n", env->cpu_index, irq);
266 return (env->interrupt_request & CPU_INTERRUPT_HARD) != 0;
269 #ifdef KVM_CAP_USER_NMI
270 void kvm_arch_push_nmi(void)
272 CPUState *env = cpu_single_env;
273 int r;
275 if (likely(!(env->interrupt_request & CPU_INTERRUPT_NMI))) {
276 return;
279 env->interrupt_request &= ~CPU_INTERRUPT_NMI;
280 r = kvm_inject_nmi(env);
281 if (r < 0) {
282 printf("cpu %d fail inject NMI\n", env->cpu_index);
285 #endif /* KVM_CAP_USER_NMI */
287 #ifdef CONFIG_KVM_DEVICE_ASSIGNMENT
288 void kvm_arch_do_ioperm(void *_data)
290 struct ioperm_data *data = _data;
291 ioperm(data->start_port, data->num, data->turn_on);
293 #endif
296 * Setup x86 specific IRQ routing
298 int kvm_arch_init_irq_routing(void)
300 int i, r;
302 if (kvm_irqchip && kvm_has_gsi_routing()) {
303 kvm_clear_gsi_routes();
304 for (i = 0; i < 8; ++i) {
305 if (i == 2) {
306 continue;
308 r = kvm_add_irq_route(i, KVM_IRQCHIP_PIC_MASTER, i);
309 if (r < 0) {
310 return r;
313 for (i = 8; i < 16; ++i) {
314 r = kvm_add_irq_route(i, KVM_IRQCHIP_PIC_SLAVE, i - 8);
315 if (r < 0) {
316 return r;
319 for (i = 0; i < 24; ++i) {
320 if (i == 0 && irq0override) {
321 r = kvm_add_irq_route(i, KVM_IRQCHIP_IOAPIC, 2);
322 } else if (i != 2 || !irq0override) {
323 r = kvm_add_irq_route(i, KVM_IRQCHIP_IOAPIC, i);
325 if (r < 0) {
326 return r;
329 kvm_commit_irq_routes();
331 return 0;
334 void kvm_arch_process_irqchip_events(CPUState *env)
336 if (env->interrupt_request & CPU_INTERRUPT_INIT) {
337 kvm_cpu_synchronize_state(env);
338 do_cpu_init(env);
340 if (env->interrupt_request & CPU_INTERRUPT_SIPI) {
341 kvm_cpu_synchronize_state(env);
342 do_cpu_sipi(env);
346 int kvm_arch_process_async_events(CPUState *env)
348 if (env->interrupt_request & CPU_INTERRUPT_MCE) {
349 /* We must not raise CPU_INTERRUPT_MCE if it's not supported. */
350 assert(env->mcg_cap);
352 env->interrupt_request &= ~CPU_INTERRUPT_MCE;
354 kvm_cpu_synchronize_state(env);
356 if (env->exception_injected == EXCP08_DBLE) {
357 /* this means triple fault */
358 qemu_system_reset_request();
359 env->exit_request = 1;
360 return 0;
362 env->exception_injected = EXCP12_MCHK;
363 env->has_error_code = 0;
365 env->halted = 0;
366 if (kvm_irqchip_in_kernel() && env->mp_state == KVM_MP_STATE_HALTED) {
367 env->mp_state = KVM_MP_STATE_RUNNABLE;
370 return 0;