d38598568c6e70e0644317f24dc89e1221218524vboxsync/* $Id$ */
d38598568c6e70e0644317f24dc89e1221218524vboxsync/** @file
d38598568c6e70e0644317f24dc89e1221218524vboxsync * IPRT - Linux Ring-0 Driver Helpers for Abstracting Wait Queues,
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/*
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Copyright (C) 2006-2010 Oracle Corporation
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
d38598568c6e70e0644317f24dc89e1221218524vboxsync * available from http://www.virtualbox.org. This file is free software;
d38598568c6e70e0644317f24dc89e1221218524vboxsync * you can redistribute it and/or modify it under the terms of the GNU
d38598568c6e70e0644317f24dc89e1221218524vboxsync * General Public License (GPL) as published by the Free Software
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * The contents of this file may alternatively be used under the terms
d38598568c6e70e0644317f24dc89e1221218524vboxsync * of the Common Development and Distribution License Version 1.0
d38598568c6e70e0644317f24dc89e1221218524vboxsync * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * VirtualBox OSE distribution, in which case the provisions of the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * CDDL are applicable instead of those of the GPL.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * You may elect to license modified versions of this file under the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * terms and conditions of either the GPL or the CDDL or both.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync#ifndef ___r0drv_linux_waitqueue_r0drv_linux_h
d38598568c6e70e0644317f24dc89e1221218524vboxsync#define ___r0drv_linux_waitqueue_r0drv_linux_h
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync#include "the-linux-kernel.h"
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync#include <iprt/asm-math.h>
d38598568c6e70e0644317f24dc89e1221218524vboxsync#include <iprt/err.h>
a7cf0b2d7ef1bf4fd75f3e50230752d0326bd324vboxsync#include <iprt/string.h>
d38598568c6e70e0644317f24dc89e1221218524vboxsync#include <iprt/time.h>
d38598568c6e70e0644317f24dc89e1221218524vboxsync
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync/** The resolution (nanoseconds) specified when using
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync * schedule_hrtimeout_range. */
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync#define RTR0SEMLNXWAIT_RESOLUTION 50000
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Kernel mode Linux wait state structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsynctypedef struct RTR0SEMLNXWAIT
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** The wait queue entry. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync wait_queue_t WaitQE;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** The absolute timeout given as nano seconds since the start of the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * monotonic clock. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync uint64_t uNsAbsTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** The timeout in nano seconds relative to the start of the wait. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync uint64_t cNsRelTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** The native timeout value. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync union
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync#ifdef IPRT_LINUX_HAS_HRTIMER
ad27e1d5e48ca41245120c331cc88b50464813cevboxsync /** The timeout when fHighRes is true. Absolute, so no updating. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync ktime_t KtTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync#endif
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** The timeout when fHighRes is false. Updated after waiting. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync long lTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync } u;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** Set if we use high resolution timeouts. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync bool fHighRes;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** Set if it's an indefinite wait. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync bool fIndefinite;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** Set if we've already timed out.
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Set by rtR0SemLnxWaitDoIt and read by rtR0SemLnxWaitHasTimedOut. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync bool fTimedOut;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** TASK_INTERRUPTIBLE or TASK_UNINTERRUPTIBLE. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync int iWaitState;
d38598568c6e70e0644317f24dc89e1221218524vboxsync /** The wait queue. */
d38598568c6e70e0644317f24dc89e1221218524vboxsync wait_queue_head_t *pWaitQueue;
d38598568c6e70e0644317f24dc89e1221218524vboxsync} RTR0SEMLNXWAIT;
d38598568c6e70e0644317f24dc89e1221218524vboxsync/** Pointer to a linux wait state. */
d38598568c6e70e0644317f24dc89e1221218524vboxsynctypedef RTR0SEMLNXWAIT *PRTR0SEMLNXWAIT;
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Initializes a wait.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * The caller MUST check the wait condition BEFORE calling this function or the
d38598568c6e70e0644317f24dc89e1221218524vboxsync * timeout logic will be flawed.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @returns VINF_SUCCESS or VERR_TIMEOUT.
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWait The wait structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param fFlags The wait flags.
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param uTimeout The timeout.
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWaitQueue The wait queue head.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsyncDECLINLINE(int) rtR0SemLnxWaitInit(PRTR0SEMLNXWAIT pWait, uint32_t fFlags, uint64_t uTimeout,
d38598568c6e70e0644317f24dc89e1221218524vboxsync wait_queue_head_t *pWaitQueue)
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync /*
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Process the flags and timeout.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (!(fFlags & RTSEMWAIT_FLAGS_INDEFINITE))
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync/** @todo optimize: millisecs -> nanosecs -> millisec -> jiffies */
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (fFlags & RTSEMWAIT_FLAGS_MILLISECS)
446339370a612cb2cf7d523122584ac05b59b0devboxsync uTimeout = uTimeout < UINT64_MAX / RT_US_1SEC * RT_US_1SEC
446339370a612cb2cf7d523122584ac05b59b0devboxsync ? uTimeout * RT_US_1SEC
d38598568c6e70e0644317f24dc89e1221218524vboxsync : UINT64_MAX;
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (uTimeout == UINT64_MAX)
d38598568c6e70e0644317f24dc89e1221218524vboxsync fFlags |= RTSEMWAIT_FLAGS_INDEFINITE;
d38598568c6e70e0644317f24dc89e1221218524vboxsync else
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync uint64_t u64Now;
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (fFlags & RTSEMWAIT_FLAGS_RELATIVE)
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (uTimeout == 0)
d38598568c6e70e0644317f24dc89e1221218524vboxsync return VERR_TIMEOUT;
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync u64Now = RTTimeSystemNanoTS();
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->cNsRelTimeout = uTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->uNsAbsTimeout = u64Now + uTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (pWait->uNsAbsTimeout < u64Now) /* overflow */
d38598568c6e70e0644317f24dc89e1221218524vboxsync fFlags |= RTSEMWAIT_FLAGS_INDEFINITE;
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync else
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync u64Now = RTTimeSystemNanoTS();
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (u64Now >= uTimeout)
d38598568c6e70e0644317f24dc89e1221218524vboxsync return VERR_TIMEOUT;
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->cNsRelTimeout = uTimeout - u64Now;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->uNsAbsTimeout = uTimeout;
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (!(fFlags & RTSEMWAIT_FLAGS_INDEFINITE))
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fIndefinite = false;
d38598568c6e70e0644317f24dc89e1221218524vboxsync#ifdef IPRT_LINUX_HAS_HRTIMER
d38598568c6e70e0644317f24dc89e1221218524vboxsync if ( (fFlags & (RTSEMWAIT_FLAGS_NANOSECS | RTSEMWAIT_FLAGS_ABSOLUTE))
446339370a612cb2cf7d523122584ac05b59b0devboxsync || pWait->cNsRelTimeout < RT_NS_1SEC / HZ * 4)
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fHighRes = true;
d38598568c6e70e0644317f24dc89e1221218524vboxsync# if BITS_PER_LONG < 64
d38598568c6e70e0644317f24dc89e1221218524vboxsync if ( KTIME_SEC_MAX <= LONG_MAX
446339370a612cb2cf7d523122584ac05b59b0devboxsync && pWait->uNsAbsTimeout >= KTIME_SEC_MAX * RT_NS_1SEC_64 + (RT_NS_1SEC - 1))
d38598568c6e70e0644317f24dc89e1221218524vboxsync fFlags |= RTSEMWAIT_FLAGS_INDEFINITE;
d38598568c6e70e0644317f24dc89e1221218524vboxsync else
d38598568c6e70e0644317f24dc89e1221218524vboxsync# endif
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->u.KtTimeout = ns_to_ktime(pWait->uNsAbsTimeout);
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync else
d38598568c6e70e0644317f24dc89e1221218524vboxsync#endif
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
446339370a612cb2cf7d523122584ac05b59b0devboxsync uint64_t cJiffies = ASMMultU64ByU32DivByU32(pWait->cNsRelTimeout, HZ, RT_NS_1SEC);
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (cJiffies >= MAX_JIFFY_OFFSET)
d38598568c6e70e0644317f24dc89e1221218524vboxsync fFlags |= RTSEMWAIT_FLAGS_INDEFINITE;
d38598568c6e70e0644317f24dc89e1221218524vboxsync else
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->u.lTimeout = (long)cJiffies;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fHighRes = false;
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (fFlags & RTSEMWAIT_FLAGS_INDEFINITE)
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fIndefinite = true;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fHighRes = false;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->uNsAbsTimeout = UINT64_MAX;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->cNsRelTimeout = UINT64_MAX;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->u.lTimeout = LONG_MAX;
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fTimedOut = false;
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync /*
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Initialize the wait queue related bits.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
9240b1b3e2c579905429014c7a77b09371c535a5vboxsync#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 39)
27a426b028cd468fd20f97dc24798e71350edc0fvboxsync init_wait((&pWait->WaitQE));
9240b1b3e2c579905429014c7a77b09371c535a5vboxsync#else
9240b1b3e2c579905429014c7a77b09371c535a5vboxsync RT_ZERO(pWait->WaitQE);
9240b1b3e2c579905429014c7a77b09371c535a5vboxsync init_waitqueue_entry((&pWait->WaitQE), current);
9240b1b3e2c579905429014c7a77b09371c535a5vboxsync#endif
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->pWaitQueue = pWaitQueue;
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->iWaitState = fFlags & RTSEMWAIT_FLAGS_INTERRUPTIBLE
d38598568c6e70e0644317f24dc89e1221218524vboxsync ? TASK_INTERRUPTIBLE : TASK_UNINTERRUPTIBLE;
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync return VINF_SUCCESS;
d38598568c6e70e0644317f24dc89e1221218524vboxsync}
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Prepares the next wait.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * This must be called before rtR0SemLnxWaitDoIt, and the caller should check
ad27e1d5e48ca41245120c331cc88b50464813cevboxsync * the exit conditions in-between the two calls.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWait The wait structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsyncDECLINLINE(void) rtR0SemLnxWaitPrepare(PRTR0SEMLNXWAIT pWait)
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync /* Make everything thru schedule*() atomic scheduling wise. (Is this correct?) */
d38598568c6e70e0644317f24dc89e1221218524vboxsync prepare_to_wait(pWait->pWaitQueue, &pWait->WaitQE, pWait->iWaitState);
d38598568c6e70e0644317f24dc89e1221218524vboxsync}
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Do the actual wait.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWait The wait structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsyncDECLINLINE(void) rtR0SemLnxWaitDoIt(PRTR0SEMLNXWAIT pWait)
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (pWait->fIndefinite)
d38598568c6e70e0644317f24dc89e1221218524vboxsync schedule();
d38598568c6e70e0644317f24dc89e1221218524vboxsync#ifdef IPRT_LINUX_HAS_HRTIMER
d38598568c6e70e0644317f24dc89e1221218524vboxsync else if (pWait->fHighRes)
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync int rc = schedule_hrtimeout_range(&pWait->u.KtTimeout, HRTIMER_MODE_ABS, RTR0SEMLNXWAIT_RESOLUTION);
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (!rc)
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fTimedOut = true;
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d38598568c6e70e0644317f24dc89e1221218524vboxsync#endif
d38598568c6e70e0644317f24dc89e1221218524vboxsync else
d38598568c6e70e0644317f24dc89e1221218524vboxsync {
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->u.lTimeout = schedule_timeout(pWait->u.lTimeout);
d38598568c6e70e0644317f24dc89e1221218524vboxsync if (pWait->u.lTimeout <= 0)
d38598568c6e70e0644317f24dc89e1221218524vboxsync pWait->fTimedOut = true;
d38598568c6e70e0644317f24dc89e1221218524vboxsync }
d3a63bcf2ba3480f1621e7dd45a087e1815529d3vboxsync after_wait((&pWait->WaitQE));
d38598568c6e70e0644317f24dc89e1221218524vboxsync}
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Checks if a linux wait was interrupted.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @returns true / false
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWait The wait structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @remarks This shall be called before the first rtR0SemLnxWaitDoIt().
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsyncDECLINLINE(bool) rtR0SemLnxWaitWasInterrupted(PRTR0SEMLNXWAIT pWait)
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync return pWait->iWaitState == TASK_INTERRUPTIBLE
d38598568c6e70e0644317f24dc89e1221218524vboxsync && signal_pending(current);
d38598568c6e70e0644317f24dc89e1221218524vboxsync}
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Checks if a linux wait has timed out.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @returns true / false
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWait The wait structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsyncDECLINLINE(bool) rtR0SemLnxWaitHasTimedOut(PRTR0SEMLNXWAIT pWait)
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync return pWait->fTimedOut;
d38598568c6e70e0644317f24dc89e1221218524vboxsync}
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync/**
d38598568c6e70e0644317f24dc89e1221218524vboxsync * Deletes a linux wait.
d38598568c6e70e0644317f24dc89e1221218524vboxsync *
d38598568c6e70e0644317f24dc89e1221218524vboxsync * @param pWait The wait structure.
d38598568c6e70e0644317f24dc89e1221218524vboxsync */
d38598568c6e70e0644317f24dc89e1221218524vboxsyncDECLINLINE(void) rtR0SemLnxWaitDelete(PRTR0SEMLNXWAIT pWait)
d38598568c6e70e0644317f24dc89e1221218524vboxsync{
d38598568c6e70e0644317f24dc89e1221218524vboxsync finish_wait(pWait->pWaitQueue, &pWait->WaitQE);
d38598568c6e70e0644317f24dc89e1221218524vboxsync}
d38598568c6e70e0644317f24dc89e1221218524vboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync/**
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync * Gets the max resolution of the timeout machinery.
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync *
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync * @returns Resolution specified in nanoseconds.
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync */
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsyncDECLINLINE(uint32_t) rtR0SemLnxWaitGetResolution(void)
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync{
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync#ifdef IPRT_LINUX_HAS_HRTIMER
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync return RTR0SEMLNXWAIT_RESOLUTION;
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync#else
446339370a612cb2cf7d523122584ac05b59b0devboxsync return RT_NS_1SEC / HZ; /* ns */
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync#endif
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync}
e0e7da0420be1398d23ffa9953686d3a43619abdvboxsync
d38598568c6e70e0644317f24dc89e1221218524vboxsync#endif
d38598568c6e70e0644317f24dc89e1221218524vboxsync