qemu-timer.c revision 1091d5d16923c044d35fcacfe845ab6b76e83143
16a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/*
26a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * QEMU System Emulator
36a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner *
46a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * Copyright (c) 2003-2008 Fabrice Bellard
56a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner *
66a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * Permission is hereby granted, free of charge, to any person obtaining a copy
76a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * of this software and associated documentation files (the "Software"), to deal
86a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * in the Software without restriction, including without limitation the rights
96a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * copies of the Software, and to permit persons to whom the Software is
116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * furnished to do so, subject to the following conditions:
126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner *
136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * The above copyright notice and this permission notice shall be included in
146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * all copies or substantial portions of the Software.
156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner *
166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner * THE SOFTWARE.
236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner */
246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "sysemu.h"
266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "net.h"
276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "monitor.h"
286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "console.h"
296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "hw/hw.h"
316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <unistd.h>
336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <fcntl.h>
346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <time.h>
356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <errno.h>
366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <sys/time.h>
376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <signal.h>
386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef __FreeBSD__
396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <sys/param.h>
406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef __linux__
436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <sys/ioctl.h>
446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <linux/rtc.h>
456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* For the benefit of older linux systems which don't supply it,
466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner   we use a local copy of hpet.h. */
476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* #include <linux/hpet.h> */
486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "hpet.h"
496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef _WIN32
526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <windows.h>
536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include <mmsystem.h>
546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#include "qemu-timer.h"
576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* Conversion factor from emulated instructions to virtual clock ticks.  */
596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint icount_time_shift;
606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* Arbitrarily pick 1MIPS as the minimum allowable speed.  */
616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define MAX_ICOUNT_SHIFT 10
626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* Compensate for varying guest execution speed.  */
636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t qemu_icount_bias;
646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic QEMUTimer *icount_rt_timer;
656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic QEMUTimer *icount_vm_timer;
666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/***********************************************************/
696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* real time host monotonic timer */
706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int64_t get_clock_realtime(void)
736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct timeval tv;
756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    gettimeofday(&tv, NULL);
776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return tv.tv_sec * 1000000000LL + (tv.tv_usec * 1000);
786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef WIN32
816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int64_t clock_freq;
836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void init_get_clock(void)
856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    LARGE_INTEGER freq;
876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int ret;
886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ret = QueryPerformanceFrequency(&freq);
896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (ret == 0) {
906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Could not calibrate ticks\n");
916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        exit(1);
926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    clock_freq = freq.QuadPart;
946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int64_t get_clock(void)
976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    LARGE_INTEGER ti;
996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QueryPerformanceCounter(&ti);
1006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return muldiv64(ti.QuadPart, get_ticks_per_sec(), clock_freq);
1016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
1026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#else
1046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int use_rt_clock;
1066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void init_get_clock(void)
1086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
1096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    use_rt_clock = 0;
1106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#if defined(__linux__) || (defined(__FreeBSD__) && __FreeBSD_version >= 500000) \
1116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    || defined(__DragonFly__) || defined(__FreeBSD_kernel__)
1126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {
1136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        struct timespec ts;
1146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (clock_gettime(CLOCK_MONOTONIC, &ts) == 0) {
1156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            use_rt_clock = 1;
1166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
1176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
1186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
1196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
1206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int64_t get_clock(void)
1226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
1236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#if defined(__linux__) || (defined(__FreeBSD__) && __FreeBSD_version >= 500000) \
1246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner	|| defined(__DragonFly__) || defined(__FreeBSD_kernel__)
1256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (use_rt_clock) {
1266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        struct timespec ts;
1276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        clock_gettime(CLOCK_MONOTONIC, &ts);
1286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return ts.tv_sec * 1000000000LL + ts.tv_nsec;
1296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else
1306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
1316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {
1326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* XXX: using gettimeofday leads to problems if the date
1336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner           changes, so it should be avoided. */
1346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return get_clock_realtime();
1356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
1366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
1376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
1386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/***********************************************************/
1406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* guest cycle counter */
1416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnertypedef struct TimersState {
1436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t cpu_ticks_prev;
1446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t cpu_ticks_offset;
1456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t cpu_clock_offset;
1466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int32_t cpu_ticks_enabled;
1476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t dummy;
1486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner} TimersState;
1496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void timer_save(QEMUFile *f, void *opaque)
1516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
1526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    TimersState *s = opaque;
1536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (s->cpu_ticks_enabled) {
1556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        hw_error("cannot save state if virtual timers are running");
1566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
1576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_put_be64(f, s->cpu_ticks_prev);
1586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_put_be64(f, s->cpu_ticks_offset);
1596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_put_be64(f, s->cpu_clock_offset);
1606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner }
1616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int timer_load(QEMUFile *f, void *opaque, int version_id)
1636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
1646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    TimersState *s = opaque;
1656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (version_id != 1 && version_id != 2)
1676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -EINVAL;
1686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (s->cpu_ticks_enabled) {
1696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -EINVAL;
1706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
1716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    s->cpu_ticks_prev   = qemu_get_sbe64(f);
1726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    s->cpu_ticks_offset = qemu_get_sbe64(f);
1736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (version_id == 2) {
1746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        s->cpu_clock_offset = qemu_get_sbe64(f);
1756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
1766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
1776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
1786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1806a9ef1773bf874dea493ff3861782a1e577b67ddDavid TurnerTimersState timers_state;
1816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
1826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* return the host CPU cycle counter and handle stop/restart */
1836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t cpu_get_ticks(void)
1846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
1856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (use_icount) {
1866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return cpu_get_icount();
1876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
1886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!timers_state.cpu_ticks_enabled) {
1896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return timers_state.cpu_ticks_offset;
1906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else {
1916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        int64_t ticks;
1926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ticks = cpu_get_real_ticks();
1936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (timers_state.cpu_ticks_prev > ticks) {
1946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            /* Note: non increasing ticks may happen if the host uses
1956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner               software suspend */
1966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            timers_state.cpu_ticks_offset += timers_state.cpu_ticks_prev - ticks;
1976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
1986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_ticks_prev = ticks;
1996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return ticks + timers_state.cpu_ticks_offset;
2006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
2016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* return the host CPU monotonic timer and handle stop/restart */
2046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int64_t cpu_get_clock(void)
2056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t ti;
2076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!timers_state.cpu_ticks_enabled) {
2086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return timers_state.cpu_clock_offset;
2096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else {
2106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ti = get_clock();
2116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return ti + timers_state.cpu_clock_offset;
2126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
2136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifndef CONFIG_IOTHREAD
2166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int64_t qemu_icount_delta(void)
2176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!use_icount) {
2196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return 5000 * (int64_t) 1000000;
2206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else if (use_icount == 1) {
2216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* When not using an adaptive execution frequency
2226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner           we tend to get badly out of sync with real time,
2236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner           so just delay for a reasonable amount of time.  */
2246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return 0;
2256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else {
2266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return cpu_get_icount() - cpu_get_clock();
2276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
2286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
2306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* enable cpu_get_ticks() */
2326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid cpu_enable_ticks(void)
2336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!timers_state.cpu_ticks_enabled) {
2356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_ticks_offset -= cpu_get_real_ticks();
2366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_clock_offset -= get_clock();
2376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_ticks_enabled = 1;
2386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
2396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* disable cpu_get_ticks() : the clock is stopped. You must not call
2426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner   cpu_get_ticks() after that.  */
2436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid cpu_disable_ticks(void)
2446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (timers_state.cpu_ticks_enabled) {
2466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_ticks_offset = cpu_get_ticks();
2476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_clock_offset = cpu_get_clock();
2486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timers_state.cpu_ticks_enabled = 0;
2496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
2506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/***********************************************************/
2536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* timers */
2546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define QEMU_CLOCK_REALTIME 0
2566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define QEMU_CLOCK_VIRTUAL  1
2576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define QEMU_CLOCK_HOST     2
2586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstruct QEMUClock {
2606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int type;
2616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int enabled;
2626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* XXX: add frequency */
2636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner};
2646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstruct QEMUTimer {
2666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUClock *clock;
2676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t expire_time;
2686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUTimerCB *cb;
2696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    void *opaque;
2706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct QEMUTimer *next;
2716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner};
2726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstruct qemu_alarm_timer {
2746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    char const *name;
2756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int (*start)(struct qemu_alarm_timer *t);
2766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    void (*stop)(struct qemu_alarm_timer *t);
2776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    void (*rearm)(struct qemu_alarm_timer *t);
2786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    void *priv;
2796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    char expired;
2816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    char pending;
2826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner};
2836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic struct qemu_alarm_timer *alarm_timer;
2856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint qemu_alarm_pending(void)
2876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return alarm_timer->pending;
2896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic inline int alarm_has_dynticks(struct qemu_alarm_timer *t)
2926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return !!t->rearm;
2946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
2956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
2966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void qemu_rearm_alarm_timer(struct qemu_alarm_timer *t)
2976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
2986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!alarm_has_dynticks(t))
2996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
3006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    t->rearm(t);
3026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
3036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* TODO: MIN_TIMER_REARM_US should be optimized */
3056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define MIN_TIMER_REARM_US 250
3066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef _WIN32
3086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstruct qemu_alarm_win32 {
3106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    MMRESULT timerId;
3116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    unsigned int period;
3126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner} alarm_win32_data = {0, 0};
3136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int win32_start_timer(struct qemu_alarm_timer *t);
3156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void win32_stop_timer(struct qemu_alarm_timer *t);
3166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void win32_rearm_timer(struct qemu_alarm_timer *t);
3176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#else
3196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int unix_start_timer(struct qemu_alarm_timer *t);
3216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void unix_stop_timer(struct qemu_alarm_timer *t);
3226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef __linux__
3246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int dynticks_start_timer(struct qemu_alarm_timer *t);
3266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void dynticks_stop_timer(struct qemu_alarm_timer *t);
3276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void dynticks_rearm_timer(struct qemu_alarm_timer *t);
3286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int hpet_start_timer(struct qemu_alarm_timer *t);
3306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void hpet_stop_timer(struct qemu_alarm_timer *t);
3316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int rtc_start_timer(struct qemu_alarm_timer *t);
3336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void rtc_stop_timer(struct qemu_alarm_timer *t);
3346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif /* __linux__ */
3366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif /* _WIN32 */
3386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* Correlation between real and virtual time is always going to be
3406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner   fairly approximate, so ignore small variation.
3416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner   When the guest is idle real and virtual time will be aligned in
3426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner   the IO wait loop.  */
3436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define ICOUNT_WOBBLE (get_ticks_per_sec() / 10)
3446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void icount_adjust(void)
3466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
3476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t cur_time;
3486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t cur_icount;
3496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t delta;
3506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    static int64_t last_delta;
3516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* If the VM is not running, then do nothing.  */
3526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!vm_running)
3536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
3546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    cur_time = cpu_get_clock();
3566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    cur_icount = qemu_get_clock(vm_clock);
3576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    delta = cur_icount - cur_time;
3586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* FIXME: This is a very crude algorithm, somewhat prone to oscillation.  */
3596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (delta > 0
3606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        && last_delta + ICOUNT_WOBBLE < delta * 2
3616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        && icount_time_shift > 0) {
3626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* The guest is getting too far ahead.  Slow time down.  */
3636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        icount_time_shift--;
3646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
3656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (delta < 0
3666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        && last_delta - ICOUNT_WOBBLE > delta * 2
3676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        && icount_time_shift < MAX_ICOUNT_SHIFT) {
3686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* The guest is getting too far behind.  Speed time up.  */
3696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        icount_time_shift++;
3706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
3716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    last_delta = delta;
3726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_icount_bias = cur_icount - (qemu_icount << icount_time_shift);
3736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
3746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void icount_adjust_rt(void * opaque)
3766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
3776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_mod_timer(icount_rt_timer,
3786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                   qemu_get_clock(rt_clock) + 1000);
3796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    icount_adjust();
3806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
3816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void icount_adjust_vm(void * opaque)
3836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
3846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_mod_timer(icount_vm_timer,
3856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                   qemu_get_clock(vm_clock) + get_ticks_per_sec() / 10);
3866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    icount_adjust();
3876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
3886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t qemu_icount_round(int64_t count)
3906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
3916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return (count + (1 << icount_time_shift) - 1) >> icount_time_shift;
3926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
3936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
3946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic struct qemu_alarm_timer alarm_timers[] = {
3956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifndef _WIN32
3966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef __linux__
3976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {"dynticks", dynticks_start_timer,
3986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     dynticks_stop_timer, dynticks_rearm_timer, NULL},
3996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* HPET - if available - is preferred */
4006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {"hpet", hpet_start_timer, hpet_stop_timer, NULL, NULL},
4016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* ...otherwise try RTC */
4026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {"rtc", rtc_start_timer, rtc_stop_timer, NULL, NULL},
4036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
4046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {"unix", unix_start_timer, unix_stop_timer, NULL, NULL},
4056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#else
4066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {"dynticks", win32_start_timer,
4076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     win32_stop_timer, win32_rearm_timer, &alarm_win32_data},
4086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {"win32", win32_start_timer,
4096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     win32_stop_timer, NULL, &alarm_win32_data},
4106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
4116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {NULL, }
4126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner};
4136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void show_available_alarms(void)
4156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
4166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int i;
4176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    printf("Available alarm timers, in order of precedence:\n");
4196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    for (i = 0; alarm_timers[i].name; i++)
4206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        printf("%s\n", alarm_timers[i].name);
4216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
4226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid configure_alarms(char const *opt)
4246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
4256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int i;
4266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int cur = 0;
4276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int count = ARRAY_SIZE(alarm_timers) - 1;
4286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    char *arg;
4296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    char *name;
4306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_timer tmp;
4316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!strcmp(opt, "?")) {
4336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        show_available_alarms();
4346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        exit(0);
4356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
4366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    arg = qemu_strdup(opt);
4386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Reorder the array */
4406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    name = strtok(arg, ",");
4416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    while (name) {
4426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        for (i = 0; i < count && alarm_timers[i].name; i++) {
4436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            if (!strcmp(alarm_timers[i].name, name))
4446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                break;
4456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
4466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (i == count) {
4486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            fprintf(stderr, "Unknown clock %s\n", name);
4496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            goto next;
4506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
4516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (i < cur)
4536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            /* Ignore */
4546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            goto next;
4556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner	/* Swap */
4576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        tmp = alarm_timers[i];
4586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        alarm_timers[i] = alarm_timers[cur];
4596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        alarm_timers[cur] = tmp;
4606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        cur++;
4626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnernext:
4636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        name = strtok(NULL, ",");
4646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
4656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_free(arg);
4676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (cur) {
4696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* Disable remaining timers */
4706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        for (i = cur; i < count; i++)
4716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            alarm_timers[i].name = NULL;
4726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else {
4736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        show_available_alarms();
4746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        exit(1);
4756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
4766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
4776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define QEMU_NUM_CLOCKS 3
4796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4806a9ef1773bf874dea493ff3861782a1e577b67ddDavid TurnerQEMUClock *rt_clock;
4816a9ef1773bf874dea493ff3861782a1e577b67ddDavid TurnerQEMUClock *vm_clock;
4826a9ef1773bf874dea493ff3861782a1e577b67ddDavid TurnerQEMUClock *host_clock;
4836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic QEMUTimer *active_timers[QEMU_NUM_CLOCKS];
4856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic QEMUClock *qemu_new_clock(int type)
4876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
4886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUClock *clock;
4896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    clock = qemu_mallocz(sizeof(QEMUClock));
4906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    clock->type = type;
4916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    clock->enabled = 1;
4926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return clock;
4936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
4946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
4956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_clock_enable(QEMUClock *clock, int enabled)
4966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
4976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    clock->enabled = enabled;
4986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
4996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5006a9ef1773bf874dea493ff3861782a1e577b67ddDavid TurnerQEMUTimer *qemu_new_timer(QEMUClock *clock, QEMUTimerCB *cb, void *opaque)
5016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUTimer *ts;
5036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ts = qemu_mallocz(sizeof(QEMUTimer));
5056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ts->clock = clock;
5066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ts->cb = cb;
5076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ts->opaque = opaque;
5086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return ts;
5096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
5106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_free_timer(QEMUTimer *ts)
5126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_free(ts);
5146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
5156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* stop a timer, but do not dealloc it */
5176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_del_timer(QEMUTimer *ts)
5186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUTimer **pt, *t;
5206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* NOTE: this code must be signal safe because
5226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       qemu_timer_expired() can be called from a signal. */
5236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    pt = &active_timers[ts->clock->type];
5246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    for(;;) {
5256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        t = *pt;
5266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (!t)
5276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            break;
5286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (t == ts) {
5296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            *pt = t->next;
5306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            break;
5316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
5326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        pt = &t->next;
5336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
5346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
5356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* modify the current timer so that it will be fired when current_time
5376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner   >= expire_time. The corresponding callback will be called. */
5386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_mod_timer(QEMUTimer *ts, int64_t expire_time)
5396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUTimer **pt, *t;
5416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_del_timer(ts);
5436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* add the timer in the sorted list */
5456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* NOTE: this code must be signal safe because
5466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       qemu_timer_expired() can be called from a signal. */
5476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    pt = &active_timers[ts->clock->type];
5486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    for(;;) {
5496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        t = *pt;
5506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (!t)
5516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            break;
5526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (t->expire_time > expire_time)
5536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            break;
5546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        pt = &t->next;
5556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
5566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ts->expire_time = expire_time;
5576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ts->next = *pt;
5586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    *pt = ts;
5596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Rearm if necessary  */
5616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (pt == &active_timers[ts->clock->type]) {
5626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (!alarm_timer->pending) {
5636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            qemu_rearm_alarm_timer(alarm_timer);
5646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
5656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* Interrupt execution to force deadline recalculation.  */
5666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (use_icount)
5676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            qemu_notify_event();
5686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
5696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
5706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint qemu_timer_pending(QEMUTimer *ts)
5726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUTimer *t;
5746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    for(t = active_timers[ts->clock->type]; t != NULL; t = t->next) {
5756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (t == ts)
5766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            return 1;
5776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
5786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
5796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
5806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint qemu_timer_expired(QEMUTimer *timer_head, int64_t current_time)
5826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!timer_head)
5846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return 0;
5856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return (timer_head->expire_time <= current_time);
5866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
5876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void qemu_run_timers(QEMUClock *clock)
5896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
5906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    QEMUTimer **ptimer_head, *ts;
5916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t current_time;
5926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!clock->enabled)
5946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
5956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
5966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    current_time = qemu_get_clock (clock);
5976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ptimer_head = &active_timers[clock->type];
5986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    for(;;) {
5996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ts = *ptimer_head;
6006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (!ts || ts->expire_time > current_time)
6016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            break;
6026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* remove timer from the list before calling the callback */
6036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        *ptimer_head = ts->next;
6046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ts->next = NULL;
6056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* run the callback (the timer list can be modified) */
6076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ts->cb(ts->opaque);
6086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
6096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
6106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t qemu_get_clock(QEMUClock *clock)
6126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
6136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    switch(clock->type) {
6146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    case QEMU_CLOCK_REALTIME:
6156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return get_clock() / 1000000;
6166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    default:
6176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    case QEMU_CLOCK_VIRTUAL:
6186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (use_icount) {
6196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            return cpu_get_icount();
6206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        } else {
6216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            return cpu_get_clock();
6226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
6236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    case QEMU_CLOCK_HOST:
6246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return get_clock_realtime();
6256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
6266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
6276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t qemu_get_clock_ns(QEMUClock *clock)
6296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
6306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    switch(clock->type) {
6316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    case QEMU_CLOCK_REALTIME:
6326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return get_clock();
6336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    default:
6346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    case QEMU_CLOCK_VIRTUAL:
6356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (use_icount) {
6366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            return cpu_get_icount();
6376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        } else {
6386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            return cpu_get_clock();
6396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
6406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    case QEMU_CLOCK_HOST:
6416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return get_clock_realtime();
6426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
6436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
6446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid init_clocks(void)
6466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
6476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    init_get_clock();
6486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    rt_clock = qemu_new_clock(QEMU_CLOCK_REALTIME);
6496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    vm_clock = qemu_new_clock(QEMU_CLOCK_VIRTUAL);
6506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    host_clock = qemu_new_clock(QEMU_CLOCK_HOST);
6516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    rtc_clock = host_clock;
6536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
6546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* save a timer */
6566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_put_timer(QEMUFile *f, QEMUTimer *ts)
6576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
6586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    uint64_t expire_time;
6596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (qemu_timer_pending(ts)) {
6616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        expire_time = ts->expire_time;
6626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else {
6636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        expire_time = -1;
6646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
6656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_put_be64(f, expire_time);
6666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
6676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_get_timer(QEMUFile *f, QEMUTimer *ts)
6696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
6706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    uint64_t expire_time;
6716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    expire_time = qemu_get_be64(f);
6736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (expire_time != -1) {
6746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_mod_timer(ts, expire_time);
6756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    } else {
6766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_del_timer(ts);
6776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
6786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
6796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#if 0
6816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic const VMStateDescription vmstate_timers = {
6826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    .name = "timer",
6836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    .version_id = 2,
6846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    .minimum_version_id = 1,
6856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    .minimum_version_id_old = 1,
6866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    .fields      = (VMStateField []) {
6876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        VMSTATE_INT64(cpu_ticks_offset, TimersState),
6886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        VMSTATE_INT64(dummy, TimersState),
6896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        VMSTATE_INT64_V(cpu_clock_offset, TimersState, 2),
6906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        VMSTATE_END_OF_LIST()
6916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
6926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner};
6936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
6946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid configure_icount(const char *option)
6966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
6971091d5d16923c044d35fcacfe845ab6b76e83143Ot ten Thije    register_savevm("timer", 0, 2, timer_save, timer_load, &timers_state);
6986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
6996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!option)
7006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
7016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (strcmp(option, "auto") != 0) {
7036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        icount_time_shift = strtol(option, NULL, 0);
7046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        use_icount = 1;
7056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
7066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
7076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    use_icount = 2;
7096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* 125MIPS seems a reasonable initial guess at the guest speed.
7116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       It will be corrected fairly quickly anyway.  */
7126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    icount_time_shift = 3;
7136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Have both realtime and virtual time triggers for speed adjustment.
7156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       The realtime trigger catches emulated time passing too slowly,
7166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       the virtual time trigger catches emulated time passing too fast.
7176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       Realtime triggers occur even when idle, so use them less frequently
7186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner       than VM triggers.  */
7196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    icount_rt_timer = qemu_new_timer(rt_clock, icount_adjust_rt, NULL);
7206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_mod_timer(icount_rt_timer,
7216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                   qemu_get_clock(rt_clock) + 1000);
7226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    icount_vm_timer = qemu_new_timer(vm_clock, icount_adjust_vm, NULL);
7236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_mod_timer(icount_vm_timer,
7246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                   qemu_get_clock(vm_clock) + get_ticks_per_sec() / 10);
7256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
7266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid qemu_run_all_timers(void)
7286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
7296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    alarm_timer->pending = 0;
7306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* rearm timer, if not periodic */
7326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (alarm_timer->expired) {
7336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        alarm_timer->expired = 0;
7346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_rearm_alarm_timer(alarm_timer);
7356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
7366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* vm time timers */
7386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (vm_running) {
7396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_run_timers(vm_clock);
7406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
7416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_run_timers(rt_clock);
7436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_run_timers(host_clock);
7446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
7456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef _WIN32
7476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void CALLBACK host_alarm_handler(UINT uTimerID, UINT uMsg,
7486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                                        DWORD_PTR dwUser, DWORD_PTR dw1,
7496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                                        DWORD_PTR dw2)
7506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#else
7516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void host_alarm_handler(int host_signum)
7526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
7536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
7546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_timer *t = alarm_timer;
7556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!t)
7566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner	return;
7576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#if 0
7596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define DISP_FREQ 1000
7606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    {
7616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        static int64_t delta_min = INT64_MAX;
7626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        static int64_t delta_max, delta_cum, last_clock, delta, ti;
7636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        static int count;
7646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ti = qemu_get_clock(vm_clock);
7656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (last_clock != 0) {
7666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            delta = ti - last_clock;
7676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            if (delta < delta_min)
7686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                delta_min = delta;
7696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            if (delta > delta_max)
7706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                delta_max = delta;
7716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            delta_cum += delta;
7726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            if (++count == DISP_FREQ) {
7736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                printf("timer: min=%" PRId64 " us max=%" PRId64 " us avg=%" PRId64 " us avg_freq=%0.3f Hz\n",
7746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                       muldiv64(delta_min, 1000000, get_ticks_per_sec()),
7756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                       muldiv64(delta_max, 1000000, get_ticks_per_sec()),
7766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                       muldiv64(delta_cum, 1000000 / DISP_FREQ, get_ticks_per_sec()),
7776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                       (double)get_ticks_per_sec() / ((double)delta_cum / DISP_FREQ));
7786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                count = 0;
7796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                delta_min = INT64_MAX;
7806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                delta_max = 0;
7816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                delta_cum = 0;
7826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            }
7836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
7846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        last_clock = ti;
7856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
7866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
7876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (alarm_has_dynticks(t) ||
7886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        (!use_icount &&
7896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            qemu_timer_expired(active_timers[QEMU_CLOCK_VIRTUAL],
7906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                               qemu_get_clock(vm_clock))) ||
7916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_timer_expired(active_timers[QEMU_CLOCK_REALTIME],
7926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                           qemu_get_clock(rt_clock)) ||
7936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_timer_expired(active_timers[QEMU_CLOCK_HOST],
7946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                           qemu_get_clock(host_clock))) {
7956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
7966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        t->expired = alarm_has_dynticks(t);
7976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        t->pending = 1;
7986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_notify_event();
7996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
8006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
8016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t qemu_next_deadline(void)
8036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
8046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* To avoid problems with overflow limit this to 2^32.  */
8056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t delta = INT32_MAX;
8066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (active_timers[QEMU_CLOCK_VIRTUAL]) {
8086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        delta = active_timers[QEMU_CLOCK_VIRTUAL]->expire_time -
8096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                     qemu_get_clock(vm_clock);
8106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
8116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (active_timers[QEMU_CLOCK_HOST]) {
8126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        int64_t hdelta = active_timers[QEMU_CLOCK_HOST]->expire_time -
8136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                 qemu_get_clock(host_clock);
8146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (hdelta < delta)
8156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            delta = hdelta;
8166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
8176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (delta < 0)
8196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        delta = 0;
8206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return delta;
8226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
8236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifndef _WIN32
8256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#if defined(__linux__)
8276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#define RTC_FREQ 1024
8296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic uint64_t qemu_next_deadline_dyntick(void)
8316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
8326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t delta;
8336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t rtdelta;
8346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (use_icount)
8366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        delta = INT32_MAX;
8376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    else
8386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        delta = (qemu_next_deadline() + 999) / 1000;
8396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (active_timers[QEMU_CLOCK_REALTIME]) {
8416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        rtdelta = (active_timers[QEMU_CLOCK_REALTIME]->expire_time -
8426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                 qemu_get_clock(rt_clock))*1000;
8436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (rtdelta < delta)
8446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            delta = rtdelta;
8456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
8466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (delta < MIN_TIMER_REARM_US)
8486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        delta = MIN_TIMER_REARM_US;
8496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return delta;
8516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
8526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void enable_sigio_timer(int fd)
8546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
8556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct sigaction act;
8566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* timer signal */
8586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    sigfillset(&act.sa_mask);
8596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    act.sa_flags = 0;
8606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    act.sa_handler = host_alarm_handler;
8616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    sigaction(SIGIO, &act, NULL);
8636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    fcntl_setfl(fd, O_ASYNC);
8646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    fcntl(fd, F_SETOWN, getpid());
8656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
8666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int hpet_start_timer(struct qemu_alarm_timer *t)
8686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
8696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct hpet_info info;
8706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int r, fd;
8716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    fd = open("/dev/hpet", O_RDONLY);
8736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (fd < 0)
8746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -1;
8756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Set frequency */
8776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    r = ioctl(fd, HPET_IRQFREQ, RTC_FREQ);
8786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (r < 0) {
8796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Could not configure '/dev/hpet' to have a 1024Hz timer. This is not a fatal\n"
8806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                "error, but for better emulation accuracy type:\n"
8816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                "'echo 1024 > /proc/sys/dev/hpet/max-user-freq' as root.\n");
8826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        goto fail;
8836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
8846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Check capabilities */
8866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    r = ioctl(fd, HPET_INFO, &info);
8876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (r < 0)
8886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        goto fail;
8896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Enable periodic mode */
8916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    r = ioctl(fd, HPET_EPI, 0);
8926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (info.hi_flags && (r < 0))
8936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        goto fail;
8946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
8956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* Enable interrupt */
8966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    r = ioctl(fd, HPET_IE_ON, 0);
8976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (r < 0)
8986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        goto fail;
8996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    enable_sigio_timer(fd);
9016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    t->priv = (void *)(long)fd;
9026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
9046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerfail:
9056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    close(fd);
9066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return -1;
9076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
9086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void hpet_stop_timer(struct qemu_alarm_timer *t)
9106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
9116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int fd = (long)t->priv;
9126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    close(fd);
9146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
9156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int rtc_start_timer(struct qemu_alarm_timer *t)
9176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
9186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int rtc_fd;
9196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    unsigned long current_rtc_freq = 0;
9206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    TFR(rtc_fd = open("/dev/rtc", O_RDONLY));
9226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (rtc_fd < 0)
9236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -1;
9246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ioctl(rtc_fd, RTC_IRQP_READ, &current_rtc_freq);
9256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (current_rtc_freq != RTC_FREQ &&
9266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        ioctl(rtc_fd, RTC_IRQP_SET, RTC_FREQ) < 0) {
9276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Could not configure '/dev/rtc' to have a 1024 Hz timer. This is not a fatal\n"
9286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                "error, but for better emulation accuracy either use a 2.6 host Linux kernel or\n"
9296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                "type 'echo 1024 > /proc/sys/dev/rtc/max-user-freq' as root.\n");
9306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        goto fail;
9316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
9326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (ioctl(rtc_fd, RTC_PIE_ON, 0) < 0) {
9336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    fail:
9346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        close(rtc_fd);
9356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -1;
9366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
9376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    enable_sigio_timer(rtc_fd);
9396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    t->priv = (void *)(long)rtc_fd;
9416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
9436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
9446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void rtc_stop_timer(struct qemu_alarm_timer *t)
9466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
9476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int rtc_fd = (long)t->priv;
9486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    close(rtc_fd);
9506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
9516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int dynticks_start_timer(struct qemu_alarm_timer *t)
9536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
9546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct sigevent ev;
9556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timer_t host_timer;
9566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct sigaction act;
9576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    sigfillset(&act.sa_mask);
9596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    act.sa_flags = 0;
9606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    act.sa_handler = host_alarm_handler;
9616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    sigaction(SIGALRM, &act, NULL);
9636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /*
9656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     * Initialize ev struct to 0 to avoid valgrind complaining
9666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     * about uninitialized data in timer_create call
9676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     */
9686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    memset(&ev, 0, sizeof(ev));
9696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ev.sigev_value.sival_int = 0;
9706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ev.sigev_notify = SIGEV_SIGNAL;
9716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    ev.sigev_signo = SIGALRM;
9726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (timer_create(CLOCK_REALTIME, &ev, &host_timer)) {
9746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        perror("timer_create");
9756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* disable dynticks */
9776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Dynamic Ticks disabled\n");
9786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -1;
9806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
9816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    t->priv = (void *)(long)host_timer;
9836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
9856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
9866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void dynticks_stop_timer(struct qemu_alarm_timer *t)
9886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
9896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timer_t host_timer = (timer_t)(long)t->priv;
9906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timer_delete(host_timer);
9926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
9936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
9946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void dynticks_rearm_timer(struct qemu_alarm_timer *t)
9956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
9966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timer_t host_timer = (timer_t)(long)t->priv;
9976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct itimerspec timeout;
9986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t nearest_delta_us = INT64_MAX;
9996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t current_us;
10006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    assert(alarm_has_dynticks(t));
10026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!active_timers[QEMU_CLOCK_REALTIME] &&
10036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        !active_timers[QEMU_CLOCK_VIRTUAL] &&
10046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        !active_timers[QEMU_CLOCK_HOST])
10056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
10066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    nearest_delta_us = qemu_next_deadline_dyntick();
10086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* check whether a timer is already running */
10106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (timer_gettime(host_timer, &timeout)) {
10116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        perror("gettime");
10126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Internal timer error: aborting\n");
10136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        exit(1);
10146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
10156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    current_us = timeout.it_value.tv_sec * 1000000 + timeout.it_value.tv_nsec/1000;
10166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (current_us && current_us <= nearest_delta_us)
10176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
10186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeout.it_interval.tv_sec = 0;
10206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeout.it_interval.tv_nsec = 0; /* 0 for one-shot timer */
10216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeout.it_value.tv_sec =  nearest_delta_us / 1000000;
10226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeout.it_value.tv_nsec = (nearest_delta_us % 1000000) * 1000;
10236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (timer_settime(host_timer, 0 /* RELATIVE */, &timeout, NULL)) {
10246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        perror("settime");
10256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Internal timer error: aborting\n");
10266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        exit(1);
10276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
10286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
10296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif /* defined(__linux__) */
10316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int unix_start_timer(struct qemu_alarm_timer *t)
10336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
10346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct sigaction act;
10356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct itimerval itv;
10366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int err;
10376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* timer signal */
10396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    sigfillset(&act.sa_mask);
10406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    act.sa_flags = 0;
10416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    act.sa_handler = host_alarm_handler;
10426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    sigaction(SIGALRM, &act, NULL);
10446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    itv.it_interval.tv_sec = 0;
10466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* for i386 kernel 2.6 to get 1 ms */
10476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    itv.it_interval.tv_usec = 999;
10486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    itv.it_value.tv_sec = 0;
10496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    itv.it_value.tv_usec = 10 * 1000;
10506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    err = setitimer(ITIMER_REAL, &itv, NULL);
10526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (err)
10536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -1;
10546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
10566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
10576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void unix_stop_timer(struct qemu_alarm_timer *t)
10596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
10606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct itimerval itv;
10616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    memset(&itv, 0, sizeof(itv));
10636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    setitimer(ITIMER_REAL, &itv, NULL);
10646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
10656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif /* !defined(_WIN32) */
10676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifdef _WIN32
10706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic int win32_start_timer(struct qemu_alarm_timer *t)
10726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
10736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    TIMECAPS tc;
10746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_win32 *data = t->priv;
10756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    UINT flags;
10766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    memset(&tc, 0, sizeof(tc));
10786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeGetDevCaps(&tc, sizeof(tc));
10796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    data->period = tc.wPeriodMin;
10816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeBeginPeriod(data->period);
10826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    flags = TIME_CALLBACK_FUNCTION;
10846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (alarm_has_dynticks(t))
10856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        flags |= TIME_ONESHOT;
10866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    else
10876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        flags |= TIME_PERIODIC;
10886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    data->timerId = timeSetEvent(1,         // interval (ms)
10906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        data->period,       // resolution
10916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        host_alarm_handler, // function
10926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        (DWORD)t,           // parameter
10936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        flags);
10946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
10956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!data->timerId) {
10966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Failed to initialize win32 alarm timer: %ld\n",
10976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                GetLastError());
10986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timeEndPeriod(data->period);
10996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return -1;
11006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
11016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
11036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
11046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void win32_stop_timer(struct qemu_alarm_timer *t)
11066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
11076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_win32 *data = t->priv;
11086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeKillEvent(data->timerId);
11106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeEndPeriod(data->period);
11116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
11126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void win32_rearm_timer(struct qemu_alarm_timer *t)
11146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
11156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_win32 *data = t->priv;
11166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    assert(alarm_has_dynticks(t));
11186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!active_timers[QEMU_CLOCK_REALTIME] &&
11196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        !active_timers[QEMU_CLOCK_VIRTUAL] &&
11206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        !active_timers[QEMU_CLOCK_HOST])
11216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        return;
11226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    timeKillEvent(data->timerId);
11246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    data->timerId = timeSetEvent(1,
11266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        data->period,
11276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        host_alarm_handler,
11286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        (DWORD)t,
11296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                        TIME_ONESHOT | TIME_CALLBACK_FUNCTION);
11306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!data->timerId) {
11326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        fprintf(stderr, "Failed to re-arm win32 alarm timer %ld\n",
11336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                GetLastError());
11346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timeEndPeriod(data->period);
11366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        exit(1);
11376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
11386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
11396a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11406a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif /* _WIN32 */
11416a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11426a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerstatic void alarm_timer_on_change_state_rearm(void *opaque, int running, int reason)
11436a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
11446a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (running)
11456a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        qemu_rearm_alarm_timer((struct qemu_alarm_timer *) opaque);
11466a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
11476a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11486a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint init_timer_alarm(void)
11496a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
11506a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_timer *t = NULL;
11516a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int i, err = -1;
11526a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11536a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    for (i = 0; alarm_timers[i].name; i++) {
11546a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        t = &alarm_timers[i];
11556a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11566a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        err = t->start(t);
11576a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (!err)
11586a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            break;
11596a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
11606a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11616a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (err) {
11626a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        err = -ENOENT;
11636a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        goto fail;
11646a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
11656a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11666a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    /* first event is at time 0 */
11676a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    t->pending = 1;
11686a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    alarm_timer = t;
11696a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    qemu_add_vm_change_state_handler(alarm_timer_on_change_state_rearm, t);
11706a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11716a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 0;
11726a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11736a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerfail:
11746a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return err;
11756a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
11766a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11776a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnervoid quit_timers(void)
11786a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
11796a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    struct qemu_alarm_timer *t = alarm_timer;
11806a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    alarm_timer = NULL;
11816a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    t->stop(t);
11826a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
11836a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11846a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint qemu_calculate_timeout(void)
11856a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
11866a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#ifndef CONFIG_IOTHREAD
11876a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int timeout;
11886a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
11896a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (!vm_running)
11906a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        timeout = 5000;
11916a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    else {
11926a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner     /* XXX: use timeout computed from timers */
11936a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        int64_t add;
11946a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        int64_t delta;
11956a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        /* Advance virtual time to the next event.  */
11966a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner	delta = qemu_icount_delta();
11976a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (delta > 0) {
11986a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            /* If virtual time is ahead of real time then just
11996a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner               wait for IO.  */
12006a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            timeout = (delta + 999999) / 1000000;
12016a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        } else {
12026a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            /* Wait for either IO to occur or the next
12036a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner               timer event.  */
12046a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            add = qemu_next_deadline();
12056a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            /* We advance the timer before checking for IO.
12066a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner               Limit the amount we advance so that early IO
12076a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner               activity won't get the guest too far ahead.  */
12086a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            if (add > 10000000)
12096a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                add = 10000000;
12106a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            delta += add;
12116a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            qemu_icount += qemu_icount_round (add);
12126a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            timeout = delta / 1000000;
12136a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            if (timeout < 0)
12146a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner                timeout = 0;
12156a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
12166a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
12176a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
12186a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return timeout;
12196a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#else /* CONFIG_IOTHREAD */
12206a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return 1000;
12216a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner#endif
12226a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
12236a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
12246a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner/* Return the virtual CPU time, based on the instruction counter.  */
12256a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turnerint64_t cpu_get_icount(void)
12266a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner{
12276a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    int64_t icount;
12286a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    CPUState *env = cpu_single_env;;
12296a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner
12306a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    icount = qemu_icount;
12316a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    if (env) {
12326a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        if (!can_do_io(env)) {
12336a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner            fprintf(stderr, "Bad clock read\n");
12346a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        }
12356a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner        icount -= (env->icount_decr.u16.low + env->icount_extra);
12366a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    }
12376a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner    return qemu_icount_bias + (icount << icount_time_shift);
12386a9ef1773bf874dea493ff3861782a1e577b67ddDavid Turner}
1239