aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorK. Y. Srinivasan <kys@microsoft.com>2015-12-23 16:15:49 -0500
committerMartin K. Petersen <martin.petersen@oracle.com>2016-01-06 15:55:11 -0500
commitdac582417bc449b1f7f572d3f1dd9d23eec15cc9 (patch)
treed814fa829bf9c6a4191629f355b3de8365a8d62a
parent83d1e8b9b51b06d79653293d0bf34ff2c61abe46 (diff)
storvsc: Properly support Fibre Channel devices
For FC devices managed by this driver, atttach the appropriate transport template. This will allow us to create the appropriate sysfs files for these devices. With this we can publish the wwn for both the port and the node. Signed-off-by: K. Y. Srinivasan <kys@microsoft.com> Reviewed-by: Long Li <longli@microsoft.com> Tested-by: Alex Ng <alexng@microsoft.com> Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
-rw-r--r--drivers/scsi/storvsc_drv.c181
1 files changed, 134 insertions, 47 deletions
diff --git a/drivers/scsi/storvsc_drv.c b/drivers/scsi/storvsc_drv.c
index 00bb4bdffe85..cfbb2890b31f 100644
--- a/drivers/scsi/storvsc_drv.c
+++ b/drivers/scsi/storvsc_drv.c
@@ -41,6 +41,7 @@
41#include <scsi/scsi_eh.h> 41#include <scsi/scsi_eh.h>
42#include <scsi/scsi_devinfo.h> 42#include <scsi/scsi_devinfo.h>
43#include <scsi/scsi_dbg.h> 43#include <scsi/scsi_dbg.h>
44#include <scsi/scsi_transport_fc.h>
44 45
45/* 46/*
46 * All wire protocol details (storage protocol between the guest and the host) 47 * All wire protocol details (storage protocol between the guest and the host)
@@ -397,6 +398,9 @@ static int storvsc_timeout = 180;
397 398
398static int msft_blist_flags = BLIST_TRY_VPD_PAGES; 399static int msft_blist_flags = BLIST_TRY_VPD_PAGES;
399 400
401#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
402static struct scsi_transport_template *fc_transport_template;
403#endif
400 404
401static void storvsc_on_channel_callback(void *context); 405static void storvsc_on_channel_callback(void *context);
402 406
@@ -456,6 +460,11 @@ struct storvsc_device {
456 /* Used for vsc/vsp channel reset process */ 460 /* Used for vsc/vsp channel reset process */
457 struct storvsc_cmd_request init_request; 461 struct storvsc_cmd_request init_request;
458 struct storvsc_cmd_request reset_request; 462 struct storvsc_cmd_request reset_request;
463 /*
464 * Currently active port and node names for FC devices.
465 */
466 u64 node_name;
467 u64 port_name;
459}; 468};
460 469
461struct hv_host_device { 470struct hv_host_device {
@@ -695,7 +704,26 @@ static void handle_multichannel_storage(struct hv_device *device, int max_chns)
695 vmbus_are_subchannels_present(device->channel); 704 vmbus_are_subchannels_present(device->channel);
696} 705}
697 706
698static int storvsc_channel_init(struct hv_device *device) 707static void cache_wwn(struct storvsc_device *stor_device,
708 struct vstor_packet *vstor_packet)
709{
710 /*
711 * Cache the currently active port and node ww names.
712 */
713 if (vstor_packet->wwn_packet.primary_active) {
714 stor_device->node_name =
715 wwn_to_u64(vstor_packet->wwn_packet.primary_node_wwn);
716 stor_device->port_name =
717 wwn_to_u64(vstor_packet->wwn_packet.primary_port_wwn);
718 } else {
719 stor_device->node_name =
720 wwn_to_u64(vstor_packet->wwn_packet.secondary_node_wwn);
721 stor_device->port_name =
722 wwn_to_u64(vstor_packet->wwn_packet.secondary_port_wwn);
723 }
724}
725
726static int storvsc_channel_init(struct hv_device *device, bool is_fc)
699{ 727{
700 struct storvsc_device *stor_device; 728 struct storvsc_device *stor_device;
701 struct storvsc_cmd_request *request; 729 struct storvsc_cmd_request *request;
@@ -727,19 +755,15 @@ static int storvsc_channel_init(struct hv_device *device)
727 VM_PKT_DATA_INBAND, 755 VM_PKT_DATA_INBAND,
728 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED); 756 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
729 if (ret != 0) 757 if (ret != 0)
730 goto cleanup; 758 return ret;
731 759
732 t = wait_for_completion_timeout(&request->wait_event, 5*HZ); 760 t = wait_for_completion_timeout(&request->wait_event, 5*HZ);
733 if (t == 0) { 761 if (t == 0)
734 ret = -ETIMEDOUT; 762 return -ETIMEDOUT;
735 goto cleanup;
736 }
737 763
738 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO || 764 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
739 vstor_packet->status != 0) { 765 vstor_packet->status != 0)
740 ret = -EINVAL; 766 return -EINVAL;
741 goto cleanup;
742 }
743 767
744 768
745 for (i = 0; i < ARRAY_SIZE(vmstor_protocols); i++) { 769 for (i = 0; i < ARRAY_SIZE(vmstor_protocols); i++) {
@@ -764,18 +788,14 @@ static int storvsc_channel_init(struct hv_device *device)
764 VM_PKT_DATA_INBAND, 788 VM_PKT_DATA_INBAND,
765 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED); 789 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
766 if (ret != 0) 790 if (ret != 0)
767 goto cleanup; 791 return ret;
768 792
769 t = wait_for_completion_timeout(&request->wait_event, 5*HZ); 793 t = wait_for_completion_timeout(&request->wait_event, 5*HZ);
770 if (t == 0) { 794 if (t == 0)
771 ret = -ETIMEDOUT; 795 return -ETIMEDOUT;
772 goto cleanup;
773 }
774 796
775 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO) { 797 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO)
776 ret = -EINVAL; 798 return -EINVAL;
777 goto cleanup;
778 }
779 799
780 if (vstor_packet->status == 0) { 800 if (vstor_packet->status == 0) {
781 vmstor_proto_version = 801 vmstor_proto_version =
@@ -791,10 +811,8 @@ static int storvsc_channel_init(struct hv_device *device)
791 } 811 }
792 } 812 }
793 813
794 if (vstor_packet->status != 0) { 814 if (vstor_packet->status != 0)
795 ret = -EINVAL; 815 return -EINVAL;
796 goto cleanup;
797 }
798 816
799 817
800 memset(vstor_packet, 0, sizeof(struct vstor_packet)); 818 memset(vstor_packet, 0, sizeof(struct vstor_packet));
@@ -809,19 +827,15 @@ static int storvsc_channel_init(struct hv_device *device)
809 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED); 827 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
810 828
811 if (ret != 0) 829 if (ret != 0)
812 goto cleanup; 830 return ret;
813 831
814 t = wait_for_completion_timeout(&request->wait_event, 5*HZ); 832 t = wait_for_completion_timeout(&request->wait_event, 5*HZ);
815 if (t == 0) { 833 if (t == 0)
816 ret = -ETIMEDOUT; 834 return -ETIMEDOUT;
817 goto cleanup;
818 }
819 835
820 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO || 836 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
821 vstor_packet->status != 0) { 837 vstor_packet->status != 0)
822 ret = -EINVAL; 838 return -EINVAL;
823 goto cleanup;
824 }
825 839
826 /* 840 /*
827 * Check to see if multi-channel support is there. 841 * Check to see if multi-channel support is there.
@@ -837,6 +851,38 @@ static int storvsc_channel_init(struct hv_device *device)
837 stor_device->max_transfer_bytes = 851 stor_device->max_transfer_bytes =
838 vstor_packet->storage_channel_properties.max_transfer_bytes; 852 vstor_packet->storage_channel_properties.max_transfer_bytes;
839 853
854 if (!is_fc)
855 goto done;
856
857 memset(vstor_packet, 0, sizeof(struct vstor_packet));
858 vstor_packet->operation = VSTOR_OPERATION_FCHBA_DATA;
859 vstor_packet->flags = REQUEST_COMPLETION_FLAG;
860
861 ret = vmbus_sendpacket(device->channel, vstor_packet,
862 (sizeof(struct vstor_packet) -
863 vmscsi_size_delta),
864 (unsigned long)request,
865 VM_PKT_DATA_INBAND,
866 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
867
868 if (ret != 0)
869 return ret;
870
871 t = wait_for_completion_timeout(&request->wait_event, 5*HZ);
872 if (t == 0)
873 return -ETIMEDOUT;
874
875 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
876 vstor_packet->status != 0)
877 return -EINVAL;
878
879 /*
880 * Cache the currently active port and node ww names.
881 */
882 cache_wwn(stor_device, vstor_packet);
883
884done:
885
840 memset(vstor_packet, 0, sizeof(struct vstor_packet)); 886 memset(vstor_packet, 0, sizeof(struct vstor_packet));
841 vstor_packet->operation = VSTOR_OPERATION_END_INITIALIZATION; 887 vstor_packet->operation = VSTOR_OPERATION_END_INITIALIZATION;
842 vstor_packet->flags = REQUEST_COMPLETION_FLAG; 888 vstor_packet->flags = REQUEST_COMPLETION_FLAG;
@@ -849,25 +895,19 @@ static int storvsc_channel_init(struct hv_device *device)
849 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED); 895 VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
850 896
851 if (ret != 0) 897 if (ret != 0)
852 goto cleanup; 898 return ret;
853 899
854 t = wait_for_completion_timeout(&request->wait_event, 5*HZ); 900 t = wait_for_completion_timeout(&request->wait_event, 5*HZ);
855 if (t == 0) { 901 if (t == 0)
856 ret = -ETIMEDOUT; 902 return -ETIMEDOUT;
857 goto cleanup;
858 }
859 903
860 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO || 904 if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
861 vstor_packet->status != 0) { 905 vstor_packet->status != 0)
862 ret = -EINVAL; 906 return -EINVAL;
863 goto cleanup;
864 }
865 907
866 if (process_sub_channels) 908 if (process_sub_channels)
867 handle_multichannel_storage(device, max_chns); 909 handle_multichannel_storage(device, max_chns);
868 910
869
870cleanup:
871 return ret; 911 return ret;
872} 912}
873 913
@@ -1076,6 +1116,14 @@ static void storvsc_on_receive(struct hv_device *device,
1076 schedule_work(&work->work); 1116 schedule_work(&work->work);
1077 break; 1117 break;
1078 1118
1119 case VSTOR_OPERATION_FCHBA_DATA:
1120 stor_device = get_in_stor_device(device);
1121 cache_wwn(stor_device, vstor_packet);
1122#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1123 fc_host_node_name(stor_device->host) = stor_device->node_name;
1124 fc_host_port_name(stor_device->host) = stor_device->port_name;
1125#endif
1126 break;
1079 default: 1127 default:
1080 break; 1128 break;
1081 } 1129 }
@@ -1131,7 +1179,8 @@ static void storvsc_on_channel_callback(void *context)
1131 return; 1179 return;
1132} 1180}
1133 1181
1134static int storvsc_connect_to_vsp(struct hv_device *device, u32 ring_size) 1182static int storvsc_connect_to_vsp(struct hv_device *device, u32 ring_size,
1183 bool is_fc)
1135{ 1184{
1136 struct vmstorage_channel_properties props; 1185 struct vmstorage_channel_properties props;
1137 int ret; 1186 int ret;
@@ -1148,7 +1197,7 @@ static int storvsc_connect_to_vsp(struct hv_device *device, u32 ring_size)
1148 if (ret != 0) 1197 if (ret != 0)
1149 return ret; 1198 return ret;
1150 1199
1151 ret = storvsc_channel_init(device); 1200 ret = storvsc_channel_init(device, is_fc);
1152 1201
1153 return ret; 1202 return ret;
1154} 1203}
@@ -1573,6 +1622,7 @@ static int storvsc_probe(struct hv_device *device,
1573 struct Scsi_Host *host; 1622 struct Scsi_Host *host;
1574 struct hv_host_device *host_dev; 1623 struct hv_host_device *host_dev;
1575 bool dev_is_ide = ((dev_id->driver_data == IDE_GUID) ? true : false); 1624 bool dev_is_ide = ((dev_id->driver_data == IDE_GUID) ? true : false);
1625 bool is_fc = ((dev_id->driver_data == SFC_GUID) ? true : false);
1576 int target = 0; 1626 int target = 0;
1577 struct storvsc_device *stor_device; 1627 struct storvsc_device *stor_device;
1578 int max_luns_per_target; 1628 int max_luns_per_target;
@@ -1630,7 +1680,7 @@ static int storvsc_probe(struct hv_device *device,
1630 hv_set_drvdata(device, stor_device); 1680 hv_set_drvdata(device, stor_device);
1631 1681
1632 stor_device->port_number = host->host_no; 1682 stor_device->port_number = host->host_no;
1633 ret = storvsc_connect_to_vsp(device, storvsc_ringbuffer_size); 1683 ret = storvsc_connect_to_vsp(device, storvsc_ringbuffer_size, is_fc);
1634 if (ret) 1684 if (ret)
1635 goto err_out1; 1685 goto err_out1;
1636 1686
@@ -1642,6 +1692,9 @@ static int storvsc_probe(struct hv_device *device,
1642 host->max_lun = STORVSC_FC_MAX_LUNS_PER_TARGET; 1692 host->max_lun = STORVSC_FC_MAX_LUNS_PER_TARGET;
1643 host->max_id = STORVSC_FC_MAX_TARGETS; 1693 host->max_id = STORVSC_FC_MAX_TARGETS;
1644 host->max_channel = STORVSC_FC_MAX_CHANNELS - 1; 1694 host->max_channel = STORVSC_FC_MAX_CHANNELS - 1;
1695#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1696 host->transportt = fc_transport_template;
1697#endif
1645 break; 1698 break;
1646 1699
1647 case SCSI_GUID: 1700 case SCSI_GUID:
@@ -1681,6 +1734,12 @@ static int storvsc_probe(struct hv_device *device,
1681 goto err_out2; 1734 goto err_out2;
1682 } 1735 }
1683 } 1736 }
1737#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1738 if (host->transportt == fc_transport_template) {
1739 fc_host_node_name(host) = stor_device->node_name;
1740 fc_host_port_name(host) = stor_device->port_name;
1741 }
1742#endif
1684 return 0; 1743 return 0;
1685 1744
1686err_out2: 1745err_out2:
@@ -1706,6 +1765,10 @@ static int storvsc_remove(struct hv_device *dev)
1706 struct storvsc_device *stor_device = hv_get_drvdata(dev); 1765 struct storvsc_device *stor_device = hv_get_drvdata(dev);
1707 struct Scsi_Host *host = stor_device->host; 1766 struct Scsi_Host *host = stor_device->host;
1708 1767
1768#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1769 if (host->transportt == fc_transport_template)
1770 fc_remove_host(host);
1771#endif
1709 scsi_remove_host(host); 1772 scsi_remove_host(host);
1710 storvsc_dev_remove(dev); 1773 storvsc_dev_remove(dev);
1711 scsi_host_put(host); 1774 scsi_host_put(host);
@@ -1720,8 +1783,16 @@ static struct hv_driver storvsc_drv = {
1720 .remove = storvsc_remove, 1783 .remove = storvsc_remove,
1721}; 1784};
1722 1785
1786#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1787static struct fc_function_template fc_transport_functions = {
1788 .show_host_node_name = 1,
1789 .show_host_port_name = 1,
1790};
1791#endif
1792
1723static int __init storvsc_drv_init(void) 1793static int __init storvsc_drv_init(void)
1724{ 1794{
1795 int ret;
1725 1796
1726 /* 1797 /*
1727 * Divide the ring buffer data size (which is 1 page less 1798 * Divide the ring buffer data size (which is 1 page less
@@ -1736,12 +1807,28 @@ static int __init storvsc_drv_init(void)
1736 vmscsi_size_delta, 1807 vmscsi_size_delta,
1737 sizeof(u64))); 1808 sizeof(u64)));
1738 1809
1739 return vmbus_driver_register(&storvsc_drv); 1810#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1811 fc_transport_template = fc_attach_transport(&fc_transport_functions);
1812 if (!fc_transport_template)
1813 return -ENODEV;
1814#endif
1815
1816 ret = vmbus_driver_register(&storvsc_drv);
1817
1818#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1819 if (ret)
1820 fc_release_transport(fc_transport_template);
1821#endif
1822
1823 return ret;
1740} 1824}
1741 1825
1742static void __exit storvsc_drv_exit(void) 1826static void __exit storvsc_drv_exit(void)
1743{ 1827{
1744 vmbus_driver_unregister(&storvsc_drv); 1828 vmbus_driver_unregister(&storvsc_drv);
1829#if IS_ENABLED(CONFIG_SCSI_FC_ATTRS)
1830 fc_release_transport(fc_transport_template);
1831#endif
1745} 1832}
1746 1833
1747MODULE_LICENSE("GPL"); 1834MODULE_LICENSE("GPL");