qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Qemu-devel] [PATCH V3] rtc: fix a infinite loop inwindowsvmstartup


From: peng.hao2
Subject: Re: [Qemu-devel] [PATCH V3] rtc: fix a infinite loop inwindowsvmstartup
Date: Thu, 27 Jul 2017 10:25:34 +0800 (CST)

> On 26/07/2017 03:28, address@hidden wrote:




> > 
> > 
> > when the problem happens , windows kernel is checking  whether REG_A_UIP is 
> > changing after periodic timer has stopped. windows kernel access REG_A
> > according to INB instrunction and it will spend several microseconds because
> > of VM_EXIT. 

> A vmexit to the RTC timer should be around 10.000 clock cycles, which is
> less than a microsecond.
I use perf tools getting data(windows VM)

IO Port   Access    Samples  Samples%     Time%   Min Time   Max Time         
Avg time 

0x71:      PIN           126         56.76%       32.62%        1us         2us 
             1.83us ( +-   0.62% )


0x70:    POUT         63          28.38%        51.56%        4us         15us  
           5.78us ( +-   3.12% )

But I'm not sure it is accurate.

> > update timer has changed to a long expire time (as alarm timer)on the
> > one hand.
> > 
> > on the other hand  244 microseconds in one second is too short to hit
> > the region.
> > 
> > windows kernel may check REG_A_UIP when considering RTC something wrong.
> > many windows VM reboot at the same time and rtc periodic timer may delay
> > badly..

> Does Windows do this test when Hyper-V englightenments are enabled
> (especially hv-relaxed)?
yes ,I enable hv-relaxed.in my windows VM.But I'm not sure the interconnection 
between them.

> It seems to be a Windows issue to me.  I'm not sure adding hacks to the

> device model is the right thing to do, especially because I don't
> understand why your fix worked.

1. guest closes periodic timer,from then on rtc don't send interrupt anymore 
and no rtc handler can run to read


   RTC_REG_C(this read set RTC_REG_C = 0, clear REG_C_UF)


2. update timer expires, rtc_update_timer clears REG_A_UIP, and set REG_C_UF


3. because REG_C_UF is setted, check_update_timer sets update_timer's expire 
time to next_alarm_time, which is 


   over ten hours


4. guest checks that REG_A_UIP changes from 0 to 1 in a infinte loop (we don't 
know why windows kernel does this) by read RTC_REG_A


5. update_in_progress called from cmos_ioport_read


6. beause update_timer is switched to alarm timer, which has a too big expire 
time to satisfes the fowllowing condition:


        if (qemu_clock_get_ns(rtc_clock) >=


            (next_update_time - UIP_HOLD_LENGTH)) {


            s->cmos_data[RTC_REG_A] |= REG_A_UIP


            return 1


        }


7. update_in_progress's second condition don't satisfes:


        if ((guest_nsec % NANOSECONDS_PER_SECOND) >=


        (NANOSECONDS_PER_SECOND - UIP_HOLD_LENGTH)) {


        return 1


    }


   because when many vms startup, inb instruction wastes much more time than 
normal situation and 


   guest_nsec % NANOSECONDS_PER_SECOND is nearly < NANOSECONDS_PER_SECOND - 
UIP_HOLD_LENGTH always.


8. finally, REG_A_UIP is always cleared, REG_C_UF is always set, update_timer 
is always alarm timer, 


   guest is always checking REG_A_UIP, and guest hung up.

reply via email to

[Prev in Thread] Current Thread [Next in Thread]