mc146818rtc: precisely count the clock for periodic timer
commit369b41359af46bded5799c9ef8be2b641d92e043
authorTai Yunfang <yunfangtai@tencent.com>
Wed, 10 May 2017 08:32:56 +0000 (10 16:32 +0800)
committerPaolo Bonzini <pbonzini@redhat.com>
Tue, 6 Jun 2017 18:18:35 +0000 (6 20:18 +0200)
tree52f99940031aa1b4ce9238a7bc3e9ad54f12d0ec
parent9a6e2dcfdda31275296c2a55ae10ec9ee5265459
mc146818rtc: precisely count the clock for periodic timer

There are two issues in current code:
1) If the period is changed by re-configuring RegA, the coalesced
   irq will be scaled to reflect the new period, however, it
   calculates the new interrupt number like this:
    s->irq_coalesced = (s->irq_coalesced * s->period) / period;

   There are some clocks will be lost if they are not enough to
   be squeezed to a single new period that will cause the VM clock
   slower

   In order to fix the issue, we calculate the interrupt window
   based on the precise clock rather than period, then the clocks
   lost during period is scaled can be compensated properly

2) If periodic_timer_update() is called due to RegA reconfiguration,
   i.e, the period is updated, current time is not the start point
   for the next periodic timer, instead, which should start from the
   last interrupt, otherwise, the clock in VM will become slow

   This patch takes the clocks from last interrupt to current clock
   into account and compensates the clocks for the next interrupt,
   especially if a complete interrupt was lost in this window, the
   time can be caught up by LOST_TICK_POLICY_SLEW

Signed-off-by: Tai Yunfang <yunfangtai@tencent.com>
Signed-off-by: Xiao Guangrong <xiaoguangrong@tencent.com>
Message-Id: <20170510083259.3900-3-xiaoguangrong@tencent.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
hw/timer/mc146818rtc.c