Пример #1
0
/* afs_osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout and EINTR if signalled.
 */
int
afs_osi_TimedSleep(void *event, afs_int32 ams, int aintok)
{
    int code = 0;
    struct afs_event *evp;
    clock_t ticks;

    ticks = (ams * afs_hz) / 1000;
#if defined(AFS_SUN510_ENV)
    ticks = ticks + ddi_get_lbolt();
#else
    ticks = ticks + lbolt;
#endif

    evp = afs_getevent(event);

    AFS_ASSERT_GLOCK();
    if (aintok) {
	if (cv_timedwait_sig(&evp->cond, &afs_global_lock, ticks) == 0)
	    code = EINTR;
    } else {
	cv_timedwait(&evp->cond, &afs_global_lock, ticks);
    }

    relevent(evp);
    return code;
}
Пример #2
0
void
afs_osi_Sleep(void *event)
{
    struct afs_event *evp;
    int seq;

    evp = afs_getevent(event);
#ifdef AFS_DARWIN80_ENV
     AFS_ASSERT_GLOCK();
     AFS_GUNLOCK();
#endif
    seq = evp->seq;
    while (seq == evp->seq) {
#ifdef AFS_DARWIN80_ENV
	evp->owner = 0;
	msleep(event, evp->lck, PVFS, "afs_osi_Sleep", NULL);
	evp->owner = current_thread();
#else
	AFS_ASSERT_GLOCK();
	AFS_GUNLOCK();
	/* this is probably safe for all versions, but testing is hard */
	sleep(event, PVFS);
	AFS_GLOCK();
#endif
    }
    relevent(evp);
#ifdef AFS_DARWIN80_ENV
    AFS_GLOCK();
#endif
}
Пример #3
0
/* afs_osi_SleepSig
 *
 * Waits for an event to be notified, returning early if a signal
 * is received.  Returns EINTR if signaled, and 0 otherwise.
 */
int
afs_osi_SleepSig(void *event)
{
    struct afs_event *evp;
    int seq, retval;
    int code;

    evp = afs_getevent(event);
    if (!evp) {
	afs_addevent(event);
	evp = afs_getevent(event);
    }

    seq = evp->seq;
    retval = 0;

    AFS_GUNLOCK();
    code = wait_event_freezable(evp->cond, seq != evp->seq);
    AFS_GLOCK();

    if (code == -ERESTARTSYS)
	code = EINTR;
    else
	code = -code;

    relevent(evp);
    return code;
}
Пример #4
0
/* afs_osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout, EINTR if signalled, and EGAIN if it might
 * have raced.
 */
int
afs_osi_TimedSleep(void *event, afs_int32 ams, int aintok)
{
    int code = 0;
    long ticks = (ams * HZ / 1000) + 1;
    struct afs_event *evp;
    int seq;

    evp = afs_getevent(event);
    if (!evp) {
	afs_addevent(event);
	evp = afs_getevent(event);
    }

    seq = evp->seq;

    AFS_GUNLOCK();
    code = wait_event_freezable_timeout(evp->cond, evp->seq != seq, ticks);
    AFS_GLOCK();
    if (code == -ERESTARTSYS)
	code = EINTR;
    else
	code = -code;

    relevent(evp);

    return code;
}
Пример #5
0
/* afs_osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout, EINTR if signalled, and EGAIN if it might
 * have raced.
 */
int
afs_osi_TimedSleep(void *event, afs_int32 ams, int aintok)
{
    int code = 0;
    long ticks = (ams * HZ / 1000) + 1;
    struct afs_event *evp;
#ifdef DECLARE_WAITQUEUE
    DECLARE_WAITQUEUE(wait, current);
#else
    struct wait_queue wait = { current, NULL };
#endif

    evp = afs_getevent(event);
    if (!evp) {
	afs_addevent(event);
	evp = afs_getevent(event);
    }

    add_wait_queue(&evp->cond, &wait);
    set_current_state(TASK_INTERRUPTIBLE);
    /* always sleep TASK_INTERRUPTIBLE to keep load average
     * from artifically increasing. */
    AFS_GUNLOCK();

    if (aintok) {
	if (schedule_timeout(ticks))
	    code = EINTR;
    } else
	schedule_timeout(ticks);
#ifdef CONFIG_PM
    if (
#ifdef PF_FREEZE
	    current->flags & PF_FREEZE
#else
#if defined(STRUCT_TASK_STRUCT_HAS_TODO)
	    !current->todo
#else
#if defined(STRUCT_TASK_STRUCT_HAS_THREAD_INFO)
            test_ti_thread_flag(current->thread_info, TIF_FREEZE)
#else
            test_ti_thread_flag(task_thread_info(current), TIF_FREEZE)
#endif
#endif
#endif
	    )
#ifdef LINUX_REFRIGERATOR_TAKES_PF_FREEZE
	refrigerator(PF_FREEZE);
#else
	refrigerator();
#endif
#endif

    AFS_GLOCK();
    remove_wait_queue(&evp->cond, &wait);
    set_current_state(TASK_RUNNING);

    relevent(evp);

    return code;
}
Пример #6
0
/* afs_osi_SleepSig
 *
 * Waits for an event to be notified, returning early if a signal
 * is received.  Returns EINTR if signaled, and 0 otherwise.
 */
int
afs_osi_SleepSig(void *event)
{
    struct afs_event *evp;
    int seq, retval;
#ifdef DECLARE_WAITQUEUE
    DECLARE_WAITQUEUE(wait, current);
#else
    struct wait_queue wait = { current, NULL };
#endif

    evp = afs_getevent(event);
    if (!evp) {
	afs_addevent(event);
	evp = afs_getevent(event);
    }

    seq = evp->seq;
    retval = 0;

    add_wait_queue(&evp->cond, &wait);
    while (seq == evp->seq) {
	set_current_state(TASK_INTERRUPTIBLE);
	AFS_ASSERT_GLOCK();
	AFS_GUNLOCK();
	schedule();
#ifdef CONFIG_PM
	if (
#ifdef PF_FREEZE
	    current->flags & PF_FREEZE
#else
#if defined(STRUCT_TASK_STRUCT_HAS_TODO)
	    !current->todo
#else
#if defined(STRUCT_TASK_STRUCT_HAS_THREAD_INFO)
            test_ti_thread_flag(current->thread_info, TIF_FREEZE)
#else
            test_ti_thread_flag(task_thread_info(current), TIF_FREEZE)
#endif
#endif
#endif
	    )
#ifdef LINUX_REFRIGERATOR_TAKES_PF_FREEZE
	    refrigerator(PF_FREEZE);
#else
	    refrigerator();
#endif
#endif
	AFS_GLOCK();
	if (signal_pending(current)) {
	    retval = EINTR;
	    break;
	}
    }
    remove_wait_queue(&evp->cond, &wait);
    set_current_state(TASK_RUNNING);

    relevent(evp);
    return retval;
}
Пример #7
0
/* afs_osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout and EINTR if signalled.
 */
int
afs_osi_TimedSleep(void *event, afs_int32 ams, int aintok)
{
    int code = 0;
    struct afs_event *evp;
    int seq;
    int prio;
#ifdef AFS_DARWIN80_ENV
    struct timespec ts;
#else
    int ticks;
#endif



    evp = afs_getevent(event);
    seq = evp->seq;
    AFS_GUNLOCK();
#ifdef AFS_DARWIN80_ENV
    if (aintok)
        prio = PCATCH | PPAUSE;
    else
        prio = PVFS;
    ts.tv_sec = ams / 1000;
    ts.tv_nsec = (ams % 1000) * 1000000;
    evp->owner = 0;
    code = msleep(event, evp->lck, prio, "afs_osi_TimedSleep", &ts);
    evp->owner = current_thread();
#else
    ticks = (ams * afs_hz) / 1000;
    /* this is probably safe for all versions, but testing is hard. */
    /* using tsleep instead of assert_wait/thread_set_timer/thread_block
     * allows shutdown to work in 1.4 */
    /* lack of PCATCH does *not* prevent signal delivery, neither does 
     * a low priority. We would need to deal with ERESTART here if we 
     * wanted to mess with p->p_sigmask, and messing with p_sigignore is
     * not the way to go.... (someone correct me if I'm wrong)
     */
    if (aintok)
	prio = PCATCH | PPAUSE;
    else
	prio = PVFS;
    code = tsleep(event, prio, "afs_osi_TimedSleep", ticks);
    AFS_GLOCK();
#endif
    if (seq == evp->seq)
	code = EINTR;

    relevent(evp);
#ifdef AFS_DARWIN80_ENV
    AFS_GLOCK();
#endif
    return code;
}
Пример #8
0
void
afs_osi_Sleep(void *event)
{
    struct afs_event *evp;
    int seq;

    evp = afs_getevent(event);
    seq = evp->seq;
    while (seq == evp->seq) {
	AFS_ASSERT_GLOCK();
	cv_wait(&evp->cond, &afs_global_lock);
    }
    relevent(evp);
}
Пример #9
0
int
afs_osi_Wakeup(void *event)
{
    int ret = 1;
    struct afs_event *evp;

    evp = afs_getevent(event);
    if (evp->refcount > 1) {
	evp->seq++;
	thread_wakeup((vm_offset_t) (&evp->cond));
	ret = 0;
    }
    relevent(evp);
    return ret;
}
Пример #10
0
int
afs_osi_Wakeup(void *event)
{
    int ret = 1;
    struct afs_event *evp;

    evp = afs_getevent(event);
    if (evp->refcount > 1) {
	evp->seq++;
	e_wakeup(&evp->cond);
	ret = 0;
    }
    relevent(evp);
    return ret;
}
Пример #11
0
int
afs_osi_Wakeup(void *event)
{
    struct afs_event *evp;
    int ret = 1;

    evp = afs_getevent(event);
    if (evp->refcount > 1) {
	evp->seq++;
	/* this is probably safe for all versions, but testing is hard. */
	wakeup(event);
	ret = 0;
    }
    relevent(evp);
    return ret;
}
Пример #12
0
void
afs_osi_Sleep(void *event)
{
    struct afs_event *evp;
    int seq;

    evp = afs_getevent(event);
    seq = evp->seq;
    while (seq == evp->seq) {
	AFS_ASSERT_GLOCK();
	e_assert_wait(&evp->cond, 0);
	AFS_GUNLOCK();
	e_block_thread();
	AFS_GLOCK();
    }
    relevent(evp);
}
Пример #13
0
void
afs_osi_Sleep(void *event)
{
    struct afs_event *evp;
    int seq;

    evp = afs_getevent(event);
    seq = evp->seq;
    while (seq == evp->seq) {
	AFS_ASSERT_GLOCK();
	assert_wait((vm_offset_t) (&evp->cond), 0);
	AFS_GUNLOCK();
	thread_block();
	AFS_GLOCK();
    }
    relevent(evp);
}
Пример #14
0
int
afs_osi_Wakeup(void *event)
{
    int ret = 2;
    struct afs_event *evp;

    evp = afs_getevent(event);
    if (!evp)			/* No sleepers */
	return 1;

    if (evp->refcount > 1) {
	evp->seq++;
	wake_up(&evp->cond);
	ret = 0;
    }
    relevent(evp);
    return ret;
}
Пример #15
0
int
afs_osi_SleepSig(void *event)
{
    struct afs_event *evp;
    int seq, code = 0;

    evp = afs_getevent(event);
    seq = evp->seq;
    while (seq == evp->seq) {
	AFS_ASSERT_GLOCK();
	if (cv_wait_sig(&evp->cond, &afs_global_lock) == 0) {
	    code = EINTR;
	    break;
	}
    }
    relevent(evp);
    return code;
}
Пример #16
0
/* afs_osi_SleepSig
 *
 * Waits for an event to be notified, returning early if a signal
 * is received.  Returns EINTR if signaled, and 0 otherwise.
 */
int
afs_osi_SleepSig(void *event)
{
    struct afs_event *evp;
    int seq, retval;
#ifdef DECLARE_WAITQUEUE
    DECLARE_WAITQUEUE(wait, current);
#else
    struct wait_queue wait = { current, NULL };
#endif

    evp = afs_getevent(event);
    if (!evp) {
	afs_addevent(event);
	evp = afs_getevent(event);
    }

    seq = evp->seq;
    retval = 0;

    add_wait_queue(&evp->cond, &wait);
    while (seq == evp->seq) {
	set_current_state(TASK_INTERRUPTIBLE);
	AFS_ASSERT_GLOCK();
	AFS_GUNLOCK();
	schedule();
	try_to_freeze();

	AFS_GLOCK();
	if (signal_pending(current)) {
	    retval = EINTR;
	    break;
	}
    }
    remove_wait_queue(&evp->cond, &wait);
    set_current_state(TASK_RUNNING);

    relevent(evp);
    return retval;
}
Пример #17
0
/* afs_osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout, EINTR if signalled, and EGAIN if it might
 * have raced.
 */
int
afs_osi_TimedSleep(void *event, afs_int32 ams, int aintok)
{
    int code = 0;
    long ticks = (ams * HZ / 1000) + 1;
    struct afs_event *evp;
#ifdef DECLARE_WAITQUEUE
    DECLARE_WAITQUEUE(wait, current);
#else
    struct wait_queue wait = { current, NULL };
#endif

    evp = afs_getevent(event);
    if (!evp) {
	afs_addevent(event);
	evp = afs_getevent(event);
    }

    add_wait_queue(&evp->cond, &wait);
    set_current_state(TASK_INTERRUPTIBLE);
    /* always sleep TASK_INTERRUPTIBLE to keep load average
     * from artifically increasing. */
    AFS_GUNLOCK();

    if (schedule_timeout(ticks)) {
	if (aintok)
	    code = EINTR;
    }

    try_to_freeze();

    AFS_GLOCK();
    remove_wait_queue(&evp->cond, &wait);
    set_current_state(TASK_RUNNING);

    relevent(evp);

    return code;
}
Пример #18
0
/* afs_osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout and EINTR if signalled.
 */
int
afs_osi_TimedSleep(void *event, afs_int32 ams, int aintok)
{
    int code = 0;
    struct afs_event *evp;
    struct timestruc_t ticks;
    struct trb *trb;
    int rc;

    ticks.tv_sec = ams / 1000;
    ticks.tv_nsec = (ams - (ticks.tv_sec * 1000)) * 1000000;


    evp = afs_getevent(event);

    trb = talloc();
    if (trb == NULL)
	osi_Panic("talloc returned NULL");
    trb->flags = 0;
    trb->func = AfsWaitHack;
    trb->eventlist = EVENT_NULL;
    trb->ipri = INTTIMER;
    trb->func_data = thread_self();
    trb->timeout.it_value = ticks;

    e_assert_wait(&evp->cond, aintok);
    AFS_GUNLOCK();
    tstart(trb);
    rc = e_block_thread();
    while (tstop(trb));
    if (rc == THREAD_INTERRUPTED)
	code = EINTR;
    tfree(trb);
    AFS_GLOCK();

    relevent(evp);
    return code;
}
Пример #19
0
/* osi_TimedSleep
 * 
 * Arguments:
 * event - event to sleep on
 * ams --- max sleep time in milliseconds
 * aintok - 1 if should sleep interruptibly
 *
 * Returns 0 if timeout and EINTR if signalled.
 */
static int
osi_TimedSleep(char *event, afs_int32 ams, int aintok)
{
    int code = 0;
    struct afs_event *evp;
    int ticks;

    ticks = (ams * afs_hz) / 1000;


    evp = afs_getevent(event);

    assert_wait((vm_offset_t) (&evp->cond), aintok);
    AFS_GUNLOCK();
    thread_set_timeout(ticks);
    thread_block();
    AFS_GLOCK();
    /*    if (current_thread()->wait_result != THREAD_AWAKENED)
     * code = EINTR; */

    relevent(evp);
    return code;
}