xref: /spdk/lib/vhost/vhost_scsi.c (revision 8f633fa1c331383d74e6e529481c7bb6bae4c8aa)
1 /*-
2  *   BSD LICENSE
3  *
4  *   Copyright(c) Intel Corporation. All rights reserved.
5  *   All rights reserved.
6  *
7  *   Redistribution and use in source and binary forms, with or without
8  *   modification, are permitted provided that the following conditions
9  *   are met:
10  *
11  *     * Redistributions of source code must retain the above copyright
12  *       notice, this list of conditions and the following disclaimer.
13  *     * Redistributions in binary form must reproduce the above copyright
14  *       notice, this list of conditions and the following disclaimer in
15  *       the documentation and/or other materials provided with the
16  *       distribution.
17  *     * Neither the name of Intel Corporation nor the names of its
18  *       contributors may be used to endorse or promote products derived
19  *       from this software without specific prior written permission.
20  *
21  *   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  *   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  *   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24  *   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25  *   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26  *   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27  *   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28  *   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29  *   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30  *   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31  *   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 #include "spdk/stdinc.h"
35 
36 #include <linux/virtio_scsi.h>
37 
38 #include "spdk/env.h"
39 #include "spdk/thread.h"
40 #include "spdk/scsi.h"
41 #include "spdk/scsi_spec.h"
42 #include "spdk/util.h"
43 #include "spdk/likely.h"
44 
45 #include "spdk/vhost.h"
46 #include "vhost_internal.h"
47 
48 /* Features supported by SPDK VHOST lib. */
49 #define SPDK_VHOST_SCSI_FEATURES	(SPDK_VHOST_FEATURES | \
50 					(1ULL << VIRTIO_SCSI_F_INOUT) | \
51 					(1ULL << VIRTIO_SCSI_F_HOTPLUG) | \
52 					(1ULL << VIRTIO_SCSI_F_CHANGE ) | \
53 					(1ULL << VIRTIO_SCSI_F_T10_PI ))
54 
55 /* Features that are specified in VIRTIO SCSI but currently not supported:
56  * - Live migration not supported yet
57  * - T10 PI
58  */
59 #define SPDK_VHOST_SCSI_DISABLED_FEATURES	(SPDK_VHOST_DISABLED_FEATURES | \
60 						(1ULL << VIRTIO_SCSI_F_T10_PI ))
61 
62 /* Vhost-user-scsi support protocol features */
63 #define SPDK_VHOST_SCSI_PROTOCOL_FEATURES	(1ULL << VHOST_USER_PROTOCOL_F_INFLIGHT_SHMFD)
64 
65 #define MGMT_POLL_PERIOD_US (1000 * 5)
66 
67 #define VIRTIO_SCSI_CONTROLQ   0
68 #define VIRTIO_SCSI_EVENTQ   1
69 #define VIRTIO_SCSI_REQUESTQ   2
70 
71 enum spdk_scsi_dev_vhost_status {
72 	/* Target ID is empty. */
73 	VHOST_SCSI_DEV_EMPTY,
74 
75 	/* Target is still being added. */
76 	VHOST_SCSI_DEV_ADDING,
77 
78 	/* Target ID occupied. */
79 	VHOST_SCSI_DEV_PRESENT,
80 
81 	/* Target ID is occupied but removal is in progress. */
82 	VHOST_SCSI_DEV_REMOVING,
83 
84 	/* In session - device (SCSI target) seen but removed. */
85 	VHOST_SCSI_DEV_REMOVED,
86 };
87 
88 /** Context for a SCSI target in a vhost device */
89 struct spdk_scsi_dev_vhost_state {
90 	struct spdk_scsi_dev *dev;
91 	enum spdk_scsi_dev_vhost_status status;
92 	spdk_vhost_event_fn remove_cb;
93 	void *remove_ctx;
94 };
95 
96 struct spdk_vhost_scsi_dev {
97 	int ref;
98 	bool registered;
99 	struct spdk_vhost_dev vdev;
100 	struct spdk_scsi_dev_vhost_state scsi_dev_state[SPDK_VHOST_SCSI_CTRLR_MAX_DEVS];
101 };
102 
103 /** Context for a SCSI target in a vhost session */
104 struct spdk_scsi_dev_session_state {
105 	struct spdk_scsi_dev *dev;
106 	enum spdk_scsi_dev_vhost_status status;
107 };
108 
109 struct spdk_vhost_scsi_session {
110 	struct spdk_vhost_session vsession;
111 
112 	struct spdk_vhost_scsi_dev *svdev;
113 	/** Local copy of the device state */
114 	struct spdk_scsi_dev_session_state scsi_dev_state[SPDK_VHOST_SCSI_CTRLR_MAX_DEVS];
115 	struct spdk_poller *requestq_poller;
116 	struct spdk_poller *mgmt_poller;
117 	struct spdk_poller *stop_poller;
118 };
119 
120 struct spdk_vhost_scsi_task {
121 	struct spdk_scsi_task	scsi;
122 	struct iovec iovs[SPDK_VHOST_IOVS_MAX];
123 
124 	union {
125 		struct virtio_scsi_cmd_resp *resp;
126 		struct virtio_scsi_ctrl_tmf_resp *tmf_resp;
127 	};
128 
129 	struct spdk_vhost_scsi_session *svsession;
130 	struct spdk_scsi_dev *scsi_dev;
131 
132 	/** Number of bytes that were written. */
133 	uint32_t used_len;
134 
135 	int req_idx;
136 
137 	/* If set, the task is currently used for I/O processing. */
138 	bool used;
139 
140 	struct spdk_vhost_virtqueue *vq;
141 };
142 
143 static int vhost_scsi_start(struct spdk_vhost_session *vsession);
144 static int vhost_scsi_stop(struct spdk_vhost_session *vsession);
145 static void vhost_scsi_dump_info_json(struct spdk_vhost_dev *vdev,
146 				      struct spdk_json_write_ctx *w);
147 static void vhost_scsi_write_config_json(struct spdk_vhost_dev *vdev,
148 		struct spdk_json_write_ctx *w);
149 static int vhost_scsi_dev_remove(struct spdk_vhost_dev *vdev);
150 static int vhost_scsi_dev_param_changed(struct spdk_vhost_dev *vdev,
151 					unsigned scsi_tgt_num);
152 
153 static const struct spdk_vhost_dev_backend spdk_vhost_scsi_device_backend = {
154 	.session_ctx_size = sizeof(struct spdk_vhost_scsi_session) - sizeof(struct spdk_vhost_session),
155 	.start_session =  vhost_scsi_start,
156 	.stop_session = vhost_scsi_stop,
157 	.dump_info_json = vhost_scsi_dump_info_json,
158 	.write_config_json = vhost_scsi_write_config_json,
159 	.remove_device = vhost_scsi_dev_remove,
160 };
161 
162 static inline void
163 scsi_task_init(struct spdk_vhost_scsi_task *task)
164 {
165 	memset(&task->scsi, 0, sizeof(task->scsi));
166 	/* Tmf_resp pointer and resp pointer are in a union.
167 	 * Here means task->tmf_resp = task->resp = NULL.
168 	 */
169 	task->resp = NULL;
170 	task->used = true;
171 	task->used_len = 0;
172 }
173 
174 static void
175 vhost_scsi_task_put(struct spdk_vhost_scsi_task *task)
176 {
177 	spdk_scsi_task_put(&task->scsi);
178 }
179 
180 static void
181 vhost_scsi_task_free_cb(struct spdk_scsi_task *scsi_task)
182 {
183 	struct spdk_vhost_scsi_task *task = SPDK_CONTAINEROF(scsi_task, struct spdk_vhost_scsi_task, scsi);
184 	struct spdk_vhost_session *vsession = &task->svsession->vsession;
185 
186 	assert(vsession->task_cnt > 0);
187 	vsession->task_cnt--;
188 	task->used = false;
189 }
190 
191 static void
192 remove_scsi_tgt(struct spdk_vhost_scsi_dev *svdev,
193 		unsigned scsi_tgt_num)
194 {
195 	struct spdk_scsi_dev_vhost_state *state;
196 	struct spdk_scsi_dev *dev;
197 
198 	state = &svdev->scsi_dev_state[scsi_tgt_num];
199 	dev = state->dev;
200 	state->dev = NULL;
201 	assert(state->status == VHOST_SCSI_DEV_REMOVING);
202 	state->status = VHOST_SCSI_DEV_EMPTY;
203 	spdk_scsi_dev_destruct(dev, NULL, NULL);
204 	if (state->remove_cb) {
205 		state->remove_cb(&svdev->vdev, state->remove_ctx);
206 		state->remove_cb = NULL;
207 	}
208 	SPDK_INFOLOG(vhost, "removed target 'Target %u'\n", scsi_tgt_num);
209 
210 	if (--svdev->ref == 0 && svdev->registered == false) {
211 		free(svdev);
212 	}
213 }
214 
215 static void
216 vhost_scsi_dev_process_removed_cpl_cb(struct spdk_vhost_dev *vdev, void *ctx)
217 {
218 	unsigned scsi_tgt_num = (unsigned)(uintptr_t)ctx;
219 	struct spdk_vhost_scsi_dev *svdev = SPDK_CONTAINEROF(vdev,
220 					    struct spdk_vhost_scsi_dev, vdev);
221 
222 	/* all sessions have already detached the device */
223 	if (svdev->scsi_dev_state[scsi_tgt_num].status != VHOST_SCSI_DEV_REMOVING) {
224 		/* device was already removed in the meantime */
225 		return;
226 	}
227 
228 	remove_scsi_tgt(svdev, scsi_tgt_num);
229 }
230 
231 static int
232 vhost_scsi_session_process_removed(struct spdk_vhost_dev *vdev,
233 				   struct spdk_vhost_session *vsession, void *ctx)
234 {
235 	unsigned scsi_tgt_num = (unsigned)(uintptr_t)ctx;
236 	struct spdk_vhost_scsi_session *svsession = (struct spdk_vhost_scsi_session *)vsession;
237 	struct spdk_scsi_dev_session_state *state = &svsession->scsi_dev_state[scsi_tgt_num];
238 
239 	if (state->dev != NULL) {
240 		/* there's still a session that references this device,
241 		 * so abort our foreach chain here. We'll be called
242 		 * again from this session's management poller after it
243 		 * is removed in there
244 		 */
245 		return -1;
246 	}
247 
248 	return 0;
249 }
250 
251 static void
252 process_removed_devs(struct spdk_vhost_scsi_session *svsession)
253 {
254 	struct spdk_scsi_dev *dev;
255 	struct spdk_scsi_dev_session_state *state;
256 	int i;
257 
258 	for (i = 0; i < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; ++i) {
259 		state = &svsession->scsi_dev_state[i];
260 		dev = state->dev;
261 
262 		if (dev && state->status == VHOST_SCSI_DEV_REMOVING &&
263 		    !spdk_scsi_dev_has_pending_tasks(dev, NULL)) {
264 			/* detach the device from this session */
265 			spdk_scsi_dev_free_io_channels(dev);
266 			state->dev = NULL;
267 			state->status = VHOST_SCSI_DEV_REMOVED;
268 			/* try to detach it globally */
269 			spdk_vhost_lock();
270 			vhost_dev_foreach_session(&svsession->svdev->vdev,
271 						  vhost_scsi_session_process_removed,
272 						  vhost_scsi_dev_process_removed_cpl_cb,
273 						  (void *)(uintptr_t)i);
274 			spdk_vhost_unlock();
275 		}
276 	}
277 }
278 
279 static void
280 eventq_enqueue(struct spdk_vhost_scsi_session *svsession, unsigned scsi_dev_num,
281 	       uint32_t event, uint32_t reason)
282 {
283 	struct spdk_vhost_session *vsession = &svsession->vsession;
284 	struct spdk_vhost_virtqueue *vq;
285 	struct vring_desc *desc, *desc_table;
286 	struct virtio_scsi_event *desc_ev;
287 	uint32_t desc_table_size, req_size = 0;
288 	uint16_t req;
289 	int rc;
290 
291 	assert(scsi_dev_num < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS);
292 	vq = &vsession->virtqueue[VIRTIO_SCSI_EVENTQ];
293 
294 	if (vq->vring.desc == NULL || vhost_vq_avail_ring_get(vq, &req, 1) != 1) {
295 		SPDK_ERRLOG("%s: failed to send virtio event (no avail ring entries?).\n",
296 			    vsession->name);
297 		return;
298 	}
299 
300 	rc = vhost_vq_get_desc(vsession, vq, req, &desc, &desc_table, &desc_table_size);
301 	if (rc != 0 || desc->len < sizeof(*desc_ev)) {
302 		SPDK_ERRLOG("%s: invalid eventq descriptor at index %"PRIu16".\n",
303 			    vsession->name, req);
304 		goto out;
305 	}
306 
307 	desc_ev = vhost_gpa_to_vva(vsession, desc->addr, sizeof(*desc_ev));
308 	if (desc_ev == NULL) {
309 		SPDK_ERRLOG("%s: eventq descriptor at index %"PRIu16" points "
310 			    "to unmapped guest memory address %p.\n",
311 			    vsession->name, req, (void *)(uintptr_t)desc->addr);
312 		goto out;
313 	}
314 
315 	desc_ev->event = event;
316 	desc_ev->lun[0] = 1;
317 	desc_ev->lun[1] = scsi_dev_num;
318 	/* virtio LUN id 0 can refer either to the entire device
319 	 * or actual LUN 0 (the only supported by vhost for now)
320 	 */
321 	desc_ev->lun[2] = 0 >> 8;
322 	desc_ev->lun[3] = 0 & 0xFF;
323 	/* virtio doesn't specify any strict format for LUN id (bytes 2 and 3)
324 	 * current implementation relies on linux kernel sources
325 	 */
326 	memset(&desc_ev->lun[4], 0, 4);
327 	desc_ev->reason = reason;
328 	req_size = sizeof(*desc_ev);
329 
330 out:
331 	vhost_vq_used_ring_enqueue(vsession, vq, req, req_size);
332 }
333 
334 static void
335 submit_completion(struct spdk_vhost_scsi_task *task)
336 {
337 	struct spdk_vhost_session *vsession = &task->svsession->vsession;
338 
339 	vhost_vq_used_ring_enqueue(vsession, task->vq, task->req_idx,
340 				   task->used_len);
341 	SPDK_DEBUGLOG(vhost_scsi, "Finished task (%p) req_idx=%d\n", task, task->req_idx);
342 
343 	vhost_scsi_task_put(task);
344 }
345 
346 static void
347 vhost_scsi_task_mgmt_cpl(struct spdk_scsi_task *scsi_task)
348 {
349 	struct spdk_vhost_scsi_task *task = SPDK_CONTAINEROF(scsi_task, struct spdk_vhost_scsi_task, scsi);
350 
351 	submit_completion(task);
352 }
353 
354 static void
355 vhost_scsi_task_cpl(struct spdk_scsi_task *scsi_task)
356 {
357 	struct spdk_vhost_scsi_task *task = SPDK_CONTAINEROF(scsi_task, struct spdk_vhost_scsi_task, scsi);
358 
359 	/* The SCSI task has completed.  Do final processing and then post
360 	   notification to the virtqueue's "used" ring.
361 	 */
362 	task->resp->status = task->scsi.status;
363 
364 	if (task->scsi.status != SPDK_SCSI_STATUS_GOOD) {
365 		memcpy(task->resp->sense, task->scsi.sense_data, task->scsi.sense_data_len);
366 		task->resp->sense_len = task->scsi.sense_data_len;
367 		SPDK_DEBUGLOG(vhost_scsi, "Task (%p) req_idx=%d failed - status=%u\n", task, task->req_idx,
368 			      task->scsi.status);
369 	}
370 	assert(task->scsi.transfer_len == task->scsi.length);
371 	task->resp->resid = task->scsi.length - task->scsi.data_transferred;
372 
373 	submit_completion(task);
374 }
375 
376 static void
377 task_submit(struct spdk_vhost_scsi_task *task)
378 {
379 	task->resp->response = VIRTIO_SCSI_S_OK;
380 	spdk_scsi_dev_queue_task(task->scsi_dev, &task->scsi);
381 }
382 
383 static void
384 mgmt_task_submit(struct spdk_vhost_scsi_task *task, enum spdk_scsi_task_func func)
385 {
386 	task->tmf_resp->response = VIRTIO_SCSI_S_OK;
387 	task->scsi.function = func;
388 	spdk_scsi_dev_queue_mgmt_task(task->scsi_dev, &task->scsi);
389 }
390 
391 static void
392 invalid_request(struct spdk_vhost_scsi_task *task)
393 {
394 	struct spdk_vhost_session *vsession = &task->svsession->vsession;
395 
396 	vhost_vq_used_ring_enqueue(vsession, task->vq, task->req_idx,
397 				   task->used_len);
398 	vhost_scsi_task_put(task);
399 
400 	SPDK_DEBUGLOG(vhost_scsi, "Invalid request (status=%" PRIu8")\n",
401 		      task->resp ? task->resp->response : -1);
402 }
403 
404 static int
405 vhost_scsi_task_init_target(struct spdk_vhost_scsi_task *task, const __u8 *lun)
406 {
407 	struct spdk_vhost_scsi_session *svsession = task->svsession;
408 	struct spdk_scsi_dev_session_state *state;
409 	uint16_t lun_id = (((uint16_t)lun[2] << 8) | lun[3]) & 0x3FFF;
410 
411 	SPDK_LOGDUMP(vhost_scsi_queue, "LUN", lun, 8);
412 
413 	/* First byte must be 1 and second is target */
414 	if (lun[0] != 1 || lun[1] >= SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
415 		return -1;
416 	}
417 
418 	state = &svsession->scsi_dev_state[lun[1]];
419 	task->scsi_dev = state->dev;
420 	if (state->dev == NULL || state->status != VHOST_SCSI_DEV_PRESENT) {
421 		/* If dev has been hotdetached, return 0 to allow sending
422 		 * additional hotremove event via sense codes.
423 		 */
424 		return state->status != VHOST_SCSI_DEV_EMPTY ? 0 : -1;
425 	}
426 
427 	task->scsi.target_port = spdk_scsi_dev_find_port_by_id(task->scsi_dev, 0);
428 	task->scsi.lun = spdk_scsi_dev_get_lun(state->dev, lun_id);
429 	return 0;
430 }
431 
432 static void
433 process_ctrl_request(struct spdk_vhost_scsi_task *task)
434 {
435 	struct spdk_vhost_session *vsession = &task->svsession->vsession;
436 	struct vring_desc *desc, *desc_table;
437 	struct virtio_scsi_ctrl_tmf_req *ctrl_req;
438 	struct virtio_scsi_ctrl_an_resp *an_resp;
439 	uint32_t desc_table_size, used_len = 0;
440 	int rc;
441 
442 	spdk_scsi_task_construct(&task->scsi, vhost_scsi_task_mgmt_cpl, vhost_scsi_task_free_cb);
443 	rc = vhost_vq_get_desc(vsession, task->vq, task->req_idx, &desc, &desc_table,
444 			       &desc_table_size);
445 	if (spdk_unlikely(rc != 0)) {
446 		SPDK_ERRLOG("%s: invalid controlq descriptor at index %d.\n",
447 			    vsession->name, task->req_idx);
448 		goto out;
449 	}
450 
451 	ctrl_req = vhost_gpa_to_vva(vsession, desc->addr, sizeof(*ctrl_req));
452 	if (ctrl_req == NULL) {
453 		SPDK_ERRLOG("%s: invalid task management request at index %d.\n",
454 			    vsession->name, task->req_idx);
455 		goto out;
456 	}
457 
458 	SPDK_DEBUGLOG(vhost_scsi_queue,
459 		      "Processing controlq descriptor: desc %d/%p, desc_addr %p, len %d, flags %d, last_used_idx %d; kickfd %d; size %d\n",
460 		      task->req_idx, desc, (void *)desc->addr, desc->len, desc->flags, task->vq->last_used_idx,
461 		      task->vq->vring.kickfd, task->vq->vring.size);
462 	SPDK_LOGDUMP(vhost_scsi_queue, "Request descriptor", (uint8_t *)ctrl_req, desc->len);
463 
464 	vhost_scsi_task_init_target(task, ctrl_req->lun);
465 
466 	vhost_vring_desc_get_next(&desc, desc_table, desc_table_size);
467 	if (spdk_unlikely(desc == NULL)) {
468 		SPDK_ERRLOG("%s: no response descriptor for controlq request %d.\n",
469 			    vsession->name, task->req_idx);
470 		goto out;
471 	}
472 
473 	/* Process the TMF request */
474 	switch (ctrl_req->type) {
475 	case VIRTIO_SCSI_T_TMF:
476 		task->tmf_resp = vhost_gpa_to_vva(vsession, desc->addr, sizeof(*task->tmf_resp));
477 		if (spdk_unlikely(desc->len < sizeof(struct virtio_scsi_ctrl_tmf_resp) || task->tmf_resp == NULL)) {
478 			SPDK_ERRLOG("%s: TMF response descriptor at index %d points to invalid guest memory region\n",
479 				    vsession->name, task->req_idx);
480 			goto out;
481 		}
482 
483 		/* Check if we are processing a valid request */
484 		if (task->scsi_dev == NULL) {
485 			task->tmf_resp->response = VIRTIO_SCSI_S_BAD_TARGET;
486 			break;
487 		}
488 
489 		switch (ctrl_req->subtype) {
490 		case VIRTIO_SCSI_T_TMF_LOGICAL_UNIT_RESET:
491 			/* Handle LUN reset */
492 			SPDK_DEBUGLOG(vhost_scsi_queue, "%s: LUN reset\n", vsession->name);
493 
494 			mgmt_task_submit(task, SPDK_SCSI_TASK_FUNC_LUN_RESET);
495 			return;
496 		default:
497 			task->tmf_resp->response = VIRTIO_SCSI_S_ABORTED;
498 			/* Unsupported command */
499 			SPDK_DEBUGLOG(vhost_scsi_queue, "%s: unsupported TMF command %x\n",
500 				      vsession->name, ctrl_req->subtype);
501 			break;
502 		}
503 		break;
504 	case VIRTIO_SCSI_T_AN_QUERY:
505 	case VIRTIO_SCSI_T_AN_SUBSCRIBE: {
506 		an_resp = vhost_gpa_to_vva(vsession, desc->addr, sizeof(*an_resp));
507 		if (spdk_unlikely(desc->len < sizeof(struct virtio_scsi_ctrl_an_resp) || an_resp == NULL)) {
508 			SPDK_WARNLOG("%s: asynchronous response descriptor points to invalid guest memory region\n",
509 				     vsession->name);
510 			goto out;
511 		}
512 
513 		an_resp->response = VIRTIO_SCSI_S_ABORTED;
514 		break;
515 	}
516 	default:
517 		SPDK_DEBUGLOG(vhost_scsi_queue, "%s: Unsupported control command %x\n",
518 			      vsession->name, ctrl_req->type);
519 		break;
520 	}
521 
522 	used_len = sizeof(struct virtio_scsi_ctrl_tmf_resp);
523 out:
524 	vhost_vq_used_ring_enqueue(vsession, task->vq, task->req_idx, used_len);
525 	vhost_scsi_task_put(task);
526 }
527 
528 /*
529  * Process task's descriptor chain and setup data related fields.
530  * Return
531  *   -1 if request is invalid and must be aborted,
532  *    0 if all data are set.
533  */
534 static int
535 task_data_setup(struct spdk_vhost_scsi_task *task,
536 		struct virtio_scsi_cmd_req **req)
537 {
538 	struct spdk_vhost_session *vsession = &task->svsession->vsession;
539 	struct vring_desc *desc, *desc_table;
540 	struct iovec *iovs = task->iovs;
541 	uint16_t iovcnt = 0;
542 	uint32_t desc_table_len, len = 0;
543 	int rc;
544 
545 	spdk_scsi_task_construct(&task->scsi, vhost_scsi_task_cpl, vhost_scsi_task_free_cb);
546 
547 	rc = vhost_vq_get_desc(vsession, task->vq, task->req_idx, &desc, &desc_table, &desc_table_len);
548 	/* First descriptor must be readable */
549 	if (spdk_unlikely(rc != 0  || vhost_vring_desc_is_wr(desc) ||
550 			  desc->len < sizeof(struct virtio_scsi_cmd_req))) {
551 		SPDK_WARNLOG("%s: invalid first request descriptor at index %"PRIu16".\n",
552 			     vsession->name, task->req_idx);
553 		goto invalid_task;
554 	}
555 
556 	*req = vhost_gpa_to_vva(vsession, desc->addr, sizeof(**req));
557 	if (spdk_unlikely(*req == NULL)) {
558 		SPDK_WARNLOG("%s: request descriptor at index %d points to invalid guest memory region\n",
559 			     vsession->name, task->req_idx);
560 		goto invalid_task;
561 	}
562 
563 	/* Each request must have at least 2 descriptors (e.g. request and response) */
564 	vhost_vring_desc_get_next(&desc, desc_table, desc_table_len);
565 	if (desc == NULL) {
566 		SPDK_WARNLOG("%s: descriptor chain at index %d contains neither payload nor response buffer.\n",
567 			     vsession->name, task->req_idx);
568 		goto invalid_task;
569 	}
570 	task->scsi.dxfer_dir = vhost_vring_desc_is_wr(desc) ? SPDK_SCSI_DIR_FROM_DEV :
571 			       SPDK_SCSI_DIR_TO_DEV;
572 	task->scsi.iovs = iovs;
573 
574 	if (task->scsi.dxfer_dir == SPDK_SCSI_DIR_FROM_DEV) {
575 		/*
576 		 * FROM_DEV (READ): [RD_req][WR_resp][WR_buf0]...[WR_bufN]
577 		 */
578 		task->resp = vhost_gpa_to_vva(vsession, desc->addr, sizeof(*task->resp));
579 		if (spdk_unlikely(desc->len < sizeof(struct virtio_scsi_cmd_resp) || task->resp == NULL)) {
580 			SPDK_WARNLOG("%s: response descriptor at index %d points to invalid guest memory region\n",
581 				     vsession->name, task->req_idx);
582 			goto invalid_task;
583 		}
584 		rc = vhost_vring_desc_get_next(&desc, desc_table, desc_table_len);
585 		if (spdk_unlikely(rc != 0)) {
586 			SPDK_WARNLOG("%s: invalid descriptor chain at request index %d (descriptor id overflow?).\n",
587 				     vsession->name, task->req_idx);
588 			goto invalid_task;
589 		}
590 
591 		if (desc == NULL) {
592 			/*
593 			 * TEST UNIT READY command and some others might not contain any payload and this is not an error.
594 			 */
595 			SPDK_DEBUGLOG(vhost_scsi_data,
596 				      "No payload descriptors for FROM DEV command req_idx=%"PRIu16".\n", task->req_idx);
597 			SPDK_LOGDUMP(vhost_scsi_data, "CDB=", (*req)->cdb, VIRTIO_SCSI_CDB_SIZE);
598 			task->used_len = sizeof(struct virtio_scsi_cmd_resp);
599 			task->scsi.iovcnt = 1;
600 			task->scsi.iovs[0].iov_len = 0;
601 			task->scsi.length = 0;
602 			task->scsi.transfer_len = 0;
603 			return 0;
604 		}
605 
606 		/* All remaining descriptors are data. */
607 		while (desc) {
608 			if (spdk_unlikely(!vhost_vring_desc_is_wr(desc))) {
609 				SPDK_WARNLOG("%s: FROM DEV cmd: descriptor nr %" PRIu16" in payload chain is read only.\n",
610 					     vsession->name, iovcnt);
611 				goto invalid_task;
612 			}
613 
614 			if (spdk_unlikely(vhost_vring_desc_to_iov(vsession, iovs, &iovcnt, desc))) {
615 				goto invalid_task;
616 			}
617 			len += desc->len;
618 
619 			rc = vhost_vring_desc_get_next(&desc, desc_table, desc_table_len);
620 			if (spdk_unlikely(rc != 0)) {
621 				SPDK_WARNLOG("%s: invalid payload in descriptor chain starting at index %d.\n",
622 					     vsession->name, task->req_idx);
623 				goto invalid_task;
624 			}
625 		}
626 
627 		task->used_len = sizeof(struct virtio_scsi_cmd_resp) + len;
628 	} else {
629 		SPDK_DEBUGLOG(vhost_scsi_data, "TO DEV");
630 		/*
631 		 * TO_DEV (WRITE):[RD_req][RD_buf0]...[RD_bufN][WR_resp]
632 		 * No need to check descriptor WR flag as this is done while setting scsi.dxfer_dir.
633 		 */
634 
635 		/* Process descriptors up to response. */
636 		while (!vhost_vring_desc_is_wr(desc)) {
637 			if (spdk_unlikely(vhost_vring_desc_to_iov(vsession, iovs, &iovcnt, desc))) {
638 				goto invalid_task;
639 			}
640 			len += desc->len;
641 
642 			vhost_vring_desc_get_next(&desc, desc_table, desc_table_len);
643 			if (spdk_unlikely(desc == NULL)) {
644 				SPDK_WARNLOG("%s: TO_DEV cmd: no response descriptor.\n", vsession->name);
645 				goto invalid_task;
646 			}
647 		}
648 
649 		task->resp = vhost_gpa_to_vva(vsession, desc->addr, sizeof(*task->resp));
650 		if (spdk_unlikely(desc->len < sizeof(struct virtio_scsi_cmd_resp) || task->resp == NULL)) {
651 			SPDK_WARNLOG("%s: response descriptor at index %d points to invalid guest memory region\n",
652 				     vsession->name, task->req_idx);
653 			goto invalid_task;
654 		}
655 
656 		task->used_len = sizeof(struct virtio_scsi_cmd_resp);
657 	}
658 
659 	task->scsi.iovcnt = iovcnt;
660 	task->scsi.length = len;
661 	task->scsi.transfer_len = len;
662 	return 0;
663 
664 invalid_task:
665 	SPDK_DEBUGLOG(vhost_scsi_data, "%s: Invalid task at index %"PRIu16".\n",
666 		      vsession->name, task->req_idx);
667 	return -1;
668 }
669 
670 static int
671 process_request(struct spdk_vhost_scsi_task *task)
672 {
673 	struct virtio_scsi_cmd_req *req;
674 	int result;
675 
676 	result = task_data_setup(task, &req);
677 	if (result) {
678 		return result;
679 	}
680 
681 	result = vhost_scsi_task_init_target(task, req->lun);
682 	if (spdk_unlikely(result != 0)) {
683 		task->resp->response = VIRTIO_SCSI_S_BAD_TARGET;
684 		return -1;
685 	}
686 
687 	task->scsi.cdb = req->cdb;
688 	SPDK_LOGDUMP(vhost_scsi_data, "request CDB", req->cdb, VIRTIO_SCSI_CDB_SIZE);
689 
690 	if (spdk_unlikely(task->scsi.lun == NULL)) {
691 		spdk_scsi_task_process_null_lun(&task->scsi);
692 		task->resp->response = VIRTIO_SCSI_S_OK;
693 		return 1;
694 	}
695 
696 	return 0;
697 }
698 
699 static void
700 process_scsi_task(struct spdk_vhost_session *vsession,
701 		  struct spdk_vhost_virtqueue *vq,
702 		  uint16_t req_idx)
703 {
704 	struct spdk_vhost_scsi_task *task;
705 	int result;
706 
707 	task = &((struct spdk_vhost_scsi_task *)vq->tasks)[req_idx];
708 	if (spdk_unlikely(task->used)) {
709 		SPDK_ERRLOG("%s: request with idx '%"PRIu16"' is already pending.\n",
710 			    vsession->name, req_idx);
711 		vhost_vq_used_ring_enqueue(vsession, vq, req_idx, 0);
712 		return;
713 	}
714 
715 	vsession->task_cnt++;
716 	scsi_task_init(task);
717 
718 	if (spdk_unlikely(vq->vring_idx == VIRTIO_SCSI_CONTROLQ)) {
719 		process_ctrl_request(task);
720 	} else {
721 		result = process_request(task);
722 		if (likely(result == 0)) {
723 			task_submit(task);
724 			SPDK_DEBUGLOG(vhost_scsi, "====== Task %p req_idx %d submitted ======\n", task,
725 				      task->req_idx);
726 		} else if (result > 0) {
727 			vhost_scsi_task_cpl(&task->scsi);
728 			SPDK_DEBUGLOG(vhost_scsi, "====== Task %p req_idx %d finished early ======\n", task,
729 				      task->req_idx);
730 		} else {
731 			invalid_request(task);
732 			SPDK_DEBUGLOG(vhost_scsi, "====== Task %p req_idx %d failed ======\n", task,
733 				      task->req_idx);
734 		}
735 	}
736 }
737 
738 static void
739 submit_inflight_desc(struct spdk_vhost_scsi_session *svsession,
740 		     struct spdk_vhost_virtqueue *vq)
741 {
742 	struct spdk_vhost_session *vsession = &svsession->vsession;
743 	spdk_vhost_resubmit_info *resubmit = vq->vring_inflight.resubmit_inflight;
744 	spdk_vhost_resubmit_desc *resubmit_list;
745 	uint16_t req_idx;
746 
747 	if (spdk_likely(resubmit == NULL || resubmit->resubmit_list == NULL)) {
748 		return;
749 	}
750 
751 	resubmit_list = resubmit->resubmit_list;
752 	while (resubmit->resubmit_num-- > 0) {
753 		req_idx = resubmit_list[resubmit->resubmit_num].index;
754 		SPDK_DEBUGLOG(vhost_scsi, "====== Start processing request idx %"PRIu16"======\n",
755 			      req_idx);
756 
757 		if (spdk_unlikely(req_idx >= vq->vring.size)) {
758 			SPDK_ERRLOG("%s: request idx '%"PRIu16"' exceeds virtqueue size (%"PRIu16").\n",
759 				    vsession->name, req_idx, vq->vring.size);
760 			vhost_vq_used_ring_enqueue(vsession, vq, req_idx, 0);
761 			continue;
762 		}
763 
764 		process_scsi_task(vsession, vq, req_idx);
765 	}
766 	/* reset the submit_num to 0 to avoid underflow. */
767 	resubmit->resubmit_num = 0;
768 
769 	free(resubmit_list);
770 	resubmit->resubmit_list = NULL;
771 }
772 
773 static void
774 process_vq(struct spdk_vhost_scsi_session *svsession, struct spdk_vhost_virtqueue *vq)
775 {
776 	struct spdk_vhost_session *vsession = &svsession->vsession;
777 	uint16_t reqs[32];
778 	uint16_t reqs_cnt, i;
779 
780 	submit_inflight_desc(svsession, vq);
781 
782 	reqs_cnt = vhost_vq_avail_ring_get(vq, reqs, SPDK_COUNTOF(reqs));
783 	assert(reqs_cnt <= 32);
784 
785 	for (i = 0; i < reqs_cnt; i++) {
786 		SPDK_DEBUGLOG(vhost_scsi, "====== Starting processing request idx %"PRIu16"======\n",
787 			      reqs[i]);
788 
789 		if (spdk_unlikely(reqs[i] >= vq->vring.size)) {
790 			SPDK_ERRLOG("%s: request idx '%"PRIu16"' exceeds virtqueue size (%"PRIu16").\n",
791 				    vsession->name, reqs[i], vq->vring.size);
792 			vhost_vq_used_ring_enqueue(vsession, vq, reqs[i], 0);
793 			continue;
794 		}
795 
796 		rte_vhost_set_inflight_desc_split(vsession->vid, vq->vring_idx, reqs[i]);
797 
798 		process_scsi_task(vsession, vq, reqs[i]);
799 	}
800 }
801 
802 static int
803 vdev_mgmt_worker(void *arg)
804 {
805 	struct spdk_vhost_scsi_session *svsession = arg;
806 	struct spdk_vhost_session *vsession = &svsession->vsession;
807 
808 	process_removed_devs(svsession);
809 
810 	if (vsession->virtqueue[VIRTIO_SCSI_EVENTQ].vring.desc) {
811 		vhost_vq_used_signal(vsession, &vsession->virtqueue[VIRTIO_SCSI_EVENTQ]);
812 	}
813 
814 	if (vsession->virtqueue[VIRTIO_SCSI_CONTROLQ].vring.desc) {
815 		process_vq(svsession, &vsession->virtqueue[VIRTIO_SCSI_CONTROLQ]);
816 		vhost_vq_used_signal(vsession, &vsession->virtqueue[VIRTIO_SCSI_CONTROLQ]);
817 	}
818 
819 	return SPDK_POLLER_BUSY;
820 }
821 
822 static int
823 vdev_worker(void *arg)
824 {
825 	struct spdk_vhost_scsi_session *svsession = arg;
826 	struct spdk_vhost_session *vsession = &svsession->vsession;
827 	uint32_t q_idx;
828 
829 	for (q_idx = VIRTIO_SCSI_REQUESTQ; q_idx < vsession->max_queues; q_idx++) {
830 		process_vq(svsession, &vsession->virtqueue[q_idx]);
831 	}
832 
833 	vhost_session_used_signal(vsession);
834 
835 	return SPDK_POLLER_BUSY;
836 }
837 
838 static struct spdk_vhost_scsi_dev *
839 to_scsi_dev(struct spdk_vhost_dev *ctrlr)
840 {
841 	if (ctrlr == NULL) {
842 		return NULL;
843 	}
844 
845 	if (ctrlr->backend != &spdk_vhost_scsi_device_backend) {
846 		SPDK_ERRLOG("%s: not a vhost-scsi device.\n", ctrlr->name);
847 		return NULL;
848 	}
849 
850 	return SPDK_CONTAINEROF(ctrlr, struct spdk_vhost_scsi_dev, vdev);
851 }
852 
853 static struct spdk_vhost_scsi_session *
854 to_scsi_session(struct spdk_vhost_session *vsession)
855 {
856 	assert(vsession->vdev->backend == &spdk_vhost_scsi_device_backend);
857 	return (struct spdk_vhost_scsi_session *)vsession;
858 }
859 
860 int
861 spdk_vhost_scsi_dev_construct(const char *name, const char *cpumask)
862 {
863 	struct spdk_vhost_scsi_dev *svdev = calloc(1, sizeof(*svdev));
864 	int rc;
865 
866 	if (svdev == NULL) {
867 		return -ENOMEM;
868 	}
869 
870 	svdev->vdev.virtio_features = SPDK_VHOST_SCSI_FEATURES;
871 	svdev->vdev.disabled_features = SPDK_VHOST_SCSI_DISABLED_FEATURES;
872 	svdev->vdev.protocol_features = SPDK_VHOST_SCSI_PROTOCOL_FEATURES;
873 
874 	spdk_vhost_lock();
875 	rc = vhost_dev_register(&svdev->vdev, name, cpumask,
876 				&spdk_vhost_scsi_device_backend);
877 
878 	if (rc) {
879 		free(svdev);
880 		spdk_vhost_unlock();
881 		return rc;
882 	}
883 
884 	svdev->registered = true;
885 
886 	spdk_vhost_unlock();
887 	return rc;
888 }
889 
890 static int
891 vhost_scsi_dev_remove(struct spdk_vhost_dev *vdev)
892 {
893 	struct spdk_vhost_scsi_dev *svdev = to_scsi_dev(vdev);
894 	int rc, i;
895 
896 	assert(svdev != NULL);
897 	for (i = 0; i < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; ++i) {
898 		if (svdev->scsi_dev_state[i].dev) {
899 			if (vdev->registered) {
900 				SPDK_ERRLOG("%s: SCSI target %d is still present.\n", vdev->name, i);
901 				return -EBUSY;
902 			}
903 
904 			rc = spdk_vhost_scsi_dev_remove_tgt(vdev, i, NULL, NULL);
905 			if (rc != 0) {
906 				SPDK_ERRLOG("%s: failed to force-remove target %d\n", vdev->name, i);
907 				return rc;
908 			}
909 		}
910 	}
911 
912 	rc = vhost_dev_unregister(vdev);
913 	if (rc != 0) {
914 		return rc;
915 	}
916 	svdev->registered = false;
917 
918 	if (svdev->ref == 0) {
919 		free(svdev);
920 	}
921 
922 	return 0;
923 }
924 
925 struct spdk_scsi_dev *
926 spdk_vhost_scsi_dev_get_tgt(struct spdk_vhost_dev *vdev, uint8_t num)
927 {
928 	struct spdk_vhost_scsi_dev *svdev;
929 
930 	assert(num < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS);
931 	svdev = to_scsi_dev(vdev);
932 	assert(svdev != NULL);
933 	if (svdev->scsi_dev_state[num].status != VHOST_SCSI_DEV_PRESENT) {
934 		return NULL;
935 	}
936 
937 	assert(svdev->scsi_dev_state[num].dev != NULL);
938 	return svdev->scsi_dev_state[num].dev;
939 }
940 
941 static unsigned
942 get_scsi_dev_num(const struct spdk_vhost_scsi_dev *svdev,
943 		 const struct spdk_scsi_lun *lun)
944 {
945 	const struct spdk_scsi_dev *scsi_dev;
946 	unsigned scsi_dev_num;
947 
948 	assert(lun != NULL);
949 	assert(svdev != NULL);
950 	scsi_dev = spdk_scsi_lun_get_dev(lun);
951 	for (scsi_dev_num = 0; scsi_dev_num < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; scsi_dev_num++) {
952 		if (svdev->scsi_dev_state[scsi_dev_num].dev == scsi_dev) {
953 			break;
954 		}
955 	}
956 
957 	return scsi_dev_num;
958 }
959 
960 static void
961 vhost_scsi_lun_resize(const struct spdk_scsi_lun *lun, void *arg)
962 {
963 	struct spdk_vhost_scsi_dev *svdev = arg;
964 	unsigned scsi_dev_num;
965 
966 	scsi_dev_num = get_scsi_dev_num(svdev, lun);
967 	if (scsi_dev_num == SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
968 		/* The entire device has been already removed. */
969 		return;
970 	}
971 
972 	vhost_scsi_dev_param_changed(&svdev->vdev, scsi_dev_num);
973 }
974 
975 static void
976 vhost_scsi_lun_hotremove(const struct spdk_scsi_lun *lun, void *arg)
977 {
978 	struct spdk_vhost_scsi_dev *svdev = arg;
979 	unsigned scsi_dev_num;
980 
981 	scsi_dev_num = get_scsi_dev_num(svdev, lun);
982 	if (scsi_dev_num == SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
983 		/* The entire device has been already removed. */
984 		return;
985 	}
986 
987 	/* remove entire device */
988 	spdk_vhost_scsi_dev_remove_tgt(&svdev->vdev, scsi_dev_num, NULL, NULL);
989 }
990 
991 static void
992 vhost_scsi_dev_add_tgt_cpl_cb(struct spdk_vhost_dev *vdev, void *ctx)
993 {
994 	unsigned scsi_tgt_num = (unsigned)(uintptr_t)ctx;
995 	struct spdk_vhost_scsi_dev *svdev = SPDK_CONTAINEROF(vdev,
996 					    struct spdk_vhost_scsi_dev, vdev);
997 	struct spdk_scsi_dev_vhost_state *vhost_sdev;
998 
999 	vhost_sdev = &svdev->scsi_dev_state[scsi_tgt_num];
1000 
1001 	/* All sessions have added the target */
1002 	assert(vhost_sdev->status == VHOST_SCSI_DEV_ADDING);
1003 	vhost_sdev->status = VHOST_SCSI_DEV_PRESENT;
1004 	svdev->ref++;
1005 }
1006 
1007 static int
1008 vhost_scsi_session_add_tgt(struct spdk_vhost_dev *vdev,
1009 			   struct spdk_vhost_session *vsession, void *ctx)
1010 {
1011 	unsigned scsi_tgt_num = (unsigned)(uintptr_t)ctx;
1012 	struct spdk_vhost_scsi_session *svsession = (struct spdk_vhost_scsi_session *)vsession;
1013 	struct spdk_scsi_dev_session_state *session_sdev = &svsession->scsi_dev_state[scsi_tgt_num];
1014 	struct spdk_scsi_dev_vhost_state *vhost_sdev;
1015 	int rc;
1016 
1017 	if (!vsession->started || session_sdev->dev != NULL) {
1018 		/* Nothing to do. */
1019 		return 0;
1020 	}
1021 
1022 	vhost_sdev = &svsession->svdev->scsi_dev_state[scsi_tgt_num];
1023 	session_sdev->dev = vhost_sdev->dev;
1024 	session_sdev->status = VHOST_SCSI_DEV_PRESENT;
1025 
1026 	rc = spdk_scsi_dev_allocate_io_channels(svsession->scsi_dev_state[scsi_tgt_num].dev);
1027 	if (rc != 0) {
1028 		SPDK_ERRLOG("%s: Couldn't allocate io channnel for SCSI target %u.\n",
1029 			    vsession->name, scsi_tgt_num);
1030 
1031 		/* unset the SCSI target so that all I/O to it will be rejected */
1032 		session_sdev->dev = NULL;
1033 		/* Set status to EMPTY so that we won't reply with SCSI hotremove
1034 		 * sense codes - the device hasn't ever been added.
1035 		 */
1036 		session_sdev->status = VHOST_SCSI_DEV_EMPTY;
1037 
1038 		/* Return with no error. We'll continue allocating io_channels for
1039 		 * other sessions on this device in hopes they succeed. The sessions
1040 		 * that failed to allocate io_channels simply won't be able to
1041 		 * detect the SCSI target, nor do any I/O to it.
1042 		 */
1043 		return 0;
1044 	}
1045 
1046 	if (vhost_dev_has_feature(vsession, VIRTIO_SCSI_F_HOTPLUG)) {
1047 		eventq_enqueue(svsession, scsi_tgt_num,
1048 			       VIRTIO_SCSI_T_TRANSPORT_RESET, VIRTIO_SCSI_EVT_RESET_RESCAN);
1049 	} else {
1050 		SPDK_NOTICELOG("%s: driver does not support hotplug. "
1051 			       "Please restart it or perform a rescan.\n",
1052 			       vsession->name);
1053 	}
1054 
1055 	return 0;
1056 }
1057 
1058 int
1059 spdk_vhost_scsi_dev_add_tgt(struct spdk_vhost_dev *vdev, int scsi_tgt_num,
1060 			    const char *bdev_name)
1061 {
1062 	struct spdk_vhost_scsi_dev *svdev;
1063 	struct spdk_scsi_dev_vhost_state *state;
1064 	char target_name[SPDK_SCSI_DEV_MAX_NAME];
1065 	int lun_id_list[1];
1066 	const char *bdev_names_list[1];
1067 
1068 	svdev = to_scsi_dev(vdev);
1069 	if (!svdev) {
1070 		SPDK_ERRLOG("Before adding a SCSI target, there should be a SCSI device.");
1071 		return -EINVAL;
1072 	}
1073 
1074 	if (scsi_tgt_num < 0) {
1075 		for (scsi_tgt_num = 0; scsi_tgt_num < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; scsi_tgt_num++) {
1076 			if (svdev->scsi_dev_state[scsi_tgt_num].dev == NULL) {
1077 				break;
1078 			}
1079 		}
1080 
1081 		if (scsi_tgt_num == SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
1082 			SPDK_ERRLOG("%s: all SCSI target slots are already in use.\n", vdev->name);
1083 			return -ENOSPC;
1084 		}
1085 	} else {
1086 		if (scsi_tgt_num >= SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
1087 			SPDK_ERRLOG("%s: SCSI target number is too big (got %d, max %d)\n",
1088 				    vdev->name, scsi_tgt_num, SPDK_VHOST_SCSI_CTRLR_MAX_DEVS);
1089 			return -EINVAL;
1090 		}
1091 	}
1092 
1093 	if (bdev_name == NULL) {
1094 		SPDK_ERRLOG("No lun name specified\n");
1095 		return -EINVAL;
1096 	}
1097 
1098 	state = &svdev->scsi_dev_state[scsi_tgt_num];
1099 	if (state->dev != NULL) {
1100 		SPDK_ERRLOG("%s: SCSI target %u already occupied\n", vdev->name, scsi_tgt_num);
1101 		return -EEXIST;
1102 	}
1103 
1104 	/*
1105 	 * At this stage only one LUN per target
1106 	 */
1107 	snprintf(target_name, sizeof(target_name), "Target %u", scsi_tgt_num);
1108 	lun_id_list[0] = 0;
1109 	bdev_names_list[0] = (char *)bdev_name;
1110 
1111 	state->status = VHOST_SCSI_DEV_ADDING;
1112 	state->dev = spdk_scsi_dev_construct_ext(target_name, bdev_names_list, lun_id_list, 1,
1113 			SPDK_SPC_PROTOCOL_IDENTIFIER_SAS,
1114 			vhost_scsi_lun_resize, svdev,
1115 			vhost_scsi_lun_hotremove, svdev);
1116 
1117 	if (state->dev == NULL) {
1118 		state->status = VHOST_SCSI_DEV_EMPTY;
1119 		SPDK_ERRLOG("%s: couldn't create SCSI target %u using bdev '%s'\n",
1120 			    vdev->name, scsi_tgt_num, bdev_name);
1121 		return -EINVAL;
1122 	}
1123 	spdk_scsi_dev_add_port(state->dev, 0, "vhost");
1124 
1125 	SPDK_INFOLOG(vhost, "%s: added SCSI target %u using bdev '%s'\n",
1126 		     vdev->name, scsi_tgt_num, bdev_name);
1127 
1128 	vhost_dev_foreach_session(vdev, vhost_scsi_session_add_tgt,
1129 				  vhost_scsi_dev_add_tgt_cpl_cb,
1130 				  (void *)(uintptr_t)scsi_tgt_num);
1131 	return scsi_tgt_num;
1132 }
1133 
1134 struct scsi_tgt_hotplug_ctx {
1135 	unsigned scsi_tgt_num;
1136 	bool async_fini;
1137 };
1138 
1139 static void
1140 vhost_scsi_dev_remove_tgt_cpl_cb(struct spdk_vhost_dev *vdev, void *_ctx)
1141 {
1142 	struct scsi_tgt_hotplug_ctx *ctx = _ctx;
1143 	struct spdk_vhost_scsi_dev *svdev = SPDK_CONTAINEROF(vdev,
1144 					    struct spdk_vhost_scsi_dev, vdev);
1145 
1146 	if (!ctx->async_fini) {
1147 		/* there aren't any active sessions, so remove the dev and exit */
1148 		remove_scsi_tgt(svdev, ctx->scsi_tgt_num);
1149 	}
1150 
1151 	free(ctx);
1152 }
1153 
1154 static int
1155 vhost_scsi_session_remove_tgt(struct spdk_vhost_dev *vdev,
1156 			      struct spdk_vhost_session *vsession, void *_ctx)
1157 {
1158 	struct scsi_tgt_hotplug_ctx *ctx = _ctx;
1159 	unsigned scsi_tgt_num = ctx->scsi_tgt_num;
1160 	struct spdk_vhost_scsi_session *svsession = (struct spdk_vhost_scsi_session *)vsession;
1161 	struct spdk_scsi_dev_session_state *state = &svsession->scsi_dev_state[scsi_tgt_num];
1162 
1163 	if (!vsession->started || state->dev == NULL) {
1164 		/* Nothing to do */
1165 		return 0;
1166 	}
1167 
1168 	/* Mark the target for removal */
1169 	assert(state->status == VHOST_SCSI_DEV_PRESENT);
1170 	state->status = VHOST_SCSI_DEV_REMOVING;
1171 
1172 	/* Send a hotremove virtio event */
1173 	if (vhost_dev_has_feature(vsession, VIRTIO_SCSI_F_HOTPLUG)) {
1174 		eventq_enqueue(svsession, scsi_tgt_num,
1175 			       VIRTIO_SCSI_T_TRANSPORT_RESET, VIRTIO_SCSI_EVT_RESET_REMOVED);
1176 	}
1177 
1178 	/* Wait for the session's management poller to remove the target after
1179 	 * all its pending I/O has finished.
1180 	 */
1181 	ctx->async_fini = true;
1182 	return 0;
1183 }
1184 
1185 int
1186 spdk_vhost_scsi_dev_remove_tgt(struct spdk_vhost_dev *vdev, unsigned scsi_tgt_num,
1187 			       spdk_vhost_event_fn cb_fn, void *cb_arg)
1188 {
1189 	struct spdk_vhost_scsi_dev *svdev;
1190 	struct spdk_scsi_dev_vhost_state *scsi_dev_state;
1191 	struct scsi_tgt_hotplug_ctx *ctx;
1192 
1193 	if (scsi_tgt_num >= SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
1194 		SPDK_ERRLOG("%s: invalid SCSI target number %d\n", vdev->name, scsi_tgt_num);
1195 		return -EINVAL;
1196 	}
1197 
1198 	svdev = to_scsi_dev(vdev);
1199 	if (!svdev) {
1200 		SPDK_ERRLOG("An invalid SCSI device that removing from a SCSI target.");
1201 		return -EINVAL;
1202 	}
1203 
1204 	scsi_dev_state = &svdev->scsi_dev_state[scsi_tgt_num];
1205 
1206 	if (scsi_dev_state->status != VHOST_SCSI_DEV_PRESENT) {
1207 		return -EBUSY;
1208 	}
1209 
1210 	if (scsi_dev_state->dev == NULL || scsi_dev_state->status == VHOST_SCSI_DEV_ADDING) {
1211 		SPDK_ERRLOG("%s: SCSI target %u is not occupied\n", vdev->name, scsi_tgt_num);
1212 		return -ENODEV;
1213 	}
1214 
1215 	assert(scsi_dev_state->status != VHOST_SCSI_DEV_EMPTY);
1216 	ctx = calloc(1, sizeof(*ctx));
1217 	if (ctx == NULL) {
1218 		SPDK_ERRLOG("calloc failed\n");
1219 		return -ENOMEM;
1220 	}
1221 
1222 	ctx->scsi_tgt_num = scsi_tgt_num;
1223 	ctx->async_fini = false;
1224 
1225 	scsi_dev_state->remove_cb = cb_fn;
1226 	scsi_dev_state->remove_ctx = cb_arg;
1227 	scsi_dev_state->status = VHOST_SCSI_DEV_REMOVING;
1228 
1229 	vhost_dev_foreach_session(vdev, vhost_scsi_session_remove_tgt,
1230 				  vhost_scsi_dev_remove_tgt_cpl_cb, ctx);
1231 	return 0;
1232 }
1233 
1234 static int
1235 vhost_scsi_session_param_changed(struct spdk_vhost_dev *vdev,
1236 				 struct spdk_vhost_session *vsession, void *ctx)
1237 {
1238 	unsigned scsi_tgt_num = (unsigned)(uintptr_t)ctx;
1239 	struct spdk_vhost_scsi_session *svsession = (struct spdk_vhost_scsi_session *)vsession;
1240 	struct spdk_scsi_dev_session_state *state = &svsession->scsi_dev_state[scsi_tgt_num];
1241 
1242 	if (!vsession->started || state->dev == NULL) {
1243 		/* Nothing to do */
1244 		return 0;
1245 	}
1246 
1247 	/* Send a parameter change virtio event */
1248 	if (vhost_dev_has_feature(vsession, VIRTIO_SCSI_F_CHANGE)) {
1249 		/*
1250 		 * virtio 1.0 spec says:
1251 		 * By sending this event, the device signals a change in the configuration
1252 		 * parameters of a logical unit, for example the capacity or cache mode.
1253 		 * event is set to VIRTIO_SCSI_T_PARAM_CHANGE. lun addresses a logical unit
1254 		 * in the SCSI host. The same event SHOULD also be reported as a unit
1255 		 * attention condition. reason contains the additional sense code and
1256 		 * additional sense code qualifier, respectively in bits 0…7 and 8…15.
1257 		 * Note: For example, a change in * capacity will be reported as asc
1258 		 * 0x2a, ascq 0x09 (CAPACITY DATA HAS CHANGED).
1259 		 */
1260 		eventq_enqueue(svsession, scsi_tgt_num, VIRTIO_SCSI_T_PARAM_CHANGE, 0x2a | (0x09 << 8));
1261 	}
1262 
1263 	return 0;
1264 }
1265 
1266 static int
1267 vhost_scsi_dev_param_changed(struct spdk_vhost_dev *vdev, unsigned scsi_tgt_num)
1268 {
1269 	struct spdk_vhost_scsi_dev *svdev;
1270 	struct spdk_scsi_dev_vhost_state *scsi_dev_state;
1271 
1272 	if (scsi_tgt_num >= SPDK_VHOST_SCSI_CTRLR_MAX_DEVS) {
1273 		SPDK_ERRLOG("%s: invalid SCSI target number %d\n", vdev->name, scsi_tgt_num);
1274 		return -EINVAL;
1275 	}
1276 
1277 	svdev = to_scsi_dev(vdev);
1278 	if (!svdev) {
1279 		SPDK_ERRLOG("An invalid SCSI device that removing from a SCSI target.");
1280 		return -EINVAL;
1281 	}
1282 
1283 	scsi_dev_state = &svdev->scsi_dev_state[scsi_tgt_num];
1284 
1285 	if (scsi_dev_state->status != VHOST_SCSI_DEV_PRESENT) {
1286 		return -EBUSY;
1287 	}
1288 
1289 	if (scsi_dev_state->dev == NULL || scsi_dev_state->status == VHOST_SCSI_DEV_ADDING) {
1290 		SPDK_ERRLOG("%s: SCSI target %u is not occupied\n", vdev->name, scsi_tgt_num);
1291 		return -ENODEV;
1292 	}
1293 
1294 	assert(scsi_dev_state->status != VHOST_SCSI_DEV_EMPTY);
1295 
1296 	vhost_dev_foreach_session(vdev, vhost_scsi_session_param_changed,
1297 				  NULL, (void *)(uintptr_t)scsi_tgt_num);
1298 	return 0;
1299 }
1300 
1301 static void
1302 free_task_pool(struct spdk_vhost_scsi_session *svsession)
1303 {
1304 	struct spdk_vhost_session *vsession = &svsession->vsession;
1305 	struct spdk_vhost_virtqueue *vq;
1306 	uint16_t i;
1307 
1308 	for (i = 0; i < vsession->max_queues; i++) {
1309 		vq = &vsession->virtqueue[i];
1310 		if (vq->tasks == NULL) {
1311 			continue;
1312 		}
1313 
1314 		spdk_free(vq->tasks);
1315 		vq->tasks = NULL;
1316 	}
1317 }
1318 
1319 static int
1320 alloc_task_pool(struct spdk_vhost_scsi_session *svsession)
1321 {
1322 	struct spdk_vhost_session *vsession = &svsession->vsession;
1323 	struct spdk_vhost_virtqueue *vq;
1324 	struct spdk_vhost_scsi_task *task;
1325 	uint32_t task_cnt;
1326 	uint16_t i;
1327 	uint32_t j;
1328 
1329 	for (i = 0; i < vsession->max_queues; i++) {
1330 		vq = &vsession->virtqueue[i];
1331 		if (vq->vring.desc == NULL) {
1332 			continue;
1333 		}
1334 
1335 		task_cnt = vq->vring.size;
1336 		if (task_cnt > SPDK_VHOST_MAX_VQ_SIZE) {
1337 			/* sanity check */
1338 			SPDK_ERRLOG("%s: virtuque %"PRIu16" is too big. (size = %"PRIu32", max = %"PRIu32")\n",
1339 				    vsession->name, i, task_cnt, SPDK_VHOST_MAX_VQ_SIZE);
1340 			free_task_pool(svsession);
1341 			return -1;
1342 		}
1343 		vq->tasks = spdk_zmalloc(sizeof(struct spdk_vhost_scsi_task) * task_cnt,
1344 					 SPDK_CACHE_LINE_SIZE, NULL,
1345 					 SPDK_ENV_LCORE_ID_ANY, SPDK_MALLOC_DMA);
1346 		if (vq->tasks == NULL) {
1347 			SPDK_ERRLOG("%s: failed to allocate %"PRIu32" tasks for virtqueue %"PRIu16"\n",
1348 				    vsession->name, task_cnt, i);
1349 			free_task_pool(svsession);
1350 			return -1;
1351 		}
1352 
1353 		for (j = 0; j < task_cnt; j++) {
1354 			task = &((struct spdk_vhost_scsi_task *)vq->tasks)[j];
1355 			task->svsession = svsession;
1356 			task->vq = vq;
1357 			task->req_idx = j;
1358 		}
1359 	}
1360 
1361 	return 0;
1362 }
1363 
1364 static int
1365 vhost_scsi_start_cb(struct spdk_vhost_dev *vdev,
1366 		    struct spdk_vhost_session *vsession, void *unused)
1367 {
1368 	struct spdk_vhost_scsi_session *svsession = to_scsi_session(vsession);
1369 	struct spdk_vhost_scsi_dev *svdev = svsession->svdev;
1370 	struct spdk_scsi_dev_vhost_state *state;
1371 	uint32_t i;
1372 	int rc;
1373 
1374 	/* validate all I/O queues are in a contiguous index range */
1375 	for (i = VIRTIO_SCSI_REQUESTQ; i < vsession->max_queues; i++) {
1376 		if (vsession->virtqueue[i].vring.desc == NULL) {
1377 			SPDK_ERRLOG("%s: queue %"PRIu32" is empty\n", vsession->name, i);
1378 			rc = -1;
1379 			goto out;
1380 		}
1381 	}
1382 
1383 	rc = alloc_task_pool(svsession);
1384 	if (rc != 0) {
1385 		SPDK_ERRLOG("%s: failed to alloc task pool.\n", vsession->name);
1386 		goto out;
1387 	}
1388 
1389 	for (i = 0; i < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; i++) {
1390 		state = &svdev->scsi_dev_state[i];
1391 		if (state->dev == NULL || state->status == VHOST_SCSI_DEV_REMOVING) {
1392 			continue;
1393 		}
1394 
1395 		assert(svsession->scsi_dev_state[i].status == VHOST_SCSI_DEV_EMPTY);
1396 		svsession->scsi_dev_state[i].dev = state->dev;
1397 		svsession->scsi_dev_state[i].status = VHOST_SCSI_DEV_PRESENT;
1398 		rc = spdk_scsi_dev_allocate_io_channels(state->dev);
1399 		if (rc != 0) {
1400 			SPDK_ERRLOG("%s: failed to alloc io_channel for SCSI target %"PRIu32"\n",
1401 				    vsession->name, i);
1402 			/* unset the SCSI target so that all I/O to it will be rejected */
1403 			svsession->scsi_dev_state[i].dev = NULL;
1404 			/* set EMPTY state so that we won't reply with SCSI hotremove
1405 			 * sense codes - the device hasn't ever been added.
1406 			 */
1407 			svsession->scsi_dev_state[i].status = VHOST_SCSI_DEV_EMPTY;
1408 			continue;
1409 		}
1410 	}
1411 	SPDK_INFOLOG(vhost, "%s: started poller on lcore %d\n",
1412 		     vsession->name, spdk_env_get_current_core());
1413 
1414 	svsession->requestq_poller = SPDK_POLLER_REGISTER(vdev_worker, svsession, 0);
1415 	svsession->mgmt_poller = SPDK_POLLER_REGISTER(vdev_mgmt_worker, svsession,
1416 				 MGMT_POLL_PERIOD_US);
1417 out:
1418 	vhost_session_start_done(vsession, rc);
1419 	return rc;
1420 }
1421 
1422 static int
1423 vhost_scsi_start(struct spdk_vhost_session *vsession)
1424 {
1425 	struct spdk_vhost_scsi_session *svsession = to_scsi_session(vsession);
1426 	struct spdk_vhost_scsi_dev *svdev;
1427 
1428 	svdev = to_scsi_dev(vsession->vdev);
1429 	assert(svdev != NULL);
1430 	svsession->svdev = svdev;
1431 
1432 	return vhost_session_send_event(vsession, vhost_scsi_start_cb,
1433 					3, "start session");
1434 }
1435 
1436 static int
1437 destroy_session_poller_cb(void *arg)
1438 {
1439 	struct spdk_vhost_scsi_session *svsession = arg;
1440 	struct spdk_vhost_session *vsession = &svsession->vsession;
1441 	struct spdk_scsi_dev_session_state *state;
1442 	uint32_t i;
1443 
1444 	if (vsession->task_cnt > 0) {
1445 		return SPDK_POLLER_BUSY;
1446 	}
1447 
1448 	if (spdk_vhost_trylock() != 0) {
1449 		return SPDK_POLLER_BUSY;
1450 	}
1451 
1452 	for (i = 0; i < vsession->max_queues; i++) {
1453 		vhost_vq_used_signal(vsession, &vsession->virtqueue[i]);
1454 	}
1455 
1456 	for (i = 0; i < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; i++) {
1457 		enum spdk_scsi_dev_vhost_status prev_status;
1458 
1459 		state = &svsession->scsi_dev_state[i];
1460 		/* clear the REMOVED status so that we won't send hotremove events anymore */
1461 		prev_status = state->status;
1462 		state->status = VHOST_SCSI_DEV_EMPTY;
1463 		if (state->dev == NULL) {
1464 			continue;
1465 		}
1466 
1467 		spdk_scsi_dev_free_io_channels(state->dev);
1468 
1469 		state->dev = NULL;
1470 
1471 		if (prev_status == VHOST_SCSI_DEV_REMOVING) {
1472 			/* try to detach it globally */
1473 			vhost_dev_foreach_session(vsession->vdev,
1474 						  vhost_scsi_session_process_removed,
1475 						  vhost_scsi_dev_process_removed_cpl_cb,
1476 						  (void *)(uintptr_t)i);
1477 		}
1478 	}
1479 
1480 	SPDK_INFOLOG(vhost, "%s: stopping poller on lcore %d\n",
1481 		     vsession->name, spdk_env_get_current_core());
1482 
1483 	free_task_pool(svsession);
1484 
1485 	spdk_poller_unregister(&svsession->stop_poller);
1486 	vhost_session_stop_done(vsession, 0);
1487 
1488 	spdk_vhost_unlock();
1489 	return SPDK_POLLER_BUSY;
1490 }
1491 
1492 static int
1493 vhost_scsi_stop_cb(struct spdk_vhost_dev *vdev,
1494 		   struct spdk_vhost_session *vsession, void *unused)
1495 {
1496 	struct spdk_vhost_scsi_session *svsession = to_scsi_session(vsession);
1497 
1498 	/* Stop receiving new I/O requests */
1499 	spdk_poller_unregister(&svsession->requestq_poller);
1500 
1501 	/* Stop receiving controlq requests, also stop processing the
1502 	 * asynchronous hotremove events. All the remaining events
1503 	 * will be finalized by the stop_poller below.
1504 	 */
1505 	spdk_poller_unregister(&svsession->mgmt_poller);
1506 
1507 	/* Wait for all pending I/Os to complete, then process all the
1508 	 * remaining hotremove events one last time.
1509 	 */
1510 	svsession->stop_poller = SPDK_POLLER_REGISTER(destroy_session_poller_cb,
1511 				 svsession, 1000);
1512 
1513 	return 0;
1514 }
1515 
1516 static int
1517 vhost_scsi_stop(struct spdk_vhost_session *vsession)
1518 {
1519 	return vhost_session_send_event(vsession, vhost_scsi_stop_cb,
1520 					3, "stop session");
1521 }
1522 
1523 static void
1524 vhost_scsi_dump_info_json(struct spdk_vhost_dev *vdev, struct spdk_json_write_ctx *w)
1525 {
1526 	struct spdk_scsi_dev *sdev;
1527 	struct spdk_scsi_lun *lun;
1528 	uint32_t dev_idx;
1529 
1530 	assert(vdev != NULL);
1531 	spdk_json_write_named_array_begin(w, "scsi");
1532 	for (dev_idx = 0; dev_idx < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; dev_idx++) {
1533 		sdev = spdk_vhost_scsi_dev_get_tgt(vdev, dev_idx);
1534 		if (!sdev) {
1535 			continue;
1536 		}
1537 
1538 		spdk_json_write_object_begin(w);
1539 
1540 		spdk_json_write_named_uint32(w, "scsi_dev_num", dev_idx);
1541 
1542 		spdk_json_write_named_uint32(w, "id", spdk_scsi_dev_get_id(sdev));
1543 
1544 		spdk_json_write_named_string(w, "target_name", spdk_scsi_dev_get_name(sdev));
1545 
1546 		spdk_json_write_named_array_begin(w, "luns");
1547 
1548 		for (lun = spdk_scsi_dev_get_first_lun(sdev); lun != NULL;
1549 		     lun = spdk_scsi_dev_get_next_lun(lun)) {
1550 			spdk_json_write_object_begin(w);
1551 
1552 			spdk_json_write_named_int32(w, "id", spdk_scsi_lun_get_id(lun));
1553 
1554 			spdk_json_write_named_string(w, "bdev_name", spdk_scsi_lun_get_bdev_name(lun));
1555 
1556 			spdk_json_write_object_end(w);
1557 		}
1558 
1559 		spdk_json_write_array_end(w);
1560 		spdk_json_write_object_end(w);
1561 	}
1562 
1563 	spdk_json_write_array_end(w);
1564 }
1565 
1566 static void
1567 vhost_scsi_write_config_json(struct spdk_vhost_dev *vdev, struct spdk_json_write_ctx *w)
1568 {
1569 	struct spdk_scsi_dev *scsi_dev;
1570 	struct spdk_scsi_lun *lun;
1571 	uint32_t i;
1572 
1573 	spdk_json_write_object_begin(w);
1574 	spdk_json_write_named_string(w, "method", "vhost_create_scsi_controller");
1575 
1576 	spdk_json_write_named_object_begin(w, "params");
1577 	spdk_json_write_named_string(w, "ctrlr", vdev->name);
1578 	spdk_json_write_named_string(w, "cpumask",
1579 				     spdk_cpuset_fmt(spdk_thread_get_cpumask(vdev->thread)));
1580 	spdk_json_write_object_end(w);
1581 
1582 	spdk_json_write_object_end(w);
1583 
1584 	for (i = 0; i < SPDK_VHOST_SCSI_CTRLR_MAX_DEVS; i++) {
1585 		scsi_dev = spdk_vhost_scsi_dev_get_tgt(vdev, i);
1586 		if (scsi_dev == NULL) {
1587 			continue;
1588 		}
1589 
1590 		lun = spdk_scsi_dev_get_lun(scsi_dev, 0);
1591 		assert(lun != NULL);
1592 
1593 		spdk_json_write_object_begin(w);
1594 		spdk_json_write_named_string(w, "method", "vhost_scsi_controller_add_target");
1595 
1596 		spdk_json_write_named_object_begin(w, "params");
1597 		spdk_json_write_named_string(w, "ctrlr", vdev->name);
1598 		spdk_json_write_named_uint32(w, "scsi_target_num", i);
1599 
1600 		spdk_json_write_named_string(w, "bdev_name", spdk_scsi_lun_get_bdev_name(lun));
1601 		spdk_json_write_object_end(w);
1602 
1603 		spdk_json_write_object_end(w);
1604 	}
1605 }
1606 
1607 SPDK_LOG_REGISTER_COMPONENT(vhost_scsi)
1608 SPDK_LOG_REGISTER_COMPONENT(vhost_scsi_queue)
1609 SPDK_LOG_REGISTER_COMPONENT(vhost_scsi_data)
1610