1 /* 2 * QEMU System Emulator 3 * 4 * Copyright (c) 2003-2008 Fabrice Bellard 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a copy 7 * of this software and associated documentation files (the "Software"), to deal 8 * in the Software without restriction, including without limitation the rights 9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 * copies of the Software, and to permit persons to whom the Software is 11 * furnished to do so, subject to the following conditions: 12 * 13 * The above copyright notice and this permission notice shall be included in 14 * all copies or substantial portions of the Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 * THE SOFTWARE. 23 */ 24 25 #include "sysemu/sysemu.h" 26 #include "monitor/monitor.h" 27 #include "ui/console.h" 28 29 #include "hw/hw.h" 30 31 #include "qemu/thread.h" 32 #include "qemu/timer.h" 33 #ifdef CONFIG_POSIX 34 #include <pthread.h> 35 #endif 36 37 #ifdef CONFIG_PPOLL 38 #include <poll.h> 39 #endif 40 41 #ifdef CONFIG_PRCTL_PR_SET_TIMERSLACK 42 #include <sys/prctl.h> 43 #endif 44 45 /***********************************************************/ 46 /* timers */ 47 48 typedef struct QEMUClock { 49 /* We rely on BQL to protect the timerlists */ 50 QLIST_HEAD(, QEMUTimerList) timerlists; 51 52 NotifierList reset_notifiers; 53 int64_t last; 54 55 QEMUClockType type; 56 bool enabled; 57 } QEMUClock; 58 59 QEMUTimerListGroup main_loop_tlg; 60 QEMUClock qemu_clocks[QEMU_CLOCK_MAX]; 61 62 /* A QEMUTimerList is a list of timers attached to a clock. More 63 * than one QEMUTimerList can be attached to each clock, for instance 64 * used by different AioContexts / threads. Each clock also has 65 * a list of the QEMUTimerLists associated with it, in order that 66 * reenabling the clock can call all the notifiers. 67 */ 68 69 struct QEMUTimerList { 70 QEMUClock *clock; 71 QemuMutex active_timers_lock; 72 QEMUTimer *active_timers; 73 QLIST_ENTRY(QEMUTimerList) list; 74 QEMUTimerListNotifyCB *notify_cb; 75 void *notify_opaque; 76 77 /* lightweight method to mark the end of timerlist's running */ 78 QemuEvent timers_done_ev; 79 }; 80 81 /** 82 * qemu_clock_ptr: 83 * @type: type of clock 84 * 85 * Translate a clock type into a pointer to QEMUClock object. 86 * 87 * Returns: a pointer to the QEMUClock object 88 */ 89 static inline QEMUClock *qemu_clock_ptr(QEMUClockType type) 90 { 91 return &qemu_clocks[type]; 92 } 93 94 static bool timer_expired_ns(QEMUTimer *timer_head, int64_t current_time) 95 { 96 return timer_head && (timer_head->expire_time <= current_time); 97 } 98 99 QEMUTimerList *timerlist_new(QEMUClockType type, 100 QEMUTimerListNotifyCB *cb, 101 void *opaque) 102 { 103 QEMUTimerList *timer_list; 104 QEMUClock *clock = qemu_clock_ptr(type); 105 106 timer_list = g_malloc0(sizeof(QEMUTimerList)); 107 qemu_event_init(&timer_list->timers_done_ev, false); 108 timer_list->clock = clock; 109 timer_list->notify_cb = cb; 110 timer_list->notify_opaque = opaque; 111 qemu_mutex_init(&timer_list->active_timers_lock); 112 QLIST_INSERT_HEAD(&clock->timerlists, timer_list, list); 113 return timer_list; 114 } 115 116 void timerlist_free(QEMUTimerList *timer_list) 117 { 118 assert(!timerlist_has_timers(timer_list)); 119 if (timer_list->clock) { 120 QLIST_REMOVE(timer_list, list); 121 } 122 qemu_mutex_destroy(&timer_list->active_timers_lock); 123 g_free(timer_list); 124 } 125 126 static void qemu_clock_init(QEMUClockType type) 127 { 128 QEMUClock *clock = qemu_clock_ptr(type); 129 130 clock->type = type; 131 clock->enabled = true; 132 clock->last = INT64_MIN; 133 QLIST_INIT(&clock->timerlists); 134 notifier_list_init(&clock->reset_notifiers); 135 main_loop_tlg.tl[type] = timerlist_new(type, NULL, NULL); 136 } 137 138 bool qemu_clock_use_for_deadline(QEMUClockType type) 139 { 140 return !(use_icount && (type == QEMU_CLOCK_VIRTUAL)); 141 } 142 143 void qemu_clock_notify(QEMUClockType type) 144 { 145 QEMUTimerList *timer_list; 146 QEMUClock *clock = qemu_clock_ptr(type); 147 QLIST_FOREACH(timer_list, &clock->timerlists, list) { 148 timerlist_notify(timer_list); 149 } 150 } 151 152 /* Disabling the clock will wait for related timerlists to stop 153 * executing qemu_run_timers. Thus, this functions should not 154 * be used from the callback of a timer that is based on @clock. 155 * Doing so would cause a deadlock. 156 * 157 * Caller should hold BQL. 158 */ 159 void qemu_clock_enable(QEMUClockType type, bool enabled) 160 { 161 QEMUClock *clock = qemu_clock_ptr(type); 162 QEMUTimerList *tl; 163 bool old = clock->enabled; 164 clock->enabled = enabled; 165 if (enabled && !old) { 166 qemu_clock_notify(type); 167 } else if (!enabled && old) { 168 QLIST_FOREACH(tl, &clock->timerlists, list) { 169 qemu_event_wait(&tl->timers_done_ev); 170 } 171 } 172 } 173 174 bool timerlist_has_timers(QEMUTimerList *timer_list) 175 { 176 return !!timer_list->active_timers; 177 } 178 179 bool qemu_clock_has_timers(QEMUClockType type) 180 { 181 return timerlist_has_timers( 182 main_loop_tlg.tl[type]); 183 } 184 185 bool timerlist_expired(QEMUTimerList *timer_list) 186 { 187 int64_t expire_time; 188 189 qemu_mutex_lock(&timer_list->active_timers_lock); 190 if (!timer_list->active_timers) { 191 qemu_mutex_unlock(&timer_list->active_timers_lock); 192 return false; 193 } 194 expire_time = timer_list->active_timers->expire_time; 195 qemu_mutex_unlock(&timer_list->active_timers_lock); 196 197 return expire_time < qemu_clock_get_ns(timer_list->clock->type); 198 } 199 200 bool qemu_clock_expired(QEMUClockType type) 201 { 202 return timerlist_expired( 203 main_loop_tlg.tl[type]); 204 } 205 206 /* 207 * As above, but return -1 for no deadline, and do not cap to 2^32 208 * as we know the result is always positive. 209 */ 210 211 int64_t timerlist_deadline_ns(QEMUTimerList *timer_list) 212 { 213 int64_t delta; 214 int64_t expire_time; 215 216 if (!timer_list->clock->enabled) { 217 return -1; 218 } 219 220 /* The active timers list may be modified before the caller uses our return 221 * value but ->notify_cb() is called when the deadline changes. Therefore 222 * the caller should notice the change and there is no race condition. 223 */ 224 qemu_mutex_lock(&timer_list->active_timers_lock); 225 if (!timer_list->active_timers) { 226 qemu_mutex_unlock(&timer_list->active_timers_lock); 227 return -1; 228 } 229 expire_time = timer_list->active_timers->expire_time; 230 qemu_mutex_unlock(&timer_list->active_timers_lock); 231 232 delta = expire_time - qemu_clock_get_ns(timer_list->clock->type); 233 234 if (delta <= 0) { 235 return 0; 236 } 237 238 return delta; 239 } 240 241 /* Calculate the soonest deadline across all timerlists attached 242 * to the clock. This is used for the icount timeout so we 243 * ignore whether or not the clock should be used in deadline 244 * calculations. 245 */ 246 int64_t qemu_clock_deadline_ns_all(QEMUClockType type) 247 { 248 int64_t deadline = -1; 249 QEMUTimerList *timer_list; 250 QEMUClock *clock = qemu_clock_ptr(type); 251 QLIST_FOREACH(timer_list, &clock->timerlists, list) { 252 deadline = qemu_soonest_timeout(deadline, 253 timerlist_deadline_ns(timer_list)); 254 } 255 return deadline; 256 } 257 258 QEMUClockType timerlist_get_clock(QEMUTimerList *timer_list) 259 { 260 return timer_list->clock->type; 261 } 262 263 QEMUTimerList *qemu_clock_get_main_loop_timerlist(QEMUClockType type) 264 { 265 return main_loop_tlg.tl[type]; 266 } 267 268 void timerlist_notify(QEMUTimerList *timer_list) 269 { 270 if (timer_list->notify_cb) { 271 timer_list->notify_cb(timer_list->notify_opaque); 272 } else { 273 qemu_notify_event(); 274 } 275 } 276 277 /* Transition function to convert a nanosecond timeout to ms 278 * This is used where a system does not support ppoll 279 */ 280 int qemu_timeout_ns_to_ms(int64_t ns) 281 { 282 int64_t ms; 283 if (ns < 0) { 284 return -1; 285 } 286 287 if (!ns) { 288 return 0; 289 } 290 291 /* Always round up, because it's better to wait too long than to wait too 292 * little and effectively busy-wait 293 */ 294 ms = (ns + SCALE_MS - 1) / SCALE_MS; 295 296 /* To avoid overflow problems, limit this to 2^31, i.e. approx 25 days */ 297 if (ms > (int64_t) INT32_MAX) { 298 ms = INT32_MAX; 299 } 300 301 return (int) ms; 302 } 303 304 #ifndef CONFIG_ANDROID // TODO(digit): Implement g_poll() 305 /* qemu implementation of g_poll which uses a nanosecond timeout but is 306 * otherwise identical to g_poll 307 */ 308 int qemu_poll_ns(GPollFD *fds, guint nfds, int64_t timeout) 309 { 310 #ifdef CONFIG_PPOLL 311 if (timeout < 0) { 312 return ppoll((struct pollfd *)fds, nfds, NULL, NULL); 313 } else { 314 struct timespec ts; 315 ts.tv_sec = timeout / 1000000000LL; 316 ts.tv_nsec = timeout % 1000000000LL; 317 return ppoll((struct pollfd *)fds, nfds, &ts, NULL); 318 } 319 #else 320 return g_poll(fds, nfds, qemu_timeout_ns_to_ms(timeout)); 321 #endif 322 } 323 #endif // !CONFIG_ANDROID 324 325 void timer_init(QEMUTimer *ts, 326 QEMUTimerList *timer_list, int scale, 327 QEMUTimerCB *cb, void *opaque) 328 { 329 ts->timer_list = timer_list; 330 ts->cb = cb; 331 ts->opaque = opaque; 332 ts->scale = scale; 333 ts->expire_time = -1; 334 } 335 336 void timer_free(QEMUTimer *ts) 337 { 338 g_free(ts); 339 } 340 341 static void timer_del_locked(QEMUTimerList *timer_list, QEMUTimer *ts) 342 { 343 QEMUTimer **pt, *t; 344 345 ts->expire_time = -1; 346 pt = &timer_list->active_timers; 347 for(;;) { 348 t = *pt; 349 if (!t) 350 break; 351 if (t == ts) { 352 *pt = t->next; 353 break; 354 } 355 pt = &t->next; 356 } 357 } 358 359 static bool timer_mod_ns_locked(QEMUTimerList *timer_list, 360 QEMUTimer *ts, int64_t expire_time) 361 { 362 QEMUTimer **pt, *t; 363 364 /* add the timer in the sorted list */ 365 pt = &timer_list->active_timers; 366 for (;;) { 367 t = *pt; 368 if (!timer_expired_ns(t, expire_time)) { 369 break; 370 } 371 pt = &t->next; 372 } 373 ts->expire_time = MAX(expire_time, 0); 374 ts->next = *pt; 375 *pt = ts; 376 377 return pt == &timer_list->active_timers; 378 } 379 380 static void timerlist_rearm(QEMUTimerList *timer_list) 381 { 382 /* Interrupt execution to force deadline recalculation. */ 383 qemu_clock_warp(timer_list->clock->type); 384 timerlist_notify(timer_list); 385 } 386 387 /* stop a timer, but do not dealloc it */ 388 void timer_del(QEMUTimer *ts) 389 { 390 QEMUTimerList *timer_list = ts->timer_list; 391 392 qemu_mutex_lock(&timer_list->active_timers_lock); 393 timer_del_locked(timer_list, ts); 394 qemu_mutex_unlock(&timer_list->active_timers_lock); 395 } 396 397 /* modify the current timer so that it will be fired when current_time 398 >= expire_time. The corresponding callback will be called. */ 399 void timer_mod_ns(QEMUTimer *ts, int64_t expire_time) 400 { 401 QEMUTimerList *timer_list = ts->timer_list; 402 bool rearm; 403 404 qemu_mutex_lock(&timer_list->active_timers_lock); 405 timer_del_locked(timer_list, ts); 406 rearm = timer_mod_ns_locked(timer_list, ts, expire_time); 407 qemu_mutex_unlock(&timer_list->active_timers_lock); 408 409 if (rearm) { 410 timerlist_rearm(timer_list); 411 } 412 } 413 414 /* modify the current timer so that it will be fired when current_time 415 >= expire_time or the current deadline, whichever comes earlier. 416 The corresponding callback will be called. */ 417 void timer_mod_anticipate_ns(QEMUTimer *ts, int64_t expire_time) 418 { 419 QEMUTimerList *timer_list = ts->timer_list; 420 bool rearm; 421 422 qemu_mutex_lock(&timer_list->active_timers_lock); 423 if (ts->expire_time == -1 || ts->expire_time > expire_time) { 424 if (ts->expire_time != -1) { 425 timer_del_locked(timer_list, ts); 426 } 427 rearm = timer_mod_ns_locked(timer_list, ts, expire_time); 428 } else { 429 rearm = false; 430 } 431 qemu_mutex_unlock(&timer_list->active_timers_lock); 432 433 if (rearm) { 434 timerlist_rearm(timer_list); 435 } 436 } 437 438 void timer_mod(QEMUTimer *ts, int64_t expire_time) 439 { 440 timer_mod_ns(ts, expire_time * ts->scale); 441 } 442 443 void timer_mod_anticipate(QEMUTimer *ts, int64_t expire_time) 444 { 445 timer_mod_anticipate_ns(ts, expire_time * ts->scale); 446 } 447 448 bool timer_pending(QEMUTimer *ts) 449 { 450 return ts->expire_time >= 0; 451 } 452 453 bool timer_expired(QEMUTimer *timer_head, int64_t current_time) 454 { 455 return timer_expired_ns(timer_head, current_time * timer_head->scale); 456 } 457 458 bool timerlist_run_timers(QEMUTimerList *timer_list) 459 { 460 QEMUTimer *ts; 461 int64_t current_time; 462 bool progress = false; 463 QEMUTimerCB *cb; 464 void *opaque; 465 466 qemu_event_reset(&timer_list->timers_done_ev); 467 if (!timer_list->clock->enabled) { 468 goto out; 469 } 470 471 current_time = qemu_clock_get_ns(timer_list->clock->type); 472 for(;;) { 473 qemu_mutex_lock(&timer_list->active_timers_lock); 474 ts = timer_list->active_timers; 475 if (!timer_expired_ns(ts, current_time)) { 476 qemu_mutex_unlock(&timer_list->active_timers_lock); 477 break; 478 } 479 480 /* remove timer from the list before calling the callback */ 481 timer_list->active_timers = ts->next; 482 ts->next = NULL; 483 ts->expire_time = -1; 484 cb = ts->cb; 485 opaque = ts->opaque; 486 qemu_mutex_unlock(&timer_list->active_timers_lock); 487 488 /* run the callback (the timer list can be modified) */ 489 cb(opaque); 490 progress = true; 491 } 492 493 out: 494 qemu_event_set(&timer_list->timers_done_ev); 495 return progress; 496 } 497 498 bool qemu_clock_run_timers(QEMUClockType type) 499 { 500 return timerlist_run_timers(main_loop_tlg.tl[type]); 501 } 502 503 void timerlistgroup_init(QEMUTimerListGroup *tlg, 504 QEMUTimerListNotifyCB *cb, void *opaque) 505 { 506 QEMUClockType type; 507 for (type = 0; type < QEMU_CLOCK_MAX; type++) { 508 tlg->tl[type] = timerlist_new(type, cb, opaque); 509 } 510 } 511 512 void timerlistgroup_deinit(QEMUTimerListGroup *tlg) 513 { 514 QEMUClockType type; 515 for (type = 0; type < QEMU_CLOCK_MAX; type++) { 516 timerlist_free(tlg->tl[type]); 517 } 518 } 519 520 bool timerlistgroup_run_timers(QEMUTimerListGroup *tlg) 521 { 522 QEMUClockType type; 523 bool progress = false; 524 for (type = 0; type < QEMU_CLOCK_MAX; type++) { 525 progress |= timerlist_run_timers(tlg->tl[type]); 526 } 527 return progress; 528 } 529 530 int64_t timerlistgroup_deadline_ns(QEMUTimerListGroup *tlg) 531 { 532 int64_t deadline = -1; 533 QEMUClockType type; 534 for (type = 0; type < QEMU_CLOCK_MAX; type++) { 535 if (qemu_clock_use_for_deadline(tlg->tl[type]->clock->type)) { 536 deadline = qemu_soonest_timeout(deadline, 537 timerlist_deadline_ns( 538 tlg->tl[type])); 539 } 540 } 541 return deadline; 542 } 543 544 int64_t qemu_clock_get_ns(QEMUClockType type) 545 { 546 int64_t now, last; 547 QEMUClock *clock = qemu_clock_ptr(type); 548 549 switch (type) { 550 case QEMU_CLOCK_REALTIME: 551 return get_clock(); 552 default: 553 case QEMU_CLOCK_VIRTUAL: 554 if (use_icount) { 555 return cpu_get_icount(); 556 } else { 557 return cpu_get_clock(); 558 } 559 case QEMU_CLOCK_HOST: 560 now = get_clock_realtime(); 561 last = clock->last; 562 clock->last = now; 563 if (now < last) { 564 notifier_list_notify(&clock->reset_notifiers, &now); 565 } 566 return now; 567 } 568 } 569 570 void qemu_clock_register_reset_notifier(QEMUClockType type, 571 Notifier *notifier) 572 { 573 QEMUClock *clock = qemu_clock_ptr(type); 574 notifier_list_add(&clock->reset_notifiers, notifier); 575 } 576 577 void qemu_clock_unregister_reset_notifier(QEMUClockType type, 578 Notifier *notifier) 579 { 580 notifier_remove(notifier); 581 } 582 583 void init_clocks(void) 584 { 585 QEMUClockType type; 586 for (type = 0; type < QEMU_CLOCK_MAX; type++) { 587 qemu_clock_init(type); 588 } 589 590 #ifdef CONFIG_PRCTL_PR_SET_TIMERSLACK 591 prctl(PR_SET_TIMERSLACK, 1, 0, 0, 0); 592 #endif 593 } 594 595 uint64_t timer_expire_time_ns(QEMUTimer *ts) 596 { 597 return timer_pending(ts) ? ts->expire_time : -1; 598 } 599 600 bool qemu_clock_run_all_timers(void) 601 { 602 bool progress = false; 603 QEMUClockType type; 604 605 for (type = 0; type < QEMU_CLOCK_MAX; type++) { 606 progress |= qemu_clock_run_timers(type); 607 } 608 609 return progress; 610 } 611