1 /*
2  * QEMU MC146818 RTC emulation
3  *
4  * Copyright (c) 2003-2004 Fabrice Bellard
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a copy
7  * of this software and associated documentation files (the "Software"), to
8  * deal in the Software without restriction, including without limitation the
9  * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
10  * sell copies of the Software, and to permit persons to whom the Software is
11  * furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be included in
14  * all copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22  * IN THE SOFTWARE.
23  */
24 
25 #include <asm/mc146818rtc.h>
26 #include <asm/hvm/vpt.h>
27 #include <asm/hvm/io.h>
28 #include <asm/hvm/support.h>
29 #include <asm/current.h>
30 #include <xen/trace.h>
31 #include <public/hvm/params.h>
32 
33 #define USEC_PER_SEC    1000000UL
34 #define NS_PER_USEC     1000UL
35 #define NS_PER_SEC      1000000000ULL
36 
37 #define SEC_PER_MIN     60
38 #define SEC_PER_HOUR    3600
39 #define MIN_PER_HOUR    60
40 #define HOUR_PER_DAY    24
41 
42 #define domain_vrtc(x) (&(x)->arch.hvm.pl_time->vrtc)
43 #define vcpu_vrtc(x)   (domain_vrtc((x)->domain))
44 #define vrtc_domain(x) (container_of(x, struct pl_time, vrtc)->domain)
45 #define vrtc_vcpu(x)   (pt_global_vcpu_target(vrtc_domain(x)))
46 #define epoch_year     1900
47 #define get_year(x)    (x + epoch_year)
48 
49 enum rtc_mode {
50    rtc_mode_no_ack,
51    rtc_mode_strict
52 };
53 
54 /* This must be in sync with how hvmloader sets the ACPI WAET flags. */
55 #define mode_is(d, m) ((void)(d), rtc_mode_##m == rtc_mode_no_ack)
56 #define rtc_mode_is(s, m) mode_is(vrtc_domain(s), m)
57 
58 static void rtc_copy_date(RTCState *s);
59 static void rtc_set_time(RTCState *s);
60 static inline int from_bcd(RTCState *s, int a);
61 static inline int convert_hour(RTCState *s, int hour);
62 
rtc_update_irq(RTCState * s)63 static void rtc_update_irq(RTCState *s)
64 {
65     ASSERT(spin_is_locked(&s->lock));
66 
67     if ( rtc_mode_is(s, strict) && (s->hw.cmos_data[RTC_REG_C] & RTC_IRQF) )
68         return;
69 
70     /* IRQ is raised if any source is both raised & enabled */
71     if ( !(s->hw.cmos_data[RTC_REG_B] &
72            s->hw.cmos_data[RTC_REG_C] &
73            (RTC_PF | RTC_AF | RTC_UF)) )
74         return;
75 
76     s->hw.cmos_data[RTC_REG_C] |= RTC_IRQF;
77     if ( rtc_mode_is(s, no_ack) )
78         hvm_isa_irq_deassert(vrtc_domain(s), RTC_IRQ);
79     hvm_isa_irq_assert(vrtc_domain(s), RTC_IRQ, NULL);
80 }
81 
82 /* Called by the VPT code after it's injected a PF interrupt for us.
83  * Fix up the register state to reflect what happened. */
rtc_pf_callback(struct vcpu * v,void * opaque)84 static void rtc_pf_callback(struct vcpu *v, void *opaque)
85 {
86     RTCState *s = opaque;
87 
88     spin_lock(&s->lock);
89 
90     if ( !rtc_mode_is(s, no_ack)
91          && (s->hw.cmos_data[RTC_REG_C] & RTC_IRQF)
92          && ++(s->pt_dead_ticks) >= 10 )
93     {
94         /* VM is ignoring its RTC; no point in running the timer */
95         TRACE_0D(TRC_HVM_EMUL_RTC_STOP_TIMER);
96         destroy_periodic_time(&s->pt);
97         s->period = 0;
98     }
99 
100     s->hw.cmos_data[RTC_REG_C] |= RTC_PF|RTC_IRQF;
101 
102     spin_unlock(&s->lock);
103 }
104 
105 /* Check whether the REG_C.PF bit should have been set by a tick since
106  * the last time we looked. This is used to track ticks when REG_B.PIE
107  * is clear; when PIE is set, PF ticks are handled by the VPT callbacks.  */
check_for_pf_ticks(RTCState * s)108 static void check_for_pf_ticks(RTCState *s)
109 {
110     s_time_t now;
111 
112     if ( s->period == 0 || (s->hw.cmos_data[RTC_REG_B] & RTC_PIE) )
113         return;
114 
115     now = NOW();
116     if ( (now - s->start_time) / s->period
117          != (s->check_ticks_since - s->start_time) / s->period )
118         s->hw.cmos_data[RTC_REG_C] |= RTC_PF;
119 
120     s->check_ticks_since = now;
121 }
122 
123 /* Enable/configure/disable the periodic timer based on the RTC_PIE and
124  * RTC_RATE_SELECT settings */
rtc_timer_update(RTCState * s)125 static void rtc_timer_update(RTCState *s)
126 {
127     int period_code, period, delta;
128     struct vcpu *v = vrtc_vcpu(s);
129 
130     ASSERT(spin_is_locked(&s->lock));
131 
132     s->pt_dead_ticks = 0;
133 
134     period_code = s->hw.cmos_data[RTC_REG_A] & RTC_RATE_SELECT;
135     switch ( s->hw.cmos_data[RTC_REG_A] & RTC_DIV_CTL )
136     {
137     case RTC_REF_CLCK_32KHZ:
138         if ( (period_code != 0) && (period_code <= 2) )
139             period_code += 7;
140         /* fall through */
141     case RTC_REF_CLCK_1MHZ:
142     case RTC_REF_CLCK_4MHZ:
143         if ( period_code != 0 )
144         {
145             period = 1 << (period_code - 1); /* period in 32 Khz cycles */
146             period = DIV_ROUND(period * 1000000000ULL, 32768); /* in ns */
147             if ( period != s->period )
148             {
149                 s_time_t now = NOW();
150 
151                 s->period = period;
152                 if ( v->domain->arch.hvm.params[HVM_PARAM_VPT_ALIGN] )
153                     delta = 0;
154                 else
155                     delta = period - ((now - s->start_time) % period);
156                 if ( s->hw.cmos_data[RTC_REG_B] & RTC_PIE )
157                 {
158                     TRACE_2D(TRC_HVM_EMUL_RTC_START_TIMER, delta, period);
159                     create_periodic_time(v, &s->pt, delta, period,
160                                          RTC_IRQ, rtc_pf_callback, s, false);
161                 }
162                 else
163                     s->check_ticks_since = now;
164             }
165             break;
166         }
167         /* fall through */
168     default:
169         TRACE_0D(TRC_HVM_EMUL_RTC_STOP_TIMER);
170         destroy_periodic_time(&s->pt);
171         s->period = 0;
172         break;
173     }
174 }
175 
176 /* handle update-ended timer */
check_update_timer(RTCState * s)177 static void check_update_timer(RTCState *s)
178 {
179     uint64_t next_update_time, expire_time;
180     uint64_t guest_usec;
181     struct domain *d = vrtc_domain(s);
182     stop_timer(&s->update_timer);
183     stop_timer(&s->update_timer2);
184 
185     ASSERT(spin_is_locked(&s->lock));
186 
187     if (!(s->hw.cmos_data[RTC_REG_C] & RTC_UF) &&
188             !(s->hw.cmos_data[RTC_REG_B] & RTC_SET))
189     {
190         s->use_timer = 1;
191         guest_usec = get_localtime_us(d) % USEC_PER_SEC;
192         if (guest_usec >= (USEC_PER_SEC - 244))
193         {
194             /* RTC is in update cycle */
195             s->hw.cmos_data[RTC_REG_A] |= RTC_UIP;
196             next_update_time = (USEC_PER_SEC - guest_usec) * NS_PER_USEC;
197             expire_time = NOW() + next_update_time;
198             /* release lock before set timer */
199             spin_unlock(&s->lock);
200             set_timer(&s->update_timer2, expire_time);
201             /* fetch lock again */
202             spin_lock(&s->lock);
203         }
204         else
205         {
206             next_update_time = (USEC_PER_SEC - guest_usec - 244) * NS_PER_USEC;
207             expire_time = NOW() + next_update_time;
208             s->next_update_time = expire_time;
209             /* release lock before set timer */
210             spin_unlock(&s->lock);
211             set_timer(&s->update_timer, expire_time);
212             /* fetch lock again */
213             spin_lock(&s->lock);
214         }
215     }
216     else
217         s->use_timer = 0;
218 }
219 
rtc_update_timer(void * opaque)220 static void rtc_update_timer(void *opaque)
221 {
222     RTCState *s = opaque;
223 
224     spin_lock(&s->lock);
225     if (!(s->hw.cmos_data[RTC_REG_B] & RTC_SET))
226     {
227         s->hw.cmos_data[RTC_REG_A] |= RTC_UIP;
228         set_timer(&s->update_timer2, s->next_update_time + 244000UL);
229     }
230     spin_unlock(&s->lock);
231 }
232 
rtc_update_timer2(void * opaque)233 static void rtc_update_timer2(void *opaque)
234 {
235     RTCState *s = opaque;
236 
237     spin_lock(&s->lock);
238     if (!(s->hw.cmos_data[RTC_REG_B] & RTC_SET))
239     {
240         s->hw.cmos_data[RTC_REG_C] |= RTC_UF;
241         s->hw.cmos_data[RTC_REG_A] &= ~RTC_UIP;
242         rtc_update_irq(s);
243         check_update_timer(s);
244     }
245     spin_unlock(&s->lock);
246 }
247 
248 /* handle alarm timer */
alarm_timer_update(RTCState * s)249 static void alarm_timer_update(RTCState *s)
250 {
251     uint64_t next_update_time, next_alarm_sec;
252     uint64_t expire_time;
253     int32_t alarm_sec, alarm_min, alarm_hour, cur_hour, cur_min, cur_sec;
254     int32_t hour, min;
255     struct domain *d = vrtc_domain(s);
256 
257     ASSERT(spin_is_locked(&s->lock));
258 
259     stop_timer(&s->alarm_timer);
260 
261     if (!(s->hw.cmos_data[RTC_REG_C] & RTC_AF) &&
262             !(s->hw.cmos_data[RTC_REG_B] & RTC_SET))
263     {
264         s->current_tm = gmtime(get_localtime(d));
265         rtc_copy_date(s);
266 
267         alarm_sec = from_bcd(s, s->hw.cmos_data[RTC_SECONDS_ALARM]);
268         alarm_min = from_bcd(s, s->hw.cmos_data[RTC_MINUTES_ALARM]);
269         alarm_hour = convert_hour(s, s->hw.cmos_data[RTC_HOURS_ALARM]);
270 
271         cur_sec = from_bcd(s, s->hw.cmos_data[RTC_SECONDS]);
272         cur_min = from_bcd(s, s->hw.cmos_data[RTC_MINUTES]);
273         cur_hour = convert_hour(s, s->hw.cmos_data[RTC_HOURS]);
274 
275         next_update_time = USEC_PER_SEC - (get_localtime_us(d) % USEC_PER_SEC);
276         next_update_time = next_update_time * NS_PER_USEC + NOW();
277 
278         if ((s->hw.cmos_data[RTC_HOURS_ALARM] & 0xc0) == 0xc0)
279         {
280             if ((s->hw.cmos_data[RTC_MINUTES_ALARM] & 0xc0) == 0xc0)
281             {
282                 if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
283                     next_alarm_sec = 1;
284                 else if (cur_sec < alarm_sec)
285                     next_alarm_sec = alarm_sec - cur_sec;
286                 else
287                     next_alarm_sec = alarm_sec + SEC_PER_MIN - cur_sec;
288             }
289             else
290             {
291                 if (cur_min < alarm_min)
292                 {
293                     min = alarm_min - cur_min;
294                     next_alarm_sec = min * SEC_PER_MIN - cur_sec;
295                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
296                         next_alarm_sec += 0;
297                     else
298                         next_alarm_sec += alarm_sec;
299                 }
300                 else if (cur_min == alarm_min)
301                 {
302                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
303                         next_alarm_sec = 1;
304                     else if (cur_sec < alarm_sec)
305                         next_alarm_sec = alarm_sec - cur_sec;
306                     else
307                     {
308                         min = alarm_min + MIN_PER_HOUR - cur_min;
309                         next_alarm_sec =
310                             alarm_sec + min * SEC_PER_MIN - cur_sec;
311                     }
312                 }
313                 else
314                 {
315                     min = alarm_min + MIN_PER_HOUR - cur_min;
316                     next_alarm_sec = min * SEC_PER_MIN - cur_sec;
317                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
318                         next_alarm_sec += 0;
319                     else
320                         next_alarm_sec += alarm_sec;
321                 }
322             }
323         }
324         else
325         {
326             if (cur_hour < alarm_hour)
327             {
328                 hour = alarm_hour - cur_hour;
329                 next_alarm_sec = hour * SEC_PER_HOUR -
330                     cur_min * SEC_PER_MIN - cur_sec;
331                 if ((s->hw.cmos_data[RTC_MINUTES_ALARM] & 0xc0) == 0xc0)
332                 {
333                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
334                         next_alarm_sec += 0;
335                     else
336                         next_alarm_sec += alarm_sec;
337                 }
338                 else
339                 {
340                     next_alarm_sec += alarm_min * SEC_PER_MIN;
341                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
342                         next_alarm_sec += 0;
343                     else
344                         next_alarm_sec += alarm_sec;
345                 }
346             }
347             else if (cur_hour == alarm_hour)
348             {
349                 if ((s->hw.cmos_data[RTC_MINUTES_ALARM] & 0xc0) == 0xc0)
350                 {
351                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
352                         next_alarm_sec = 1;
353                     else if (cur_sec < alarm_sec)
354                         next_alarm_sec = alarm_sec - cur_sec;
355                     else
356                         next_alarm_sec = alarm_sec + SEC_PER_MIN - cur_sec;
357                 }
358                 else if (cur_min < alarm_min)
359                 {
360                     min = alarm_min - cur_min;
361                     next_alarm_sec = min * SEC_PER_MIN - cur_sec;
362                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
363                         next_alarm_sec += 0;
364                     else
365                         next_alarm_sec += alarm_sec;
366                 }
367                 else if (cur_min == alarm_min)
368                 {
369                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
370                         next_alarm_sec = 1;
371                     else if (cur_sec < alarm_sec)
372                         next_alarm_sec = alarm_sec - cur_sec;
373                     else
374                     {
375                         hour = alarm_hour + HOUR_PER_DAY - cur_hour;
376                         next_alarm_sec = hour * SEC_PER_HOUR -
377                             cur_min * SEC_PER_MIN - cur_sec;
378                         next_alarm_sec += alarm_min * SEC_PER_MIN + alarm_sec;
379                     }
380                 }
381                 else
382                 {
383                     hour = alarm_hour + HOUR_PER_DAY - cur_hour;
384                     next_alarm_sec = hour * SEC_PER_HOUR -
385                         cur_min * SEC_PER_MIN - cur_sec;
386                     next_alarm_sec += alarm_min * SEC_PER_MIN;
387                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
388                         next_alarm_sec += 0;
389                     else
390                         next_alarm_sec += alarm_sec;
391                 }
392             }
393             else
394             {
395                 hour = alarm_hour + HOUR_PER_DAY - cur_hour;
396                 next_alarm_sec = hour * SEC_PER_HOUR -
397                     cur_min * SEC_PER_MIN - cur_sec;
398                 if ((s->hw.cmos_data[RTC_MINUTES_ALARM] & 0xc0) == 0xc0)
399                 {
400                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
401                         next_alarm_sec += 0;
402                     else
403                         next_alarm_sec += alarm_sec;
404                 }
405                 else
406                 {
407                     next_alarm_sec += alarm_min * SEC_PER_MIN;
408                     if ((s->hw.cmos_data[RTC_SECONDS_ALARM] & 0xc0) == 0xc0)
409                         next_alarm_sec += 0;
410                     else
411                         next_alarm_sec += alarm_sec;
412                 }
413             }
414         }
415         expire_time = (next_alarm_sec - 1) * NS_PER_SEC + next_update_time;
416         /* release lock before set timer */
417         spin_unlock(&s->lock);
418         set_timer(&s->alarm_timer, expire_time);
419         /* fetch lock again */
420         spin_lock(&s->lock);
421     }
422 }
423 
rtc_alarm_cb(void * opaque)424 static void rtc_alarm_cb(void *opaque)
425 {
426     RTCState *s = opaque;
427 
428     spin_lock(&s->lock);
429     if (!(s->hw.cmos_data[RTC_REG_B] & RTC_SET))
430     {
431         s->hw.cmos_data[RTC_REG_C] |= RTC_AF;
432         rtc_update_irq(s);
433         alarm_timer_update(s);
434     }
435     spin_unlock(&s->lock);
436 }
437 
rtc_ioport_write(void * opaque,uint32_t addr,uint32_t data)438 static int rtc_ioport_write(void *opaque, uint32_t addr, uint32_t data)
439 {
440     RTCState *s = opaque;
441     struct domain *d = vrtc_domain(s);
442     uint32_t orig;
443 
444     spin_lock(&s->lock);
445 
446     if ( (addr & 1) == 0 )
447     {
448         data &= 0x7f;
449         s->hw.cmos_index = data;
450         spin_unlock(&s->lock);
451         return (data < RTC_CMOS_SIZE);
452     }
453 
454     if ( s->hw.cmos_index >= RTC_CMOS_SIZE )
455     {
456         spin_unlock(&s->lock);
457         return 0;
458     }
459 
460     orig = s->hw.cmos_data[s->hw.cmos_index];
461     switch ( s->hw.cmos_index )
462     {
463     case RTC_SECONDS_ALARM:
464     case RTC_MINUTES_ALARM:
465     case RTC_HOURS_ALARM:
466         s->hw.cmos_data[s->hw.cmos_index] = data;
467         alarm_timer_update(s);
468         break;
469     case RTC_SECONDS:
470     case RTC_MINUTES:
471     case RTC_HOURS:
472     case RTC_DAY_OF_WEEK:
473     case RTC_DAY_OF_MONTH:
474     case RTC_MONTH:
475     case RTC_YEAR:
476         /* if in set mode, just write the register */
477         if ( (s->hw.cmos_data[RTC_REG_B] & RTC_SET) )
478             s->hw.cmos_data[s->hw.cmos_index] = data;
479         else
480         {
481             /* Fetch the current time and update just this field. */
482             s->current_tm = gmtime(get_localtime(d));
483             rtc_copy_date(s);
484             s->hw.cmos_data[s->hw.cmos_index] = data;
485             rtc_set_time(s);
486         }
487         alarm_timer_update(s);
488         break;
489     case RTC_REG_A:
490         /* UIP bit is read only */
491         s->hw.cmos_data[RTC_REG_A] = (data & ~RTC_UIP) | (orig & RTC_UIP);
492         if ( (data ^ orig) & ~RTC_UIP )
493             rtc_timer_update(s);
494         break;
495     case RTC_REG_B:
496         if ( data & RTC_SET )
497         {
498             /* set mode: reset UIP mode */
499             s->hw.cmos_data[RTC_REG_A] &= ~RTC_UIP;
500             /* adjust cmos before stopping */
501             if (!(orig & RTC_SET))
502             {
503                 s->current_tm = gmtime(get_localtime(d));
504                 rtc_copy_date(s);
505             }
506         }
507         else
508         {
509             /* if disabling set mode, update the time */
510             if ( orig & RTC_SET )
511                 rtc_set_time(s);
512         }
513         check_for_pf_ticks(s);
514         s->hw.cmos_data[RTC_REG_B] = data;
515         /*
516          * If the interrupt is already set when the interrupt becomes
517          * enabled, raise an interrupt immediately.
518          */
519         rtc_update_irq(s);
520         if ( (data ^ orig) & RTC_PIE )
521         {
522             TRACE_0D(TRC_HVM_EMUL_RTC_STOP_TIMER);
523             destroy_periodic_time(&s->pt);
524             s->period = 0;
525             rtc_timer_update(s);
526         }
527         if ( (data ^ orig) & RTC_SET )
528             check_update_timer(s);
529         if ( (data ^ orig) & (RTC_24H | RTC_DM_BINARY | RTC_SET) )
530             alarm_timer_update(s);
531         break;
532     case RTC_REG_C:
533     case RTC_REG_D:
534         /* cannot write to them */
535         break;
536     }
537 
538     spin_unlock(&s->lock);
539 
540     return 1;
541 }
542 
to_bcd(RTCState * s,int a)543 static inline int to_bcd(RTCState *s, int a)
544 {
545     if ( s->hw.cmos_data[RTC_REG_B] & RTC_DM_BINARY )
546         return a;
547     else
548         return ((a / 10) << 4) | (a % 10);
549 }
550 
from_bcd(RTCState * s,int a)551 static inline int from_bcd(RTCState *s, int a)
552 {
553     if ( s->hw.cmos_data[RTC_REG_B] & RTC_DM_BINARY )
554         return a;
555     else
556         return ((a >> 4) * 10) + (a & 0x0f);
557 }
558 
559 /* Hours in 12 hour mode are in 1-12 range, not 0-11.
560  * So we need convert it before using it*/
convert_hour(RTCState * s,int raw)561 static inline int convert_hour(RTCState *s, int raw)
562 {
563     int hour = from_bcd(s, raw & 0x7f);
564 
565     if (!(s->hw.cmos_data[RTC_REG_B] & RTC_24H))
566     {
567         hour %= 12;
568         if (raw & 0x80)
569             hour += 12;
570     }
571     return hour;
572 }
573 
rtc_set_time(RTCState * s)574 static void rtc_set_time(RTCState *s)
575 {
576     struct tm *tm = &s->current_tm;
577     struct domain *d = vrtc_domain(s);
578     unsigned long before, after; /* XXX s_time_t */
579 
580     ASSERT(spin_is_locked(&s->lock));
581 
582     before = mktime(get_year(tm->tm_year), tm->tm_mon + 1, tm->tm_mday,
583 		    tm->tm_hour, tm->tm_min, tm->tm_sec);
584 
585     tm->tm_sec = from_bcd(s, s->hw.cmos_data[RTC_SECONDS]);
586     tm->tm_min = from_bcd(s, s->hw.cmos_data[RTC_MINUTES]);
587     tm->tm_hour = convert_hour(s, s->hw.cmos_data[RTC_HOURS]);
588     tm->tm_wday = from_bcd(s, s->hw.cmos_data[RTC_DAY_OF_WEEK]);
589     tm->tm_mday = from_bcd(s, s->hw.cmos_data[RTC_DAY_OF_MONTH]);
590     tm->tm_mon = from_bcd(s, s->hw.cmos_data[RTC_MONTH]) - 1;
591     tm->tm_year = from_bcd(s, s->hw.cmos_data[RTC_YEAR]) + 100;
592 
593     after = mktime(get_year(tm->tm_year), tm->tm_mon + 1, tm->tm_mday,
594                    tm->tm_hour, tm->tm_min, tm->tm_sec);
595 
596     /* We use the guest's setting of the RTC to define the local-time
597      * offset for this domain. */
598     d->time_offset.seconds += (after - before);
599     update_domain_wallclock_time(d);
600     /* Also tell qemu-dm about it so it will be remembered for next boot. */
601     send_timeoffset_req(after - before);
602 }
603 
rtc_copy_date(RTCState * s)604 static void rtc_copy_date(RTCState *s)
605 {
606     const struct tm *tm = &s->current_tm;
607 
608     ASSERT(spin_is_locked(&s->lock));
609 
610     s->hw.cmos_data[RTC_SECONDS] = to_bcd(s, tm->tm_sec);
611     s->hw.cmos_data[RTC_MINUTES] = to_bcd(s, tm->tm_min);
612     if ( s->hw.cmos_data[RTC_REG_B] & RTC_24H )
613     {
614         /* 24 hour format */
615         s->hw.cmos_data[RTC_HOURS] = to_bcd(s, tm->tm_hour);
616     }
617     else
618     {
619         /* 12 hour format */
620         int h = (tm->tm_hour % 12) ? tm->tm_hour % 12 : 12;
621         s->hw.cmos_data[RTC_HOURS] = to_bcd(s, h);
622         if ( tm->tm_hour >= 12 )
623             s->hw.cmos_data[RTC_HOURS] |= 0x80;
624     }
625     s->hw.cmos_data[RTC_DAY_OF_WEEK] = to_bcd(s, tm->tm_wday);
626     s->hw.cmos_data[RTC_DAY_OF_MONTH] = to_bcd(s, tm->tm_mday);
627     s->hw.cmos_data[RTC_MONTH] = to_bcd(s, tm->tm_mon + 1);
628     s->hw.cmos_data[RTC_YEAR] = to_bcd(s, tm->tm_year % 100);
629 }
630 
update_in_progress(RTCState * s)631 static int update_in_progress(RTCState *s)
632 {
633     uint64_t guest_usec;
634     struct domain *d = vrtc_domain(s);
635 
636     if (s->hw.cmos_data[RTC_REG_B] & RTC_SET)
637         return 0;
638 
639     guest_usec = get_localtime_us(d);
640     /* UIP bit will be set at last 244us of every second. */
641     if ((guest_usec % USEC_PER_SEC) >= (USEC_PER_SEC - 244))
642         return 1;
643 
644     return 0;
645 }
646 
rtc_ioport_read(RTCState * s,uint32_t addr)647 static uint32_t rtc_ioport_read(RTCState *s, uint32_t addr)
648 {
649     int ret;
650     struct domain *d = vrtc_domain(s);
651 
652     if ( (addr & 1) == 0 )
653         return 0xff;
654 
655     spin_lock(&s->lock);
656 
657     switch ( s->hw.cmos_index )
658     {
659     case RTC_SECONDS:
660     case RTC_MINUTES:
661     case RTC_HOURS:
662     case RTC_DAY_OF_WEEK:
663     case RTC_DAY_OF_MONTH:
664     case RTC_MONTH:
665     case RTC_YEAR:
666         /* if not in set mode, adjust cmos before reading*/
667         if (!(s->hw.cmos_data[RTC_REG_B] & RTC_SET))
668         {
669             s->current_tm = gmtime(get_localtime(d));
670             rtc_copy_date(s);
671         }
672         ret = s->hw.cmos_data[s->hw.cmos_index];
673         break;
674     case RTC_REG_A:
675         ret = s->hw.cmos_data[s->hw.cmos_index];
676         if ((s->use_timer == 0) && update_in_progress(s))
677             ret |= RTC_UIP;
678         break;
679     case RTC_REG_C:
680         check_for_pf_ticks(s);
681         ret = s->hw.cmos_data[s->hw.cmos_index];
682         s->hw.cmos_data[RTC_REG_C] = 0x00;
683         if ( ret & RTC_IRQF )
684             hvm_isa_irq_deassert(d, RTC_IRQ);
685         check_update_timer(s);
686         alarm_timer_update(s);
687         s->pt_dead_ticks = 0;
688         break;
689     default:
690         ret = s->hw.cmos_data[s->hw.cmos_index];
691         break;
692     }
693 
694     spin_unlock(&s->lock);
695 
696     return ret;
697 }
698 
handle_rtc_io(int dir,unsigned int port,unsigned int bytes,uint32_t * val)699 static int handle_rtc_io(
700     int dir, unsigned int port, unsigned int bytes, uint32_t *val)
701 {
702     struct RTCState *vrtc = vcpu_vrtc(current);
703 
704     if ( bytes != 1 )
705     {
706         gdprintk(XENLOG_WARNING, "HVM_RTC bad access\n");
707         *val = ~0;
708         return X86EMUL_OKAY;
709     }
710 
711     if ( dir == IOREQ_WRITE )
712     {
713         if ( rtc_ioport_write(vrtc, port, (uint8_t)*val) )
714             return X86EMUL_OKAY;
715     }
716     else if ( vrtc->hw.cmos_index < RTC_CMOS_SIZE )
717     {
718         *val = rtc_ioport_read(vrtc, port);
719         return X86EMUL_OKAY;
720     }
721 
722     return X86EMUL_UNHANDLEABLE;
723 }
724 
rtc_migrate_timers(struct vcpu * v)725 void rtc_migrate_timers(struct vcpu *v)
726 {
727     RTCState *s = vcpu_vrtc(v);
728 
729     if ( !has_vrtc(v->domain) )
730         return;
731 
732     if ( v->vcpu_id == 0 )
733     {
734         migrate_timer(&s->update_timer, v->processor);
735         migrate_timer(&s->update_timer2, v->processor);
736         migrate_timer(&s->alarm_timer, v->processor);
737     }
738 }
739 
740 /* Save RTC hardware state */
rtc_save(struct vcpu * v,hvm_domain_context_t * h)741 static int rtc_save(struct vcpu *v, hvm_domain_context_t *h)
742 {
743     const struct domain *d = v->domain;
744     RTCState *s = domain_vrtc(d);
745     int rc;
746 
747     if ( !has_vrtc(d) )
748         return 0;
749 
750     spin_lock(&s->lock);
751     s->hw.rtc_offset = d->time_offset.seconds;
752     rc = hvm_save_entry(RTC, 0, h, &s->hw);
753     spin_unlock(&s->lock);
754 
755     return rc;
756 }
757 
758 /* Reload the hardware state from a saved domain */
rtc_load(struct domain * d,hvm_domain_context_t * h)759 static int rtc_load(struct domain *d, hvm_domain_context_t *h)
760 {
761     RTCState *s = domain_vrtc(d);
762 
763     if ( !has_vrtc(d) )
764         return -ENODEV;
765 
766     spin_lock(&s->lock);
767 
768     /* Restore the registers */
769     if ( hvm_load_entry_zeroextend(RTC, h, &s->hw) != 0 )
770     {
771         spin_unlock(&s->lock);
772         return -EINVAL;
773     }
774 
775     /* Reset the wall-clock time.  In normal running, this runs with host
776      * time, so let's keep doing that. */
777     if ( !d->time_offset.set )
778     {
779         d->time_offset.seconds = s->hw.rtc_offset;
780         update_domain_wallclock_time(d);
781     }
782 
783     s->current_tm = gmtime(get_localtime(d));
784     rtc_copy_date(s);
785 
786     /* Reset the periodic interrupt timer based on the registers */
787     rtc_timer_update(s);
788     check_update_timer(s);
789     alarm_timer_update(s);
790 
791     spin_unlock(&s->lock);
792 
793     return 0;
794 }
795 
796 HVM_REGISTER_SAVE_RESTORE(RTC, rtc_save, rtc_load, 1, HVMSR_PER_DOM);
797 
rtc_reset(struct domain * d)798 void rtc_reset(struct domain *d)
799 {
800     RTCState *s = domain_vrtc(d);
801 
802     if ( !has_vrtc(d) )
803         return;
804 
805     TRACE_0D(TRC_HVM_EMUL_RTC_STOP_TIMER);
806     destroy_periodic_time(&s->pt);
807     s->period = 0;
808     s->pt.source = PTSRC_isa;
809 }
810 
811 /* RTC mediator for HVM hardware domain. */
hw_rtc_io(int dir,unsigned int port,unsigned int size,uint32_t * val)812 static int hw_rtc_io(int dir, unsigned int port, unsigned int size,
813                      uint32_t *val)
814 {
815     if ( dir == IOREQ_READ )
816         *val = ~0;
817 
818     if ( size != 1 )
819     {
820         gdprintk(XENLOG_WARNING, "bad RTC access size (%u)\n", size);
821         return X86EMUL_OKAY;
822     }
823 
824     if ( dir == IOREQ_WRITE )
825         rtc_guest_write(port, *val);
826     else
827         *val = rtc_guest_read(port);
828 
829     return X86EMUL_OKAY;
830 }
831 
rtc_init(struct domain * d)832 void rtc_init(struct domain *d)
833 {
834     RTCState *s = domain_vrtc(d);
835 
836     if ( !has_vrtc(d) )
837     {
838         if ( is_hardware_domain(d) )
839             /* Hardware domain gets mediated access to the physical RTC. */
840             register_portio_handler(d, RTC_PORT(0), 2, hw_rtc_io);
841         return;
842     }
843 
844     spin_lock_init(&s->lock);
845 
846     init_timer(&s->update_timer, rtc_update_timer, s, smp_processor_id());
847     init_timer(&s->update_timer2, rtc_update_timer2, s, smp_processor_id());
848     init_timer(&s->alarm_timer, rtc_alarm_cb, s, smp_processor_id());
849 
850     register_portio_handler(d, RTC_PORT(0), 2, handle_rtc_io);
851 
852     rtc_reset(d);
853 
854     spin_lock(&s->lock);
855 
856     s->hw.cmos_data[RTC_REG_A] = RTC_REF_CLCK_32KHZ | 6; /* ~1kHz */
857     s->hw.cmos_data[RTC_REG_B] = RTC_24H;
858     s->hw.cmos_data[RTC_REG_C] = 0;
859     s->hw.cmos_data[RTC_REG_D] = RTC_VRT;
860 
861     s->current_tm = gmtime(get_localtime(d));
862     s->start_time = NOW();
863 
864     rtc_copy_date(s);
865 
866     check_update_timer(s);
867     spin_unlock(&s->lock);
868 }
869 
rtc_deinit(struct domain * d)870 void rtc_deinit(struct domain *d)
871 {
872     RTCState *s = domain_vrtc(d);
873 
874     if ( !has_vrtc(d) || !d->arch.hvm.pl_time ||
875          s->update_timer.status == TIMER_STATUS_invalid )
876         return;
877 
878     spin_barrier(&s->lock);
879 
880     TRACE_0D(TRC_HVM_EMUL_RTC_STOP_TIMER);
881     destroy_periodic_time(&s->pt);
882     kill_timer(&s->update_timer);
883     kill_timer(&s->update_timer2);
884     kill_timer(&s->alarm_timer);
885 }
886 
rtc_update_clock(struct domain * d)887 void rtc_update_clock(struct domain *d)
888 {
889     RTCState *s = domain_vrtc(d);
890 
891     if ( !has_vrtc(d) )
892         return;
893 
894     spin_lock(&s->lock);
895     s->current_tm = gmtime(get_localtime(d));
896     spin_unlock(&s->lock);
897 }
898 
899 /*
900  * Local variables:
901  * mode: C
902  * c-file-style: "BSD"
903  * c-basic-offset: 4
904  * indent-tabs-mode: nil
905  * End:
906  */
907