Hi,
When dom0 is poweroff, the hypervisor panics by the assertion at
spinlock.c:51. So the system cannot power off.
This is because spin_lock_irq() is called in irq disabled context, and
ASSERT macro is enabled since cset 19001:b9721b2766c1.
This patch fixes it.
Thanks,
KAZ
Signed-off-by: Kazuhiro Suzuki <kaz@xxxxxxxxxxxxxx>
diff -r f8187a343ad2 xen/arch/x86/io_apic.c
--- a/xen/arch/x86/io_apic.c Fri Feb 20 17:02:36 2009 +0000
+++ b/xen/arch/x86/io_apic.c Thu Feb 26 16:56:31 2009 +0900
@@ -1779,6 +1779,22 @@ static inline void check_timer(void)
*/
#define PIC_IRQS (1 << PIC_CASCADE_IR)
+struct IO_APIC_route_entry *ioapic_pm_state=NULL;
+
+void ioapic_pm_state_alloc(void)
+{
+ int i, nr_entry = 0;
+
+ if (ioapic_pm_state != NULL)
+ return;
+
+ for (i = 0; i < nr_ioapics; i++)
+ nr_entry += nr_ioapic_registers[i];
+
+ ioapic_pm_state = _xmalloc(sizeof(struct IO_APIC_route_entry)*nr_entry,
+ sizeof(struct IO_APIC_route_entry));
+}
+
void __init setup_IO_APIC(void)
{
enable_IO_APIC();
@@ -1801,24 +1817,9 @@ void __init setup_IO_APIC(void)
init_IO_APIC_traps();
check_timer();
print_IO_APIC();
+ ioapic_pm_state_alloc();
register_keyhandler('z', print_IO_APIC_keyhandler, "print ioapic info");
-}
-
-struct IO_APIC_route_entry *ioapic_pm_state=NULL;
-
-void ioapic_pm_state_alloc(void)
-{
- int i, nr_entry = 0;
-
- if (ioapic_pm_state != NULL)
- return;
-
- for (i = 0; i < nr_ioapics; i++)
- nr_entry += nr_ioapic_registers[i];
-
- ioapic_pm_state = _xmalloc(sizeof(struct IO_APIC_route_entry)*nr_entry,
- sizeof(struct IO_APIC_route_entry));
}
int ioapic_suspend(void)
@@ -1826,8 +1827,6 @@ int ioapic_suspend(void)
struct IO_APIC_route_entry *entry;
unsigned long flags;
int apic,i;
-
- ioapic_pm_state_alloc();
if (ioapic_pm_state == NULL) {
printk("Cannot suspend ioapic due to lack of memory\n");
diff -r f8187a343ad2 xen/arch/x86/time.c
--- a/xen/arch/x86/time.c Fri Feb 20 17:02:36 2009 +0000
+++ b/xen/arch/x86/time.c Thu Feb 26 16:56:32 2009 +0900
@@ -603,17 +603,24 @@ static s_time_t read_platform_stime(void
return stime;
}
-static void platform_time_calibration(void)
+static void __platform_time_calibration(void)
{
u64 count;
s_time_t stamp;
- spin_lock_irq(&platform_timer_lock);
+ spin_lock(&platform_timer_lock);
count = plt_stamp64 + ((plt_src.read_counter() - plt_stamp) & plt_mask);
stamp = __read_platform_stime(count);
stime_platform_stamp = stamp;
platform_timer_stamp = count;
- spin_unlock_irq(&platform_timer_lock);
+ spin_unlock(&platform_timer_lock);
+}
+
+static void platform_time_calibration(void)
+{
+ local_irq_disable();
+ __platform_time_calibration();
+ local_irq_enable();
}
static void resume_platform_timer(void)
@@ -1277,7 +1284,7 @@ int time_suspend(void)
kill_timer(&calibration_timer);
/* Sync platform timer stamps. */
- platform_time_calibration();
+ __platform_time_calibration();
}
/* Better to cancel calibration timer for accuracy. */
_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
|