powerpc/spufs: wait for stable spu status in spu_stopped()
authorLuke Browning <lukebrowning@us.ibm.com>
Thu, 29 May 2008 20:46:10 +0000 (17:46 -0300)
committerJeremy Kerr <jk@ozlabs.org>
Mon, 16 Jun 2008 04:34:59 +0000 (14:34 +1000)
If the spu is stopping (ie, the SPU_STATUS_RUNNING bit is still set),
re-read the register to get the final stopped value.

Signed-off-by: Luke Browning <lukebrowning@us.ibm.com>
Signed-off-by: Jeremy Kerr <jk@ozlabs.org>
arch/powerpc/platforms/cell/spufs/run.c

index b7493b8..0046bcf 100644 (file)
@@ -51,14 +51,22 @@ int spu_stopped(struct spu_context *ctx, u32 *stat)
        u64 dsisr;
        u32 stopped;
 
-       *stat = ctx->ops->status_read(ctx);
+       stopped = SPU_STATUS_INVALID_INSTR | SPU_STATUS_SINGLE_STEP |
+               SPU_STATUS_STOPPED_BY_HALT | SPU_STATUS_STOPPED_BY_STOP;
 
-       if (test_bit(SPU_SCHED_NOTIFY_ACTIVE, &ctx->sched_flags))
+top:
+       *stat = ctx->ops->status_read(ctx);
+       if (*stat & stopped) {
+               /*
+                * If the spu hasn't finished stopping, we need to
+                * re-read the register to get the stopped value.
+                */
+               if (*stat & SPU_STATUS_RUNNING)
+                       goto top;
                return 1;
+       }
 
-       stopped = SPU_STATUS_INVALID_INSTR | SPU_STATUS_SINGLE_STEP |
-               SPU_STATUS_STOPPED_BY_HALT | SPU_STATUS_STOPPED_BY_STOP;
-       if (!(*stat & SPU_STATUS_RUNNING) && (*stat & stopped))
+       if (test_bit(SPU_SCHED_NOTIFY_ACTIVE, &ctx->sched_flags))
                return 1;
 
        dsisr = ctx->csa.class_0_dsisr;