On Thu, Jul 25, 2013 at 05:32:04PM +0900, MORITA Kazutaka wrote: > This patch tries to cancel aio requests in pending queue and failed > queue. When the sheepdog driver cannot cancel the requests, it waits > for them to be completed. > > Signed-off-by: MORITA Kazutaka <morita.kazut...@lab.ntt.co.jp> > --- > block/sheepdog.c | 70 > +++++++++++++++++++++++++++++++++++++++++++++++--------- > 1 file changed, 59 insertions(+), 11 deletions(-) > > diff --git a/block/sheepdog.c b/block/sheepdog.c > index 9f3fa89..7bf882a 100644 > --- a/block/sheepdog.c > +++ b/block/sheepdog.c > @@ -294,7 +294,8 @@ struct SheepdogAIOCB { > Coroutine *coroutine; > void (*aio_done_func)(SheepdogAIOCB *); > > - bool canceled; > + bool cancelable; > + bool *finished; > int nr_pending; > }; > > @@ -411,6 +412,7 @@ static inline void free_aio_req(BDRVSheepdogState *s, > AIOReq *aio_req) > { > SheepdogAIOCB *acb = aio_req->aiocb; > > + acb->cancelable = false; > QLIST_REMOVE(aio_req, aio_siblings); > g_free(aio_req); > > @@ -419,23 +421,68 @@ static inline void free_aio_req(BDRVSheepdogState *s, > AIOReq *aio_req) > > static void coroutine_fn sd_finish_aiocb(SheepdogAIOCB *acb) > { > - if (!acb->canceled) { > - qemu_coroutine_enter(acb->coroutine, NULL); > + qemu_coroutine_enter(acb->coroutine, NULL); > + if (acb->finished) { > + *acb->finished = true; > } > qemu_aio_release(acb); > } > > +/* > + * Check whether the specified acb can be canceled > + * > + * We can cancel aio when any request belonging to the acb is: > + * - Not processed by the sheepdog server. > + * - Not linked to the inflight queue. > + */ > +static bool sd_acb_cancelable(const SheepdogAIOCB *acb) > +{ > + BDRVSheepdogState *s = acb->common.bs->opaque; > + AIOReq *aioreq; > + > + if (!acb->cancelable) { > + return false; > + } > + > + QLIST_FOREACH(aioreq, &s->inflight_aio_head, aio_siblings) { > + if (aioreq->aiocb == acb) { > + return false; > + } > + } > + > + return false;
return true; ? > +} Thanks Yuan