@ -245,6 +245,14 @@ static void spu_add_to_rq(struct spu_context *ctx)
spin_unlock ( & spu_prio - > runq_lock ) ;
}
static void __spu_del_from_rq ( struct spu_context * ctx , int prio )
{
if ( ! list_empty ( & ctx - > rq ) )
list_del_init ( & ctx - > rq ) ;
if ( list_empty ( & spu_prio - > runq [ prio ] ) )
clear_bit ( ctx - > prio , spu_prio - > bitmap ) ;
}
/**
* spu_del_from_rq - remove a context from the runqueue
* @ ctx : context to remove
@ -252,33 +260,10 @@ static void spu_add_to_rq(struct spu_context *ctx)
static void spu_del_from_rq ( struct spu_context * ctx )
{
spin_lock ( & spu_prio - > runq_lock ) ;
list_del_init ( & ctx - > rq ) ;
if ( list_empty ( & spu_prio - > runq [ ctx - > prio ] ) )
clear_bit ( ctx - > prio , spu_prio - > bitmap ) ;
__spu_del_from_rq ( ctx , ctx - > prio ) ;
spin_unlock ( & spu_prio - > runq_lock ) ;
}
/**
* spu_grab_context - remove one context from the runqueue
* @ prio : priority of the context to be removed
*
* This function removes one context from the runqueue for priority @ prio .
* If there is more than one context with the given priority the first
* task on the runqueue will be taken .
*
* Returns the spu_context it just removed .
*
* Must be called with spu_prio - > runq_lock held .
*/
static struct spu_context * spu_grab_context ( int prio )
{
struct list_head * rq = & spu_prio - > runq [ prio ] ;
if ( list_empty ( rq ) )
return NULL ;
return list_entry ( rq - > next , struct spu_context , rq ) ;
}
static void spu_prio_wait ( struct spu_context * ctx )
{
DEFINE_WAIT ( wait ) ;
@ -309,9 +294,14 @@ static void spu_reschedule(struct spu *spu)
spin_lock ( & spu_prio - > runq_lock ) ;
best = sched_find_first_bit ( spu_prio - > bitmap ) ;
if ( best < MAX_PRIO ) {
struct spu_context * ctx = spu_grab_context ( best ) ;
if ( ctx )
wake_up ( & ctx - > stop_wq ) ;
struct list_head * rq = & spu_prio - > runq [ best ] ;
struct spu_context * ctx ;
BUG_ON ( list_empty ( rq ) ) ;
ctx = list_entry ( rq - > next , struct spu_context , rq ) ;
__spu_del_from_rq ( ctx , best ) ;
wake_up ( & ctx - > stop_wq ) ;
}
spin_unlock ( & spu_prio - > runq_lock ) ;
}