]> Pileus Git - ~andy/linux/blob - drivers/vhost/tcm_vhost.c
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/sparc
[~andy/linux] / drivers / vhost / tcm_vhost.c
1 /*******************************************************************************
2  * Vhost kernel TCM fabric driver for virtio SCSI initiators
3  *
4  * (C) Copyright 2010-2012 RisingTide Systems LLC.
5  * (C) Copyright 2010-2012 IBM Corp.
6  *
7  * Licensed to the Linux Foundation under the General Public License (GPL) version 2.
8  *
9  * Authors: Nicholas A. Bellinger <nab@risingtidesystems.com>
10  *          Stefan Hajnoczi <stefanha@linux.vnet.ibm.com>
11  *
12  * This program is free software; you can redistribute it and/or modify
13  * it under the terms of the GNU General Public License as published by
14  * the Free Software Foundation; either version 2 of the License, or
15  * (at your option) any later version.
16  *
17  * This program is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20  * GNU General Public License for more details.
21  *
22  ****************************************************************************/
23
24 #include <linux/module.h>
25 #include <linux/moduleparam.h>
26 #include <generated/utsrelease.h>
27 #include <linux/utsname.h>
28 #include <linux/init.h>
29 #include <linux/slab.h>
30 #include <linux/kthread.h>
31 #include <linux/types.h>
32 #include <linux/string.h>
33 #include <linux/configfs.h>
34 #include <linux/ctype.h>
35 #include <linux/compat.h>
36 #include <linux/eventfd.h>
37 #include <linux/vhost.h>
38 #include <linux/fs.h>
39 #include <linux/miscdevice.h>
40 #include <asm/unaligned.h>
41 #include <scsi/scsi.h>
42 #include <scsi/scsi_tcq.h>
43 #include <target/target_core_base.h>
44 #include <target/target_core_fabric.h>
45 #include <target/target_core_fabric_configfs.h>
46 #include <target/target_core_configfs.h>
47 #include <target/configfs_macros.h>
48 #include <linux/vhost.h>
49 #include <linux/virtio_net.h> /* TODO vhost.h currently depends on this */
50 #include <linux/virtio_scsi.h>
51
52 #include "vhost.c"
53 #include "vhost.h"
54 #include "tcm_vhost.h"
55
56 struct vhost_scsi {
57         atomic_t vhost_ref_cnt;
58         struct tcm_vhost_tpg *vs_tpg;
59         struct vhost_dev dev;
60         struct vhost_virtqueue vqs[3];
61
62         struct vhost_work vs_completion_work; /* cmd completion work item */
63         struct list_head vs_completion_list;  /* cmd completion queue */
64         spinlock_t vs_completion_lock;        /* protects s_completion_list */
65 };
66
67 /* Local pointer to allocated TCM configfs fabric module */
68 static struct target_fabric_configfs *tcm_vhost_fabric_configfs;
69
70 static struct workqueue_struct *tcm_vhost_workqueue;
71
72 /* Global spinlock to protect tcm_vhost TPG list for vhost IOCTL access */
73 static DEFINE_MUTEX(tcm_vhost_mutex);
74 static LIST_HEAD(tcm_vhost_list);
75
76 static int tcm_vhost_check_true(struct se_portal_group *se_tpg)
77 {
78         return 1;
79 }
80
81 static int tcm_vhost_check_false(struct se_portal_group *se_tpg)
82 {
83         return 0;
84 }
85
86 static char *tcm_vhost_get_fabric_name(void)
87 {
88         return "vhost";
89 }
90
91 static u8 tcm_vhost_get_fabric_proto_ident(struct se_portal_group *se_tpg)
92 {
93         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
94                                 struct tcm_vhost_tpg, se_tpg);
95         struct tcm_vhost_tport *tport = tpg->tport;
96
97         switch (tport->tport_proto_id) {
98         case SCSI_PROTOCOL_SAS:
99                 return sas_get_fabric_proto_ident(se_tpg);
100         case SCSI_PROTOCOL_FCP:
101                 return fc_get_fabric_proto_ident(se_tpg);
102         case SCSI_PROTOCOL_ISCSI:
103                 return iscsi_get_fabric_proto_ident(se_tpg);
104         default:
105                 pr_err("Unknown tport_proto_id: 0x%02x, using"
106                         " SAS emulation\n", tport->tport_proto_id);
107                 break;
108         }
109
110         return sas_get_fabric_proto_ident(se_tpg);
111 }
112
113 static char *tcm_vhost_get_fabric_wwn(struct se_portal_group *se_tpg)
114 {
115         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
116                                 struct tcm_vhost_tpg, se_tpg);
117         struct tcm_vhost_tport *tport = tpg->tport;
118
119         return &tport->tport_name[0];
120 }
121
122 static u16 tcm_vhost_get_tag(struct se_portal_group *se_tpg)
123 {
124         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
125                                 struct tcm_vhost_tpg, se_tpg);
126         return tpg->tport_tpgt;
127 }
128
129 static u32 tcm_vhost_get_default_depth(struct se_portal_group *se_tpg)
130 {
131         return 1;
132 }
133
134 static u32 tcm_vhost_get_pr_transport_id(
135         struct se_portal_group *se_tpg,
136         struct se_node_acl *se_nacl,
137         struct t10_pr_registration *pr_reg,
138         int *format_code,
139         unsigned char *buf)
140 {
141         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
142                                 struct tcm_vhost_tpg, se_tpg);
143         struct tcm_vhost_tport *tport = tpg->tport;
144
145         switch (tport->tport_proto_id) {
146         case SCSI_PROTOCOL_SAS:
147                 return sas_get_pr_transport_id(se_tpg, se_nacl, pr_reg,
148                                         format_code, buf);
149         case SCSI_PROTOCOL_FCP:
150                 return fc_get_pr_transport_id(se_tpg, se_nacl, pr_reg,
151                                         format_code, buf);
152         case SCSI_PROTOCOL_ISCSI:
153                 return iscsi_get_pr_transport_id(se_tpg, se_nacl, pr_reg,
154                                         format_code, buf);
155         default:
156                 pr_err("Unknown tport_proto_id: 0x%02x, using"
157                         " SAS emulation\n", tport->tport_proto_id);
158                 break;
159         }
160
161         return sas_get_pr_transport_id(se_tpg, se_nacl, pr_reg,
162                         format_code, buf);
163 }
164
165 static u32 tcm_vhost_get_pr_transport_id_len(
166         struct se_portal_group *se_tpg,
167         struct se_node_acl *se_nacl,
168         struct t10_pr_registration *pr_reg,
169         int *format_code)
170 {
171         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
172                                 struct tcm_vhost_tpg, se_tpg);
173         struct tcm_vhost_tport *tport = tpg->tport;
174
175         switch (tport->tport_proto_id) {
176         case SCSI_PROTOCOL_SAS:
177                 return sas_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg,
178                                         format_code);
179         case SCSI_PROTOCOL_FCP:
180                 return fc_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg,
181                                         format_code);
182         case SCSI_PROTOCOL_ISCSI:
183                 return iscsi_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg,
184                                         format_code);
185         default:
186                 pr_err("Unknown tport_proto_id: 0x%02x, using"
187                         " SAS emulation\n", tport->tport_proto_id);
188                 break;
189         }
190
191         return sas_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg,
192                         format_code);
193 }
194
195 static char *tcm_vhost_parse_pr_out_transport_id(
196         struct se_portal_group *se_tpg,
197         const char *buf,
198         u32 *out_tid_len,
199         char **port_nexus_ptr)
200 {
201         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
202                                 struct tcm_vhost_tpg, se_tpg);
203         struct tcm_vhost_tport *tport = tpg->tport;
204
205         switch (tport->tport_proto_id) {
206         case SCSI_PROTOCOL_SAS:
207                 return sas_parse_pr_out_transport_id(se_tpg, buf, out_tid_len,
208                                         port_nexus_ptr);
209         case SCSI_PROTOCOL_FCP:
210                 return fc_parse_pr_out_transport_id(se_tpg, buf, out_tid_len,
211                                         port_nexus_ptr);
212         case SCSI_PROTOCOL_ISCSI:
213                 return iscsi_parse_pr_out_transport_id(se_tpg, buf, out_tid_len,
214                                         port_nexus_ptr);
215         default:
216                 pr_err("Unknown tport_proto_id: 0x%02x, using"
217                         " SAS emulation\n", tport->tport_proto_id);
218                 break;
219         }
220
221         return sas_parse_pr_out_transport_id(se_tpg, buf, out_tid_len,
222                         port_nexus_ptr);
223 }
224
225 static struct se_node_acl *tcm_vhost_alloc_fabric_acl(
226         struct se_portal_group *se_tpg)
227 {
228         struct tcm_vhost_nacl *nacl;
229
230         nacl = kzalloc(sizeof(struct tcm_vhost_nacl), GFP_KERNEL);
231         if (!nacl) {
232                 pr_err("Unable to alocate struct tcm_vhost_nacl\n");
233                 return NULL;
234         }
235
236         return &nacl->se_node_acl;
237 }
238
239 static void tcm_vhost_release_fabric_acl(
240         struct se_portal_group *se_tpg,
241         struct se_node_acl *se_nacl)
242 {
243         struct tcm_vhost_nacl *nacl = container_of(se_nacl,
244                         struct tcm_vhost_nacl, se_node_acl);
245         kfree(nacl);
246 }
247
248 static u32 tcm_vhost_tpg_get_inst_index(struct se_portal_group *se_tpg)
249 {
250         return 1;
251 }
252
253 static void tcm_vhost_release_cmd(struct se_cmd *se_cmd)
254 {
255         return;
256 }
257
258 static int tcm_vhost_shutdown_session(struct se_session *se_sess)
259 {
260         return 0;
261 }
262
263 static void tcm_vhost_close_session(struct se_session *se_sess)
264 {
265         return;
266 }
267
268 static u32 tcm_vhost_sess_get_index(struct se_session *se_sess)
269 {
270         return 0;
271 }
272
273 static int tcm_vhost_write_pending(struct se_cmd *se_cmd)
274 {
275         /* Go ahead and process the write immediately */
276         target_execute_cmd(se_cmd);
277         return 0;
278 }
279
280 static int tcm_vhost_write_pending_status(struct se_cmd *se_cmd)
281 {
282         return 0;
283 }
284
285 static void tcm_vhost_set_default_node_attrs(struct se_node_acl *nacl)
286 {
287         return;
288 }
289
290 static u32 tcm_vhost_get_task_tag(struct se_cmd *se_cmd)
291 {
292         return 0;
293 }
294
295 static int tcm_vhost_get_cmd_state(struct se_cmd *se_cmd)
296 {
297         return 0;
298 }
299
300 static void vhost_scsi_complete_cmd(struct tcm_vhost_cmd *);
301
302 static int tcm_vhost_queue_data_in(struct se_cmd *se_cmd)
303 {
304         struct tcm_vhost_cmd *tv_cmd = container_of(se_cmd,
305                                 struct tcm_vhost_cmd, tvc_se_cmd);
306         vhost_scsi_complete_cmd(tv_cmd);
307         return 0;
308 }
309
310 static int tcm_vhost_queue_status(struct se_cmd *se_cmd)
311 {
312         struct tcm_vhost_cmd *tv_cmd = container_of(se_cmd,
313                                 struct tcm_vhost_cmd, tvc_se_cmd);
314         vhost_scsi_complete_cmd(tv_cmd);
315         return 0;
316 }
317
318 static int tcm_vhost_queue_tm_rsp(struct se_cmd *se_cmd)
319 {
320         return 0;
321 }
322
323 static u16 tcm_vhost_set_fabric_sense_len(struct se_cmd *se_cmd,
324         u32 sense_length)
325 {
326         return 0;
327 }
328
329 static u16 tcm_vhost_get_fabric_sense_len(void)
330 {
331         return 0;
332 }
333
334 static void vhost_scsi_free_cmd(struct tcm_vhost_cmd *tv_cmd)
335 {
336         struct se_cmd *se_cmd = &tv_cmd->tvc_se_cmd;
337
338         /* TODO locking against target/backend threads? */
339         transport_generic_free_cmd(se_cmd, 1);
340
341         if (tv_cmd->tvc_sgl_count) {
342                 u32 i;
343                 for (i = 0; i < tv_cmd->tvc_sgl_count; i++)
344                         put_page(sg_page(&tv_cmd->tvc_sgl[i]));
345
346                 kfree(tv_cmd->tvc_sgl);
347         }
348
349         kfree(tv_cmd);
350 }
351
352 /* Dequeue a command from the completion list */
353 static struct tcm_vhost_cmd *vhost_scsi_get_cmd_from_completion(
354         struct vhost_scsi *vs)
355 {
356         struct tcm_vhost_cmd *tv_cmd = NULL;
357
358         spin_lock_bh(&vs->vs_completion_lock);
359         if (list_empty(&vs->vs_completion_list)) {
360                 spin_unlock_bh(&vs->vs_completion_lock);
361                 return NULL;
362         }
363
364         list_for_each_entry(tv_cmd, &vs->vs_completion_list,
365                             tvc_completion_list) {
366                 list_del(&tv_cmd->tvc_completion_list);
367                 break;
368         }
369         spin_unlock_bh(&vs->vs_completion_lock);
370         return tv_cmd;
371 }
372
373 /* Fill in status and signal that we are done processing this command
374  *
375  * This is scheduled in the vhost work queue so we are called with the owner
376  * process mm and can access the vring.
377  */
378 static void vhost_scsi_complete_cmd_work(struct vhost_work *work)
379 {
380         struct vhost_scsi *vs = container_of(work, struct vhost_scsi,
381                                         vs_completion_work);
382         struct tcm_vhost_cmd *tv_cmd;
383
384         while ((tv_cmd = vhost_scsi_get_cmd_from_completion(vs)) != NULL) {
385                 struct virtio_scsi_cmd_resp v_rsp;
386                 struct se_cmd *se_cmd = &tv_cmd->tvc_se_cmd;
387                 int ret;
388
389                 pr_debug("%s tv_cmd %p resid %u status %#02x\n", __func__,
390                         tv_cmd, se_cmd->residual_count, se_cmd->scsi_status);
391
392                 memset(&v_rsp, 0, sizeof(v_rsp));
393                 v_rsp.resid = se_cmd->residual_count;
394                 /* TODO is status_qualifier field needed? */
395                 v_rsp.status = se_cmd->scsi_status;
396                 v_rsp.sense_len = se_cmd->scsi_sense_length;
397                 memcpy(v_rsp.sense, tv_cmd->tvc_sense_buf,
398                        v_rsp.sense_len);
399                 ret = copy_to_user(tv_cmd->tvc_resp, &v_rsp, sizeof(v_rsp));
400                 if (likely(ret == 0))
401                         vhost_add_used(&vs->vqs[2], tv_cmd->tvc_vq_desc, 0);
402                 else
403                         pr_err("Faulted on virtio_scsi_cmd_resp\n");
404
405                 vhost_scsi_free_cmd(tv_cmd);
406         }
407
408         vhost_signal(&vs->dev, &vs->vqs[2]);
409 }
410
411 static void vhost_scsi_complete_cmd(struct tcm_vhost_cmd *tv_cmd)
412 {
413         struct vhost_scsi *vs = tv_cmd->tvc_vhost;
414
415         pr_debug("%s tv_cmd %p\n", __func__, tv_cmd);
416
417         spin_lock_bh(&vs->vs_completion_lock);
418         list_add_tail(&tv_cmd->tvc_completion_list, &vs->vs_completion_list);
419         spin_unlock_bh(&vs->vs_completion_lock);
420
421         vhost_work_queue(&vs->dev, &vs->vs_completion_work);
422 }
423
424 static struct tcm_vhost_cmd *vhost_scsi_allocate_cmd(
425         struct tcm_vhost_tpg *tv_tpg,
426         struct virtio_scsi_cmd_req *v_req,
427         u32 exp_data_len,
428         int data_direction)
429 {
430         struct tcm_vhost_cmd *tv_cmd;
431         struct tcm_vhost_nexus *tv_nexus;
432         struct se_portal_group *se_tpg = &tv_tpg->se_tpg;
433         struct se_session *se_sess;
434         struct se_cmd *se_cmd;
435         int sam_task_attr;
436
437         tv_nexus = tv_tpg->tpg_nexus;
438         if (!tv_nexus) {
439                 pr_err("Unable to locate active struct tcm_vhost_nexus\n");
440                 return ERR_PTR(-EIO);
441         }
442         se_sess = tv_nexus->tvn_se_sess;
443
444         tv_cmd = kzalloc(sizeof(struct tcm_vhost_cmd), GFP_ATOMIC);
445         if (!tv_cmd) {
446                 pr_err("Unable to allocate struct tcm_vhost_cmd\n");
447                 return ERR_PTR(-ENOMEM);
448         }
449         INIT_LIST_HEAD(&tv_cmd->tvc_completion_list);
450         tv_cmd->tvc_tag = v_req->tag;
451
452         se_cmd = &tv_cmd->tvc_se_cmd;
453         /*
454          * Locate the SAM Task Attr from virtio_scsi_cmd_req
455          */
456         sam_task_attr = v_req->task_attr;
457         /*
458          * Initialize struct se_cmd descriptor from TCM infrastructure
459          */
460         transport_init_se_cmd(se_cmd, se_tpg->se_tpg_tfo, se_sess, exp_data_len,
461                                 data_direction, sam_task_attr,
462                                 &tv_cmd->tvc_sense_buf[0]);
463
464 #if 0   /* FIXME: vhost_scsi_allocate_cmd() BIDI operation */
465         if (bidi)
466                 se_cmd->se_cmd_flags |= SCF_BIDI;
467 #endif
468         return tv_cmd;
469 }
470
471 /*
472  * Map a user memory range into a scatterlist
473  *
474  * Returns the number of scatterlist entries used or -errno on error.
475  */
476 static int vhost_scsi_map_to_sgl(struct scatterlist *sgl,
477         unsigned int sgl_count, void __user *ptr, size_t len, int write)
478 {
479         struct scatterlist *sg = sgl;
480         unsigned int npages = 0;
481         int ret;
482
483         while (len > 0) {
484                 struct page *page;
485                 unsigned int offset = (uintptr_t)ptr & ~PAGE_MASK;
486                 unsigned int nbytes = min_t(unsigned int,
487                                 PAGE_SIZE - offset, len);
488
489                 if (npages == sgl_count) {
490                         ret = -ENOBUFS;
491                         goto err;
492                 }
493
494                 ret = get_user_pages_fast((unsigned long)ptr, 1, write, &page);
495                 BUG_ON(ret == 0); /* we should either get our page or fail */
496                 if (ret < 0)
497                         goto err;
498
499                 sg_set_page(sg, page, nbytes, offset);
500                 ptr += nbytes;
501                 len -= nbytes;
502                 sg++;
503                 npages++;
504         }
505         return npages;
506
507 err:
508         /* Put pages that we hold */
509         for (sg = sgl; sg != &sgl[npages]; sg++)
510                 put_page(sg_page(sg));
511         return ret;
512 }
513
514 static int vhost_scsi_map_iov_to_sgl(struct tcm_vhost_cmd *tv_cmd,
515         struct iovec *iov, unsigned int niov, int write)
516 {
517         int ret;
518         unsigned int i;
519         u32 sgl_count;
520         struct scatterlist *sg;
521
522         /*
523          * Find out how long sglist needs to be
524          */
525         sgl_count = 0;
526         for (i = 0; i < niov; i++) {
527                 sgl_count += (((uintptr_t)iov[i].iov_base + iov[i].iov_len +
528                                 PAGE_SIZE - 1) >> PAGE_SHIFT) -
529                                 ((uintptr_t)iov[i].iov_base >> PAGE_SHIFT);
530         }
531         /* TODO overflow checking */
532
533         sg = kmalloc(sizeof(tv_cmd->tvc_sgl[0]) * sgl_count, GFP_ATOMIC);
534         if (!sg)
535                 return -ENOMEM;
536         pr_debug("%s sg %p sgl_count %u is_err %ld\n", __func__,
537                sg, sgl_count, IS_ERR(sg));
538         sg_init_table(sg, sgl_count);
539
540         tv_cmd->tvc_sgl = sg;
541         tv_cmd->tvc_sgl_count = sgl_count;
542
543         pr_debug("Mapping %u iovecs for %u pages\n", niov, sgl_count);
544         for (i = 0; i < niov; i++) {
545                 ret = vhost_scsi_map_to_sgl(sg, sgl_count, iov[i].iov_base,
546                                         iov[i].iov_len, write);
547                 if (ret < 0) {
548                         for (i = 0; i < tv_cmd->tvc_sgl_count; i++)
549                                 put_page(sg_page(&tv_cmd->tvc_sgl[i]));
550                         kfree(tv_cmd->tvc_sgl);
551                         tv_cmd->tvc_sgl = NULL;
552                         tv_cmd->tvc_sgl_count = 0;
553                         return ret;
554                 }
555
556                 sg += ret;
557                 sgl_count -= ret;
558         }
559         return 0;
560 }
561
562 static void tcm_vhost_submission_work(struct work_struct *work)
563 {
564         struct tcm_vhost_cmd *tv_cmd =
565                 container_of(work, struct tcm_vhost_cmd, work);
566         struct se_cmd *se_cmd = &tv_cmd->tvc_se_cmd;
567         struct scatterlist *sg_ptr, *sg_bidi_ptr = NULL;
568         int rc, sg_no_bidi = 0;
569         /*
570          * Locate the struct se_lun pointer based on v_req->lun, and
571          * attach it to struct se_cmd
572          */
573         rc = transport_lookup_cmd_lun(&tv_cmd->tvc_se_cmd, tv_cmd->tvc_lun);
574         if (rc < 0) {
575                 pr_err("Failed to look up lun: %d\n", tv_cmd->tvc_lun);
576                 transport_send_check_condition_and_sense(&tv_cmd->tvc_se_cmd,
577                         tv_cmd->tvc_se_cmd.scsi_sense_reason, 0);
578                 transport_generic_free_cmd(se_cmd, 0);
579                 return;
580         }
581
582         rc = target_setup_cmd_from_cdb(se_cmd, tv_cmd->tvc_cdb);
583         if (rc == -ENOMEM) {
584                 transport_send_check_condition_and_sense(se_cmd,
585                                 TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE, 0);
586                 transport_generic_free_cmd(se_cmd, 0);
587                 return;
588         } else if (rc < 0) {
589                 if (se_cmd->se_cmd_flags & SCF_SCSI_RESERVATION_CONFLICT)
590                         tcm_vhost_queue_status(se_cmd);
591                 else
592                         transport_send_check_condition_and_sense(se_cmd,
593                                         se_cmd->scsi_sense_reason, 0);
594                 transport_generic_free_cmd(se_cmd, 0);
595                 return;
596         }
597
598         if (tv_cmd->tvc_sgl_count) {
599                 sg_ptr = tv_cmd->tvc_sgl;
600                 /*
601                  * For BIDI commands, pass in the extra READ buffer
602                  * to transport_generic_map_mem_to_cmd() below..
603                  */
604 /* FIXME: Fix BIDI operation in tcm_vhost_submission_work() */
605 #if 0
606                 if (se_cmd->se_cmd_flags & SCF_BIDI) {
607                         sg_bidi_ptr = NULL;
608                         sg_no_bidi = 0;
609                 }
610 #endif
611         } else {
612                 sg_ptr = NULL;
613         }
614
615         rc = transport_generic_map_mem_to_cmd(se_cmd, sg_ptr,
616                                 tv_cmd->tvc_sgl_count, sg_bidi_ptr,
617                                 sg_no_bidi);
618         if (rc < 0) {
619                 transport_send_check_condition_and_sense(se_cmd,
620                                 se_cmd->scsi_sense_reason, 0);
621                 transport_generic_free_cmd(se_cmd, 0);
622                 return;
623         }
624         transport_handle_cdb_direct(se_cmd);
625 }
626
627 static void vhost_scsi_handle_vq(struct vhost_scsi *vs)
628 {
629         struct vhost_virtqueue *vq = &vs->vqs[2];
630         struct virtio_scsi_cmd_req v_req;
631         struct tcm_vhost_tpg *tv_tpg;
632         struct tcm_vhost_cmd *tv_cmd;
633         u32 exp_data_len, data_first, data_num, data_direction;
634         unsigned out, in, i;
635         int head, ret;
636
637         /* Must use ioctl VHOST_SCSI_SET_ENDPOINT */
638         tv_tpg = vs->vs_tpg;
639         if (unlikely(!tv_tpg)) {
640                 pr_err("%s endpoint not set\n", __func__);
641                 return;
642         }
643
644         mutex_lock(&vq->mutex);
645         vhost_disable_notify(&vs->dev, vq);
646
647         for (;;) {
648                 head = vhost_get_vq_desc(&vs->dev, vq, vq->iov,
649                                         ARRAY_SIZE(vq->iov), &out, &in,
650                                         NULL, NULL);
651                 pr_debug("vhost_get_vq_desc: head: %d, out: %u in: %u\n",
652                                         head, out, in);
653                 /* On error, stop handling until the next kick. */
654                 if (unlikely(head < 0))
655                         break;
656                 /* Nothing new?  Wait for eventfd to tell us they refilled. */
657                 if (head == vq->num) {
658                         if (unlikely(vhost_enable_notify(&vs->dev, vq))) {
659                                 vhost_disable_notify(&vs->dev, vq);
660                                 continue;
661                         }
662                         break;
663                 }
664
665 /* FIXME: BIDI operation */
666                 if (out == 1 && in == 1) {
667                         data_direction = DMA_NONE;
668                         data_first = 0;
669                         data_num = 0;
670                 } else if (out == 1 && in > 1) {
671                         data_direction = DMA_FROM_DEVICE;
672                         data_first = out + 1;
673                         data_num = in - 1;
674                 } else if (out > 1 && in == 1) {
675                         data_direction = DMA_TO_DEVICE;
676                         data_first = 1;
677                         data_num = out - 1;
678                 } else {
679                         vq_err(vq, "Invalid buffer layout out: %u in: %u\n",
680                                         out, in);
681                         break;
682                 }
683
684                 /*
685                  * Check for a sane resp buffer so we can report errors to
686                  * the guest.
687                  */
688                 if (unlikely(vq->iov[out].iov_len !=
689                                         sizeof(struct virtio_scsi_cmd_resp))) {
690                         vq_err(vq, "Expecting virtio_scsi_cmd_resp, got %zu"
691                                 " bytes\n", vq->iov[out].iov_len);
692                         break;
693                 }
694
695                 if (unlikely(vq->iov[0].iov_len != sizeof(v_req))) {
696                         vq_err(vq, "Expecting virtio_scsi_cmd_req, got %zu"
697                                 " bytes\n", vq->iov[0].iov_len);
698                         break;
699                 }
700                 pr_debug("Calling __copy_from_user: vq->iov[0].iov_base: %p,"
701                         " len: %zu\n", vq->iov[0].iov_base, sizeof(v_req));
702                 ret = __copy_from_user(&v_req, vq->iov[0].iov_base,
703                                 sizeof(v_req));
704                 if (unlikely(ret)) {
705                         vq_err(vq, "Faulted on virtio_scsi_cmd_req\n");
706                         break;
707                 }
708
709                 exp_data_len = 0;
710                 for (i = 0; i < data_num; i++)
711                         exp_data_len += vq->iov[data_first + i].iov_len;
712
713                 tv_cmd = vhost_scsi_allocate_cmd(tv_tpg, &v_req,
714                                         exp_data_len, data_direction);
715                 if (IS_ERR(tv_cmd)) {
716                         vq_err(vq, "vhost_scsi_allocate_cmd failed %ld\n",
717                                         PTR_ERR(tv_cmd));
718                         break;
719                 }
720                 pr_debug("Allocated tv_cmd: %p exp_data_len: %d, data_direction"
721                         ": %d\n", tv_cmd, exp_data_len, data_direction);
722
723                 tv_cmd->tvc_vhost = vs;
724
725                 if (unlikely(vq->iov[out].iov_len !=
726                                 sizeof(struct virtio_scsi_cmd_resp))) {
727                         vq_err(vq, "Expecting virtio_scsi_cmd_resp, got %zu"
728                                 " bytes, out: %d, in: %d\n",
729                                 vq->iov[out].iov_len, out, in);
730                         break;
731                 }
732
733                 tv_cmd->tvc_resp = vq->iov[out].iov_base;
734
735                 /*
736                  * Copy in the recieved CDB descriptor into tv_cmd->tvc_cdb
737                  * that will be used by tcm_vhost_new_cmd_map() and down into
738                  * target_setup_cmd_from_cdb()
739                  */
740                 memcpy(tv_cmd->tvc_cdb, v_req.cdb, TCM_VHOST_MAX_CDB_SIZE);
741                 /*
742                  * Check that the recieved CDB size does not exceeded our
743                  * hardcoded max for tcm_vhost
744                  */
745                 /* TODO what if cdb was too small for varlen cdb header? */
746                 if (unlikely(scsi_command_size(tv_cmd->tvc_cdb) >
747                                         TCM_VHOST_MAX_CDB_SIZE)) {
748                         vq_err(vq, "Received SCSI CDB with command_size: %d that"
749                                 " exceeds SCSI_MAX_VARLEN_CDB_SIZE: %d\n",
750                                 scsi_command_size(tv_cmd->tvc_cdb),
751                                 TCM_VHOST_MAX_CDB_SIZE);
752                         break; /* TODO */
753                 }
754                 tv_cmd->tvc_lun = ((v_req.lun[2] << 8) | v_req.lun[3]) & 0x3FFF;
755
756                 pr_debug("vhost_scsi got command opcode: %#02x, lun: %d\n",
757                         tv_cmd->tvc_cdb[0], tv_cmd->tvc_lun);
758
759                 if (data_direction != DMA_NONE) {
760                         ret = vhost_scsi_map_iov_to_sgl(tv_cmd,
761                                         &vq->iov[data_first], data_num,
762                                         data_direction == DMA_TO_DEVICE);
763                         if (unlikely(ret)) {
764                                 vq_err(vq, "Failed to map iov to sgl\n");
765                                 break; /* TODO */
766                         }
767                 }
768
769                 /*
770                  * Save the descriptor from vhost_get_vq_desc() to be used to
771                  * complete the virtio-scsi request in TCM callback context via
772                  * tcm_vhost_queue_data_in() and tcm_vhost_queue_status()
773                  */
774                 tv_cmd->tvc_vq_desc = head;
775                 /*
776                  * Dispatch tv_cmd descriptor for cmwq execution in process
777                  * context provided by tcm_vhost_workqueue.  This also ensures
778                  * tv_cmd is executed on the same kworker CPU as this vhost
779                  * thread to gain positive L2 cache locality effects..
780                  */
781                 INIT_WORK(&tv_cmd->work, tcm_vhost_submission_work);
782                 queue_work(tcm_vhost_workqueue, &tv_cmd->work);
783         }
784
785         mutex_unlock(&vq->mutex);
786 }
787
788 static void vhost_scsi_ctl_handle_kick(struct vhost_work *work)
789 {
790         pr_err("%s: The handling func for control queue.\n", __func__);
791 }
792
793 static void vhost_scsi_evt_handle_kick(struct vhost_work *work)
794 {
795         pr_err("%s: The handling func for event queue.\n", __func__);
796 }
797
798 static void vhost_scsi_handle_kick(struct vhost_work *work)
799 {
800         struct vhost_virtqueue *vq = container_of(work, struct vhost_virtqueue,
801                                                 poll.work);
802         struct vhost_scsi *vs = container_of(vq->dev, struct vhost_scsi, dev);
803
804         vhost_scsi_handle_vq(vs);
805 }
806
807 /*
808  * Called from vhost_scsi_ioctl() context to walk the list of available
809  * tcm_vhost_tpg with an active struct tcm_vhost_nexus
810  */
811 static int vhost_scsi_set_endpoint(
812         struct vhost_scsi *vs,
813         struct vhost_scsi_target *t)
814 {
815         struct tcm_vhost_tport *tv_tport;
816         struct tcm_vhost_tpg *tv_tpg;
817         int index;
818
819         mutex_lock(&vs->dev.mutex);
820         /* Verify that ring has been setup correctly. */
821         for (index = 0; index < vs->dev.nvqs; ++index) {
822                 /* Verify that ring has been setup correctly. */
823                 if (!vhost_vq_access_ok(&vs->vqs[index])) {
824                         mutex_unlock(&vs->dev.mutex);
825                         return -EFAULT;
826                 }
827         }
828
829         if (vs->vs_tpg) {
830                 mutex_unlock(&vs->dev.mutex);
831                 return -EEXIST;
832         }
833         mutex_unlock(&vs->dev.mutex);
834
835         mutex_lock(&tcm_vhost_mutex);
836         list_for_each_entry(tv_tpg, &tcm_vhost_list, tv_tpg_list) {
837                 mutex_lock(&tv_tpg->tv_tpg_mutex);
838                 if (!tv_tpg->tpg_nexus) {
839                         mutex_unlock(&tv_tpg->tv_tpg_mutex);
840                         continue;
841                 }
842                 if (atomic_read(&tv_tpg->tv_tpg_vhost_count)) {
843                         mutex_unlock(&tv_tpg->tv_tpg_mutex);
844                         continue;
845                 }
846                 tv_tport = tv_tpg->tport;
847
848                 if (!strcmp(tv_tport->tport_name, t->vhost_wwpn) &&
849                     (tv_tpg->tport_tpgt == t->vhost_tpgt)) {
850                         atomic_inc(&tv_tpg->tv_tpg_vhost_count);
851                         smp_mb__after_atomic_inc();
852                         mutex_unlock(&tv_tpg->tv_tpg_mutex);
853                         mutex_unlock(&tcm_vhost_mutex);
854
855                         mutex_lock(&vs->dev.mutex);
856                         vs->vs_tpg = tv_tpg;
857                         atomic_inc(&vs->vhost_ref_cnt);
858                         smp_mb__after_atomic_inc();
859                         mutex_unlock(&vs->dev.mutex);
860                         return 0;
861                 }
862                 mutex_unlock(&tv_tpg->tv_tpg_mutex);
863         }
864         mutex_unlock(&tcm_vhost_mutex);
865         return -EINVAL;
866 }
867
868 static int vhost_scsi_clear_endpoint(
869         struct vhost_scsi *vs,
870         struct vhost_scsi_target *t)
871 {
872         struct tcm_vhost_tport *tv_tport;
873         struct tcm_vhost_tpg *tv_tpg;
874         int index;
875
876         mutex_lock(&vs->dev.mutex);
877         /* Verify that ring has been setup correctly. */
878         for (index = 0; index < vs->dev.nvqs; ++index) {
879                 if (!vhost_vq_access_ok(&vs->vqs[index])) {
880                         mutex_unlock(&vs->dev.mutex);
881                         return -EFAULT;
882                 }
883         }
884
885         if (!vs->vs_tpg) {
886                 mutex_unlock(&vs->dev.mutex);
887                 return -ENODEV;
888         }
889         tv_tpg = vs->vs_tpg;
890         tv_tport = tv_tpg->tport;
891
892         if (strcmp(tv_tport->tport_name, t->vhost_wwpn) ||
893             (tv_tpg->tport_tpgt != t->vhost_tpgt)) {
894                 mutex_unlock(&vs->dev.mutex);
895                 pr_warn("tv_tport->tport_name: %s, tv_tpg->tport_tpgt: %hu"
896                         " does not match t->vhost_wwpn: %s, t->vhost_tpgt: %hu\n",
897                         tv_tport->tport_name, tv_tpg->tport_tpgt,
898                         t->vhost_wwpn, t->vhost_tpgt);
899                 return -EINVAL;
900         }
901         atomic_dec(&tv_tpg->tv_tpg_vhost_count);
902         vs->vs_tpg = NULL;
903         mutex_unlock(&vs->dev.mutex);
904
905         return 0;
906 }
907
908 static int vhost_scsi_open(struct inode *inode, struct file *f)
909 {
910         struct vhost_scsi *s;
911         int r;
912
913         s = kzalloc(sizeof(*s), GFP_KERNEL);
914         if (!s)
915                 return -ENOMEM;
916
917         vhost_work_init(&s->vs_completion_work, vhost_scsi_complete_cmd_work);
918         INIT_LIST_HEAD(&s->vs_completion_list);
919         spin_lock_init(&s->vs_completion_lock);
920
921         s->vqs[0].handle_kick = vhost_scsi_ctl_handle_kick;
922         s->vqs[1].handle_kick = vhost_scsi_evt_handle_kick;
923         s->vqs[2].handle_kick = vhost_scsi_handle_kick;
924         r = vhost_dev_init(&s->dev, s->vqs, 3);
925         if (r < 0) {
926                 kfree(s);
927                 return r;
928         }
929
930         f->private_data = s;
931         return 0;
932 }
933
934 static int vhost_scsi_release(struct inode *inode, struct file *f)
935 {
936         struct vhost_scsi *s = f->private_data;
937
938         if (s->vs_tpg && s->vs_tpg->tport) {
939                 struct vhost_scsi_target backend;
940
941                 memcpy(backend.vhost_wwpn, s->vs_tpg->tport->tport_name,
942                                 sizeof(backend.vhost_wwpn));
943                 backend.vhost_tpgt = s->vs_tpg->tport_tpgt;
944                 vhost_scsi_clear_endpoint(s, &backend);
945         }
946
947         vhost_dev_cleanup(&s->dev, false);
948         kfree(s);
949         return 0;
950 }
951
952 static int vhost_scsi_set_features(struct vhost_scsi *vs, u64 features)
953 {
954         if (features & ~VHOST_FEATURES)
955                 return -EOPNOTSUPP;
956
957         mutex_lock(&vs->dev.mutex);
958         if ((features & (1 << VHOST_F_LOG_ALL)) &&
959             !vhost_log_access_ok(&vs->dev)) {
960                 mutex_unlock(&vs->dev.mutex);
961                 return -EFAULT;
962         }
963         vs->dev.acked_features = features;
964         /* TODO possibly smp_wmb() and flush vqs */
965         mutex_unlock(&vs->dev.mutex);
966         return 0;
967 }
968
969 static long vhost_scsi_ioctl(struct file *f, unsigned int ioctl,
970                                 unsigned long arg)
971 {
972         struct vhost_scsi *vs = f->private_data;
973         struct vhost_scsi_target backend;
974         void __user *argp = (void __user *)arg;
975         u64 __user *featurep = argp;
976         u64 features;
977         int r;
978
979         switch (ioctl) {
980         case VHOST_SCSI_SET_ENDPOINT:
981                 if (copy_from_user(&backend, argp, sizeof backend))
982                         return -EFAULT;
983
984                 return vhost_scsi_set_endpoint(vs, &backend);
985         case VHOST_SCSI_CLEAR_ENDPOINT:
986                 if (copy_from_user(&backend, argp, sizeof backend))
987                         return -EFAULT;
988
989                 return vhost_scsi_clear_endpoint(vs, &backend);
990         case VHOST_SCSI_GET_ABI_VERSION:
991                 if (copy_from_user(&backend, argp, sizeof backend))
992                         return -EFAULT;
993
994                 backend.abi_version = VHOST_SCSI_ABI_VERSION;
995
996                 if (copy_to_user(argp, &backend, sizeof backend))
997                         return -EFAULT;
998                 return 0;
999         case VHOST_GET_FEATURES:
1000                 features = VHOST_FEATURES;
1001                 if (copy_to_user(featurep, &features, sizeof features))
1002                         return -EFAULT;
1003                 return 0;
1004         case VHOST_SET_FEATURES:
1005                 if (copy_from_user(&features, featurep, sizeof features))
1006                         return -EFAULT;
1007                 return vhost_scsi_set_features(vs, features);
1008         default:
1009                 mutex_lock(&vs->dev.mutex);
1010                 r = vhost_dev_ioctl(&vs->dev, ioctl, arg);
1011                 mutex_unlock(&vs->dev.mutex);
1012                 return r;
1013         }
1014 }
1015
1016 static const struct file_operations vhost_scsi_fops = {
1017         .owner          = THIS_MODULE,
1018         .release        = vhost_scsi_release,
1019         .unlocked_ioctl = vhost_scsi_ioctl,
1020         /* TODO compat ioctl? */
1021         .open           = vhost_scsi_open,
1022         .llseek         = noop_llseek,
1023 };
1024
1025 static struct miscdevice vhost_scsi_misc = {
1026         MISC_DYNAMIC_MINOR,
1027         "vhost-scsi",
1028         &vhost_scsi_fops,
1029 };
1030
1031 static int __init vhost_scsi_register(void)
1032 {
1033         return misc_register(&vhost_scsi_misc);
1034 }
1035
1036 static int vhost_scsi_deregister(void)
1037 {
1038         return misc_deregister(&vhost_scsi_misc);
1039 }
1040
1041 static char *tcm_vhost_dump_proto_id(struct tcm_vhost_tport *tport)
1042 {
1043         switch (tport->tport_proto_id) {
1044         case SCSI_PROTOCOL_SAS:
1045                 return "SAS";
1046         case SCSI_PROTOCOL_FCP:
1047                 return "FCP";
1048         case SCSI_PROTOCOL_ISCSI:
1049                 return "iSCSI";
1050         default:
1051                 break;
1052         }
1053
1054         return "Unknown";
1055 }
1056
1057 static int tcm_vhost_port_link(
1058         struct se_portal_group *se_tpg,
1059         struct se_lun *lun)
1060 {
1061         struct tcm_vhost_tpg *tv_tpg = container_of(se_tpg,
1062                                 struct tcm_vhost_tpg, se_tpg);
1063
1064         atomic_inc(&tv_tpg->tv_tpg_port_count);
1065         smp_mb__after_atomic_inc();
1066
1067         return 0;
1068 }
1069
1070 static void tcm_vhost_port_unlink(
1071         struct se_portal_group *se_tpg,
1072         struct se_lun *se_lun)
1073 {
1074         struct tcm_vhost_tpg *tv_tpg = container_of(se_tpg,
1075                                 struct tcm_vhost_tpg, se_tpg);
1076
1077         atomic_dec(&tv_tpg->tv_tpg_port_count);
1078         smp_mb__after_atomic_dec();
1079 }
1080
1081 static struct se_node_acl *tcm_vhost_make_nodeacl(
1082         struct se_portal_group *se_tpg,
1083         struct config_group *group,
1084         const char *name)
1085 {
1086         struct se_node_acl *se_nacl, *se_nacl_new;
1087         struct tcm_vhost_nacl *nacl;
1088         u64 wwpn = 0;
1089         u32 nexus_depth;
1090
1091         /* tcm_vhost_parse_wwn(name, &wwpn, 1) < 0)
1092                 return ERR_PTR(-EINVAL); */
1093         se_nacl_new = tcm_vhost_alloc_fabric_acl(se_tpg);
1094         if (!se_nacl_new)
1095                 return ERR_PTR(-ENOMEM);
1096
1097         nexus_depth = 1;
1098         /*
1099          * se_nacl_new may be released by core_tpg_add_initiator_node_acl()
1100          * when converting a NodeACL from demo mode -> explict
1101          */
1102         se_nacl = core_tpg_add_initiator_node_acl(se_tpg, se_nacl_new,
1103                                 name, nexus_depth);
1104         if (IS_ERR(se_nacl)) {
1105                 tcm_vhost_release_fabric_acl(se_tpg, se_nacl_new);
1106                 return se_nacl;
1107         }
1108         /*
1109          * Locate our struct tcm_vhost_nacl and set the FC Nport WWPN
1110          */
1111         nacl = container_of(se_nacl, struct tcm_vhost_nacl, se_node_acl);
1112         nacl->iport_wwpn = wwpn;
1113
1114         return se_nacl;
1115 }
1116
1117 static void tcm_vhost_drop_nodeacl(struct se_node_acl *se_acl)
1118 {
1119         struct tcm_vhost_nacl *nacl = container_of(se_acl,
1120                                 struct tcm_vhost_nacl, se_node_acl);
1121         core_tpg_del_initiator_node_acl(se_acl->se_tpg, se_acl, 1);
1122         kfree(nacl);
1123 }
1124
1125 static int tcm_vhost_make_nexus(
1126         struct tcm_vhost_tpg *tv_tpg,
1127         const char *name)
1128 {
1129         struct se_portal_group *se_tpg;
1130         struct tcm_vhost_nexus *tv_nexus;
1131
1132         mutex_lock(&tv_tpg->tv_tpg_mutex);
1133         if (tv_tpg->tpg_nexus) {
1134                 mutex_unlock(&tv_tpg->tv_tpg_mutex);
1135                 pr_debug("tv_tpg->tpg_nexus already exists\n");
1136                 return -EEXIST;
1137         }
1138         se_tpg = &tv_tpg->se_tpg;
1139
1140         tv_nexus = kzalloc(sizeof(struct tcm_vhost_nexus), GFP_KERNEL);
1141         if (!tv_nexus) {
1142                 mutex_unlock(&tv_tpg->tv_tpg_mutex);
1143                 pr_err("Unable to allocate struct tcm_vhost_nexus\n");
1144                 return -ENOMEM;
1145         }
1146         /*
1147          *  Initialize the struct se_session pointer
1148          */
1149         tv_nexus->tvn_se_sess = transport_init_session();
1150         if (IS_ERR(tv_nexus->tvn_se_sess)) {
1151                 mutex_unlock(&tv_tpg->tv_tpg_mutex);
1152                 kfree(tv_nexus);
1153                 return -ENOMEM;
1154         }
1155         /*
1156          * Since we are running in 'demo mode' this call with generate a
1157          * struct se_node_acl for the tcm_vhost struct se_portal_group with
1158          * the SCSI Initiator port name of the passed configfs group 'name'.
1159          */
1160         tv_nexus->tvn_se_sess->se_node_acl = core_tpg_check_initiator_node_acl(
1161                                 se_tpg, (unsigned char *)name);
1162         if (!tv_nexus->tvn_se_sess->se_node_acl) {
1163                 mutex_unlock(&tv_tpg->tv_tpg_mutex);
1164                 pr_debug("core_tpg_check_initiator_node_acl() failed"
1165                                 " for %s\n", name);
1166                 transport_free_session(tv_nexus->tvn_se_sess);
1167                 kfree(tv_nexus);
1168                 return -ENOMEM;
1169         }
1170         /*
1171          * Now register the TCM vHost virtual I_T Nexus as active with the
1172          * call to __transport_register_session()
1173          */
1174         __transport_register_session(se_tpg, tv_nexus->tvn_se_sess->se_node_acl,
1175                         tv_nexus->tvn_se_sess, tv_nexus);
1176         tv_tpg->tpg_nexus = tv_nexus;
1177
1178         mutex_unlock(&tv_tpg->tv_tpg_mutex);
1179         return 0;
1180 }
1181
1182 static int tcm_vhost_drop_nexus(
1183         struct tcm_vhost_tpg *tpg)
1184 {
1185         struct se_session *se_sess;
1186         struct tcm_vhost_nexus *tv_nexus;
1187
1188         mutex_lock(&tpg->tv_tpg_mutex);
1189         tv_nexus = tpg->tpg_nexus;
1190         if (!tv_nexus) {
1191                 mutex_unlock(&tpg->tv_tpg_mutex);
1192                 return -ENODEV;
1193         }
1194
1195         se_sess = tv_nexus->tvn_se_sess;
1196         if (!se_sess) {
1197                 mutex_unlock(&tpg->tv_tpg_mutex);
1198                 return -ENODEV;
1199         }
1200
1201         if (atomic_read(&tpg->tv_tpg_port_count)) {
1202                 mutex_unlock(&tpg->tv_tpg_mutex);
1203                 pr_err("Unable to remove TCM_vHost I_T Nexus with"
1204                         " active TPG port count: %d\n",
1205                         atomic_read(&tpg->tv_tpg_port_count));
1206                 return -EPERM;
1207         }
1208
1209         if (atomic_read(&tpg->tv_tpg_vhost_count)) {
1210                 mutex_unlock(&tpg->tv_tpg_mutex);
1211                 pr_err("Unable to remove TCM_vHost I_T Nexus with"
1212                         " active TPG vhost count: %d\n",
1213                         atomic_read(&tpg->tv_tpg_vhost_count));
1214                 return -EPERM;
1215         }
1216
1217         pr_debug("TCM_vHost_ConfigFS: Removing I_T Nexus to emulated"
1218                 " %s Initiator Port: %s\n", tcm_vhost_dump_proto_id(tpg->tport),
1219                 tv_nexus->tvn_se_sess->se_node_acl->initiatorname);
1220         /*
1221          * Release the SCSI I_T Nexus to the emulated vHost Target Port
1222          */
1223         transport_deregister_session(tv_nexus->tvn_se_sess);
1224         tpg->tpg_nexus = NULL;
1225         mutex_unlock(&tpg->tv_tpg_mutex);
1226
1227         kfree(tv_nexus);
1228         return 0;
1229 }
1230
1231 static ssize_t tcm_vhost_tpg_show_nexus(
1232         struct se_portal_group *se_tpg,
1233         char *page)
1234 {
1235         struct tcm_vhost_tpg *tv_tpg = container_of(se_tpg,
1236                                 struct tcm_vhost_tpg, se_tpg);
1237         struct tcm_vhost_nexus *tv_nexus;
1238         ssize_t ret;
1239
1240         mutex_lock(&tv_tpg->tv_tpg_mutex);
1241         tv_nexus = tv_tpg->tpg_nexus;
1242         if (!tv_nexus) {
1243                 mutex_unlock(&tv_tpg->tv_tpg_mutex);
1244                 return -ENODEV;
1245         }
1246         ret = snprintf(page, PAGE_SIZE, "%s\n",
1247                         tv_nexus->tvn_se_sess->se_node_acl->initiatorname);
1248         mutex_unlock(&tv_tpg->tv_tpg_mutex);
1249
1250         return ret;
1251 }
1252
1253 static ssize_t tcm_vhost_tpg_store_nexus(
1254         struct se_portal_group *se_tpg,
1255         const char *page,
1256         size_t count)
1257 {
1258         struct tcm_vhost_tpg *tv_tpg = container_of(se_tpg,
1259                                 struct tcm_vhost_tpg, se_tpg);
1260         struct tcm_vhost_tport *tport_wwn = tv_tpg->tport;
1261         unsigned char i_port[TCM_VHOST_NAMELEN], *ptr, *port_ptr;
1262         int ret;
1263         /*
1264          * Shutdown the active I_T nexus if 'NULL' is passed..
1265          */
1266         if (!strncmp(page, "NULL", 4)) {
1267                 ret = tcm_vhost_drop_nexus(tv_tpg);
1268                 return (!ret) ? count : ret;
1269         }
1270         /*
1271          * Otherwise make sure the passed virtual Initiator port WWN matches
1272          * the fabric protocol_id set in tcm_vhost_make_tport(), and call
1273          * tcm_vhost_make_nexus().
1274          */
1275         if (strlen(page) >= TCM_VHOST_NAMELEN) {
1276                 pr_err("Emulated NAA Sas Address: %s, exceeds"
1277                                 " max: %d\n", page, TCM_VHOST_NAMELEN);
1278                 return -EINVAL;
1279         }
1280         snprintf(&i_port[0], TCM_VHOST_NAMELEN, "%s", page);
1281
1282         ptr = strstr(i_port, "naa.");
1283         if (ptr) {
1284                 if (tport_wwn->tport_proto_id != SCSI_PROTOCOL_SAS) {
1285                         pr_err("Passed SAS Initiator Port %s does not"
1286                                 " match target port protoid: %s\n", i_port,
1287                                 tcm_vhost_dump_proto_id(tport_wwn));
1288                         return -EINVAL;
1289                 }
1290                 port_ptr = &i_port[0];
1291                 goto check_newline;
1292         }
1293         ptr = strstr(i_port, "fc.");
1294         if (ptr) {
1295                 if (tport_wwn->tport_proto_id != SCSI_PROTOCOL_FCP) {
1296                         pr_err("Passed FCP Initiator Port %s does not"
1297                                 " match target port protoid: %s\n", i_port,
1298                                 tcm_vhost_dump_proto_id(tport_wwn));
1299                         return -EINVAL;
1300                 }
1301                 port_ptr = &i_port[3]; /* Skip over "fc." */
1302                 goto check_newline;
1303         }
1304         ptr = strstr(i_port, "iqn.");
1305         if (ptr) {
1306                 if (tport_wwn->tport_proto_id != SCSI_PROTOCOL_ISCSI) {
1307                         pr_err("Passed iSCSI Initiator Port %s does not"
1308                                 " match target port protoid: %s\n", i_port,
1309                                 tcm_vhost_dump_proto_id(tport_wwn));
1310                         return -EINVAL;
1311                 }
1312                 port_ptr = &i_port[0];
1313                 goto check_newline;
1314         }
1315         pr_err("Unable to locate prefix for emulated Initiator Port:"
1316                         " %s\n", i_port);
1317         return -EINVAL;
1318         /*
1319          * Clear any trailing newline for the NAA WWN
1320          */
1321 check_newline:
1322         if (i_port[strlen(i_port)-1] == '\n')
1323                 i_port[strlen(i_port)-1] = '\0';
1324
1325         ret = tcm_vhost_make_nexus(tv_tpg, port_ptr);
1326         if (ret < 0)
1327                 return ret;
1328
1329         return count;
1330 }
1331
1332 TF_TPG_BASE_ATTR(tcm_vhost, nexus, S_IRUGO | S_IWUSR);
1333
1334 static struct configfs_attribute *tcm_vhost_tpg_attrs[] = {
1335         &tcm_vhost_tpg_nexus.attr,
1336         NULL,
1337 };
1338
1339 static struct se_portal_group *tcm_vhost_make_tpg(
1340         struct se_wwn *wwn,
1341         struct config_group *group,
1342         const char *name)
1343 {
1344         struct tcm_vhost_tport *tport = container_of(wwn,
1345                         struct tcm_vhost_tport, tport_wwn);
1346
1347         struct tcm_vhost_tpg *tpg;
1348         unsigned long tpgt;
1349         int ret;
1350
1351         if (strstr(name, "tpgt_") != name)
1352                 return ERR_PTR(-EINVAL);
1353         if (kstrtoul(name + 5, 10, &tpgt) || tpgt > UINT_MAX)
1354                 return ERR_PTR(-EINVAL);
1355
1356         tpg = kzalloc(sizeof(struct tcm_vhost_tpg), GFP_KERNEL);
1357         if (!tpg) {
1358                 pr_err("Unable to allocate struct tcm_vhost_tpg");
1359                 return ERR_PTR(-ENOMEM);
1360         }
1361         mutex_init(&tpg->tv_tpg_mutex);
1362         INIT_LIST_HEAD(&tpg->tv_tpg_list);
1363         tpg->tport = tport;
1364         tpg->tport_tpgt = tpgt;
1365
1366         ret = core_tpg_register(&tcm_vhost_fabric_configfs->tf_ops, wwn,
1367                                 &tpg->se_tpg, tpg, TRANSPORT_TPG_TYPE_NORMAL);
1368         if (ret < 0) {
1369                 kfree(tpg);
1370                 return NULL;
1371         }
1372         mutex_lock(&tcm_vhost_mutex);
1373         list_add_tail(&tpg->tv_tpg_list, &tcm_vhost_list);
1374         mutex_unlock(&tcm_vhost_mutex);
1375
1376         return &tpg->se_tpg;
1377 }
1378
1379 static void tcm_vhost_drop_tpg(struct se_portal_group *se_tpg)
1380 {
1381         struct tcm_vhost_tpg *tpg = container_of(se_tpg,
1382                                 struct tcm_vhost_tpg, se_tpg);
1383
1384         mutex_lock(&tcm_vhost_mutex);
1385         list_del(&tpg->tv_tpg_list);
1386         mutex_unlock(&tcm_vhost_mutex);
1387         /*
1388          * Release the virtual I_T Nexus for this vHost TPG
1389          */
1390         tcm_vhost_drop_nexus(tpg);
1391         /*
1392          * Deregister the se_tpg from TCM..
1393          */
1394         core_tpg_deregister(se_tpg);
1395         kfree(tpg);
1396 }
1397
1398 static struct se_wwn *tcm_vhost_make_tport(
1399         struct target_fabric_configfs *tf,
1400         struct config_group *group,
1401         const char *name)
1402 {
1403         struct tcm_vhost_tport *tport;
1404         char *ptr;
1405         u64 wwpn = 0;
1406         int off = 0;
1407
1408         /* if (tcm_vhost_parse_wwn(name, &wwpn, 1) < 0)
1409                 return ERR_PTR(-EINVAL); */
1410
1411         tport = kzalloc(sizeof(struct tcm_vhost_tport), GFP_KERNEL);
1412         if (!tport) {
1413                 pr_err("Unable to allocate struct tcm_vhost_tport");
1414                 return ERR_PTR(-ENOMEM);
1415         }
1416         tport->tport_wwpn = wwpn;
1417         /*
1418          * Determine the emulated Protocol Identifier and Target Port Name
1419          * based on the incoming configfs directory name.
1420          */
1421         ptr = strstr(name, "naa.");
1422         if (ptr) {
1423                 tport->tport_proto_id = SCSI_PROTOCOL_SAS;
1424                 goto check_len;
1425         }
1426         ptr = strstr(name, "fc.");
1427         if (ptr) {
1428                 tport->tport_proto_id = SCSI_PROTOCOL_FCP;
1429                 off = 3; /* Skip over "fc." */
1430                 goto check_len;
1431         }
1432         ptr = strstr(name, "iqn.");
1433         if (ptr) {
1434                 tport->tport_proto_id = SCSI_PROTOCOL_ISCSI;
1435                 goto check_len;
1436         }
1437
1438         pr_err("Unable to locate prefix for emulated Target Port:"
1439                         " %s\n", name);
1440         kfree(tport);
1441         return ERR_PTR(-EINVAL);
1442
1443 check_len:
1444         if (strlen(name) >= TCM_VHOST_NAMELEN) {
1445                 pr_err("Emulated %s Address: %s, exceeds"
1446                         " max: %d\n", name, tcm_vhost_dump_proto_id(tport),
1447                         TCM_VHOST_NAMELEN);
1448                 kfree(tport);
1449                 return ERR_PTR(-EINVAL);
1450         }
1451         snprintf(&tport->tport_name[0], TCM_VHOST_NAMELEN, "%s", &name[off]);
1452
1453         pr_debug("TCM_VHost_ConfigFS: Allocated emulated Target"
1454                 " %s Address: %s\n", tcm_vhost_dump_proto_id(tport), name);
1455
1456         return &tport->tport_wwn;
1457 }
1458
1459 static void tcm_vhost_drop_tport(struct se_wwn *wwn)
1460 {
1461         struct tcm_vhost_tport *tport = container_of(wwn,
1462                                 struct tcm_vhost_tport, tport_wwn);
1463
1464         pr_debug("TCM_VHost_ConfigFS: Deallocating emulated Target"
1465                 " %s Address: %s\n", tcm_vhost_dump_proto_id(tport),
1466                 tport->tport_name);
1467
1468         kfree(tport);
1469 }
1470
1471 static ssize_t tcm_vhost_wwn_show_attr_version(
1472         struct target_fabric_configfs *tf,
1473         char *page)
1474 {
1475         return sprintf(page, "TCM_VHOST fabric module %s on %s/%s"
1476                 "on "UTS_RELEASE"\n", TCM_VHOST_VERSION, utsname()->sysname,
1477                 utsname()->machine);
1478 }
1479
1480 TF_WWN_ATTR_RO(tcm_vhost, version);
1481
1482 static struct configfs_attribute *tcm_vhost_wwn_attrs[] = {
1483         &tcm_vhost_wwn_version.attr,
1484         NULL,
1485 };
1486
1487 static struct target_core_fabric_ops tcm_vhost_ops = {
1488         .get_fabric_name                = tcm_vhost_get_fabric_name,
1489         .get_fabric_proto_ident         = tcm_vhost_get_fabric_proto_ident,
1490         .tpg_get_wwn                    = tcm_vhost_get_fabric_wwn,
1491         .tpg_get_tag                    = tcm_vhost_get_tag,
1492         .tpg_get_default_depth          = tcm_vhost_get_default_depth,
1493         .tpg_get_pr_transport_id        = tcm_vhost_get_pr_transport_id,
1494         .tpg_get_pr_transport_id_len    = tcm_vhost_get_pr_transport_id_len,
1495         .tpg_parse_pr_out_transport_id  = tcm_vhost_parse_pr_out_transport_id,
1496         .tpg_check_demo_mode            = tcm_vhost_check_true,
1497         .tpg_check_demo_mode_cache      = tcm_vhost_check_true,
1498         .tpg_check_demo_mode_write_protect = tcm_vhost_check_false,
1499         .tpg_check_prod_mode_write_protect = tcm_vhost_check_false,
1500         .tpg_alloc_fabric_acl           = tcm_vhost_alloc_fabric_acl,
1501         .tpg_release_fabric_acl         = tcm_vhost_release_fabric_acl,
1502         .tpg_get_inst_index             = tcm_vhost_tpg_get_inst_index,
1503         .release_cmd                    = tcm_vhost_release_cmd,
1504         .shutdown_session               = tcm_vhost_shutdown_session,
1505         .close_session                  = tcm_vhost_close_session,
1506         .sess_get_index                 = tcm_vhost_sess_get_index,
1507         .sess_get_initiator_sid         = NULL,
1508         .write_pending                  = tcm_vhost_write_pending,
1509         .write_pending_status           = tcm_vhost_write_pending_status,
1510         .set_default_node_attributes    = tcm_vhost_set_default_node_attrs,
1511         .get_task_tag                   = tcm_vhost_get_task_tag,
1512         .get_cmd_state                  = tcm_vhost_get_cmd_state,
1513         .queue_data_in                  = tcm_vhost_queue_data_in,
1514         .queue_status                   = tcm_vhost_queue_status,
1515         .queue_tm_rsp                   = tcm_vhost_queue_tm_rsp,
1516         .get_fabric_sense_len           = tcm_vhost_get_fabric_sense_len,
1517         .set_fabric_sense_len           = tcm_vhost_set_fabric_sense_len,
1518         /*
1519          * Setup callers for generic logic in target_core_fabric_configfs.c
1520          */
1521         .fabric_make_wwn                = tcm_vhost_make_tport,
1522         .fabric_drop_wwn                = tcm_vhost_drop_tport,
1523         .fabric_make_tpg                = tcm_vhost_make_tpg,
1524         .fabric_drop_tpg                = tcm_vhost_drop_tpg,
1525         .fabric_post_link               = tcm_vhost_port_link,
1526         .fabric_pre_unlink              = tcm_vhost_port_unlink,
1527         .fabric_make_np                 = NULL,
1528         .fabric_drop_np                 = NULL,
1529         .fabric_make_nodeacl            = tcm_vhost_make_nodeacl,
1530         .fabric_drop_nodeacl            = tcm_vhost_drop_nodeacl,
1531 };
1532
1533 static int tcm_vhost_register_configfs(void)
1534 {
1535         struct target_fabric_configfs *fabric;
1536         int ret;
1537
1538         pr_debug("TCM_VHOST fabric module %s on %s/%s"
1539                 " on "UTS_RELEASE"\n", TCM_VHOST_VERSION, utsname()->sysname,
1540                 utsname()->machine);
1541         /*
1542          * Register the top level struct config_item_type with TCM core
1543          */
1544         fabric = target_fabric_configfs_init(THIS_MODULE, "vhost");
1545         if (IS_ERR(fabric)) {
1546                 pr_err("target_fabric_configfs_init() failed\n");
1547                 return PTR_ERR(fabric);
1548         }
1549         /*
1550          * Setup fabric->tf_ops from our local tcm_vhost_ops
1551          */
1552         fabric->tf_ops = tcm_vhost_ops;
1553         /*
1554          * Setup default attribute lists for various fabric->tf_cit_tmpl
1555          */
1556         TF_CIT_TMPL(fabric)->tfc_wwn_cit.ct_attrs = tcm_vhost_wwn_attrs;
1557         TF_CIT_TMPL(fabric)->tfc_tpg_base_cit.ct_attrs = tcm_vhost_tpg_attrs;
1558         TF_CIT_TMPL(fabric)->tfc_tpg_attrib_cit.ct_attrs = NULL;
1559         TF_CIT_TMPL(fabric)->tfc_tpg_param_cit.ct_attrs = NULL;
1560         TF_CIT_TMPL(fabric)->tfc_tpg_np_base_cit.ct_attrs = NULL;
1561         TF_CIT_TMPL(fabric)->tfc_tpg_nacl_base_cit.ct_attrs = NULL;
1562         TF_CIT_TMPL(fabric)->tfc_tpg_nacl_attrib_cit.ct_attrs = NULL;
1563         TF_CIT_TMPL(fabric)->tfc_tpg_nacl_auth_cit.ct_attrs = NULL;
1564         TF_CIT_TMPL(fabric)->tfc_tpg_nacl_param_cit.ct_attrs = NULL;
1565         /*
1566          * Register the fabric for use within TCM
1567          */
1568         ret = target_fabric_configfs_register(fabric);
1569         if (ret < 0) {
1570                 pr_err("target_fabric_configfs_register() failed"
1571                                 " for TCM_VHOST\n");
1572                 return ret;
1573         }
1574         /*
1575          * Setup our local pointer to *fabric
1576          */
1577         tcm_vhost_fabric_configfs = fabric;
1578         pr_debug("TCM_VHOST[0] - Set fabric -> tcm_vhost_fabric_configfs\n");
1579         return 0;
1580 };
1581
1582 static void tcm_vhost_deregister_configfs(void)
1583 {
1584         if (!tcm_vhost_fabric_configfs)
1585                 return;
1586
1587         target_fabric_configfs_deregister(tcm_vhost_fabric_configfs);
1588         tcm_vhost_fabric_configfs = NULL;
1589         pr_debug("TCM_VHOST[0] - Cleared tcm_vhost_fabric_configfs\n");
1590 };
1591
1592 static int __init tcm_vhost_init(void)
1593 {
1594         int ret = -ENOMEM;
1595
1596         tcm_vhost_workqueue = alloc_workqueue("tcm_vhost", 0, 0);
1597         if (!tcm_vhost_workqueue)
1598                 goto out;
1599
1600         ret = vhost_scsi_register();
1601         if (ret < 0)
1602                 goto out_destroy_workqueue;
1603
1604         ret = tcm_vhost_register_configfs();
1605         if (ret < 0)
1606                 goto out_vhost_scsi_deregister;
1607
1608         return 0;
1609
1610 out_vhost_scsi_deregister:
1611         vhost_scsi_deregister();
1612 out_destroy_workqueue:
1613         destroy_workqueue(tcm_vhost_workqueue);
1614 out:
1615         return ret;
1616 };
1617
1618 static void tcm_vhost_exit(void)
1619 {
1620         tcm_vhost_deregister_configfs();
1621         vhost_scsi_deregister();
1622         destroy_workqueue(tcm_vhost_workqueue);
1623 };
1624
1625 MODULE_DESCRIPTION("TCM_VHOST series fabric driver");
1626 MODULE_LICENSE("GPL");
1627 module_init(tcm_vhost_init);
1628 module_exit(tcm_vhost_exit);