aboutsummaryrefslogtreecommitdiffstats
path: root/xen/arch/x86/hvm/rtc.c
diff options
context:
space:
mode:
authorJan Beulich <jbeulich@suse.com>2013-01-23 14:18:42 +0100
committerJan Beulich <jbeulich@suse.com>2013-01-23 14:18:42 +0100
commita077e5e5632e0f0bf8254972b3ebf704e5f8b0ba (patch)
treeff6af3098c9ebb4ec8ae7170cd176027790e63a6 /xen/arch/x86/hvm/rtc.c
parentf77416b2207e8692d5fc293f1bbbada361ff008e (diff)
downloadxen-a077e5e5632e0f0bf8254972b3ebf704e5f8b0ba.tar.gz
xen-a077e5e5632e0f0bf8254972b3ebf704e5f8b0ba.tar.bz2
xen-a077e5e5632e0f0bf8254972b3ebf704e5f8b0ba.zip
x86/HVM: adjust rtc_timer_update()
Don't look at RTC_PIE in rtc_timer_update(), and hence don't call the function on REG_B writes at all. Also handle the two other possible clock bases. Signed-off-by: Jan Beulich <jbeulich@suse.com> Acked-by: Keir Fraser <keir@xen.org>
Diffstat (limited to 'xen/arch/x86/hvm/rtc.c')
-rw-r--r--xen/arch/x86/hvm/rtc.c29
1 files changed, 17 insertions, 12 deletions
diff --git a/xen/arch/x86/hvm/rtc.c b/xen/arch/x86/hvm/rtc.c
index d0f4a97d08..dc9318249b 100644
--- a/xen/arch/x86/hvm/rtc.c
+++ b/xen/arch/x86/hvm/rtc.c
@@ -79,19 +79,26 @@ static void rtc_timer_update(RTCState *s)
ASSERT(spin_is_locked(&s->lock));
period_code = s->hw.cmos_data[RTC_REG_A] & RTC_RATE_SELECT;
- if ( (period_code != 0) && (s->hw.cmos_data[RTC_REG_B] & RTC_PIE) )
+ switch ( s->hw.cmos_data[RTC_REG_A] & RTC_DIV_CTL )
{
- if ( period_code <= 2 )
+ case RTC_REF_CLCK_32KHZ:
+ if ( (period_code != 0) && (period_code <= 2) )
period_code += 7;
-
- period = 1 << (period_code - 1); /* period in 32 Khz cycles */
- period = DIV_ROUND((period * 1000000000ULL), 32768); /* period in ns */
- create_periodic_time(v, &s->pt, period, period, RTC_IRQ,
- rtc_periodic_cb, s);
- }
- else
- {
+ /* fall through */
+ case RTC_REF_CLCK_1MHZ:
+ case RTC_REF_CLCK_4MHZ:
+ if ( period_code != 0 )
+ {
+ period = 1 << (period_code - 1); /* period in 32 Khz cycles */
+ period = DIV_ROUND(period * 1000000000ULL, 32768); /* in ns */
+ create_periodic_time(v, &s->pt, period, period, RTC_IRQ,
+ rtc_periodic_cb, s);
+ break;
+ }
+ /* fall through */
+ default:
destroy_periodic_time(&s->pt);
+ break;
}
}
@@ -445,8 +452,6 @@ static int rtc_ioport_write(void *opaque, uint32_t addr, uint32_t data)
rtc_toggle_irq(s);
}
s->hw.cmos_data[RTC_REG_B] = data;
- if ( (data ^ orig) & RTC_PIE )
- rtc_timer_update(s);
check_update_timer(s);
alarm_timer_update(s);
break;