qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: John Coiner <jcoiner@stanfordalumni.org>
To: qemu-devel@nongnu.org
Subject: [Qemu-devel] [patch] fix QEMU hang after hibernate
Date: Mon, 10 Oct 2005 01:24:49 -0400	[thread overview]
Message-ID: <4349FB21.9040205@stanfordalumni.org> (raw)


After I hibernate my x86 linux host machine (using the "swsusp2" 
package) and resume, QEMU and guest hang. That is odd, because 
hibernation is transparent to all other user programs.

Has anyone else noticed this? If so please try the patch.

You know QEMU is doing something weird, for it to be sensitive to 
hibernation. Indeed, the cause is something you don't see every day:

QEMU implements timers partly by reading the CPU's tick counter directly 
from hardware, with an architecture-specific assembly instruction 
('rdtsc' on intel, and so on for other archs) rather than using purely 
OS-provided features to get the time.

The problem is that following hibernation, the CPU tick counter isn't 
what it used to be. On my host, it has a lower value -- it jumped 
backwards. This breaks QEMU's timers. Some of them decide to block for a 
very long time, which causes the guest to hang or behave oddly.

(Maybe this is technically a bug in "swsusp2", maybe it should restore 
the CPU tick counter to the previous value upon resume. But who cares. 
It's easy to fix this in QEMU, and it would not be easy to check and fix 
all hibernation schemes on all architectures and operating systems.)

The following patch fixes the 'cpu_get_ticks()' function to always 
return a non-decreasing value, even if the value read from hardware 
decreases. Hope it helps. Feedback is welcome.

-- John



--- qemu-0.7.2-dmapatch/vl.c    2005-09-04 13:11:31.000000000 -0400
+++ qemu-0.7.2-broken/vl.c      2005-10-10 00:54:08.000000000 -0400
@@ -545,14 +547,21 @@
  #error unsupported CPU
  #endif

-static int64_t cpu_ticks_offset;
-static int cpu_ticks_enabled;
+static int64_t cpu_ticks_prev = 0;
+static int64_t cpu_ticks_offset = 0;
+static int cpu_ticks_enabled = 0;

  static inline int64_t cpu_get_ticks(void)
  {
      if (!cpu_ticks_enabled) {
          return cpu_ticks_offset;
      } else {
+       int64_t ticks = cpu_get_real_ticks();
+       if( cpu_ticks_prev > ticks )
+       {
+           cpu_ticks_offset += ( cpu_ticks_prev - ticks );
+       }
+       cpu_ticks_prev = ticks;
          return cpu_get_real_ticks() + cpu_ticks_offset;
      }
  }

             reply	other threads:[~2005-10-10  5:25 UTC|newest]

Thread overview: 2+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2005-10-10  5:24 John Coiner [this message]
2005-11-15 20:09 ` [Qemu-devel] [patch] fix QEMU hang after hibernate ace

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=4349FB21.9040205@stanfordalumni.org \
    --to=jcoiner@stanfordalumni.org \
    --cc=qemu-devel@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).