Distinguish warm reset from cold reset by introducing
cold/warm reset helper function instead of single reset routines.
Signed-off-by: Isaku Yamahata<address@hidden>
---
hw/hw.h | 7 +++++
sysemu.h | 4 +++
vl.c | 89 +++++++++++++++++++++++++++++++++++++++++++++++++++----------
3 files changed, 85 insertions(+), 15 deletions(-)
diff --git a/hw/hw.h b/hw/hw.h
index 4405092..6fb844e 100644
--- a/hw/hw.h
+++ b/hw/hw.h
@@ -269,6 +269,13 @@ void register_device_unmigratable(DeviceState *dev, const
char *idstr,
typedef void QEMUResetHandler(void *opaque);
+
+void qemu_register_cold_reset(QEMUResetHandler *func, void *opaque);
+void qemu_unregister_cold_reset(QEMUResetHandler *func, void *opaque);
+void qemu_register_warm_reset(QEMUResetHandler *func, void *opaque);
+void qemu_unregister_warm_reset(QEMUResetHandler *func, void *opaque);
+/* those two functions are obsoleted by cold/warm reset API. */
void qemu_register_reset(QEMUResetHandler *func, void *opaque);
void qemu_unregister_reset(QEMUResetHandler *func, void *opaque);
diff --git a/sysemu.h b/sysemu.h
index 7fc4e20..927892a 100644
--- a/sysemu.h
+++ b/sysemu.h
@@ -48,7 +48,11 @@ int64_t cpu_get_ticks(void);
void cpu_enable_ticks(void);
void cpu_disable_ticks(void);
+/* transitional compat = qemu_system_warm_reset_request() */
void qemu_system_reset_request(void);
+
+void qemu_system_cold_reset_request(void);
+void qemu_system_warm_reset_request(void);
void qemu_system_shutdown_request(void);
void qemu_system_powerdown_request(void);
extern qemu_irq qemu_system_powerdown;
diff --git a/vl.c b/vl.c
index a919a32..609d74c 100644
--- a/vl.c
+++ b/vl.c
@@ -1122,9 +1122,13 @@ typedef struct QEMUResetEntry {
} QEMUResetEntry;
QTAILQ_HEAD(reset_handlers, QEMUResetEntry);
-static struct reset_handlers reset_handlers =
- QTAILQ_HEAD_INITIALIZER(reset_handlers);
-static int reset_requested;
+
+static struct reset_handlers cold_reset_handlers =
+ QTAILQ_HEAD_INITIALIZER(cold_reset_handlers);
+static struct reset_handlers warm_reset_handlers =
+ QTAILQ_HEAD_INITIALIZER(warm_reset_handlers);
+static int cold_reset_requested;
+static int warm_reset_requested;
static int shutdown_requested;
static int powerdown_requested;
int debug_requested;
@@ -1142,9 +1146,14 @@ static int qemu_shutdown_requested(void)
return qemu_requested(&shutdown_requested);
}
-static int qemu_reset_requested(void)
+static int qemu_cold_reset_requested(void)
+{
+ return qemu_requested(&cold_reset_requested);
+}
+
+static int qemu_warm_reset_requested(void)
{
- return qemu_requested(&reset_requested);
+ return qemu_requested(&warm_reset_requested);
}
static int qemu_powerdown_requested(void)
@@ -1196,20 +1205,51 @@ static void qemu_system_reset_handler(struct
reset_handlers *handlers)
}
}
+/* obsolated by qemu_register_cold/warm_reset() */
void qemu_register_reset(QEMUResetHandler *func, void *opaque)
{
- qemu_register_reset_handler(func, opaque,&reset_handlers);
+ qemu_register_cold_reset(func, opaque);
+ qemu_register_warm_reset(func, opaque);
}
+/* obsolated by qemu_unregister_cold/warm_reset() */
void qemu_unregister_reset(QEMUResetHandler *func, void *opaque)
{
- qemu_unregister_reset_handler(func, opaque,&reset_handlers);
+ qemu_unregister_cold_reset(func, opaque);
+ qemu_unregister_warm_reset(func, opaque);
+}
+
+void qemu_register_cold_reset(QEMUResetHandler *func, void *opaque)
+{
+ qemu_register_reset_handler(func, opaque,&cold_reset_handlers);
+}
+
+void qemu_unregister_cold_reset(QEMUResetHandler *func, void *opaque)
+{
+ qemu_unregister_reset_handler(func, opaque,&cold_reset_handlers);
+}
+
+static void qemu_system_cold_reset(void)
+{
+ qemu_system_reset_handler(&cold_reset_handlers);
+ monitor_protocol_event(QEVENT_RESET, NULL); /* QEVENT_RESET_COLD? */
+ cpu_synchronize_all_post_reset();
+}
+
+void qemu_register_warm_reset(QEMUResetHandler *func, void *opaque)
+{
+ qemu_register_reset_handler(func, opaque,&warm_reset_handlers);
+}
+
+void qemu_unregister_warm_reset(QEMUResetHandler *func, void *opaque)
+{
+ qemu_unregister_reset_handler(func, opaque,&warm_reset_handlers);
}
-static void qemu_system_reset(void)
+static void qemu_system_warm_reset(void)
{
- qemu_system_reset_handler(&reset_handlers);
- monitor_protocol_event(QEVENT_RESET, NULL);
+ qemu_system_reset_handler(&warm_reset_handlers);
+ monitor_protocol_event(QEVENT_RESET, NULL); /* QEVENT_RESET_WARM? */
cpu_synchronize_all_post_reset();
}
@@ -1227,9 +1267,20 @@ static void qemu_system_request_reboot_check(int
*requested)
qemu_system_request(requested);
}
+void qemu_system_cold_reset_request(void)
+{
+ qemu_system_request_reboot_check(&cold_reset_requested);
+}
+
+void qemu_system_warm_reset_request(void)
+{
+ qemu_system_request_reboot_check(&warm_reset_requested);
+}
+
+/* trantitional compat */
void qemu_system_reset_request(void)
{
- qemu_system_request_reboot_check(&reset_requested);
+ qemu_system_request_reboot_check(&warm_reset_requested);
}
void qemu_system_shutdown_request(void)
@@ -1322,7 +1373,9 @@ static int vm_can_run(void)
{
if (powerdown_requested)
return 0;
- if (reset_requested)
+ if (cold_reset_requested)
+ return 0;
+ if (warm_reset_requested)
return 0;
if (shutdown_requested)
return 0;
@@ -1368,9 +1421,15 @@ static void main_loop(void)
} else
break;
}
- if (qemu_reset_requested()) {
+ if (qemu_warm_reset_requested()) {
+ pause_all_vcpus();
+ qemu_system_warm_reset();
+ resume_all_vcpus();
+ }
+ if (qemu_cold_reset_requested()) {
+ /* power cycle */
pause_all_vcpus();
- qemu_system_reset();
+ qemu_system_cold_reset();
resume_all_vcpus();
}
if (qemu_powerdown_requested()) {
@@ -2992,7 +3051,7 @@ int main(int argc, char **argv, char **envp)
exit(1);
}
- qemu_system_reset();
+ qemu_system_cold_reset();
if (loadvm) {
if (load_vmstate(loadvm)< 0) {
autostart = 0;