Commit cf7a2fe2eb6e100b21089faced28e8dfeaf39748
1 parent
7852e5da
SCI fixes
(Anthony Liguori) git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@4081 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
7 changed files
with
50 additions
and
8 deletions
hw/acpi.c
@@ -49,6 +49,7 @@ typedef struct PIIX4PMState { | @@ -49,6 +49,7 @@ typedef struct PIIX4PMState { | ||
49 | uint8_t smb_data1; | 49 | uint8_t smb_data1; |
50 | uint8_t smb_data[32]; | 50 | uint8_t smb_data[32]; |
51 | uint8_t smb_index; | 51 | uint8_t smb_index; |
52 | + qemu_irq irq; | ||
52 | } PIIX4PMState; | 53 | } PIIX4PMState; |
53 | 54 | ||
54 | #define RTC_EN (1 << 10) | 55 | #define RTC_EN (1 << 10) |
@@ -71,6 +72,8 @@ typedef struct PIIX4PMState { | @@ -71,6 +72,8 @@ typedef struct PIIX4PMState { | ||
71 | #define SMBHSTDAT1 0x06 | 72 | #define SMBHSTDAT1 0x06 |
72 | #define SMBBLKDAT 0x07 | 73 | #define SMBBLKDAT 0x07 |
73 | 74 | ||
75 | +PIIX4PMState *pm_state; | ||
76 | + | ||
74 | static uint32_t get_pmtmr(PIIX4PMState *s) | 77 | static uint32_t get_pmtmr(PIIX4PMState *s) |
75 | { | 78 | { |
76 | uint32_t d; | 79 | uint32_t d; |
@@ -97,11 +100,12 @@ static void pm_update_sci(PIIX4PMState *s) | @@ -97,11 +100,12 @@ static void pm_update_sci(PIIX4PMState *s) | ||
97 | pmsts = get_pmsts(s); | 100 | pmsts = get_pmsts(s); |
98 | sci_level = (((pmsts & s->pmen) & | 101 | sci_level = (((pmsts & s->pmen) & |
99 | (RTC_EN | PWRBTN_EN | GBL_EN | TMROF_EN)) != 0); | 102 | (RTC_EN | PWRBTN_EN | GBL_EN | TMROF_EN)) != 0); |
100 | - qemu_set_irq(s->dev.irq[0], sci_level); | 103 | + qemu_set_irq(s->irq, sci_level); |
101 | /* schedule a timer interruption if needed */ | 104 | /* schedule a timer interruption if needed */ |
102 | if ((s->pmen & TMROF_EN) && !(pmsts & TMROF_EN)) { | 105 | if ((s->pmen & TMROF_EN) && !(pmsts & TMROF_EN)) { |
103 | expire_time = muldiv64(s->tmr_overflow_time, ticks_per_sec, PM_FREQ); | 106 | expire_time = muldiv64(s->tmr_overflow_time, ticks_per_sec, PM_FREQ); |
104 | qemu_mod_timer(s->tmr_timer, expire_time); | 107 | qemu_mod_timer(s->tmr_timer, expire_time); |
108 | + s->tmr_overflow_time += 0x800000; | ||
105 | } else { | 109 | } else { |
106 | qemu_del_timer(s->tmr_timer); | 110 | qemu_del_timer(s->tmr_timer); |
107 | } | 111 | } |
@@ -467,7 +471,8 @@ static int pm_load(QEMUFile* f,void* opaque,int version_id) | @@ -467,7 +471,8 @@ static int pm_load(QEMUFile* f,void* opaque,int version_id) | ||
467 | return 0; | 471 | return 0; |
468 | } | 472 | } |
469 | 473 | ||
470 | -i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base) | 474 | +i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base, |
475 | + qemu_irq sci_irq) | ||
471 | { | 476 | { |
472 | PIIX4PMState *s; | 477 | PIIX4PMState *s; |
473 | uint8_t *pci_conf; | 478 | uint8_t *pci_conf; |
@@ -475,6 +480,7 @@ i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base) | @@ -475,6 +480,7 @@ i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base) | ||
475 | s = (PIIX4PMState *)pci_register_device(bus, | 480 | s = (PIIX4PMState *)pci_register_device(bus, |
476 | "PM", sizeof(PIIX4PMState), | 481 | "PM", sizeof(PIIX4PMState), |
477 | devfn, NULL, pm_write_config); | 482 | devfn, NULL, pm_write_config); |
483 | + pm_state = s; | ||
478 | pci_conf = s->dev.config; | 484 | pci_conf = s->dev.config; |
479 | pci_conf[0x00] = 0x86; | 485 | pci_conf[0x00] = 0x86; |
480 | pci_conf[0x01] = 0x80; | 486 | pci_conf[0x01] = 0x80; |
@@ -514,5 +520,16 @@ i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base) | @@ -514,5 +520,16 @@ i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base) | ||
514 | register_savevm("piix4_pm", 0, 1, pm_save, pm_load, s); | 520 | register_savevm("piix4_pm", 0, 1, pm_save, pm_load, s); |
515 | 521 | ||
516 | s->smbus = i2c_init_bus(); | 522 | s->smbus = i2c_init_bus(); |
523 | + s->irq = sci_irq; | ||
517 | return s->smbus; | 524 | return s->smbus; |
518 | } | 525 | } |
526 | + | ||
527 | +#if defined(TARGET_I386) | ||
528 | +void qemu_system_powerdown(void) | ||
529 | +{ | ||
530 | + if(pm_state->pmen & PWRBTN_EN) { | ||
531 | + pm_state->pmsts |= PWRBTN_EN; | ||
532 | + pm_update_sci(pm_state); | ||
533 | + } | ||
534 | +} | ||
535 | +#endif |
hw/mips_malta.c
@@ -905,7 +905,7 @@ void mips_malta_init (int ram_size, int vga_ram_size, | @@ -905,7 +905,7 @@ void mips_malta_init (int ram_size, int vga_ram_size, | ||
905 | piix4_devfn = piix4_init(pci_bus, 80); | 905 | piix4_devfn = piix4_init(pci_bus, 80); |
906 | pci_piix4_ide_init(pci_bus, hd, piix4_devfn + 1, i8259); | 906 | pci_piix4_ide_init(pci_bus, hd, piix4_devfn + 1, i8259); |
907 | usb_uhci_piix4_init(pci_bus, piix4_devfn + 2); | 907 | usb_uhci_piix4_init(pci_bus, piix4_devfn + 2); |
908 | - smbus = piix4_pm_init(pci_bus, piix4_devfn + 3, 0x1100); | 908 | + smbus = piix4_pm_init(pci_bus, piix4_devfn + 3, 0x1100, i8259[9]); |
909 | eeprom_buf = qemu_mallocz(8 * 256); /* XXX: make this persistent */ | 909 | eeprom_buf = qemu_mallocz(8 * 256); /* XXX: make this persistent */ |
910 | for (i = 0; i < 8; i++) { | 910 | for (i = 0; i < 8; i++) { |
911 | /* TODO: Populate SPD eeprom data. */ | 911 | /* TODO: Populate SPD eeprom data. */ |
hw/pc.c
@@ -981,7 +981,7 @@ static void pc_init1(int ram_size, int vga_ram_size, | @@ -981,7 +981,7 @@ static void pc_init1(int ram_size, int vga_ram_size, | ||
981 | i2c_bus *smbus; | 981 | i2c_bus *smbus; |
982 | 982 | ||
983 | /* TODO: Populate SPD eeprom data. */ | 983 | /* TODO: Populate SPD eeprom data. */ |
984 | - smbus = piix4_pm_init(pci_bus, piix3_devfn + 3, 0xb100); | 984 | + smbus = piix4_pm_init(pci_bus, piix3_devfn + 3, 0xb100, i8259[9]); |
985 | for (i = 0; i < 8; i++) { | 985 | for (i = 0; i < 8; i++) { |
986 | smbus_eeprom_device_init(smbus, 0x50 + i, eeprom_buf + (i * 256)); | 986 | smbus_eeprom_device_init(smbus, 0x50 + i, eeprom_buf + (i * 256)); |
987 | } | 987 | } |
hw/pc.h
@@ -88,7 +88,8 @@ int ioport_get_a20(void); | @@ -88,7 +88,8 @@ int ioport_get_a20(void); | ||
88 | 88 | ||
89 | /* acpi.c */ | 89 | /* acpi.c */ |
90 | extern int acpi_enabled; | 90 | extern int acpi_enabled; |
91 | -i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base); | 91 | +i2c_bus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base, |
92 | + qemu_irq sci_irq); | ||
92 | void piix4_smbus_register_device(SMBusDevice *dev, uint8_t addr); | 93 | void piix4_smbus_register_device(SMBusDevice *dev, uint8_t addr); |
93 | void acpi_bios_init(void); | 94 | void acpi_bios_init(void); |
94 | 95 |
hw/piix_pci.c
@@ -220,7 +220,6 @@ static void piix3_set_irq(qemu_irq *pic, int irq_num, int level) | @@ -220,7 +220,6 @@ static void piix3_set_irq(qemu_irq *pic, int irq_num, int level) | ||
220 | { | 220 | { |
221 | int i, pic_irq, pic_level; | 221 | int i, pic_irq, pic_level; |
222 | 222 | ||
223 | - piix3_dev->config[0x60 + irq_num] &= ~0x80; // enable bit | ||
224 | pci_irq_levels[irq_num] = level; | 223 | pci_irq_levels[irq_num] = level; |
225 | 224 | ||
226 | /* now we change the pic irq level according to the piix irq mappings */ | 225 | /* now we change the pic irq level according to the piix irq mappings */ |
sysemu.h
@@ -30,12 +30,16 @@ void cpu_disable_ticks(void); | @@ -30,12 +30,16 @@ void cpu_disable_ticks(void); | ||
30 | void qemu_system_reset_request(void); | 30 | void qemu_system_reset_request(void); |
31 | void qemu_system_shutdown_request(void); | 31 | void qemu_system_shutdown_request(void); |
32 | void qemu_system_powerdown_request(void); | 32 | void qemu_system_powerdown_request(void); |
33 | -#if !defined(TARGET_SPARC) | 33 | +int qemu_shutdown_requested(void); |
34 | +int qemu_reset_requested(void); | ||
35 | +int qemu_powerdown_requested(void); | ||
36 | +#if !defined(TARGET_SPARC) && !defined(TARGET_I386) | ||
34 | // Please implement a power failure function to signal the OS | 37 | // Please implement a power failure function to signal the OS |
35 | #define qemu_system_powerdown() do{}while(0) | 38 | #define qemu_system_powerdown() do{}while(0) |
36 | #else | 39 | #else |
37 | void qemu_system_powerdown(void); | 40 | void qemu_system_powerdown(void); |
38 | #endif | 41 | #endif |
42 | +void qemu_system_reset(void); | ||
39 | 43 | ||
40 | void cpu_save(QEMUFile *f, void *opaque); | 44 | void cpu_save(QEMUFile *f, void *opaque); |
41 | int cpu_load(QEMUFile *f, void *opaque, int version_id); | 45 | int cpu_load(QEMUFile *f, void *opaque, int version_id); |
vl.c
@@ -7306,6 +7306,27 @@ static int reset_requested; | @@ -7306,6 +7306,27 @@ static int reset_requested; | ||
7306 | static int shutdown_requested; | 7306 | static int shutdown_requested; |
7307 | static int powerdown_requested; | 7307 | static int powerdown_requested; |
7308 | 7308 | ||
7309 | +int qemu_shutdown_requested(void) | ||
7310 | +{ | ||
7311 | + int r = shutdown_requested; | ||
7312 | + shutdown_requested = 0; | ||
7313 | + return r; | ||
7314 | +} | ||
7315 | + | ||
7316 | +int qemu_reset_requested(void) | ||
7317 | +{ | ||
7318 | + int r = reset_requested; | ||
7319 | + reset_requested = 0; | ||
7320 | + return r; | ||
7321 | +} | ||
7322 | + | ||
7323 | +int qemu_powerdown_requested(void) | ||
7324 | +{ | ||
7325 | + int r = powerdown_requested; | ||
7326 | + powerdown_requested = 0; | ||
7327 | + return r; | ||
7328 | +} | ||
7329 | + | ||
7309 | void qemu_register_reset(QEMUResetHandler *func, void *opaque) | 7330 | void qemu_register_reset(QEMUResetHandler *func, void *opaque) |
7310 | { | 7331 | { |
7311 | QEMUResetEntry **pre, *re; | 7332 | QEMUResetEntry **pre, *re; |
@@ -7320,7 +7341,7 @@ void qemu_register_reset(QEMUResetHandler *func, void *opaque) | @@ -7320,7 +7341,7 @@ void qemu_register_reset(QEMUResetHandler *func, void *opaque) | ||
7320 | *pre = re; | 7341 | *pre = re; |
7321 | } | 7342 | } |
7322 | 7343 | ||
7323 | -static void qemu_system_reset(void) | 7344 | +void qemu_system_reset(void) |
7324 | { | 7345 | { |
7325 | QEMUResetEntry *re; | 7346 | QEMUResetEntry *re; |
7326 | 7347 |