All of lore.kernel.org
 help / color / mirror / Atom feed
From: Ming Lei <ming.lei@redhat.com>
To: ZiyangZhang <ZiyangZhang@linux.alibaba.com>
Cc: axboe@kernel.dk, xiaoguang.wang@linux.alibaba.com,
	linux-block@vger.kernel.org, linux-kernel@vger.kernel.org,
	joseph.qi@linux.alibaba.com
Subject: Re: [PATCH V3 6/7] ublk_drv: add START_USER_RECOVERY and END_USER_RECOVERY support
Date: Mon, 19 Sep 2022 21:03:23 +0800	[thread overview]
Message-ID: <Yyhom5s4AxK+wSu4@T590> (raw)
In-Reply-To: <20220913041707.197334-7-ZiyangZhang@linux.alibaba.com>

On Tue, Sep 13, 2022 at 12:17:06PM +0800, ZiyangZhang wrote:
> START_USER_RECOVERY and END_USER_RECOVERY are two new control commands
> to support user recovery feature.
> 
> After a crash, user should send START_USER_RECOVERY, it will:
> (1) check if (a)current ublk_device is UBLK_S_DEV_QUIESCED which was
>     set by quiesce_work and (b)the file struct is released.
> (2) reinit all ubqs, including:
>     (a) put the task_struct and reset ->ubq_daemon to NULL.
>     (b) reset all ublk_io.
> (3) reset ub->mm to NULL.
> 
> Then, user should start a new process and send FETCH_REQ on each
> ubq_daemon.
> 
> Finally, user should send END_USER_RECOVERY, it will:
> (1) wait for all new ubq_daemons getting ready.
> (2) update ublksrv_pid
> (3) unquiesce the request queue and expect incoming ublk_queue_rq()
> (4) convert ub's state to UBLK_S_DEV_LIVE
> 
> Note: we can handle STOP_DEV between START_USER_RECOVERY and
> END_USER_RECOVERY. This is helpful to users who cannot start new process
> after sending START_USER_RECOVERY ctrl-cmd.
> 
> Signed-off-by: ZiyangZhang <ZiyangZhang@linux.alibaba.com>
> ---
>  drivers/block/ublk_drv.c | 116 +++++++++++++++++++++++++++++++++++++++
>  1 file changed, 116 insertions(+)
> 
> diff --git a/drivers/block/ublk_drv.c b/drivers/block/ublk_drv.c
> index 4409a130d0b6..3a3af80ee938 100644
> --- a/drivers/block/ublk_drv.c
> +++ b/drivers/block/ublk_drv.c
> @@ -1961,6 +1961,116 @@ static int ublk_ctrl_set_params(struct io_uring_cmd *cmd)
>  	return ret;
>  }
>  
> +static void ublk_queue_reinit(struct ublk_device *ub, struct ublk_queue *ubq)
> +{
> +	int i;
> +
> +	WARN_ON_ONCE(!(ubq->ubq_daemon && ubq_daemon_is_dying(ubq)));
> +	/* All old ioucmds have to be completed */
> +	WARN_ON_ONCE(ubq->nr_io_ready);
> +	pr_devel("%s: prepare for recovering qid %d\n", __func__, ubq->q_id);
> +	/* old daemon is PF_EXITING, put it now */
> +	put_task_struct(ubq->ubq_daemon);
> +	/* We have to reset it to NULL, otherwise ub won't accept new FETCH_REQ */
> +	ubq->ubq_daemon = NULL;
> +
> +	for (i = 0; i < ubq->q_depth; i++) {
> +		struct ublk_io *io = &ubq->ios[i];
> +
> +		/* forget everything now and be ready for new FETCH_REQ */
> +		io->flags = 0;
> +		io->cmd = NULL;
> +		io->addr = 0;
> +	}
> +}
> +
> +static int ublk_ctrl_start_recovery(struct io_uring_cmd *cmd)
> +{
> +	struct ublksrv_ctrl_cmd *header = (struct ublksrv_ctrl_cmd *)cmd->cmd;
> +	struct ublk_device *ub;
> +	int ret = -EINVAL;
> +	int i;
> +
> +	ub = ublk_get_device_from_id(header->dev_id);
> +	if (!ub)
> +		return ret;
> +
> +	mutex_lock(&ub->mutex);
> +	if (!ublk_can_use_recovery(ub))
> +		goto out_unlock;
> +	/*
> +	 * START_RECOVERY is only allowd after:
> +	 *
> +	 * (1) UB_STATE_OPEN is not set, which means the dying process is exited
> +	 *     and related io_uring ctx is freed so file struct of /dev/ublkcX is
> +	 *     released.
> +	 *
> +	 * (2) UBLK_S_DEV_QUIESCED is set, which means the quiesce_work:
> +	 *     (a)has quiesced request queue
> +	 *     (b)has requeued every inflight rqs whose io_flags is ACTIVE
> +	 *     (c)has requeued/aborted every inflight rqs whose io_flags is NOT ACTIVE
> +	 *     (d)has completed/camceled all ioucmds owned by ther dying process
> +	 */
> +	if (test_bit(UB_STATE_OPEN, &ub->state) ||
> +			ub->dev_info.state != UBLK_S_DEV_QUIESCED) {
> +		ret = -EBUSY;
> +		goto out_unlock;
> +	}
> +	pr_devel("%s: start recovery for dev id %d.\n", __func__, header->dev_id);
> +	for (i = 0; i < ub->dev_info.nr_hw_queues; i++)
> +		ublk_queue_reinit(ub, ublk_get_queue(ub, i));
> +	/* set to NULL, otherwise new ubq_daemon cannot mmap the io_cmd_buf */
> +	ub->mm = NULL;
> +	ub->nr_queues_ready = 0;

I am wondering why you don't move the above(queue reinit, clearing ub->mm)
into ublk_ch_release(), and looks it is more clean to clear this stuff
there. Meantime I guess one control command might be enough for user
recovery.


Thanks, 
Ming


  reply	other threads:[~2022-09-19 13:03 UTC|newest]

Thread overview: 33+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-09-13  4:17 [PATCH V3 0/7] ublk_drv: add USER_RECOVERY support ZiyangZhang
2022-09-13  4:17 ` [PATCH V3 1/7] ublk_drv: check 'current' instead of 'ubq_daemon' ZiyangZhang
2022-09-13  4:17 ` [PATCH V3 2/7] ublk_drv: refactor ublk_cancel_queue() ZiyangZhang
2022-09-13  4:17 ` [PATCH V3 3/7] ublk_drv: define macros for recovery feature and check them ZiyangZhang
2022-09-20  5:04   ` Ming Lei
2022-09-13  4:17 ` [PATCH V3 4/7] ublk_drv: requeue rqs with recovery feature enabled ZiyangZhang
2022-09-19  3:55   ` Ming Lei
2022-09-19  9:12     ` Ziyang Zhang
2022-09-19 12:39       ` Ming Lei
2022-09-20  1:31         ` Ziyang Zhang
2022-09-20  2:39           ` Ming Lei
2022-09-20  3:04             ` Ziyang Zhang
2022-09-20  3:18               ` Ming Lei
2022-09-20  3:34                 ` Ziyang Zhang
2022-09-20  4:41                   ` Ming Lei
2022-09-13  4:17 ` [PATCH V3 5/7] ublk_drv: consider recovery feature in aborting mechanism ZiyangZhang
2022-09-19  9:32   ` Ming Lei
2022-09-19  9:55     ` Ziyang Zhang
2022-09-19 12:33       ` Ming Lei
2022-09-20  1:49         ` Ziyang Zhang
2022-09-20  3:04           ` Ming Lei
2022-09-20  3:24             ` Ziyang Zhang
2022-09-20  4:01               ` Ming Lei
2022-09-20  4:39                 ` Ziyang Zhang
2022-09-20  4:49                   ` Ming Lei
2022-09-20  5:03                     ` Ziyang Zhang
2022-09-20  4:45             ` Ziyang Zhang
2022-09-20  5:05               ` Ziyang Zhang
2022-09-13  4:17 ` [PATCH V3 6/7] ublk_drv: add START_USER_RECOVERY and END_USER_RECOVERY support ZiyangZhang
2022-09-19 13:03   ` Ming Lei [this message]
2022-09-20  2:41     ` Ziyang Zhang
2022-09-13  4:17 ` [PATCH V3 7/7] ublk_drv: do not run monitor_work while ub's state is QUIESCED ZiyangZhang
2022-09-19  2:17 ` [PATCH V3 0/7] ublk_drv: add USER_RECOVERY support Ziyang Zhang

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=Yyhom5s4AxK+wSu4@T590 \
    --to=ming.lei@redhat.com \
    --cc=ZiyangZhang@linux.alibaba.com \
    --cc=axboe@kernel.dk \
    --cc=joseph.qi@linux.alibaba.com \
    --cc=linux-block@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=xiaoguang.wang@linux.alibaba.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.