[Cbe-oss-dev] [PATCH 3/6] spufs: fix starvation case with terminated spes
Luke Browning
lukebr at linux.vnet.ibm.com
Thu Feb 7 04:43:33 EST 2008
Fix spu starvation case with terminated ctxts.
Terminated spe contexts need to yield the spu, so that the spufs scheduler
can service the runqueue. Can't rely on the libspe to destroy the context
as it is not a trusted entity. Fixes a testcase where a program creates
100 standalone contexts (ie. gang of one) and then waits for them to
complete before it starts to destroy contexts.
Moved spu_yield() into spu_run_fini() to avoid the extra lock reference.
Signed-off-by: Luke Browning <lukebrowning at us.ibm.com>
---
Index: spufs/arch/powerpc/platforms/cell/spufs/run.c
===================================================================
--- spufs.orig/arch/powerpc/platforms/cell/spufs/run.c 2008-02-06 12:46:01.000000000 -0200
+++ spufs/arch/powerpc/platforms/cell/spufs/run.c 2008-02-06 12:48:22.000000000 -0200
@@ -234,6 +234,9 @@
*npc = ctx->ops->npc_read(ctx);
spuctx_switch_state(ctx, SPU_UTIL_IDLE_LOADED);
+
+ __spu_yield(ctx);
+
spu_release(ctx);
if (signal_pending(current))
@@ -400,10 +403,8 @@
(ctx->state == SPU_STATE_RUNNABLE))
ctx->stats.libassist++;
-
spu_disable_spu(ctx);
ret = spu_run_fini(ctx, npc, &status);
- spu_yield(ctx);
if ((ret == 0) ||
((ret == -ERESTARTSYS) &&
Index: spufs/arch/powerpc/platforms/cell/spufs/sched.c
===================================================================
--- spufs.orig/arch/powerpc/platforms/cell/spufs/sched.c 2008-02-06 12:43:41.000000000 -0200
+++ spufs/arch/powerpc/platforms/cell/spufs/sched.c 2008-02-06 12:48:22.000000000 -0200
@@ -848,6 +848,20 @@
__spu_deactivate(ctx, 1, MAX_PRIO);
}
+void __spu_yield(struct spu_context *ctx)
+{
+ if (!(ctx->flags & SPU_CREATE_NOSCHED)) {
+ int force;
+ u32 status = ctx->ops->status_read(ctx);
+
+ if (status >> SPU_STOP_STATUS_SHIFT == 0x2000) /* PROGRAM END */
+ force = 1;
+ else
+ force = 0;
+ __spu_deactivate(ctx, force, MAX_PRIO);
+ }
+}
+
/**
* spu_yield - yield a physical spu if others are waiting
* @ctx: spu context to yield
@@ -858,11 +872,9 @@
*/
void spu_yield(struct spu_context *ctx)
{
- if (!(ctx->flags & SPU_CREATE_NOSCHED)) {
- mutex_lock(&ctx->state_mutex);
- __spu_deactivate(ctx, 0, MAX_PRIO);
- mutex_unlock(&ctx->state_mutex);
- }
+ mutex_lock(&ctx->state_mutex);
+ __spu_yield(ctx);
+ mutex_unlock(&ctx->state_mutex);
}
static noinline void spusched_tick(struct spu_context *ctx)
Index: spufs/arch/powerpc/platforms/cell/spufs/spufs.h
===================================================================
--- spufs.orig/arch/powerpc/platforms/cell/spufs/spufs.h 2008-02-06 12:43:41.000000000 -0200
+++ spufs/arch/powerpc/platforms/cell/spufs/spufs.h 2008-02-06 12:48:22.000000000 -0200
@@ -253,6 +253,7 @@
void spu_del_from_rq(struct spu_context *ctx);
int spu_activate(struct spu_context *ctx, unsigned long flags);
void spu_deactivate(struct spu_context *ctx);
+void __spu_yield(struct spu_context *ctx);
void spu_yield(struct spu_context *ctx);
void spu_switch_notify(struct spu *spu, struct spu_context *ctx);
void spu_set_timeslice(struct spu_context *ctx);
More information about the cbe-oss-dev
mailing list