aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--block/blk-core.c4
-rw-r--r--block/blk-mq-cpumap.c4
-rw-r--r--drivers/block/nbd.c18
-rw-r--r--drivers/block/xen-blkfront.c25
-rw-r--r--drivers/lightnvm/pblk-rb.c4
-rw-r--r--drivers/lightnvm/pblk-read.c23
-rw-r--r--drivers/lightnvm/pblk.h2
-rw-r--r--drivers/nvme/host/core.c6
-rw-r--r--drivers/nvme/host/fc.c121
-rw-r--r--drivers/nvme/host/pci.c6
-rw-r--r--drivers/nvme/target/fc.c101
-rw-r--r--include/linux/nvme-fc.h19
-rw-r--r--include/linux/nvme.h2
13 files changed, 197 insertions, 138 deletions
diff --git a/block/blk-core.c b/block/blk-core.c
index 970b9c9638c5..dbecbf4a64e0 100644
--- a/block/blk-core.c
+++ b/block/blk-core.c
@@ -3421,6 +3421,10 @@ EXPORT_SYMBOL(blk_finish_plug);
3421 */ 3421 */
3422void blk_pm_runtime_init(struct request_queue *q, struct device *dev) 3422void blk_pm_runtime_init(struct request_queue *q, struct device *dev)
3423{ 3423{
3424 /* not support for RQF_PM and ->rpm_status in blk-mq yet */
3425 if (q->mq_ops)
3426 return;
3427
3424 q->dev = dev; 3428 q->dev = dev;
3425 q->rpm_status = RPM_ACTIVE; 3429 q->rpm_status = RPM_ACTIVE;
3426 pm_runtime_set_autosuspend_delay(q->dev, -1); 3430 pm_runtime_set_autosuspend_delay(q->dev, -1);
diff --git a/block/blk-mq-cpumap.c b/block/blk-mq-cpumap.c
index 4891f042a22f..9f8cffc8a701 100644
--- a/block/blk-mq-cpumap.c
+++ b/block/blk-mq-cpumap.c
@@ -17,9 +17,9 @@
17static int cpu_to_queue_index(unsigned int nr_queues, const int cpu) 17static int cpu_to_queue_index(unsigned int nr_queues, const int cpu)
18{ 18{
19 /* 19 /*
20 * Non online CPU will be mapped to queue index 0. 20 * Non present CPU will be mapped to queue index 0.
21 */ 21 */
22 if (!cpu_online(cpu)) 22 if (!cpu_present(cpu))
23 return 0; 23 return 0;
24 return cpu % nr_queues; 24 return cpu % nr_queues;
25} 25}
diff --git a/drivers/block/nbd.c b/drivers/block/nbd.c
index 87a0a29f6e7e..5bdf923294a5 100644
--- a/drivers/block/nbd.c
+++ b/drivers/block/nbd.c
@@ -908,7 +908,8 @@ static int nbd_reconnect_socket(struct nbd_device *nbd, unsigned long arg)
908 continue; 908 continue;
909 } 909 }
910 sk_set_memalloc(sock->sk); 910 sk_set_memalloc(sock->sk);
911 sock->sk->sk_sndtimeo = nbd->tag_set.timeout; 911 if (nbd->tag_set.timeout)
912 sock->sk->sk_sndtimeo = nbd->tag_set.timeout;
912 atomic_inc(&config->recv_threads); 913 atomic_inc(&config->recv_threads);
913 refcount_inc(&nbd->config_refs); 914 refcount_inc(&nbd->config_refs);
914 old = nsock->sock; 915 old = nsock->sock;
@@ -922,6 +923,8 @@ static int nbd_reconnect_socket(struct nbd_device *nbd, unsigned long arg)
922 mutex_unlock(&nsock->tx_lock); 923 mutex_unlock(&nsock->tx_lock);
923 sockfd_put(old); 924 sockfd_put(old);
924 925
926 clear_bit(NBD_DISCONNECTED, &config->runtime_flags);
927
925 /* We take the tx_mutex in an error path in the recv_work, so we 928 /* We take the tx_mutex in an error path in the recv_work, so we
926 * need to queue_work outside of the tx_mutex. 929 * need to queue_work outside of the tx_mutex.
927 */ 930 */
@@ -978,11 +981,15 @@ static void send_disconnects(struct nbd_device *nbd)
978 int i, ret; 981 int i, ret;
979 982
980 for (i = 0; i < config->num_connections; i++) { 983 for (i = 0; i < config->num_connections; i++) {
984 struct nbd_sock *nsock = config->socks[i];
985
981 iov_iter_kvec(&from, WRITE | ITER_KVEC, &iov, 1, sizeof(request)); 986 iov_iter_kvec(&from, WRITE | ITER_KVEC, &iov, 1, sizeof(request));
987 mutex_lock(&nsock->tx_lock);
982 ret = sock_xmit(nbd, i, 1, &from, 0, NULL); 988 ret = sock_xmit(nbd, i, 1, &from, 0, NULL);
983 if (ret <= 0) 989 if (ret <= 0)
984 dev_err(disk_to_dev(nbd->disk), 990 dev_err(disk_to_dev(nbd->disk),
985 "Send disconnect failed %d\n", ret); 991 "Send disconnect failed %d\n", ret);
992 mutex_unlock(&nsock->tx_lock);
986 } 993 }
987} 994}
988 995
@@ -991,9 +998,8 @@ static int nbd_disconnect(struct nbd_device *nbd)
991 struct nbd_config *config = nbd->config; 998 struct nbd_config *config = nbd->config;
992 999
993 dev_info(disk_to_dev(nbd->disk), "NBD_DISCONNECT\n"); 1000 dev_info(disk_to_dev(nbd->disk), "NBD_DISCONNECT\n");
994 if (!test_and_set_bit(NBD_DISCONNECT_REQUESTED, 1001 set_bit(NBD_DISCONNECT_REQUESTED, &config->runtime_flags);
995 &config->runtime_flags)) 1002 send_disconnects(nbd);
996 send_disconnects(nbd);
997 return 0; 1003 return 0;
998} 1004}
999 1005
@@ -1074,7 +1080,9 @@ static int nbd_start_device(struct nbd_device *nbd)
1074 return -ENOMEM; 1080 return -ENOMEM;
1075 } 1081 }
1076 sk_set_memalloc(config->socks[i]->sock->sk); 1082 sk_set_memalloc(config->socks[i]->sock->sk);
1077 config->socks[i]->sock->sk->sk_sndtimeo = nbd->tag_set.timeout; 1083 if (nbd->tag_set.timeout)
1084 config->socks[i]->sock->sk->sk_sndtimeo =
1085 nbd->tag_set.timeout;
1078 atomic_inc(&config->recv_threads); 1086 atomic_inc(&config->recv_threads);
1079 refcount_inc(&nbd->config_refs); 1087 refcount_inc(&nbd->config_refs);
1080 INIT_WORK(&args->work, recv_work); 1088 INIT_WORK(&args->work, recv_work);
diff --git a/drivers/block/xen-blkfront.c b/drivers/block/xen-blkfront.c
index c852ed3c01d5..98e34e4c62b8 100644
--- a/drivers/block/xen-blkfront.c
+++ b/drivers/block/xen-blkfront.c
@@ -111,7 +111,7 @@ struct blk_shadow {
111}; 111};
112 112
113struct blkif_req { 113struct blkif_req {
114 int error; 114 blk_status_t error;
115}; 115};
116 116
117static inline struct blkif_req *blkif_req(struct request *rq) 117static inline struct blkif_req *blkif_req(struct request *rq)
@@ -708,6 +708,7 @@ static int blkif_queue_rw_req(struct request *req, struct blkfront_ring_info *ri
708 * existing persistent grants, or if we have to get new grants, 708 * existing persistent grants, or if we have to get new grants,
709 * as there are not sufficiently many free. 709 * as there are not sufficiently many free.
710 */ 710 */
711 bool new_persistent_gnts = false;
711 struct scatterlist *sg; 712 struct scatterlist *sg;
712 int num_sg, max_grefs, num_grant; 713 int num_sg, max_grefs, num_grant;
713 714
@@ -719,19 +720,21 @@ static int blkif_queue_rw_req(struct request *req, struct blkfront_ring_info *ri
719 */ 720 */
720 max_grefs += INDIRECT_GREFS(max_grefs); 721 max_grefs += INDIRECT_GREFS(max_grefs);
721 722
722 /* 723 /* Check if we have enough persistent grants to allocate a requests */
723 * We have to reserve 'max_grefs' grants because persistent 724 if (rinfo->persistent_gnts_c < max_grefs) {
724 * grants are shared by all rings. 725 new_persistent_gnts = true;
725 */ 726
726 if (max_grefs > 0) 727 if (gnttab_alloc_grant_references(
727 if (gnttab_alloc_grant_references(max_grefs, &setup.gref_head) < 0) { 728 max_grefs - rinfo->persistent_gnts_c,
729 &setup.gref_head) < 0) {
728 gnttab_request_free_callback( 730 gnttab_request_free_callback(
729 &rinfo->callback, 731 &rinfo->callback,
730 blkif_restart_queue_callback, 732 blkif_restart_queue_callback,
731 rinfo, 733 rinfo,
732 max_grefs); 734 max_grefs - rinfo->persistent_gnts_c);
733 return 1; 735 return 1;
734 } 736 }
737 }
735 738
736 /* Fill out a communications ring structure. */ 739 /* Fill out a communications ring structure. */
737 id = blkif_ring_get_request(rinfo, req, &ring_req); 740 id = blkif_ring_get_request(rinfo, req, &ring_req);
@@ -832,7 +835,7 @@ static int blkif_queue_rw_req(struct request *req, struct blkfront_ring_info *ri
832 if (unlikely(require_extra_req)) 835 if (unlikely(require_extra_req))
833 rinfo->shadow[extra_id].req = *extra_ring_req; 836 rinfo->shadow[extra_id].req = *extra_ring_req;
834 837
835 if (max_grefs > 0) 838 if (new_persistent_gnts)
836 gnttab_free_grant_references(setup.gref_head); 839 gnttab_free_grant_references(setup.gref_head);
837 840
838 return 0; 841 return 0;
@@ -906,8 +909,8 @@ out_err:
906 return BLK_STS_IOERR; 909 return BLK_STS_IOERR;
907 910
908out_busy: 911out_busy:
909 spin_unlock_irqrestore(&rinfo->ring_lock, flags);
910 blk_mq_stop_hw_queue(hctx); 912 blk_mq_stop_hw_queue(hctx);
913 spin_unlock_irqrestore(&rinfo->ring_lock, flags);
911 return BLK_STS_RESOURCE; 914 return BLK_STS_RESOURCE;
912} 915}
913 916
@@ -1616,7 +1619,7 @@ static irqreturn_t blkif_interrupt(int irq, void *dev_id)
1616 if (unlikely(bret->status == BLKIF_RSP_EOPNOTSUPP)) { 1619 if (unlikely(bret->status == BLKIF_RSP_EOPNOTSUPP)) {
1617 printk(KERN_WARNING "blkfront: %s: %s op failed\n", 1620 printk(KERN_WARNING "blkfront: %s: %s op failed\n",
1618 info->gd->disk_name, op_name(bret->operation)); 1621 info->gd->disk_name, op_name(bret->operation));
1619 blkif_req(req)->error = -EOPNOTSUPP; 1622 blkif_req(req)->error = BLK_STS_NOTSUPP;
1620 } 1623 }
1621 if (unlikely(bret->status == BLKIF_RSP_ERROR && 1624 if (unlikely(bret->status == BLKIF_RSP_ERROR &&
1622 rinfo->shadow[id].req.u.rw.nr_segments == 0)) { 1625 rinfo->shadow[id].req.u.rw.nr_segments == 0)) {
diff --git a/drivers/lightnvm/pblk-rb.c b/drivers/lightnvm/pblk-rb.c
index 5ecc154f6831..9bc32578a766 100644
--- a/drivers/lightnvm/pblk-rb.c
+++ b/drivers/lightnvm/pblk-rb.c
@@ -657,7 +657,7 @@ try:
657 * be directed to disk. 657 * be directed to disk.
658 */ 658 */
659int pblk_rb_copy_to_bio(struct pblk_rb *rb, struct bio *bio, sector_t lba, 659int pblk_rb_copy_to_bio(struct pblk_rb *rb, struct bio *bio, sector_t lba,
660 struct ppa_addr ppa, int bio_iter) 660 struct ppa_addr ppa, int bio_iter, bool advanced_bio)
661{ 661{
662 struct pblk *pblk = container_of(rb, struct pblk, rwb); 662 struct pblk *pblk = container_of(rb, struct pblk, rwb);
663 struct pblk_rb_entry *entry; 663 struct pblk_rb_entry *entry;
@@ -694,7 +694,7 @@ int pblk_rb_copy_to_bio(struct pblk_rb *rb, struct bio *bio, sector_t lba,
694 * filled with data from the cache). If part of the data resides on the 694 * filled with data from the cache). If part of the data resides on the
695 * media, we will read later on 695 * media, we will read later on
696 */ 696 */
697 if (unlikely(!bio->bi_iter.bi_idx)) 697 if (unlikely(!advanced_bio))
698 bio_advance(bio, bio_iter * PBLK_EXPOSED_PAGE_SIZE); 698 bio_advance(bio, bio_iter * PBLK_EXPOSED_PAGE_SIZE);
699 699
700 data = bio_data(bio); 700 data = bio_data(bio);
diff --git a/drivers/lightnvm/pblk-read.c b/drivers/lightnvm/pblk-read.c
index 4e5c48f3de62..d682e89e6493 100644
--- a/drivers/lightnvm/pblk-read.c
+++ b/drivers/lightnvm/pblk-read.c
@@ -26,7 +26,7 @@
26 */ 26 */
27static int pblk_read_from_cache(struct pblk *pblk, struct bio *bio, 27static int pblk_read_from_cache(struct pblk *pblk, struct bio *bio,
28 sector_t lba, struct ppa_addr ppa, 28 sector_t lba, struct ppa_addr ppa,
29 int bio_iter) 29 int bio_iter, bool advanced_bio)
30{ 30{
31#ifdef CONFIG_NVM_DEBUG 31#ifdef CONFIG_NVM_DEBUG
32 /* Callers must ensure that the ppa points to a cache address */ 32 /* Callers must ensure that the ppa points to a cache address */
@@ -34,7 +34,8 @@ static int pblk_read_from_cache(struct pblk *pblk, struct bio *bio,
34 BUG_ON(!pblk_addr_in_cache(ppa)); 34 BUG_ON(!pblk_addr_in_cache(ppa));
35#endif 35#endif
36 36
37 return pblk_rb_copy_to_bio(&pblk->rwb, bio, lba, ppa, bio_iter); 37 return pblk_rb_copy_to_bio(&pblk->rwb, bio, lba, ppa,
38 bio_iter, advanced_bio);
38} 39}
39 40
40static void pblk_read_ppalist_rq(struct pblk *pblk, struct nvm_rq *rqd, 41static void pblk_read_ppalist_rq(struct pblk *pblk, struct nvm_rq *rqd,
@@ -44,7 +45,7 @@ static void pblk_read_ppalist_rq(struct pblk *pblk, struct nvm_rq *rqd,
44 struct ppa_addr ppas[PBLK_MAX_REQ_ADDRS]; 45 struct ppa_addr ppas[PBLK_MAX_REQ_ADDRS];
45 sector_t blba = pblk_get_lba(bio); 46 sector_t blba = pblk_get_lba(bio);
46 int nr_secs = rqd->nr_ppas; 47 int nr_secs = rqd->nr_ppas;
47 int advanced_bio = 0; 48 bool advanced_bio = false;
48 int i, j = 0; 49 int i, j = 0;
49 50
50 /* logic error: lba out-of-bounds. Ignore read request */ 51 /* logic error: lba out-of-bounds. Ignore read request */
@@ -62,19 +63,26 @@ static void pblk_read_ppalist_rq(struct pblk *pblk, struct nvm_rq *rqd,
62retry: 63retry:
63 if (pblk_ppa_empty(p)) { 64 if (pblk_ppa_empty(p)) {
64 WARN_ON(test_and_set_bit(i, read_bitmap)); 65 WARN_ON(test_and_set_bit(i, read_bitmap));
65 continue; 66
67 if (unlikely(!advanced_bio)) {
68 bio_advance(bio, (i) * PBLK_EXPOSED_PAGE_SIZE);
69 advanced_bio = true;
70 }
71
72 goto next;
66 } 73 }
67 74
68 /* Try to read from write buffer. The address is later checked 75 /* Try to read from write buffer. The address is later checked
69 * on the write buffer to prevent retrieving overwritten data. 76 * on the write buffer to prevent retrieving overwritten data.
70 */ 77 */
71 if (pblk_addr_in_cache(p)) { 78 if (pblk_addr_in_cache(p)) {
72 if (!pblk_read_from_cache(pblk, bio, lba, p, i)) { 79 if (!pblk_read_from_cache(pblk, bio, lba, p, i,
80 advanced_bio)) {
73 pblk_lookup_l2p_seq(pblk, &p, lba, 1); 81 pblk_lookup_l2p_seq(pblk, &p, lba, 1);
74 goto retry; 82 goto retry;
75 } 83 }
76 WARN_ON(test_and_set_bit(i, read_bitmap)); 84 WARN_ON(test_and_set_bit(i, read_bitmap));
77 advanced_bio = 1; 85 advanced_bio = true;
78#ifdef CONFIG_NVM_DEBUG 86#ifdef CONFIG_NVM_DEBUG
79 atomic_long_inc(&pblk->cache_reads); 87 atomic_long_inc(&pblk->cache_reads);
80#endif 88#endif
@@ -83,6 +91,7 @@ retry:
83 rqd->ppa_list[j++] = p; 91 rqd->ppa_list[j++] = p;
84 } 92 }
85 93
94next:
86 if (advanced_bio) 95 if (advanced_bio)
87 bio_advance(bio, PBLK_EXPOSED_PAGE_SIZE); 96 bio_advance(bio, PBLK_EXPOSED_PAGE_SIZE);
88 } 97 }
@@ -282,7 +291,7 @@ retry:
282 * write buffer to prevent retrieving overwritten data. 291 * write buffer to prevent retrieving overwritten data.
283 */ 292 */
284 if (pblk_addr_in_cache(ppa)) { 293 if (pblk_addr_in_cache(ppa)) {
285 if (!pblk_read_from_cache(pblk, bio, lba, ppa, 0)) { 294 if (!pblk_read_from_cache(pblk, bio, lba, ppa, 0, 1)) {
286 pblk_lookup_l2p_seq(pblk, &ppa, lba, 1); 295 pblk_lookup_l2p_seq(pblk, &ppa, lba, 1);
287 goto retry; 296 goto retry;
288 } 297 }
diff --git a/drivers/lightnvm/pblk.h b/drivers/lightnvm/pblk.h
index 0c5692cc2f60..67e623bd5c2d 100644
--- a/drivers/lightnvm/pblk.h
+++ b/drivers/lightnvm/pblk.h
@@ -670,7 +670,7 @@ unsigned int pblk_rb_read_to_bio_list(struct pblk_rb *rb, struct bio *bio,
670 struct list_head *list, 670 struct list_head *list,
671 unsigned int max); 671 unsigned int max);
672int pblk_rb_copy_to_bio(struct pblk_rb *rb, struct bio *bio, sector_t lba, 672int pblk_rb_copy_to_bio(struct pblk_rb *rb, struct bio *bio, sector_t lba,
673 struct ppa_addr ppa, int bio_iter); 673 struct ppa_addr ppa, int bio_iter, bool advanced_bio);
674unsigned int pblk_rb_read_commit(struct pblk_rb *rb, unsigned int entries); 674unsigned int pblk_rb_read_commit(struct pblk_rb *rb, unsigned int entries);
675 675
676unsigned int pblk_rb_sync_init(struct pblk_rb *rb, unsigned long *flags); 676unsigned int pblk_rb_sync_init(struct pblk_rb *rb, unsigned long *flags);
diff --git a/drivers/nvme/host/core.c b/drivers/nvme/host/core.c
index 3b77cfe5aa1e..c49f1f8b2e57 100644
--- a/drivers/nvme/host/core.c
+++ b/drivers/nvme/host/core.c
@@ -1995,6 +1995,9 @@ static ssize_t wwid_show(struct device *dev, struct device_attribute *attr,
1995 int serial_len = sizeof(ctrl->serial); 1995 int serial_len = sizeof(ctrl->serial);
1996 int model_len = sizeof(ctrl->model); 1996 int model_len = sizeof(ctrl->model);
1997 1997
1998 if (!uuid_is_null(&ns->uuid))
1999 return sprintf(buf, "uuid.%pU\n", &ns->uuid);
2000
1998 if (memchr_inv(ns->nguid, 0, sizeof(ns->nguid))) 2001 if (memchr_inv(ns->nguid, 0, sizeof(ns->nguid)))
1999 return sprintf(buf, "eui.%16phN\n", ns->nguid); 2002 return sprintf(buf, "eui.%16phN\n", ns->nguid);
2000 2003
@@ -2709,7 +2712,8 @@ void nvme_kill_queues(struct nvme_ctrl *ctrl)
2709 mutex_lock(&ctrl->namespaces_mutex); 2712 mutex_lock(&ctrl->namespaces_mutex);
2710 2713
2711 /* Forcibly unquiesce queues to avoid blocking dispatch */ 2714 /* Forcibly unquiesce queues to avoid blocking dispatch */
2712 blk_mq_unquiesce_queue(ctrl->admin_q); 2715 if (ctrl->admin_q)
2716 blk_mq_unquiesce_queue(ctrl->admin_q);
2713 2717
2714 list_for_each_entry(ns, &ctrl->namespaces, list) { 2718 list_for_each_entry(ns, &ctrl->namespaces, list) {
2715 /* 2719 /*
diff --git a/drivers/nvme/host/fc.c b/drivers/nvme/host/fc.c
index d666ada39a9b..5c2a08ef08ba 100644
--- a/drivers/nvme/host/fc.c
+++ b/drivers/nvme/host/fc.c
@@ -1888,7 +1888,7 @@ nvme_fc_start_fcp_op(struct nvme_fc_ctrl *ctrl, struct nvme_fc_queue *queue,
1888 * the target device is present 1888 * the target device is present
1889 */ 1889 */
1890 if (ctrl->rport->remoteport.port_state != FC_OBJSTATE_ONLINE) 1890 if (ctrl->rport->remoteport.port_state != FC_OBJSTATE_ONLINE)
1891 return BLK_STS_IOERR; 1891 goto busy;
1892 1892
1893 if (!nvme_fc_ctrl_get(ctrl)) 1893 if (!nvme_fc_ctrl_get(ctrl))
1894 return BLK_STS_IOERR; 1894 return BLK_STS_IOERR;
@@ -1958,22 +1958,25 @@ nvme_fc_start_fcp_op(struct nvme_fc_ctrl *ctrl, struct nvme_fc_queue *queue,
1958 queue->lldd_handle, &op->fcp_req); 1958 queue->lldd_handle, &op->fcp_req);
1959 1959
1960 if (ret) { 1960 if (ret) {
1961 if (op->rq) /* normal request */ 1961 if (!(op->flags & FCOP_FLAGS_AEN))
1962 nvme_fc_unmap_data(ctrl, op->rq, op); 1962 nvme_fc_unmap_data(ctrl, op->rq, op);
1963 /* else - aen. no cleanup needed */
1964 1963
1965 nvme_fc_ctrl_put(ctrl); 1964 nvme_fc_ctrl_put(ctrl);
1966 1965
1967 if (ret != -EBUSY) 1966 if (ctrl->rport->remoteport.port_state == FC_OBJSTATE_ONLINE &&
1967 ret != -EBUSY)
1968 return BLK_STS_IOERR; 1968 return BLK_STS_IOERR;
1969 1969
1970 if (op->rq) 1970 goto busy;
1971 blk_mq_delay_run_hw_queue(queue->hctx, NVMEFC_QUEUE_DELAY);
1972
1973 return BLK_STS_RESOURCE;
1974 } 1971 }
1975 1972
1976 return BLK_STS_OK; 1973 return BLK_STS_OK;
1974
1975busy:
1976 if (!(op->flags & FCOP_FLAGS_AEN) && queue->hctx)
1977 blk_mq_delay_run_hw_queue(queue->hctx, NVMEFC_QUEUE_DELAY);
1978
1979 return BLK_STS_RESOURCE;
1977} 1980}
1978 1981
1979static blk_status_t 1982static blk_status_t
@@ -2802,66 +2805,70 @@ out_fail:
2802 return ERR_PTR(ret); 2805 return ERR_PTR(ret);
2803} 2806}
2804 2807
2805enum {
2806 FCT_TRADDR_ERR = 0,
2807 FCT_TRADDR_WWNN = 1 << 0,
2808 FCT_TRADDR_WWPN = 1 << 1,
2809};
2810 2808
2811struct nvmet_fc_traddr { 2809struct nvmet_fc_traddr {
2812 u64 nn; 2810 u64 nn;
2813 u64 pn; 2811 u64 pn;
2814}; 2812};
2815 2813
2816static const match_table_t traddr_opt_tokens = {
2817 { FCT_TRADDR_WWNN, "nn-%s" },
2818 { FCT_TRADDR_WWPN, "pn-%s" },
2819 { FCT_TRADDR_ERR, NULL }
2820};
2821
2822static int 2814static int
2823nvme_fc_parse_address(struct nvmet_fc_traddr *traddr, char *buf) 2815__nvme_fc_parse_u64(substring_t *sstr, u64 *val)
2824{ 2816{
2825 substring_t args[MAX_OPT_ARGS];
2826 char *options, *o, *p;
2827 int token, ret = 0;
2828 u64 token64; 2817 u64 token64;
2829 2818
2830 options = o = kstrdup(buf, GFP_KERNEL); 2819 if (match_u64(sstr, &token64))
2831 if (!options) 2820 return -EINVAL;
2832 return -ENOMEM; 2821 *val = token64;
2833 2822
2834 while ((p = strsep(&o, ":\n")) != NULL) { 2823 return 0;
2835 if (!*p) 2824}
2836 continue;
2837 2825
2838 token = match_token(p, traddr_opt_tokens, args); 2826/*
2839 switch (token) { 2827 * This routine validates and extracts the WWN's from the TRADDR string.
2840 case FCT_TRADDR_WWNN: 2828 * As kernel parsers need the 0x to determine number base, universally
2841 if (match_u64(args, &token64)) { 2829 * build string to parse with 0x prefix before parsing name strings.
2842 ret = -EINVAL; 2830 */
2843 goto out; 2831static int
2844 } 2832nvme_fc_parse_traddr(struct nvmet_fc_traddr *traddr, char *buf, size_t blen)
2845 traddr->nn = token64; 2833{
2846 break; 2834 char name[2 + NVME_FC_TRADDR_HEXNAMELEN + 1];
2847 case FCT_TRADDR_WWPN: 2835 substring_t wwn = { name, &name[sizeof(name)-1] };
2848 if (match_u64(args, &token64)) { 2836 int nnoffset, pnoffset;
2849 ret = -EINVAL; 2837
2850 goto out; 2838 /* validate it string one of the 2 allowed formats */
2851 } 2839 if (strnlen(buf, blen) == NVME_FC_TRADDR_MAXLENGTH &&
2852 traddr->pn = token64; 2840 !strncmp(buf, "nn-0x", NVME_FC_TRADDR_OXNNLEN) &&
2853 break; 2841 !strncmp(&buf[NVME_FC_TRADDR_MAX_PN_OFFSET],
2854 default: 2842 "pn-0x", NVME_FC_TRADDR_OXNNLEN)) {
2855 pr_warn("unknown traddr token or missing value '%s'\n", 2843 nnoffset = NVME_FC_TRADDR_OXNNLEN;
2856 p); 2844 pnoffset = NVME_FC_TRADDR_MAX_PN_OFFSET +
2857 ret = -EINVAL; 2845 NVME_FC_TRADDR_OXNNLEN;
2858 goto out; 2846 } else if ((strnlen(buf, blen) == NVME_FC_TRADDR_MINLENGTH &&
2859 } 2847 !strncmp(buf, "nn-", NVME_FC_TRADDR_NNLEN) &&
2860 } 2848 !strncmp(&buf[NVME_FC_TRADDR_MIN_PN_OFFSET],
2849 "pn-", NVME_FC_TRADDR_NNLEN))) {
2850 nnoffset = NVME_FC_TRADDR_NNLEN;
2851 pnoffset = NVME_FC_TRADDR_MIN_PN_OFFSET + NVME_FC_TRADDR_NNLEN;
2852 } else
2853 goto out_einval;
2861 2854
2862out: 2855 name[0] = '0';
2863 kfree(options); 2856 name[1] = 'x';
2864 return ret; 2857 name[2 + NVME_FC_TRADDR_HEXNAMELEN] = 0;
2858
2859 memcpy(&name[2], &buf[nnoffset], NVME_FC_TRADDR_HEXNAMELEN);
2860 if (__nvme_fc_parse_u64(&wwn, &traddr->nn))
2861 goto out_einval;
2862
2863 memcpy(&name[2], &buf[pnoffset], NVME_FC_TRADDR_HEXNAMELEN);
2864 if (__nvme_fc_parse_u64(&wwn, &traddr->pn))
2865 goto out_einval;
2866
2867 return 0;
2868
2869out_einval:
2870 pr_warn("%s: bad traddr string\n", __func__);
2871 return -EINVAL;
2865} 2872}
2866 2873
2867static struct nvme_ctrl * 2874static struct nvme_ctrl *
@@ -2875,11 +2882,11 @@ nvme_fc_create_ctrl(struct device *dev, struct nvmf_ctrl_options *opts)
2875 unsigned long flags; 2882 unsigned long flags;
2876 int ret; 2883 int ret;
2877 2884
2878 ret = nvme_fc_parse_address(&raddr, opts->traddr); 2885 ret = nvme_fc_parse_traddr(&raddr, opts->traddr, NVMF_TRADDR_SIZE);
2879 if (ret || !raddr.nn || !raddr.pn) 2886 if (ret || !raddr.nn || !raddr.pn)
2880 return ERR_PTR(-EINVAL); 2887 return ERR_PTR(-EINVAL);
2881 2888
2882 ret = nvme_fc_parse_address(&laddr, opts->host_traddr); 2889 ret = nvme_fc_parse_traddr(&laddr, opts->host_traddr, NVMF_TRADDR_SIZE);
2883 if (ret || !laddr.nn || !laddr.pn) 2890 if (ret || !laddr.nn || !laddr.pn)
2884 return ERR_PTR(-EINVAL); 2891 return ERR_PTR(-EINVAL);
2885 2892
diff --git a/drivers/nvme/host/pci.c b/drivers/nvme/host/pci.c
index 8569ee771269..cd888a47d0fc 100644
--- a/drivers/nvme/host/pci.c
+++ b/drivers/nvme/host/pci.c
@@ -1619,7 +1619,7 @@ static void nvme_free_host_mem(struct nvme_dev *dev)
1619static int nvme_alloc_host_mem(struct nvme_dev *dev, u64 min, u64 preferred) 1619static int nvme_alloc_host_mem(struct nvme_dev *dev, u64 min, u64 preferred)
1620{ 1620{
1621 struct nvme_host_mem_buf_desc *descs; 1621 struct nvme_host_mem_buf_desc *descs;
1622 u32 chunk_size, max_entries; 1622 u32 chunk_size, max_entries, len;
1623 int i = 0; 1623 int i = 0;
1624 void **bufs; 1624 void **bufs;
1625 u64 size = 0, tmp; 1625 u64 size = 0, tmp;
@@ -1638,10 +1638,10 @@ retry:
1638 if (!bufs) 1638 if (!bufs)
1639 goto out_free_descs; 1639 goto out_free_descs;
1640 1640
1641 for (size = 0; size < preferred; size += chunk_size) { 1641 for (size = 0; size < preferred; size += len) {
1642 u32 len = min_t(u64, chunk_size, preferred - size);
1643 dma_addr_t dma_addr; 1642 dma_addr_t dma_addr;
1644 1643
1644 len = min_t(u64, chunk_size, preferred - size);
1645 bufs[i] = dma_alloc_attrs(dev->dev, len, &dma_addr, GFP_KERNEL, 1645 bufs[i] = dma_alloc_attrs(dev->dev, len, &dma_addr, GFP_KERNEL,
1646 DMA_ATTR_NO_KERNEL_MAPPING | DMA_ATTR_NO_WARN); 1646 DMA_ATTR_NO_KERNEL_MAPPING | DMA_ATTR_NO_WARN);
1647 if (!bufs[i]) 1647 if (!bufs[i])
diff --git a/drivers/nvme/target/fc.c b/drivers/nvme/target/fc.c
index d5801c150b1c..31ca55dfcb1d 100644
--- a/drivers/nvme/target/fc.c
+++ b/drivers/nvme/target/fc.c
@@ -2293,66 +2293,70 @@ nvmet_fc_rcv_fcp_abort(struct nvmet_fc_target_port *target_port,
2293} 2293}
2294EXPORT_SYMBOL_GPL(nvmet_fc_rcv_fcp_abort); 2294EXPORT_SYMBOL_GPL(nvmet_fc_rcv_fcp_abort);
2295 2295
2296enum {
2297 FCT_TRADDR_ERR = 0,
2298 FCT_TRADDR_WWNN = 1 << 0,
2299 FCT_TRADDR_WWPN = 1 << 1,
2300};
2301 2296
2302struct nvmet_fc_traddr { 2297struct nvmet_fc_traddr {
2303 u64 nn; 2298 u64 nn;
2304 u64 pn; 2299 u64 pn;
2305}; 2300};
2306 2301
2307static const match_table_t traddr_opt_tokens = {
2308 { FCT_TRADDR_WWNN, "nn-%s" },
2309 { FCT_TRADDR_WWPN, "pn-%s" },
2310 { FCT_TRADDR_ERR, NULL }
2311};
2312
2313static int 2302static int
2314nvmet_fc_parse_traddr(struct nvmet_fc_traddr *traddr, char *buf) 2303__nvme_fc_parse_u64(substring_t *sstr, u64 *val)
2315{ 2304{
2316 substring_t args[MAX_OPT_ARGS];
2317 char *options, *o, *p;
2318 int token, ret = 0;
2319 u64 token64; 2305 u64 token64;
2320 2306
2321 options = o = kstrdup(buf, GFP_KERNEL); 2307 if (match_u64(sstr, &token64))
2322 if (!options) 2308 return -EINVAL;
2323 return -ENOMEM; 2309 *val = token64;
2324 2310
2325 while ((p = strsep(&o, ":\n")) != NULL) { 2311 return 0;
2326 if (!*p) 2312}
2327 continue;
2328 2313
2329 token = match_token(p, traddr_opt_tokens, args); 2314/*
2330 switch (token) { 2315 * This routine validates and extracts the WWN's from the TRADDR string.
2331 case FCT_TRADDR_WWNN: 2316 * As kernel parsers need the 0x to determine number base, universally
2332 if (match_u64(args, &token64)) { 2317 * build string to parse with 0x prefix before parsing name strings.
2333 ret = -EINVAL; 2318 */
2334 goto out; 2319static int
2335 } 2320nvme_fc_parse_traddr(struct nvmet_fc_traddr *traddr, char *buf, size_t blen)
2336 traddr->nn = token64; 2321{
2337 break; 2322 char name[2 + NVME_FC_TRADDR_HEXNAMELEN + 1];
2338 case FCT_TRADDR_WWPN: 2323 substring_t wwn = { name, &name[sizeof(name)-1] };
2339 if (match_u64(args, &token64)) { 2324 int nnoffset, pnoffset;
2340 ret = -EINVAL; 2325
2341 goto out; 2326 /* validate it string one of the 2 allowed formats */
2342 } 2327 if (strnlen(buf, blen) == NVME_FC_TRADDR_MAXLENGTH &&
2343 traddr->pn = token64; 2328 !strncmp(buf, "nn-0x", NVME_FC_TRADDR_OXNNLEN) &&
2344 break; 2329 !strncmp(&buf[NVME_FC_TRADDR_MAX_PN_OFFSET],
2345 default: 2330 "pn-0x", NVME_FC_TRADDR_OXNNLEN)) {
2346 pr_warn("unknown traddr token or missing value '%s'\n", 2331 nnoffset = NVME_FC_TRADDR_OXNNLEN;
2347 p); 2332 pnoffset = NVME_FC_TRADDR_MAX_PN_OFFSET +
2348 ret = -EINVAL; 2333 NVME_FC_TRADDR_OXNNLEN;
2349 goto out; 2334 } else if ((strnlen(buf, blen) == NVME_FC_TRADDR_MINLENGTH &&
2350 } 2335 !strncmp(buf, "nn-", NVME_FC_TRADDR_NNLEN) &&
2351 } 2336 !strncmp(&buf[NVME_FC_TRADDR_MIN_PN_OFFSET],
2337 "pn-", NVME_FC_TRADDR_NNLEN))) {
2338 nnoffset = NVME_FC_TRADDR_NNLEN;
2339 pnoffset = NVME_FC_TRADDR_MIN_PN_OFFSET + NVME_FC_TRADDR_NNLEN;
2340 } else
2341 goto out_einval;
2342
2343 name[0] = '0';
2344 name[1] = 'x';
2345 name[2 + NVME_FC_TRADDR_HEXNAMELEN] = 0;
2346
2347 memcpy(&name[2], &buf[nnoffset], NVME_FC_TRADDR_HEXNAMELEN);
2348 if (__nvme_fc_parse_u64(&wwn, &traddr->nn))
2349 goto out_einval;
2350
2351 memcpy(&name[2], &buf[pnoffset], NVME_FC_TRADDR_HEXNAMELEN);
2352 if (__nvme_fc_parse_u64(&wwn, &traddr->pn))
2353 goto out_einval;
2352 2354
2353out: 2355 return 0;
2354 kfree(options); 2356
2355 return ret; 2357out_einval:
2358 pr_warn("%s: bad traddr string\n", __func__);
2359 return -EINVAL;
2356} 2360}
2357 2361
2358static int 2362static int
@@ -2370,7 +2374,8 @@ nvmet_fc_add_port(struct nvmet_port *port)
2370 2374
2371 /* map the traddr address info to a target port */ 2375 /* map the traddr address info to a target port */
2372 2376
2373 ret = nvmet_fc_parse_traddr(&traddr, port->disc_addr.traddr); 2377 ret = nvme_fc_parse_traddr(&traddr, port->disc_addr.traddr,
2378 sizeof(port->disc_addr.traddr));
2374 if (ret) 2379 if (ret)
2375 return ret; 2380 return ret;
2376 2381
diff --git a/include/linux/nvme-fc.h b/include/linux/nvme-fc.h
index 21c37e39e41a..36cca93a5ff2 100644
--- a/include/linux/nvme-fc.h
+++ b/include/linux/nvme-fc.h
@@ -334,5 +334,24 @@ struct fcnvme_ls_disconnect_acc {
334#define NVME_FC_LS_TIMEOUT_SEC 2 /* 2 seconds */ 334#define NVME_FC_LS_TIMEOUT_SEC 2 /* 2 seconds */
335#define NVME_FC_TGTOP_TIMEOUT_SEC 2 /* 2 seconds */ 335#define NVME_FC_TGTOP_TIMEOUT_SEC 2 /* 2 seconds */
336 336
337/*
338 * TRADDR string must be of form "nn-<16hexdigits>:pn-<16hexdigits>"
339 * the string is allowed to be specified with or without a "0x" prefix
340 * infront of the <16hexdigits>. Without is considered the "min" string
341 * and with is considered the "max" string. The hexdigits may be upper
342 * or lower case.
343 */
344#define NVME_FC_TRADDR_NNLEN 3 /* "?n-" */
345#define NVME_FC_TRADDR_OXNNLEN 5 /* "?n-0x" */
346#define NVME_FC_TRADDR_HEXNAMELEN 16
347#define NVME_FC_TRADDR_MINLENGTH \
348 (2 * (NVME_FC_TRADDR_NNLEN + NVME_FC_TRADDR_HEXNAMELEN) + 1)
349#define NVME_FC_TRADDR_MAXLENGTH \
350 (2 * (NVME_FC_TRADDR_OXNNLEN + NVME_FC_TRADDR_HEXNAMELEN) + 1)
351#define NVME_FC_TRADDR_MIN_PN_OFFSET \
352 (NVME_FC_TRADDR_NNLEN + NVME_FC_TRADDR_HEXNAMELEN + 1)
353#define NVME_FC_TRADDR_MAX_PN_OFFSET \
354 (NVME_FC_TRADDR_OXNNLEN + NVME_FC_TRADDR_HEXNAMELEN + 1)
355
337 356
338#endif /* _NVME_FC_H */ 357#endif /* _NVME_FC_H */
diff --git a/include/linux/nvme.h b/include/linux/nvme.h
index bc74da018bdc..25d8225dbd04 100644
--- a/include/linux/nvme.h
+++ b/include/linux/nvme.h
@@ -1006,7 +1006,7 @@ static inline bool nvme_is_write(struct nvme_command *cmd)
1006 * Why can't we simply have a Fabrics In and Fabrics out command? 1006 * Why can't we simply have a Fabrics In and Fabrics out command?
1007 */ 1007 */
1008 if (unlikely(cmd->common.opcode == nvme_fabrics_command)) 1008 if (unlikely(cmd->common.opcode == nvme_fabrics_command))
1009 return cmd->fabrics.opcode & 1; 1009 return cmd->fabrics.fctype & 1;
1010 return cmd->common.opcode & 1; 1010 return cmd->common.opcode & 1;
1011} 1011}
1012 1012