Home | History | Annotate | Line # | Download | only in rumpkern
ltsleep.c revision 1.3.10.2
      1  1.3.10.1  bouyer /*	$NetBSD: ltsleep.c,v 1.3.10.2 2008/01/08 22:11:53 bouyer Exp $	*/
      2       1.1   pooka 
      3       1.1   pooka /*
      4       1.1   pooka  * Copyright (c) 2007 Antti Kantee.  All Rights Reserved.
      5       1.1   pooka  *
      6       1.1   pooka  * Development of this software was supported by the
      7       1.1   pooka  * Finnish Cultural Foundation.
      8       1.1   pooka  *
      9       1.1   pooka  * Redistribution and use in source and binary forms, with or without
     10       1.1   pooka  * modification, are permitted provided that the following conditions
     11       1.1   pooka  * are met:
     12       1.1   pooka  * 1. Redistributions of source code must retain the above copyright
     13       1.1   pooka  *    notice, this list of conditions and the following disclaimer.
     14       1.1   pooka  * 2. Redistributions in binary form must reproduce the above copyright
     15       1.1   pooka  *    notice, this list of conditions and the following disclaimer in the
     16       1.1   pooka  *    documentation and/or other materials provided with the distribution.
     17       1.1   pooka  *
     18       1.1   pooka  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
     19       1.1   pooka  * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     20       1.1   pooka  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
     21       1.1   pooka  * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
     22       1.1   pooka  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     23       1.1   pooka  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
     24       1.1   pooka  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     25       1.1   pooka  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
     26       1.1   pooka  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
     27       1.1   pooka  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
     28       1.1   pooka  * SUCH DAMAGE.
     29       1.1   pooka  */
     30       1.1   pooka 
     31       1.1   pooka #include <sys/param.h>
     32       1.1   pooka #include <sys/proc.h>
     33       1.1   pooka #include <sys/queue.h>
     34  1.3.10.2  bouyer #include <sys/simplelock.h>
     35       1.1   pooka 
     36       1.1   pooka #include "rump_private.h"
     37       1.3   pooka #include "rumpuser.h"
     38       1.1   pooka 
     39       1.1   pooka struct ltsleeper {
     40       1.1   pooka 	wchan_t id;
     41       1.1   pooka 	kcondvar_t cv;
     42       1.1   pooka 	LIST_ENTRY(ltsleeper) entries;
     43       1.1   pooka };
     44       1.1   pooka 
     45       1.1   pooka static LIST_HEAD(, ltsleeper) sleepers = LIST_HEAD_INITIALIZER(sleepers);
     46       1.1   pooka static kmutex_t sleepermtx;
     47       1.1   pooka 
     48       1.1   pooka int
     49       1.1   pooka ltsleep(wchan_t ident, pri_t prio, const char *wmesg, int timo,
     50       1.1   pooka 	volatile struct simplelock *slock)
     51       1.1   pooka {
     52       1.1   pooka 	struct ltsleeper lts;
     53       1.3   pooka 	int iplrecurse;
     54       1.1   pooka 
     55       1.1   pooka 	lts.id = ident;
     56       1.1   pooka 	cv_init(&lts.cv, NULL);
     57       1.1   pooka 
     58       1.1   pooka 	mutex_enter(&sleepermtx);
     59       1.1   pooka 	LIST_INSERT_HEAD(&sleepers, &lts, entries);
     60       1.3   pooka 
     61       1.3   pooka 	/* release spl */
     62       1.3   pooka 	iplrecurse = rumpuser_whatis_ipl();
     63       1.3   pooka 	while (iplrecurse--)
     64       1.3   pooka 		rumpuser_rw_exit(&rumpspl);
     65       1.3   pooka 
     66       1.2   pooka 	/* protected by sleepermtx */
     67       1.1   pooka 	if (slock)
     68       1.1   pooka 		simple_unlock(slock);
     69       1.1   pooka 	cv_wait(&lts.cv, &sleepermtx);
     70       1.3   pooka 
     71       1.3   pooka 	/* retake ipl */
     72       1.3   pooka 	iplrecurse = rumpuser_whatis_ipl();
     73       1.3   pooka 	while (iplrecurse--)
     74       1.3   pooka 		rumpuser_rw_enter(&rumpspl, 0);
     75       1.3   pooka 
     76       1.1   pooka 	LIST_REMOVE(&lts, entries);
     77       1.1   pooka 	mutex_exit(&sleepermtx);
     78       1.1   pooka 
     79       1.2   pooka 	cv_destroy(&lts.cv);
     80       1.2   pooka 
     81       1.1   pooka 	if (slock && (prio & PNORELOCK) == 0)
     82       1.1   pooka 		simple_lock(slock);
     83       1.1   pooka 
     84       1.1   pooka 	return 0;
     85       1.1   pooka }
     86       1.1   pooka 
     87  1.3.10.1  bouyer int
     88  1.3.10.1  bouyer mtsleep(wchan_t ident, pri_t prio, const char *wmesg, int timo,
     89  1.3.10.1  bouyer 	kmutex_t *lock)
     90  1.3.10.1  bouyer {
     91  1.3.10.1  bouyer 	struct ltsleeper lts;
     92  1.3.10.1  bouyer 	int iplrecurse;
     93  1.3.10.1  bouyer 
     94  1.3.10.1  bouyer 	lts.id = ident;
     95  1.3.10.1  bouyer 	cv_init(&lts.cv, NULL);
     96  1.3.10.1  bouyer 
     97  1.3.10.1  bouyer 	mutex_enter(&sleepermtx);
     98  1.3.10.1  bouyer 	LIST_INSERT_HEAD(&sleepers, &lts, entries);
     99  1.3.10.1  bouyer 
    100  1.3.10.1  bouyer 	/* release spl */
    101  1.3.10.1  bouyer 	iplrecurse = rumpuser_whatis_ipl();
    102  1.3.10.1  bouyer 	while (iplrecurse--)
    103  1.3.10.1  bouyer 		rumpuser_rw_exit(&rumpspl);
    104  1.3.10.1  bouyer 
    105  1.3.10.1  bouyer 	/* protected by sleepermtx */
    106  1.3.10.1  bouyer 	mutex_exit(lock);
    107  1.3.10.1  bouyer 	cv_wait(&lts.cv, &sleepermtx);
    108  1.3.10.1  bouyer 
    109  1.3.10.1  bouyer 	/* retake ipl */
    110  1.3.10.1  bouyer 	iplrecurse = rumpuser_whatis_ipl();
    111  1.3.10.1  bouyer 	while (iplrecurse--)
    112  1.3.10.1  bouyer 		rumpuser_rw_enter(&rumpspl, 0);
    113  1.3.10.1  bouyer 
    114  1.3.10.1  bouyer 	LIST_REMOVE(&lts, entries);
    115  1.3.10.1  bouyer 	mutex_exit(&sleepermtx);
    116  1.3.10.1  bouyer 
    117  1.3.10.1  bouyer 	cv_destroy(&lts.cv);
    118  1.3.10.1  bouyer 
    119  1.3.10.1  bouyer 	if ((prio & PNORELOCK) == 0)
    120  1.3.10.1  bouyer 		mutex_enter(lock);
    121  1.3.10.1  bouyer 
    122  1.3.10.1  bouyer 	return 0;
    123  1.3.10.1  bouyer }
    124  1.3.10.1  bouyer 
    125       1.1   pooka void
    126       1.1   pooka wakeup(wchan_t ident)
    127       1.1   pooka {
    128       1.1   pooka 	struct ltsleeper *ltsp;
    129       1.1   pooka 
    130       1.1   pooka 	mutex_enter(&sleepermtx);
    131       1.1   pooka 	LIST_FOREACH(ltsp, &sleepers, entries)
    132       1.1   pooka 		if (ltsp->id == ident)
    133       1.1   pooka 			cv_signal(&ltsp->cv);
    134       1.1   pooka 	mutex_exit(&sleepermtx);
    135       1.1   pooka }
    136       1.1   pooka 
    137       1.1   pooka void
    138       1.1   pooka rump_sleepers_init()
    139       1.1   pooka {
    140       1.1   pooka 
    141       1.1   pooka 	mutex_init(&sleepermtx, MUTEX_DEFAULT, 0);
    142       1.1   pooka }
    143