[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 16/18] kvm: Separate TCG from KVM cpu execution
From: |
Jan Kiszka |
Subject: |
[Qemu-devel] [PATCH 16/18] kvm: Separate TCG from KVM cpu execution |
Date: |
Mon, 10 Jan 2011 09:32:09 +0100 |
From: Jan Kiszka <address@hidden>
Mixing up TCG bits with KVM already led to problems around eflags
emulation on x86. Moreover, quite some code that TCG requires on cpu
enty/exit is useless for KVM. So dispatch between tcg_cpu_exec and
kvm_cpu_exec as early as possible.
The core logic of cpu_halted from cpu_exec is added to
kvm_arch_process_irqchip_events. Moving away from cpu_exec makes
exception_index meaningless for KVM, we can simply pass the exit reason
directly (only "EXCP_DEBUG vs. rest" is relevant).
Signed-off-by: Jan Kiszka <address@hidden>
---
cpu-exec.c | 19 ++++++-------------
cpus.c | 10 +++++-----
kvm-all.c | 19 +++++++++----------
target-i386/kvm.c | 6 +++---
4 files changed, 23 insertions(+), 31 deletions(-)
diff --git a/cpu-exec.c b/cpu-exec.c
index 8c9fb8b..e4fe4f8 100644
--- a/cpu-exec.c
+++ b/cpu-exec.c
@@ -248,13 +248,11 @@ int cpu_exec(CPUState *env1)
}
#if defined(TARGET_I386)
- if (!kvm_enabled()) {
- /* put eflags in CPU temporary format */
- CC_SRC = env->eflags & (CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C);
- DF = 1 - (2 * ((env->eflags >> 10) & 1));
- CC_OP = CC_OP_EFLAGS;
- env->eflags &= ~(DF_MASK | CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C);
- }
+ /* put eflags in CPU temporary format */
+ CC_SRC = env->eflags & (CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C);
+ DF = 1 - (2 * ((env->eflags >> 10) & 1));
+ CC_OP = CC_OP_EFLAGS;
+ env->eflags &= ~(DF_MASK | CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C);
#elif defined(TARGET_SPARC)
#elif defined(TARGET_M68K)
env->cc_op = CC_OP_FLAGS;
@@ -279,7 +277,7 @@ int cpu_exec(CPUState *env1)
if (setjmp(env->jmp_env) == 0) {
#if defined(__sparc__) && !defined(CONFIG_SOLARIS)
#undef env
- env = cpu_single_env;
+ env = cpu_single_env;
#define env cpu_single_env
#endif
/* if an exception is pending, we execute it here */
@@ -340,11 +338,6 @@ int cpu_exec(CPUState *env1)
}
}
- if (kvm_enabled()) {
- kvm_cpu_exec(env);
- longjmp(env->jmp_env, 1);
- }
-
next_tb = 0; /* force lookup of first TB */
for(;;) {
interrupt_request = env->interrupt_request;
diff --git a/cpus.c b/cpus.c
index 4a4d130..e4ff314 100644
--- a/cpus.c
+++ b/cpus.c
@@ -728,8 +728,6 @@ static void qemu_kvm_wait_io_event(CPUState *env)
qemu_wait_io_event_common(env);
}
-static int qemu_cpu_exec(CPUState *env);
-
static void *qemu_kvm_cpu_thread_fn(void *arg)
{
CPUState *env = arg;
@@ -756,7 +754,7 @@ static void *qemu_kvm_cpu_thread_fn(void *arg)
while (1) {
if (cpu_can_run(env)) {
- qemu_cpu_exec(env);
+ kvm_cpu_exec(env);
}
qemu_kvm_wait_io_event(env);
}
@@ -959,7 +957,7 @@ void vm_stop(int reason)
#endif
-static int qemu_cpu_exec(CPUState *env)
+static int tcg_cpu_exec(CPUState *env)
{
int ret;
#ifdef CONFIG_PROFILER
@@ -1014,9 +1012,11 @@ bool cpu_exec_all(void)
break;
}
if (cpu_can_run(env)) {
- r = qemu_cpu_exec(env);
if (kvm_enabled()) {
+ r = kvm_cpu_exec(env);
qemu_kvm_eat_signals(env);
+ } else {
+ r = tcg_cpu_exec(env);
}
if (r == EXCP_DEBUG) {
break;
diff --git a/kvm-all.c b/kvm-all.c
index 0abe088..fd5a137 100644
--- a/kvm-all.c
+++ b/kvm-all.c
@@ -823,10 +823,11 @@ int kvm_cpu_exec(CPUState *env)
if (kvm_arch_process_irqchip_events(env)) {
env->exit_request = 0;
- env->exception_index = EXCP_HLT;
- return 0;
+ return EXCP_HLT;
}
+ cpu_single_env = env;
+
do {
if (env->kvm_vcpu_dirty) {
kvm_arch_put_registers(env, KVM_PUT_RUNTIME_STATE);
@@ -855,7 +856,6 @@ int kvm_cpu_exec(CPUState *env)
kvm_flush_coalesced_mmio_buffer();
if (ret == -EINTR || ret == -EAGAIN) {
- cpu_exit(env);
DPRINTF("io window exit\n");
ret = 0;
break;
@@ -906,8 +906,8 @@ int kvm_cpu_exec(CPUState *env)
DPRINTF("kvm_exit_debug\n");
#ifdef KVM_CAP_SET_GUEST_DEBUG
if (kvm_arch_debug(&run->debug.arch)) {
- env->exception_index = EXCP_DEBUG;
- return 0;
+ ret = EXCP_DEBUG;
+ goto out;
}
/* re-enter, this exception was guest-internal */
ret = 1;
@@ -923,13 +923,12 @@ int kvm_cpu_exec(CPUState *env)
if (ret < 0) {
cpu_dump_state(env, stderr, fprintf, CPU_DUMP_CODE);
vm_stop(0);
- env->exit_request = 1;
- }
- if (env->exit_request) {
- env->exit_request = 0;
- env->exception_index = EXCP_INTERRUPT;
}
+ ret = EXCP_INTERRUPT;
+out:
+ env->exit_request = 0;
+ cpu_single_env = NULL;
return ret;
}
diff --git a/target-i386/kvm.c b/target-i386/kvm.c
index a7acd53..16dacb8 100644
--- a/target-i386/kvm.c
+++ b/target-i386/kvm.c
@@ -1563,12 +1563,13 @@ int kvm_arch_post_run(CPUState *env, struct kvm_run
*run)
int kvm_arch_process_irqchip_events(CPUState *env)
{
+ if (env->interrupt_request & (CPU_INTERRUPT_HARD | CPU_INTERRUPT_NMI)) {
+ env->halted = 0;
+ }
if (env->interrupt_request & CPU_INTERRUPT_INIT) {
kvm_cpu_synchronize_state(env);
do_cpu_init(env);
- env->exception_index = EXCP_HALTED;
}
-
if (env->interrupt_request & CPU_INTERRUPT_SIPI) {
kvm_cpu_synchronize_state(env);
do_cpu_sipi(env);
@@ -1583,7 +1584,6 @@ static int kvm_handle_halt(CPUState *env)
(env->eflags & IF_MASK)) &&
!(env->interrupt_request & CPU_INTERRUPT_NMI)) {
env->halted = 1;
- env->exception_index = EXCP_HLT;
return 0;
}
--
1.7.1
- [Qemu-devel] [PATCH 13/18] kvm: Unconditionally reenter kernel after IO exits, (continued)
- [Qemu-devel] [PATCH 13/18] kvm: Unconditionally reenter kernel after IO exits, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 15/18] kvm: Leave kvm_cpu_exec directly after KVM_EXIT_SHUTDOWN, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 17/18] kvm: x86: Prepare VCPU loop for in-kernel irqchip, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 02/18] kvm: Drop redundant kvm_enabled from kvm_cpu_thread_fn, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 01/18] Revert "kvm: Drop return value of kvm_cpu_exec", Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 05/18] kvm: Set up signal mask also for !CONFIG_IOTHREAD, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 11/18] Introduce VCPU self-signaling service, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 18/18] kvm: Drop return values from kvm_arch_pre/post_run, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 16/18] kvm: Separate TCG from KVM cpu execution,
Jan Kiszka <=
- [Qemu-devel] [PATCH 14/18] kvm: Remove static return code of kvm_handle_io, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 12/18] kvm: Move irqchip event processing out of inner loop, Jan Kiszka, 2011/01/10
- [Qemu-devel] [PATCH 07/18] kvm: Add MCE signal support for !CONFIG_IOTHREAD, Jan Kiszka, 2011/01/10
[Qemu-devel] Re: [PATCH 00/18] [uq/master] MCE & IO exit fixes, prepare for VCPU loop reuse, Jan Kiszka, 2011/01/10