Signed-off-by: Matthew Ogilvie <mmogilvi_q...@miniinfo.net> --- It is not at all clear that this is the best way to handle this. See the detailed notes in the cover letter of this patch series.
UPDATE: Also, some fixes moved the leading edge by 1 CLK tick (CLK ticks at about 1.1 MHz), and some strategies like this might risk extra interrupts just from that. ------ hw/i8259.c | 39 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/hw/i8259.c b/hw/i8259.c index 1ba9b3a..4b3c6c9 100644 --- a/hw/i8259.c +++ b/hw/i8259.c @@ -153,6 +153,45 @@ static void pic_set_irq(void *opaque, int irq, int level) s->irr &= ~mask; s->last_irr &= ~mask; } + + /* Back-migration compatibility hack: + * As of late 2012, the PIT timer model was incorrectly + * pulsing the the IRQ0 line high for only a short time to + * indicate an interrupt. It counted on a conceptual bug in + * the PIC irq model to latch onto and and deliver the + * interrupt even after it became low again. (Normally lowering + * an IRQ line before it is serviced should cancel the + * interrupt.) + * + * In late 2012 the model has been improved to match hardware + * much better by only pulsing low for a short time (in most + * PIT modes), but unfortunately that means if you back-migrate + * a guest to a version without this fix, the next interrupt + * won't have its own leading edge at all, and will + * be lost. + * + * The following hack will allow both the current + * interrupt to be serviced properly, and the next one + * as well, regardless of which version the migration is + * restored on. + * + * Unfortunately, this has a small possibility of causing + * an extra IRQ0 in cases that would not have in the old 2012 + * model, nor on real hardware. Specifically, if the current + * interrupt is processed, and then something causes an + * pit_irq_timer_update() to the same high level it was previously + * updated with. Re-setting various PIT modes (like 4) could + * do this, for example. + * + * At some point in the future (years from now?), + * when back-migration to the old 2012 version is + * no longer important, it should be safe to just delete + * this hack. + */ + if (irq==0 && s->master) { + s->last_irr &= ~1; + } + pic_update_irq(s); } -- 1.7.10.2.484.gcd07cc5