Commit 56d8b785 authored by Shuhei Matsumoto's avatar Shuhei Matsumoto Committed by Changpeng Liu
Browse files

lib/scsi: Make spdk_scsi_dev_destruct asynchronous



This is the end of the patch series. After this patch,
delete_target_node RPC will wait for the completion of
removal of the SCSI device and then free the iSCSI target.

SCSI device holds passed callback and calls it in free_dev().
free_dev() is ensured to be called after all iSCSI sessions
are closed. So iSCSI target resource can be freed safely
after that.

Change-Id: I25921b4014207092b7b3845dfeae58bcdffa2edc
Signed-off-by: default avatarShuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
Reviewed-on: https://review.gerrithub.io/c/spdk/spdk/+/450607


Reviewed-by: default avatarJim Harris <james.r.harris@intel.com>
Reviewed-by: default avatarChangpeng Liu <changpeng.liu@intel.com>
Tested-by: default avatarSPDK CI Jenkins <sys_sgci@intel.com>
parent 9e10f5fa
Loading
Loading
Loading
Loading
+5 −1
Original line number Diff line number Diff line
@@ -151,6 +151,7 @@ struct spdk_scsi_lun;
struct spdk_scsi_lun_desc;

typedef void (*spdk_scsi_lun_remove_cb_t)(struct spdk_scsi_lun *, void *);
typedef void (*spdk_scsi_dev_destruct_cb_t)(void *cb_arg, int rc);

/**
 * Initialize SCSI layer.
@@ -241,8 +242,11 @@ bool spdk_scsi_dev_has_pending_tasks(const struct spdk_scsi_dev *dev);
 * Destruct the SCSI decice.
 *
 * \param dev SCSI device.
 * \param cb_fn Callback function.
 * \param cb_arg Argument to callback function.
 */
void spdk_scsi_dev_destruct(struct spdk_scsi_dev *dev);
void spdk_scsi_dev_destruct(struct spdk_scsi_dev *dev,
			    spdk_scsi_dev_destruct_cb_t cb_fn, void *cb_arg);

/**
 * Execute the SCSI management task.
+2 −4
Original line number Diff line number Diff line
@@ -664,8 +664,7 @@ iscsi_tgt_node_check_active_conns(void *arg)

	spdk_poller_unregister(&target->destruct_poller);

	spdk_scsi_dev_destruct(target->dev);
	_iscsi_tgt_node_destruct(target, 0);
	spdk_scsi_dev_destruct(target->dev, _iscsi_tgt_node_destruct, target);

	return 1;
}
@@ -699,8 +698,7 @@ iscsi_tgt_node_destruct(struct spdk_iscsi_tgt_node *target,
		target->destruct_poller = spdk_poller_register(iscsi_tgt_node_check_active_conns,
					  target, 10);
	} else {
		spdk_scsi_dev_destruct(target->dev);
		_iscsi_tgt_node_destruct(target, 0);
		spdk_scsi_dev_destruct(target->dev, _iscsi_tgt_node_destruct, target);
	}

}
+21 −3
Original line number Diff line number Diff line
@@ -68,19 +68,37 @@ free_dev(struct spdk_scsi_dev *dev)
	assert(dev->removed == true);

	dev->is_allocated = 0;

	if (dev->remove_cb) {
		dev->remove_cb(dev->remove_ctx, 0);
		dev->remove_cb = NULL;
	}
}

void
spdk_scsi_dev_destruct(struct spdk_scsi_dev *dev)
spdk_scsi_dev_destruct(struct spdk_scsi_dev *dev,
		       spdk_scsi_dev_destruct_cb_t cb_fn, void *cb_arg)
{
	int lun_cnt;
	int i;

	if (dev == NULL || dev->removed) {
	if (dev == NULL) {
		if (cb_fn) {
			cb_fn(cb_arg, -EINVAL);
		}
		return;
	}

	if (dev->removed) {
		if (cb_fn) {
			cb_fn(cb_arg, -EINVAL);
		}
		return;
	}

	dev->removed = true;
	dev->remove_cb = cb_fn;
	dev->remove_ctx = cb_arg;
	lun_cnt = 0;

	for (i = 0; i < SPDK_SCSI_DEV_MAX_LUN; i++) {
@@ -236,7 +254,7 @@ spdk_scsi_dev_construct(const char *name, const char *bdev_name_list[],
		rc = spdk_scsi_dev_add_lun(dev, bdev_name_list[i], lun_id_list[i],
					   hotremove_cb, hotremove_ctx);
		if (rc < 0) {
			spdk_scsi_dev_destruct(dev);
			spdk_scsi_dev_destruct(dev, NULL, NULL);
			return NULL;
		}
	}
+10 −8
Original line number Diff line number Diff line
@@ -64,6 +64,8 @@ struct spdk_scsi_dev {
	int				id;
	int				is_allocated;
	bool				removed;
	spdk_scsi_dev_destruct_cb_t	remove_cb;
	void				*remove_ctx;

	char				name[SPDK_SCSI_DEV_MAX_NAME + 1];

+1 −1
Original line number Diff line number Diff line
@@ -188,7 +188,7 @@ remove_scsi_tgt(struct spdk_vhost_scsi_dev *svdev,
	state->dev = NULL;
	assert(state->status == VHOST_SCSI_DEV_REMOVING);
	state->status = VHOST_SCSI_DEV_EMPTY;
	spdk_scsi_dev_destruct(dev);
	spdk_scsi_dev_destruct(dev, NULL, NULL);
	if (state->remove_cb) {
		state->remove_cb(&svdev->vdev, state->remove_ctx);
		state->remove_cb = NULL;
Loading