Revision 7d932dfd

b/hw/hpet.c
30 30
#include "qemu-timer.h"
31 31
#include "hpet_emul.h"
32 32
#include "sysbus.h"
33
#include "mc146818rtc.h"
33 34

  
34 35
//#define HPET_DEBUG
35 36
#ifdef HPET_DEBUG
......
58 59
    SysBusDevice busdev;
59 60
    uint64_t hpet_offset;
60 61
    qemu_irq irqs[HPET_NUM_IRQ_ROUTES];
62
    uint8_t rtc_irq_level;
61 63
    HPETTimer timer[HPET_NUM_TIMERS];
62 64

  
63 65
    /* Memory-mapped, software visible registers */
......
69 71

  
70 72
static HPETState *hpet_statep;
71 73

  
72
uint32_t hpet_in_legacy_mode(void)
74
static uint32_t hpet_in_legacy_mode(HPETState *s)
73 75
{
74
    if (!hpet_statep) {
75
        return 0;
76
    }
77
    return hpet_statep->config & HPET_CFG_LEGACY;
76
    return s->config & HPET_CFG_LEGACY;
78 77
}
79 78

  
80 79
static uint32_t timer_int_route(struct HPETTimer *timer)
......
166 165
{
167 166
    int route;
168 167

  
169
    if (timer->tn <= 1 && hpet_in_legacy_mode()) {
168
    if (timer->tn <= 1 && hpet_in_legacy_mode(timer->state)) {
170 169
        /* if LegacyReplacementRoute bit is set, HPET specification requires
171 170
         * timer0 be routed to IRQ0 in NON-APIC or IRQ2 in the I/O APIC,
172 171
         * timer1 be routed to IRQ8 in NON-APIC or IRQ8 in the I/O APIC.
173 172
         */
174
        route = (timer->tn == 0) ? 0 : 8;
173
        route = (timer->tn == 0) ? 0 : RTC_ISA_IRQ;
175 174
    } else {
176 175
        route = timer_int_route(timer);
177 176
    }
......
515 514
            /* i8254 and RTC are disabled when HPET is in legacy mode */
516 515
            if (activating_bit(old_val, new_val, HPET_CFG_LEGACY)) {
517 516
                hpet_pit_disable();
517
                qemu_irq_lower(s->irqs[RTC_ISA_IRQ]);
518 518
            } else if (deactivating_bit(old_val, new_val, HPET_CFG_LEGACY)) {
519 519
                hpet_pit_enable();
520
                qemu_set_irq(s->irqs[RTC_ISA_IRQ], s->rtc_irq_level);
520 521
            }
521 522
            break;
522 523
        case HPET_CFG + 4:
......
607 608
    count = 1;
608 609
}
609 610

  
611
static void hpet_handle_rtc_irq(void *opaque, int n, int level)
612
{
613
    HPETState *s = FROM_SYSBUS(HPETState, opaque);
614

  
615
    s->rtc_irq_level = level;
616
    if (!hpet_in_legacy_mode(s)) {
617
        qemu_set_irq(s->irqs[RTC_ISA_IRQ], level);
618
    }
619
}
620

  
610 621
static int hpet_init(SysBusDevice *dev)
611 622
{
612 623
    HPETState *s = FROM_SYSBUS(HPETState, dev);
......
625 636
        timer->state = s;
626 637
    }
627 638

  
639
    isa_reserve_irq(RTC_ISA_IRQ);
640
    qdev_init_gpio_in(&dev->qdev, hpet_handle_rtc_irq, 1);
641

  
628 642
    /* HPET Area */
629 643
    iomemtype = cpu_register_io_memory(hpet_ram_read,
630 644
                                       hpet_ram_write, s);
b/hw/hpet_emul.h
47 47
#define HPET_TN_INT_ROUTE_CAP_SHIFT 32
48 48
#define HPET_TN_CFG_BITS_READONLY_OR_RESERVED 0xffff80b1U
49 49

  
50
#if defined TARGET_I386
51
extern uint32_t hpet_in_legacy_mode(void);
52
#endif
53

  
54 50
#endif
b/hw/mc146818rtc.c
27 27
#include "pc.h"
28 28
#include "apic.h"
29 29
#include "isa.h"
30
#include "hpet_emul.h"
31 30
#include "mc146818rtc.h"
32 31

  
33 32
//#define DEBUG_CMOS
......
101 100
    QEMUTimer *second_timer2;
102 101
} RTCState;
103 102

  
104
static void rtc_irq_raise(qemu_irq irq)
105
{
106
    /* When HPET is operating in legacy mode, RTC interrupts are disabled
107
     * We block qemu_irq_raise, but not qemu_irq_lower, in case legacy
108
     * mode is established while interrupt is raised. We want it to
109
     * be lowered in any case
110
     */
111
#if defined TARGET_I386
112
    if (!hpet_in_legacy_mode())
113
#endif
114
        qemu_irq_raise(irq);
115
}
116

  
117 103
static void rtc_set_time(RTCState *s);
118 104
static void rtc_copy_date(RTCState *s);
119 105

  
......
139 125
        apic_reset_irq_delivered();
140 126
        s->cmos_data[RTC_REG_C] |= 0xc0;
141 127
        DPRINTF_C("cmos: injecting from timer\n");
142
        rtc_irq_raise(s->irq);
128
        qemu_irq_raise(s->irq);
143 129
        if (apic_get_irq_delivered()) {
144 130
            s->irq_coalesced--;
145 131
            DPRINTF_C("cmos: coalesced irqs decreased to %d\n",
......
155 141
{
156 142
    int period_code, period;
157 143
    int64_t cur_clock, next_irq_clock;
158
    int enable_pie;
159 144

  
160 145
    period_code = s->cmos_data[RTC_REG_A] & 0x0f;
161
#if defined TARGET_I386
162
    /* disable periodic timer if hpet is in legacy mode, since interrupts are
163
     * disabled anyway.
164
     */
165
    enable_pie = !hpet_in_legacy_mode();
166
#else
167
    enable_pie = 1;
168
#endif
169 146
    if (period_code != 0
170
        && (((s->cmos_data[RTC_REG_B] & REG_B_PIE) && enable_pie)
147
        && ((s->cmos_data[RTC_REG_B] & REG_B_PIE)
171 148
            || ((s->cmos_data[RTC_REG_B] & REG_B_SQWE) && s->sqw_irq))) {
172 149
        if (period_code <= 2)
173 150
            period_code += 7;
......
206 183
            if (s->irq_reinject_on_ack_count >= RTC_REINJECT_ON_ACK_COUNT)
207 184
                s->irq_reinject_on_ack_count = 0;		
208 185
            apic_reset_irq_delivered();
209
            rtc_irq_raise(s->irq);
186
            qemu_irq_raise(s->irq);
210 187
            if (!apic_get_irq_delivered()) {
211 188
                s->irq_coalesced++;
212 189
                rtc_coalesced_timer_update(s);
......
215 192
            }
216 193
        } else
217 194
#endif
218
        rtc_irq_raise(s->irq);
195
        qemu_irq_raise(s->irq);
219 196
    }
220 197
    if (s->cmos_data[RTC_REG_B] & REG_B_SQWE) {
221 198
        /* Not square wave at all but we don't want 2048Hz interrupts!
......
444 421
             s->cmos_data[RTC_HOURS_ALARM] == s->current_tm.tm_hour)) {
445 422

  
446 423
            s->cmos_data[RTC_REG_C] |= 0xa0;
447
            rtc_irq_raise(s->irq);
424
            qemu_irq_raise(s->irq);
448 425
        }
449 426
    }
450 427

  
451 428
    /* update ended interrupt */
452 429
    s->cmos_data[RTC_REG_C] |= REG_C_UF;
453 430
    if (s->cmos_data[RTC_REG_B] & REG_B_UIE) {
454
      s->cmos_data[RTC_REG_C] |= REG_C_IRQF;
455
      rtc_irq_raise(s->irq);
431
        s->cmos_data[RTC_REG_C] |= REG_C_IRQF;
432
        qemu_irq_raise(s->irq);
456 433
    }
457 434

  
458 435
    /* clear update in progress bit */
......
606 583
{
607 584
    RTCState *s = DO_UPCAST(RTCState, dev, dev);
608 585
    int base = 0x70;
609
    int isairq = 8;
610

  
611
    isa_init_irq(dev, &s->irq, isairq);
612 586

  
613 587
    s->cmos_data[RTC_REG_A] = 0x26;
614 588
    s->cmos_data[RTC_REG_B] = 0x02;
......
638 612
    return 0;
639 613
}
640 614

  
641
ISADevice *rtc_init(int base_year)
615
ISADevice *rtc_init(int base_year, qemu_irq intercept_irq)
642 616
{
643 617
    ISADevice *dev;
618
    RTCState *s;
644 619

  
645 620
    dev = isa_create("mc146818rtc");
621
    s = DO_UPCAST(RTCState, dev, dev);
646 622
    qdev_prop_set_int32(&dev->qdev, "base_year", base_year);
647 623
    qdev_init_nofail(&dev->qdev);
624
    if (intercept_irq) {
625
        s->irq = intercept_irq;
626
    } else {
627
        isa_init_irq(dev, &s->irq, RTC_ISA_IRQ);
628
    }
648 629
    return dev;
649 630
}
650 631

  
b/hw/mc146818rtc.h
3 3

  
4 4
#include "isa.h"
5 5

  
6
ISADevice *rtc_init(int base_year);
6
#define RTC_ISA_IRQ 8
7

  
8
ISADevice *rtc_init(int base_year, qemu_irq intercept_irq);
7 9
void rtc_set_memory(ISADevice *dev, int addr, int val);
8 10
void rtc_set_date(ISADevice *dev, const struct tm *tm);
9 11

  
b/hw/mips_jazz.c
259 259
    fdctrl_init_sysbus(rc4030[1], 0, 0x80003000, fds);
260 260

  
261 261
    /* Real time clock */
262
    rtc_init(1980);
262
    rtc_init(1980, NULL);
263 263
    s_rtc = cpu_register_io_memory(rtc_read, rtc_write, NULL);
264 264
    cpu_register_physical_memory(0x80004000, 0x00001000, s_rtc);
265 265

  
b/hw/mips_malta.c
959 959
    /* Super I/O */
960 960
    isa_dev = isa_create_simple("i8042");
961 961
 
962
    rtc_state = rtc_init(2000);
962
    rtc_state = rtc_init(2000, NULL);
963 963
    serial_isa_init(0, serial_hds[0]);
964 964
    serial_isa_init(1, serial_hds[1]);
965 965
    if (parallel_hds[0])
b/hw/mips_r4k.c
267 267
    isa_bus_new(NULL);
268 268
    isa_bus_irqs(i8259);
269 269

  
270
    rtc_state = rtc_init(2000);
270
    rtc_state = rtc_init(2000, NULL);
271 271

  
272 272
    /* Register 64 KB of ISA IO space at 0x14000000 */
273 273
#ifdef TARGET_WORDS_BIGENDIAN
b/hw/pc.c
943 943
    int i;
944 944
    DriveInfo *fd[MAX_FD];
945 945
    PITState *pit;
946
    qemu_irq rtc_irq = NULL;
946 947
    qemu_irq *a20_line;
947 948
    ISADevice *i8042;
948 949
    qemu_irq *cpu_exit_irq;
......
951 952

  
952 953
    register_ioport_write(0xf0, 1, 1, ioportF0_write, NULL);
953 954

  
954
    *rtc_state = rtc_init(2000);
955

  
956
    qemu_register_boot_set(pc_boot_set, *rtc_state);
957

  
958
    pit = pit_init(0x40, isa_reserve_irq(0));
959
    pcspk_init(pit);
960 955
    if (!no_hpet) {
961 956
        DeviceState *hpet = sysbus_create_simple("hpet", HPET_BASE, NULL);
962 957

  
963 958
        for (i = 0; i < 24; i++) {
964 959
            sysbus_connect_irq(sysbus_from_qdev(hpet), i, isa_irq[i]);
965 960
        }
961
        rtc_irq = qdev_get_gpio_in(hpet, 0);
966 962
    }
963
    *rtc_state = rtc_init(2000, rtc_irq);
964

  
965
    qemu_register_boot_set(pc_boot_set, *rtc_state);
966

  
967
    pit = pit_init(0x40, isa_reserve_irq(0));
968
    pcspk_init(pit);
967 969

  
968 970
    for(i = 0; i < MAX_SERIAL_PORTS; i++) {
969 971
        if (serial_hds[i]) {
b/hw/ppc_prep.c
696 696
    pci_vga_init(pci_bus, 0, 0);
697 697
    //    openpic = openpic_init(0x00000000, 0xF0000000, 1);
698 698
    //    pit = pit_init(0x40, i8259[0]);
699
    rtc_init(2000);
699
    rtc_init(2000, NULL);
700 700

  
701 701
    if (serial_hds[0])
702 702
        serial_isa_init(0, serial_hds[0]);

Also available in: Unified diff