diff options
| -rw-r--r-- | drivers/scsi/fcoe/fcoe.c | 110 | ||||
| -rw-r--r-- | drivers/scsi/libfc/fc_lport.c | 7 |
2 files changed, 114 insertions, 3 deletions
diff --git a/drivers/scsi/fcoe/fcoe.c b/drivers/scsi/fcoe/fcoe.c index 9b6aebbb47d3..e3896fcb06e3 100644 --- a/drivers/scsi/fcoe/fcoe.c +++ b/drivers/scsi/fcoe/fcoe.c | |||
| @@ -101,6 +101,8 @@ static int fcoe_cpu_callback(struct notifier_block *, unsigned long, void *); | |||
| 101 | 101 | ||
| 102 | static int fcoe_create(const char *, struct kernel_param *); | 102 | static int fcoe_create(const char *, struct kernel_param *); |
| 103 | static int fcoe_destroy(const char *, struct kernel_param *); | 103 | static int fcoe_destroy(const char *, struct kernel_param *); |
| 104 | static int fcoe_enable(const char *, struct kernel_param *); | ||
| 105 | static int fcoe_disable(const char *, struct kernel_param *); | ||
| 104 | 106 | ||
| 105 | static struct fc_seq *fcoe_elsct_send(struct fc_lport *, | 107 | static struct fc_seq *fcoe_elsct_send(struct fc_lport *, |
| 106 | u32 did, struct fc_frame *, | 108 | u32 did, struct fc_frame *, |
| @@ -115,10 +117,16 @@ static void fcoe_get_lesb(struct fc_lport *, struct fc_els_lesb *); | |||
| 115 | 117 | ||
| 116 | module_param_call(create, fcoe_create, NULL, NULL, S_IWUSR); | 118 | module_param_call(create, fcoe_create, NULL, NULL, S_IWUSR); |
| 117 | __MODULE_PARM_TYPE(create, "string"); | 119 | __MODULE_PARM_TYPE(create, "string"); |
| 118 | MODULE_PARM_DESC(create, "Create fcoe fcoe using net device passed in."); | 120 | MODULE_PARM_DESC(create, " Creates fcoe instance on a ethernet interface"); |
| 119 | module_param_call(destroy, fcoe_destroy, NULL, NULL, S_IWUSR); | 121 | module_param_call(destroy, fcoe_destroy, NULL, NULL, S_IWUSR); |
| 120 | __MODULE_PARM_TYPE(destroy, "string"); | 122 | __MODULE_PARM_TYPE(destroy, "string"); |
| 121 | MODULE_PARM_DESC(destroy, "Destroy fcoe fcoe"); | 123 | MODULE_PARM_DESC(destroy, " Destroys fcoe instance on a ethernet interface"); |
| 124 | module_param_call(enable, fcoe_enable, NULL, NULL, S_IWUSR); | ||
| 125 | __MODULE_PARM_TYPE(enable, "string"); | ||
| 126 | MODULE_PARM_DESC(enable, " Enables fcoe on a ethernet interface."); | ||
| 127 | module_param_call(disable, fcoe_disable, NULL, NULL, S_IWUSR); | ||
| 128 | __MODULE_PARM_TYPE(disable, "string"); | ||
| 129 | MODULE_PARM_DESC(disable, " Disables fcoe on a ethernet interface."); | ||
| 122 | 130 | ||
| 123 | /* notification function for packets from net device */ | 131 | /* notification function for packets from net device */ |
| 124 | static struct notifier_block fcoe_notifier = { | 132 | static struct notifier_block fcoe_notifier = { |
| @@ -1859,6 +1867,104 @@ static struct net_device *fcoe_if_to_netdev(const char *buffer) | |||
| 1859 | } | 1867 | } |
| 1860 | 1868 | ||
| 1861 | /** | 1869 | /** |
| 1870 | * fcoe_disable() - Disables a FCoE interface | ||
| 1871 | * @buffer: The name of the Ethernet interface to be disabled | ||
| 1872 | * @kp: The associated kernel parameter | ||
| 1873 | * | ||
| 1874 | * Called from sysfs. | ||
| 1875 | * | ||
| 1876 | * Returns: 0 for success | ||
| 1877 | */ | ||
| 1878 | static int fcoe_disable(const char *buffer, struct kernel_param *kp) | ||
| 1879 | { | ||
| 1880 | struct fcoe_interface *fcoe; | ||
| 1881 | struct net_device *netdev; | ||
| 1882 | int rc = 0; | ||
| 1883 | |||
| 1884 | mutex_lock(&fcoe_config_mutex); | ||
| 1885 | #ifdef CONFIG_FCOE_MODULE | ||
| 1886 | /* | ||
| 1887 | * Make sure the module has been initialized, and is not about to be | ||
| 1888 | * removed. Module paramter sysfs files are writable before the | ||
| 1889 | * module_init function is called and after module_exit. | ||
| 1890 | */ | ||
| 1891 | if (THIS_MODULE->state != MODULE_STATE_LIVE) { | ||
| 1892 | rc = -ENODEV; | ||
| 1893 | goto out_nodev; | ||
| 1894 | } | ||
| 1895 | #endif | ||
| 1896 | |||
| 1897 | netdev = fcoe_if_to_netdev(buffer); | ||
| 1898 | if (!netdev) { | ||
| 1899 | rc = -ENODEV; | ||
| 1900 | goto out_nodev; | ||
| 1901 | } | ||
| 1902 | |||
| 1903 | rtnl_lock(); | ||
| 1904 | fcoe = fcoe_hostlist_lookup_port(netdev); | ||
| 1905 | rtnl_unlock(); | ||
| 1906 | |||
| 1907 | if (fcoe) | ||
| 1908 | fc_fabric_logoff(fcoe->ctlr.lp); | ||
| 1909 | else | ||
| 1910 | rc = -ENODEV; | ||
| 1911 | |||
| 1912 | dev_put(netdev); | ||
| 1913 | out_nodev: | ||
| 1914 | mutex_unlock(&fcoe_config_mutex); | ||
| 1915 | return rc; | ||
| 1916 | } | ||
| 1917 | |||
| 1918 | /** | ||
| 1919 | * fcoe_enable() - Enables a FCoE interface | ||
| 1920 | * @buffer: The name of the Ethernet interface to be enabled | ||
| 1921 | * @kp: The associated kernel parameter | ||
| 1922 | * | ||
| 1923 | * Called from sysfs. | ||
| 1924 | * | ||
| 1925 | * Returns: 0 for success | ||
| 1926 | */ | ||
| 1927 | static int fcoe_enable(const char *buffer, struct kernel_param *kp) | ||
| 1928 | { | ||
| 1929 | struct fcoe_interface *fcoe; | ||
| 1930 | struct net_device *netdev; | ||
| 1931 | int rc = 0; | ||
| 1932 | |||
| 1933 | mutex_lock(&fcoe_config_mutex); | ||
| 1934 | #ifdef CONFIG_FCOE_MODULE | ||
| 1935 | /* | ||
| 1936 | * Make sure the module has been initialized, and is not about to be | ||
| 1937 | * removed. Module paramter sysfs files are writable before the | ||
| 1938 | * module_init function is called and after module_exit. | ||
| 1939 | */ | ||
| 1940 | if (THIS_MODULE->state != MODULE_STATE_LIVE) { | ||
| 1941 | rc = -ENODEV; | ||
| 1942 | goto out_nodev; | ||
| 1943 | } | ||
| 1944 | #endif | ||
| 1945 | |||
| 1946 | netdev = fcoe_if_to_netdev(buffer); | ||
| 1947 | if (!netdev) { | ||
| 1948 | rc = -ENODEV; | ||
| 1949 | goto out_nodev; | ||
| 1950 | } | ||
| 1951 | |||
| 1952 | rtnl_lock(); | ||
| 1953 | fcoe = fcoe_hostlist_lookup_port(netdev); | ||
| 1954 | rtnl_unlock(); | ||
| 1955 | |||
| 1956 | if (fcoe) | ||
| 1957 | rc = fc_fabric_login(fcoe->ctlr.lp); | ||
| 1958 | else | ||
| 1959 | rc = -ENODEV; | ||
| 1960 | |||
| 1961 | dev_put(netdev); | ||
| 1962 | out_nodev: | ||
| 1963 | mutex_unlock(&fcoe_config_mutex); | ||
| 1964 | return rc; | ||
| 1965 | } | ||
| 1966 | |||
| 1967 | /** | ||
| 1862 | * fcoe_destroy() - Destroy a FCoE interface | 1968 | * fcoe_destroy() - Destroy a FCoE interface |
| 1863 | * @buffer: The name of the Ethernet interface to be destroyed | 1969 | * @buffer: The name of the Ethernet interface to be destroyed |
| 1864 | * @kp: The associated kernel parameter | 1970 | * @kp: The associated kernel parameter |
diff --git a/drivers/scsi/libfc/fc_lport.c b/drivers/scsi/libfc/fc_lport.c index 74338c83ad0a..0b165024a219 100644 --- a/drivers/scsi/libfc/fc_lport.c +++ b/drivers/scsi/libfc/fc_lport.c | |||
| @@ -537,7 +537,9 @@ int fc_fabric_login(struct fc_lport *lport) | |||
| 537 | int rc = -1; | 537 | int rc = -1; |
| 538 | 538 | ||
| 539 | mutex_lock(&lport->lp_mutex); | 539 | mutex_lock(&lport->lp_mutex); |
| 540 | if (lport->state == LPORT_ST_DISABLED) { | 540 | if (lport->state == LPORT_ST_DISABLED || |
| 541 | lport->state == LPORT_ST_LOGO) { | ||
| 542 | fc_lport_state_enter(lport, LPORT_ST_RESET); | ||
| 541 | fc_lport_enter_reset(lport); | 543 | fc_lport_enter_reset(lport); |
| 542 | rc = 0; | 544 | rc = 0; |
| 543 | } | 545 | } |
| @@ -967,6 +969,9 @@ static void fc_lport_enter_reset(struct fc_lport *lport) | |||
| 967 | FC_LPORT_DBG(lport, "Entered RESET state from %s state\n", | 969 | FC_LPORT_DBG(lport, "Entered RESET state from %s state\n", |
| 968 | fc_lport_state(lport)); | 970 | fc_lport_state(lport)); |
| 969 | 971 | ||
| 972 | if (lport->state == LPORT_ST_DISABLED || lport->state == LPORT_ST_LOGO) | ||
| 973 | return; | ||
| 974 | |||
| 970 | if (lport->vport) { | 975 | if (lport->vport) { |
| 971 | if (lport->link_up) | 976 | if (lport->link_up) |
| 972 | fc_vport_set_state(lport->vport, FC_VPORT_INITIALIZING); | 977 | fc_vport_set_state(lport->vport, FC_VPORT_INITIALIZING); |
