2019-05-28 20:10:09 +03:00
// SPDX-License-Identifier: GPL-2.0-only
2017-03-24 11:41:48 +03:00
/*
2018-06-07 11:24:43 +03:00
* This file is part of the Emulex Linux Device Driver for Enterprise iSCSI
* Host Bus Adapters . Refer to the README file included with this package
* for driver version and adapter compatibility .
2009-09-05 06:06:35 +04:00
*
2018-06-07 11:24:43 +03:00
* Copyright ( c ) 2018 Broadcom . All Rights Reserved .
* The term " Broadcom " refers to Broadcom Inc . and / or its subsidiaries .
*
2009-09-05 06:06:35 +04:00
* Contact Information :
2016-08-19 12:50:24 +03:00
* linux - drivers @ broadcom . com
2009-09-05 06:06:35 +04:00
*/
# include <scsi/libiscsi.h>
# include <scsi/scsi_transport_iscsi.h>
# include <scsi/scsi_transport.h>
# include <scsi/scsi_cmnd.h>
# include <scsi/scsi_device.h>
# include <scsi/scsi_host.h>
2012-04-04 08:41:51 +04:00
# include <scsi/scsi_netlink.h>
# include <net/netlink.h>
2009-09-05 06:06:35 +04:00
# include <scsi/scsi.h>
# include "be_iscsi.h"
extern struct iscsi_transport beiscsi_iscsi_transport ;
/**
* beiscsi_session_create - creates a new iscsi session
* @ cmds_max : max commands supported
* @ qdepth : max queue depth supported
* @ initial_cmdsn : initial iscsi CMDSN
*/
struct iscsi_cls_session * beiscsi_session_create ( struct iscsi_endpoint * ep ,
u16 cmds_max ,
u16 qdepth ,
u32 initial_cmdsn )
{
struct Scsi_Host * shost ;
struct beiscsi_endpoint * beiscsi_ep ;
struct iscsi_cls_session * cls_session ;
struct beiscsi_hba * phba ;
2009-09-22 06:51:22 +04:00
struct iscsi_session * sess ;
struct beiscsi_session * beiscsi_sess ;
2009-09-05 06:06:35 +04:00
struct beiscsi_io_task * io_task ;
if ( ! ep ) {
2016-08-19 12:50:11 +03:00
pr_err ( " beiscsi_session_create: invalid ep \n " ) ;
2009-09-05 06:06:35 +04:00
return NULL ;
}
beiscsi_ep = ep - > dd_data ;
phba = beiscsi_ep - > phba ;
2012-08-20 21:30:18 +04:00
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2013-09-29 02:35:58 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
2016-08-19 12:50:11 +03:00
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
return NULL ;
2013-09-29 02:35:58 +04:00
}
2012-08-20 21:30:18 +04:00
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_session_create \n " ) ;
2009-09-05 06:06:35 +04:00
if ( cmds_max > beiscsi_ep - > phba - > params . wrbs_per_cxn ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Cannot handle %d cmds. "
" Max cmds per session supported is %d. Using %d. "
" \n " , cmds_max ,
beiscsi_ep - > phba - > params . wrbs_per_cxn ,
beiscsi_ep - > phba - > params . wrbs_per_cxn ) ;
2009-09-05 06:06:35 +04:00
cmds_max = beiscsi_ep - > phba - > params . wrbs_per_cxn ;
}
2013-09-29 02:35:58 +04:00
shost = phba - > shost ;
2009-10-23 10:22:33 +04:00
cls_session = iscsi_session_setup ( & beiscsi_iscsi_transport ,
shost , cmds_max ,
sizeof ( * beiscsi_sess ) ,
sizeof ( * io_task ) ,
initial_cmdsn , ISCSI_MAX_TARGET ) ;
2009-09-05 06:06:35 +04:00
if ( ! cls_session )
return NULL ;
sess = cls_session - > dd_data ;
2009-09-22 06:52:26 +04:00
beiscsi_sess = sess - > dd_data ;
2017-07-06 11:13:03 +03:00
beiscsi_sess - > bhs_pool = dma_pool_create ( " beiscsi_bhs_pool " ,
& phba - > pcidev - > dev ,
2009-09-22 06:52:26 +04:00
sizeof ( struct be_cmd_bhs ) ,
64 , 0 ) ;
if ( ! beiscsi_sess - > bhs_pool )
goto destroy_sess ;
2009-09-05 06:06:35 +04:00
return cls_session ;
2009-09-22 06:52:26 +04:00
destroy_sess :
iscsi_session_teardown ( cls_session ) ;
return NULL ;
2009-09-05 06:06:35 +04:00
}
/**
* beiscsi_session_destroy - destroys iscsi session
* @ cls_session : pointer to iscsi cls session
*
* Destroys iSCSI session instance and releases
* resources allocated for it .
*/
void beiscsi_session_destroy ( struct iscsi_cls_session * cls_session )
{
struct iscsi_session * sess = cls_session - > dd_data ;
2009-09-22 06:52:26 +04:00
struct beiscsi_session * beiscsi_sess = sess - > dd_data ;
2009-09-05 06:06:35 +04:00
2012-08-20 21:30:18 +04:00
printk ( KERN_INFO " In beiscsi_session_destroy \n " ) ;
2017-07-06 11:13:03 +03:00
dma_pool_destroy ( beiscsi_sess - > bhs_pool ) ;
2009-09-05 06:06:35 +04:00
iscsi_session_teardown ( cls_session ) ;
}
2016-08-19 12:50:15 +03:00
/**
* beiscsi_session_fail ( ) : Closing session with appropriate error
* @ cls_session : ptr to session
* */
void beiscsi_session_fail ( struct iscsi_cls_session * cls_session )
{
iscsi_session_failure ( cls_session - > dd_data , ISCSI_ERR_CONN_FAILED ) ;
}
2009-09-05 06:06:35 +04:00
/**
* beiscsi_conn_create - create an instance of iscsi connection
* @ cls_session : ptr to iscsi_cls_session
* @ cid : iscsi cid
*/
struct iscsi_cls_conn *
beiscsi_conn_create ( struct iscsi_cls_session * cls_session , u32 cid )
{
struct beiscsi_hba * phba ;
struct Scsi_Host * shost ;
struct iscsi_cls_conn * cls_conn ;
struct beiscsi_conn * beiscsi_conn ;
struct iscsi_conn * conn ;
2009-09-22 06:52:26 +04:00
struct iscsi_session * sess ;
struct beiscsi_session * beiscsi_sess ;
2009-09-05 06:06:35 +04:00
shost = iscsi_session_to_shost ( cls_session ) ;
phba = iscsi_host_priv ( shost ) ;
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_conn_create ,cid "
" from iscsi layer=%d \n " , cid ) ;
2009-09-05 06:06:35 +04:00
cls_conn = iscsi_conn_setup ( cls_session , sizeof ( * beiscsi_conn ) , cid ) ;
if ( ! cls_conn )
return NULL ;
conn = cls_conn - > dd_data ;
beiscsi_conn = conn - > dd_data ;
beiscsi_conn - > ep = NULL ;
beiscsi_conn - > phba = phba ;
beiscsi_conn - > conn = conn ;
2009-09-22 06:52:26 +04:00
sess = cls_session - > dd_data ;
beiscsi_sess = sess - > dd_data ;
beiscsi_conn - > beiscsi_sess = beiscsi_sess ;
2009-09-05 06:06:35 +04:00
return cls_conn ;
}
/**
* beiscsi_conn_bind - Binds iscsi session / connection with TCP connection
* @ cls_session : pointer to iscsi cls session
* @ cls_conn : pointer to iscsi cls conn
* @ transport_fd : EP handle ( 64 bit )
*
* This function binds the TCP Conn with iSCSI Connection and Session .
*/
int beiscsi_conn_bind ( struct iscsi_cls_session * cls_session ,
struct iscsi_cls_conn * cls_conn ,
u64 transport_fd , int is_leading )
{
struct iscsi_conn * conn = cls_conn - > dd_data ;
struct beiscsi_conn * beiscsi_conn = conn - > dd_data ;
2011-07-25 22:48:46 +04:00
struct Scsi_Host * shost = iscsi_session_to_shost ( cls_session ) ;
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
2013-09-29 02:35:50 +04:00
struct hwi_controller * phwi_ctrlr = phba - > phwi_ctrlr ;
struct hwi_wrb_context * pwrb_context ;
2009-09-05 06:06:35 +04:00
struct beiscsi_endpoint * beiscsi_ep ;
struct iscsi_endpoint * ep ;
2016-12-13 13:26:03 +03:00
uint16_t cri_index ;
2009-09-05 06:06:35 +04:00
ep = iscsi_lookup_endpoint ( transport_fd ) ;
if ( ! ep )
return - EINVAL ;
beiscsi_ep = ep - > dd_data ;
if ( iscsi_conn_bind ( cls_session , cls_conn , is_leading ) )
return - EINVAL ;
if ( beiscsi_ep - > phba ! = phba ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : beiscsi_ep->hba=%p not equal to phba=%p \n " ,
beiscsi_ep - > phba , phba ) ;
2009-09-05 06:06:35 +04:00
return - EEXIST ;
}
2016-12-13 13:26:03 +03:00
cri_index = BE_GET_CRI_FROM_CID ( beiscsi_ep - > ep_cid ) ;
if ( phba - > conn_table [ cri_index ] ) {
if ( beiscsi_conn ! = phba - > conn_table [ cri_index ] | |
beiscsi_ep ! = phba - > conn_table [ cri_index ] - > ep ) {
__beiscsi_log ( phba , KERN_ERR ,
" BS_%d : conn_table not empty at %u: cid %u conn %p:%p \n " ,
cri_index ,
beiscsi_ep - > ep_cid ,
beiscsi_conn ,
phba - > conn_table [ cri_index ] ) ;
return - EINVAL ;
}
}
2013-09-29 02:35:50 +04:00
2009-09-05 06:06:35 +04:00
beiscsi_conn - > beiscsi_conn_cid = beiscsi_ep - > ep_cid ;
beiscsi_conn - > ep = beiscsi_ep ;
beiscsi_ep - > conn = beiscsi_conn ;
2016-12-13 13:26:03 +03:00
/**
* Each connection is associated with a WRBQ kept in wrb_context .
* Store doorbell offset for transmit path .
*/
pwrb_context = & phwi_ctrlr - > wrb_context [ cri_index ] ;
2013-09-29 02:35:50 +04:00
beiscsi_conn - > doorbell_offset = pwrb_context - > doorbell_offset ;
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
2016-12-13 13:26:03 +03:00
" BS_%d : cid %d phba->conn_table[%u]=%p \n " ,
beiscsi_ep - > ep_cid , cri_index , beiscsi_conn ) ;
phba - > conn_table [ cri_index ] = beiscsi_conn ;
return 0 ;
2009-09-05 06:06:35 +04:00
}
2016-08-19 12:50:06 +03:00
static int beiscsi_iface_create_ipv4 ( struct beiscsi_hba * phba )
2012-04-04 08:41:51 +04:00
{
if ( phba - > ipv4_iface )
return 0 ;
phba - > ipv4_iface = iscsi_create_iface ( phba - > shost ,
& beiscsi_iscsi_transport ,
ISCSI_IFACE_TYPE_IPV4 ,
0 , 0 ) ;
if ( ! phba - > ipv4_iface ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Could not "
" create default IPv4 address. \n " ) ;
2012-04-04 08:41:51 +04:00
return - ENODEV ;
}
return 0 ;
}
2016-08-19 12:50:06 +03:00
static int beiscsi_iface_create_ipv6 ( struct beiscsi_hba * phba )
2012-04-04 08:41:51 +04:00
{
if ( phba - > ipv6_iface )
return 0 ;
phba - > ipv6_iface = iscsi_create_iface ( phba - > shost ,
& beiscsi_iscsi_transport ,
ISCSI_IFACE_TYPE_IPV6 ,
0 , 0 ) ;
if ( ! phba - > ipv6_iface ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Could not "
" create default IPv6 address. \n " ) ;
2012-04-04 08:41:51 +04:00
return - ENODEV ;
}
return 0 ;
}
2016-08-19 12:50:06 +03:00
void beiscsi_iface_create_default ( struct beiscsi_hba * phba )
2012-04-04 08:41:51 +04:00
{
2013-09-29 02:35:56 +04:00
struct be_cmd_get_if_info_resp * if_info ;
2012-04-04 08:41:51 +04:00
2016-08-19 12:50:08 +03:00
if ( ! beiscsi_if_get_info ( phba , BEISCSI_IP_TYPE_V4 , & if_info ) ) {
2016-08-19 12:50:06 +03:00
beiscsi_iface_create_ipv4 ( phba ) ;
2013-09-29 02:35:56 +04:00
kfree ( if_info ) ;
}
2012-04-04 08:41:51 +04:00
2016-08-19 12:50:08 +03:00
if ( ! beiscsi_if_get_info ( phba , BEISCSI_IP_TYPE_V6 , & if_info ) ) {
2016-08-19 12:50:06 +03:00
beiscsi_iface_create_ipv6 ( phba ) ;
2013-09-29 02:35:56 +04:00
kfree ( if_info ) ;
}
2012-04-04 08:41:51 +04:00
}
2016-08-19 12:50:06 +03:00
void beiscsi_iface_destroy_default ( struct beiscsi_hba * phba )
2012-04-04 08:41:51 +04:00
{
2016-08-19 12:50:01 +03:00
if ( phba - > ipv6_iface ) {
2012-04-04 08:41:51 +04:00
iscsi_destroy_iface ( phba - > ipv6_iface ) ;
2016-08-19 12:50:01 +03:00
phba - > ipv6_iface = NULL ;
}
if ( phba - > ipv4_iface ) {
2012-04-04 08:41:51 +04:00
iscsi_destroy_iface ( phba - > ipv4_iface ) ;
2016-08-19 12:50:01 +03:00
phba - > ipv4_iface = NULL ;
}
2012-04-04 08:41:51 +04:00
}
2012-08-20 21:30:43 +04:00
/**
* beiscsi_set_vlan_tag ( ) - Set the VLAN TAG
* @ shost : Scsi Host for the driver instance
* @ iface_param : Interface paramters
*
* Set the VLAN TAG for the adapter or disable
* the VLAN config
*
* returns
* Success : 0
* Failure : Non - Zero Value
* */
static int
2016-08-19 12:50:04 +03:00
beiscsi_iface_config_vlan ( struct Scsi_Host * shost ,
struct iscsi_iface_param_info * iface_param )
2012-08-20 21:30:43 +04:00
{
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
2016-08-19 12:50:05 +03:00
int ret = - EPERM ;
2012-08-20 21:30:43 +04:00
switch ( iface_param - > param ) {
case ISCSI_NET_PARAM_VLAN_ENABLED :
2016-08-19 12:50:04 +03:00
ret = 0 ;
2012-08-20 21:30:43 +04:00
if ( iface_param - > value [ 0 ] ! = ISCSI_VLAN_ENABLE )
2016-08-19 12:50:04 +03:00
ret = beiscsi_if_set_vlan ( phba , BEISCSI_VLAN_DISABLE ) ;
2012-08-20 21:30:43 +04:00
break ;
case ISCSI_NET_PARAM_VLAN_TAG :
2016-08-19 12:50:04 +03:00
ret = beiscsi_if_set_vlan ( phba ,
* ( ( uint16_t * ) iface_param - > value ) ) ;
2012-08-20 21:30:43 +04:00
break ;
}
return ret ;
}
2012-04-04 08:41:51 +04:00
static int
2016-08-19 12:50:03 +03:00
beiscsi_iface_config_ipv4 ( struct Scsi_Host * shost ,
struct iscsi_iface_param_info * info ,
void * data , uint32_t dt_len )
2012-04-04 08:41:51 +04:00
{
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
2016-08-19 12:50:03 +03:00
u8 * ip = NULL , * subnet = NULL , * gw ;
struct nlattr * nla ;
2016-08-19 12:50:04 +03:00
int ret = - EPERM ;
2012-04-04 08:41:51 +04:00
/* Check the param */
2016-08-19 12:50:03 +03:00
switch ( info - > param ) {
2016-08-19 12:50:01 +03:00
case ISCSI_NET_PARAM_IFACE_ENABLE :
2016-08-19 12:50:03 +03:00
if ( info - > value [ 0 ] = = ISCSI_IFACE_ENABLE )
2016-08-19 12:50:06 +03:00
ret = beiscsi_iface_create_ipv4 ( phba ) ;
2016-08-19 12:50:01 +03:00
else {
iscsi_destroy_iface ( phba - > ipv4_iface ) ;
phba - > ipv4_iface = NULL ;
}
break ;
2012-04-04 08:41:51 +04:00
case ISCSI_NET_PARAM_IPV4_GW :
2016-08-19 12:50:03 +03:00
gw = info - > value ;
2016-08-19 12:50:08 +03:00
ret = beiscsi_if_set_gw ( phba , BEISCSI_IP_TYPE_V4 , gw ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IPV4_BOOTPROTO :
2016-08-19 12:50:03 +03:00
if ( info - > value [ 0 ] = = ISCSI_BOOTPROTO_DHCP )
2016-08-19 12:50:08 +03:00
ret = beiscsi_if_en_dhcp ( phba , BEISCSI_IP_TYPE_V4 ) ;
2016-08-19 12:50:03 +03:00
else if ( info - > value [ 0 ] = = ISCSI_BOOTPROTO_STATIC )
/* release DHCP IP address */
2016-08-19 12:50:08 +03:00
ret = beiscsi_if_en_static ( phba , BEISCSI_IP_TYPE_V4 ,
NULL , NULL ) ;
2012-04-04 08:41:51 +04:00
else
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Invalid BOOTPROTO: %d \n " ,
2016-08-19 12:50:03 +03:00
info - > value [ 0 ] ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IPV4_ADDR :
2016-08-19 12:50:03 +03:00
ip = info - > value ;
nla = nla_find ( data , dt_len , ISCSI_NET_PARAM_IPV4_SUBNET ) ;
if ( nla ) {
info = nla_data ( nla ) ;
subnet = info - > value ;
}
2016-08-19 12:50:08 +03:00
ret = beiscsi_if_en_static ( phba , BEISCSI_IP_TYPE_V4 ,
ip , subnet ) ;
2016-08-19 12:50:03 +03:00
break ;
case ISCSI_NET_PARAM_IPV4_SUBNET :
/*
* OPCODE_COMMON_ISCSI_NTWK_MODIFY_IP_ADDR ioctl needs IP
* and subnet both . Find IP to be applied for this subnet .
*/
subnet = info - > value ;
nla = nla_find ( data , dt_len , ISCSI_NET_PARAM_IPV4_ADDR ) ;
if ( nla ) {
info = nla_data ( nla ) ;
ip = info - > value ;
}
2016-08-19 12:50:08 +03:00
ret = beiscsi_if_en_static ( phba , BEISCSI_IP_TYPE_V4 ,
ip , subnet ) ;
2012-04-04 08:41:51 +04:00
break ;
}
return ret ;
}
static int
2016-08-19 12:50:03 +03:00
beiscsi_iface_config_ipv6 ( struct Scsi_Host * shost ,
struct iscsi_iface_param_info * iface_param ,
void * data , uint32_t dt_len )
2012-04-04 08:41:51 +04:00
{
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
2016-08-19 12:50:04 +03:00
int ret = - EPERM ;
2012-04-04 08:41:51 +04:00
switch ( iface_param - > param ) {
case ISCSI_NET_PARAM_IFACE_ENABLE :
if ( iface_param - > value [ 0 ] = = ISCSI_IFACE_ENABLE )
2016-08-19 12:50:06 +03:00
ret = beiscsi_iface_create_ipv6 ( phba ) ;
2012-04-04 08:41:51 +04:00
else {
iscsi_destroy_iface ( phba - > ipv6_iface ) ;
2016-08-19 12:50:01 +03:00
phba - > ipv6_iface = NULL ;
2012-04-04 08:41:51 +04:00
}
break ;
case ISCSI_NET_PARAM_IPV6_ADDR :
2016-08-19 12:50:08 +03:00
ret = beiscsi_if_en_static ( phba , BEISCSI_IP_TYPE_V6 ,
2016-08-19 12:50:03 +03:00
iface_param - > value , NULL ) ;
2012-04-04 08:41:51 +04:00
break ;
}
return ret ;
}
2016-08-19 12:50:06 +03:00
int beiscsi_iface_set_param ( struct Scsi_Host * shost ,
void * data , uint32_t dt_len )
2012-04-04 08:41:51 +04:00
{
struct iscsi_iface_param_info * iface_param = NULL ;
2012-08-20 21:30:18 +04:00
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
2012-04-04 08:41:51 +04:00
struct nlattr * attrib ;
uint32_t rm_len = dt_len ;
2016-08-19 12:50:05 +03:00
int ret ;
2012-04-04 08:41:51 +04:00
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
2013-09-29 02:35:58 +04:00
return - EBUSY ;
}
2016-08-19 12:50:05 +03:00
/* update interface_handle */
ret = beiscsi_if_get_handle ( phba ) ;
if ( ret ) {
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Getting Interface Handle Failed \n " ) ;
return ret ;
}
2012-04-04 08:41:51 +04:00
nla_for_each_attr ( attrib , data , dt_len , rm_len ) {
iface_param = nla_data ( attrib ) ;
if ( iface_param - > param_type ! = ISCSI_NET_PARAM )
continue ;
/*
* BE2ISCSI only supports 1 interface
*/
if ( iface_param - > iface_num ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Invalid iface_num %d. "
" Only iface_num 0 is supported. \n " ,
iface_param - > iface_num ) ;
2012-04-04 08:41:51 +04:00
return - EINVAL ;
}
2016-08-19 12:50:04 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : %s.0 set param %d " ,
( iface_param - > iface_type = = ISCSI_IFACE_TYPE_IPV4 ) ?
" ipv4 " : " ipv6 " , iface_param - > param ) ;
ret = - EPERM ;
switch ( iface_param - > param ) {
case ISCSI_NET_PARAM_VLAN_ENABLED :
case ISCSI_NET_PARAM_VLAN_TAG :
ret = beiscsi_iface_config_vlan ( shost , iface_param ) ;
2012-04-04 08:41:51 +04:00
break ;
default :
2016-08-19 12:50:04 +03:00
switch ( iface_param - > iface_type ) {
case ISCSI_IFACE_TYPE_IPV4 :
ret = beiscsi_iface_config_ipv4 ( shost ,
iface_param ,
data , dt_len ) ;
break ;
case ISCSI_IFACE_TYPE_IPV6 :
ret = beiscsi_iface_config_ipv6 ( shost ,
iface_param ,
data , dt_len ) ;
break ;
}
2012-04-04 08:41:51 +04:00
}
2016-08-19 12:50:04 +03:00
if ( ret = = - EPERM ) {
__beiscsi_log ( phba , KERN_ERR ,
" BS_%d : %s.0 set param %d not permitted " ,
( iface_param - > iface_type = =
ISCSI_IFACE_TYPE_IPV4 ) ? " ipv4 " : " ipv6 " ,
iface_param - > param ) ;
ret = 0 ;
}
2012-04-04 08:41:51 +04:00
if ( ret )
2016-08-19 12:50:04 +03:00
break ;
2012-04-04 08:41:51 +04:00
}
return ret ;
}
2016-08-19 12:50:06 +03:00
static int __beiscsi_iface_get_param ( struct beiscsi_hba * phba ,
struct iscsi_iface * iface ,
int param , char * buf )
2012-04-04 08:41:51 +04:00
{
2013-09-29 02:35:56 +04:00
struct be_cmd_get_if_info_resp * if_info ;
2016-08-19 12:50:08 +03:00
int len , ip_type = BEISCSI_IP_TYPE_V4 ;
2012-04-04 08:41:51 +04:00
if ( iface - > iface_type = = ISCSI_IFACE_TYPE_IPV6 )
2016-08-19 12:50:08 +03:00
ip_type = BEISCSI_IP_TYPE_V6 ;
2012-04-04 08:41:51 +04:00
2016-08-19 12:50:06 +03:00
len = beiscsi_if_get_info ( phba , ip_type , & if_info ) ;
2013-11-18 23:42:57 +04:00
if ( len )
2012-04-04 08:41:51 +04:00
return len ;
switch ( param ) {
case ISCSI_NET_PARAM_IPV4_ADDR :
2013-09-29 02:35:56 +04:00
len = sprintf ( buf , " %pI4 \n " , if_info - > ip_addr . addr ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IPV6_ADDR :
2013-09-29 02:35:56 +04:00
len = sprintf ( buf , " %pI6 \n " , if_info - > ip_addr . addr ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IPV4_BOOTPROTO :
2013-09-29 02:35:56 +04:00
if ( ! if_info - > dhcp_state )
2012-10-20 03:13:03 +04:00
len = sprintf ( buf , " static \n " ) ;
2012-04-04 08:41:51 +04:00
else
2012-10-20 03:13:03 +04:00
len = sprintf ( buf , " dhcp \n " ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IPV4_SUBNET :
2013-09-29 02:35:56 +04:00
len = sprintf ( buf , " %pI4 \n " , if_info - > ip_addr . subnet_mask ) ;
2012-04-04 08:41:51 +04:00
break ;
2012-08-20 21:30:43 +04:00
case ISCSI_NET_PARAM_VLAN_ENABLED :
len = sprintf ( buf , " %s \n " ,
2016-08-19 12:49:58 +03:00
( if_info - > vlan_priority = = BEISCSI_VLAN_DISABLE ) ?
" disable " : " enable " ) ;
2012-08-20 21:30:43 +04:00
break ;
case ISCSI_NET_PARAM_VLAN_ID :
2013-09-29 02:35:56 +04:00
if ( if_info - > vlan_priority = = BEISCSI_VLAN_DISABLE )
2013-11-18 23:42:57 +04:00
len = - EINVAL ;
2012-08-20 21:30:43 +04:00
else
len = sprintf ( buf , " %d \n " ,
2016-08-19 12:50:04 +03:00
( if_info - > vlan_priority &
ISCSI_MAX_VLAN_ID ) ) ;
2012-08-20 21:30:43 +04:00
break ;
case ISCSI_NET_PARAM_VLAN_PRIORITY :
2013-09-29 02:35:56 +04:00
if ( if_info - > vlan_priority = = BEISCSI_VLAN_DISABLE )
2013-11-18 23:42:57 +04:00
len = - EINVAL ;
2012-08-20 21:30:43 +04:00
else
len = sprintf ( buf , " %d \n " ,
2016-08-19 12:50:04 +03:00
( ( if_info - > vlan_priority > > 13 ) &
ISCSI_MAX_VLAN_PRIORITY ) ) ;
2012-08-20 21:30:43 +04:00
break ;
2012-04-04 08:41:51 +04:00
default :
WARN_ON ( 1 ) ;
}
2013-09-29 02:35:56 +04:00
kfree ( if_info ) ;
2012-04-04 08:41:51 +04:00
return len ;
}
2016-08-19 12:50:06 +03:00
int beiscsi_iface_get_param ( struct iscsi_iface * iface ,
enum iscsi_param_type param_type ,
int param , char * buf )
2012-04-04 08:41:51 +04:00
{
struct Scsi_Host * shost = iscsi_iface_to_shost ( iface ) ;
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
struct be_cmd_get_def_gateway_resp gateway ;
2016-08-19 12:50:05 +03:00
int len = - EPERM ;
2012-04-04 08:41:51 +04:00
2016-08-19 12:50:07 +03:00
if ( param_type ! = ISCSI_NET_PARAM )
return 0 ;
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
2013-09-29 02:35:58 +04:00
return - EBUSY ;
}
2012-04-04 08:41:51 +04:00
switch ( param ) {
case ISCSI_NET_PARAM_IPV4_ADDR :
case ISCSI_NET_PARAM_IPV4_SUBNET :
case ISCSI_NET_PARAM_IPV4_BOOTPROTO :
case ISCSI_NET_PARAM_IPV6_ADDR :
2012-08-20 21:30:43 +04:00
case ISCSI_NET_PARAM_VLAN_ENABLED :
case ISCSI_NET_PARAM_VLAN_ID :
case ISCSI_NET_PARAM_VLAN_PRIORITY :
2016-08-19 12:50:06 +03:00
len = __beiscsi_iface_get_param ( phba , iface , param , buf ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IFACE_ENABLE :
2016-08-19 12:50:01 +03:00
if ( iface - > iface_type = = ISCSI_IFACE_TYPE_IPV4 )
len = sprintf ( buf , " %s \n " ,
phba - > ipv4_iface ? " enable " : " disable " ) ;
else if ( iface - > iface_type = = ISCSI_IFACE_TYPE_IPV6 )
len = sprintf ( buf , " %s \n " ,
phba - > ipv6_iface ? " enable " : " disable " ) ;
2012-04-04 08:41:51 +04:00
break ;
case ISCSI_NET_PARAM_IPV4_GW :
memset ( & gateway , 0 , sizeof ( gateway ) ) ;
2016-08-19 12:50:08 +03:00
len = beiscsi_if_get_gw ( phba , BEISCSI_IP_TYPE_V4 , & gateway ) ;
2012-04-04 08:41:51 +04:00
if ( ! len )
len = sprintf ( buf , " %pI4 \n " , & gateway . ip_addr . addr ) ;
break ;
}
return len ;
}
2009-09-05 06:06:35 +04:00
/**
2011-02-17 00:04:41 +03:00
* beiscsi_ep_get_param - get the iscsi parameter
* @ ep : pointer to iscsi ep
2009-09-05 06:06:35 +04:00
* @ param : parameter type identifier
* @ buf : buffer pointer
*
* returns iscsi parameter
*/
2011-02-17 00:04:41 +03:00
int beiscsi_ep_get_param ( struct iscsi_endpoint * ep ,
2009-09-05 06:06:35 +04:00
enum iscsi_param param , char * buf )
{
2011-02-17 00:04:41 +03:00
struct beiscsi_endpoint * beiscsi_ep = ep - > dd_data ;
2016-08-19 12:50:05 +03:00
int len ;
2009-09-05 06:06:35 +04:00
2012-08-20 21:30:18 +04:00
beiscsi_log ( beiscsi_ep - > phba , KERN_INFO ,
BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_ep_get_param, "
" param= %d \n " , param ) ;
2009-09-05 06:06:35 +04:00
switch ( param ) {
case ISCSI_PARAM_CONN_PORT :
len = sprintf ( buf , " %hu \n " , beiscsi_ep - > dst_tcpport ) ;
break ;
case ISCSI_PARAM_CONN_ADDRESS :
2016-08-19 12:50:08 +03:00
if ( beiscsi_ep - > ip_type = = BEISCSI_IP_TYPE_V4 )
2009-09-05 06:06:35 +04:00
len = sprintf ( buf , " %pI4 \n " , & beiscsi_ep - > dst_addr ) ;
else
len = sprintf ( buf , " %pI6 \n " , & beiscsi_ep - > dst6_addr ) ;
break ;
default :
2016-08-19 12:50:05 +03:00
len = - EPERM ;
2009-09-05 06:06:35 +04:00
}
return len ;
}
int beiscsi_set_param ( struct iscsi_cls_conn * cls_conn ,
enum iscsi_param param , char * buf , int buflen )
{
struct iscsi_conn * conn = cls_conn - > dd_data ;
struct iscsi_session * session = conn - > session ;
2012-08-20 21:30:18 +04:00
struct beiscsi_hba * phba = NULL ;
2009-09-05 06:06:35 +04:00
int ret ;
2012-08-20 21:30:18 +04:00
phba = ( ( struct beiscsi_conn * ) conn - > dd_data ) - > phba ;
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_conn_set_param, "
" param= %d \n " , param ) ;
2009-09-05 06:06:35 +04:00
ret = iscsi_set_param ( cls_conn , param , buf , buflen ) ;
if ( ret )
return ret ;
/*
* If userspace tried to set the value to higher than we can
* support override here .
*/
switch ( param ) {
case ISCSI_PARAM_FIRST_BURST :
if ( session - > first_burst > 8192 )
session - > first_burst = 8192 ;
break ;
case ISCSI_PARAM_MAX_RECV_DLENGTH :
if ( conn - > max_recv_dlength > 65536 )
conn - > max_recv_dlength = 65536 ;
break ;
case ISCSI_PARAM_MAX_BURST :
2010-01-23 03:06:10 +03:00
if ( session - > max_burst > 262144 )
session - > max_burst = 262144 ;
2009-09-05 06:06:35 +04:00
break ;
2010-07-22 02:56:45 +04:00
case ISCSI_PARAM_MAX_XMIT_DLENGTH :
2013-09-29 02:35:41 +04:00
if ( conn - > max_xmit_dlength > 65536 )
2010-07-22 02:56:45 +04:00
conn - > max_xmit_dlength = 65536 ;
2018-11-26 20:46:20 +03:00
/* fall through */
2009-09-05 06:06:35 +04:00
default :
return 0 ;
}
return 0 ;
}
2012-04-04 08:41:52 +04:00
/**
* beiscsi_get_port_state - Get the Port State
* @ shost : pointer to scsi_host structure
*
*/
static void beiscsi_get_port_state ( struct Scsi_Host * shost )
{
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
struct iscsi_cls_host * ihost = shost - > shost_data ;
2016-08-19 12:50:11 +03:00
ihost - > port_state = test_bit ( BEISCSI_HBA_LINK_UP , & phba - > state ) ?
2012-04-04 08:41:52 +04:00
ISCSI_PORT_STATE_UP : ISCSI_PORT_STATE_DOWN ;
}
/**
* beiscsi_get_port_speed - Get the Port Speed from Adapter
* @ shost : pointer to scsi_host structure
*
*/
2016-01-20 11:40:58 +03:00
static void beiscsi_get_port_speed ( struct Scsi_Host * shost )
2012-04-04 08:41:52 +04:00
{
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
struct iscsi_cls_host * ihost = shost - > shost_data ;
2016-01-20 11:40:58 +03:00
switch ( phba - > port_speed ) {
2012-04-04 08:41:52 +04:00
case BE2ISCSI_LINK_SPEED_10MBPS :
ihost - > port_speed = ISCSI_PORT_SPEED_10MBPS ;
break ;
case BE2ISCSI_LINK_SPEED_100MBPS :
2014-01-29 11:16:40 +04:00
ihost - > port_speed = ISCSI_PORT_SPEED_100MBPS ;
2012-04-04 08:41:52 +04:00
break ;
case BE2ISCSI_LINK_SPEED_1GBPS :
ihost - > port_speed = ISCSI_PORT_SPEED_1GBPS ;
break ;
case BE2ISCSI_LINK_SPEED_10GBPS :
ihost - > port_speed = ISCSI_PORT_SPEED_10GBPS ;
break ;
2016-01-20 11:40:58 +03:00
case BE2ISCSI_LINK_SPEED_25GBPS :
ihost - > port_speed = ISCSI_PORT_SPEED_25GBPS ;
break ;
case BE2ISCSI_LINK_SPEED_40GBPS :
ihost - > port_speed = ISCSI_PORT_SPEED_40GBPS ;
break ;
2012-04-04 08:41:52 +04:00
default :
ihost - > port_speed = ISCSI_PORT_SPEED_UNKNOWN ;
}
}
2009-09-05 06:06:35 +04:00
/**
* beiscsi_get_host_param - get the iscsi parameter
* @ shost : pointer to scsi_host structure
* @ param : parameter type identifier
* @ buf : buffer pointer
*
*/
int beiscsi_get_host_param ( struct Scsi_Host * shost ,
enum iscsi_host_param param , char * buf )
{
2011-07-25 22:48:46 +04:00
struct beiscsi_hba * phba = iscsi_host_priv ( shost ) ;
2010-08-12 22:06:06 +04:00
int status = 0 ;
2009-09-05 06:06:35 +04:00
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2013-09-29 02:35:58 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
2016-08-19 12:50:11 +03:00
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
2017-10-10 13:48:15 +03:00
return 0 ;
2013-09-29 02:35:58 +04:00
}
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_get_host_param, param = %d \n " , param ) ;
2012-08-20 21:30:18 +04:00
2009-09-05 06:06:35 +04:00
switch ( param ) {
case ISCSI_HOST_PARAM_HWADDRESS :
2010-07-22 02:59:18 +04:00
status = beiscsi_get_macaddr ( buf , phba ) ;
if ( status < 0 ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : beiscsi_get_macaddr Failed \n " ) ;
2017-10-10 13:48:15 +03:00
return 0 ;
2010-01-05 02:40:46 +03:00
}
2009-09-05 06:06:35 +04:00
break ;
2012-04-04 08:41:49 +04:00
case ISCSI_HOST_PARAM_INITIATOR_NAME :
2017-10-10 13:48:16 +03:00
/* try fetching user configured name first */
status = beiscsi_get_initiator_name ( phba , buf , true ) ;
2012-04-04 08:41:49 +04:00
if ( status < 0 ) {
2017-10-10 13:48:16 +03:00
status = beiscsi_get_initiator_name ( phba , buf , false ) ;
if ( status < 0 ) {
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
2018-10-16 20:46:32 +03:00
" BS_%d : Retrieving Initiator Name Failed \n " ) ;
2017-10-10 13:48:16 +03:00
status = 0 ;
}
2012-04-04 08:41:49 +04:00
}
break ;
2012-04-04 08:41:52 +04:00
case ISCSI_HOST_PARAM_PORT_STATE :
beiscsi_get_port_state ( shost ) ;
status = sprintf ( buf , " %s \n " , iscsi_get_port_state_name ( shost ) ) ;
break ;
case ISCSI_HOST_PARAM_PORT_SPEED :
2016-01-20 11:40:58 +03:00
beiscsi_get_port_speed ( shost ) ;
2012-04-04 08:41:52 +04:00
status = sprintf ( buf , " %s \n " , iscsi_get_port_speed_name ( shost ) ) ;
break ;
2009-09-05 06:06:35 +04:00
default :
return iscsi_host_get_param ( shost , param , buf ) ;
}
2010-08-12 22:06:06 +04:00
return status ;
2009-09-05 06:06:35 +04:00
}
2010-07-22 02:59:18 +04:00
int beiscsi_get_macaddr ( char * buf , struct beiscsi_hba * phba )
{
2012-04-04 08:41:51 +04:00
struct be_cmd_get_nic_conf_resp resp ;
2010-07-22 02:59:18 +04:00
int rc ;
2013-09-29 02:35:40 +04:00
if ( phba - > mac_addr_set )
2012-08-20 21:30:31 +04:00
return sysfs_format_mac ( buf , phba - > mac_address , ETH_ALEN ) ;
2010-07-22 02:59:18 +04:00
2012-04-04 08:41:51 +04:00
memset ( & resp , 0 , sizeof ( resp ) ) ;
rc = mgmt_get_nic_conf ( phba , & resp ) ;
if ( rc )
return rc ;
2010-07-22 02:59:18 +04:00
2013-09-29 02:35:40 +04:00
phba - > mac_addr_set = true ;
2012-04-04 08:41:51 +04:00
memcpy ( phba - > mac_address , resp . mac_address , ETH_ALEN ) ;
return sysfs_format_mac ( buf , phba - > mac_address , ETH_ALEN ) ;
2010-07-22 02:59:18 +04:00
}
2009-09-05 06:06:35 +04:00
/**
* beiscsi_conn_get_stats - get the iscsi stats
* @ cls_conn : pointer to iscsi cls conn
* @ stats : pointer to iscsi_stats structure
*
* returns iscsi stats
*/
void beiscsi_conn_get_stats ( struct iscsi_cls_conn * cls_conn ,
struct iscsi_stats * stats )
{
struct iscsi_conn * conn = cls_conn - > dd_data ;
2012-08-20 21:30:18 +04:00
struct beiscsi_hba * phba = NULL ;
phba = ( ( struct beiscsi_conn * ) conn - > dd_data ) - > phba ;
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_conn_get_stats \n " ) ;
2009-09-05 06:06:35 +04:00
stats - > txdata_octets = conn - > txdata_octets ;
stats - > rxdata_octets = conn - > rxdata_octets ;
stats - > dataout_pdus = conn - > dataout_pdus_cnt ;
stats - > scsirsp_pdus = conn - > scsirsp_pdus_cnt ;
stats - > scsicmd_pdus = conn - > scsicmd_pdus_cnt ;
stats - > datain_pdus = conn - > datain_pdus_cnt ;
stats - > tmfrsp_pdus = conn - > tmfrsp_pdus_cnt ;
stats - > tmfcmd_pdus = conn - > tmfcmd_pdus_cnt ;
stats - > r2t_pdus = conn - > r2t_pdus_cnt ;
stats - > digest_err = 0 ;
stats - > timeout_err = 0 ;
2014-07-01 20:24:38 +04:00
stats - > custom_length = 1 ;
2009-09-05 06:06:35 +04:00
strcpy ( stats - > custom [ 0 ] . desc , " eh_abort_cnt " ) ;
stats - > custom [ 0 ] . value = conn - > eh_abort_cnt ;
}
/**
* beiscsi_set_params_for_offld - get the parameters for offload
* @ beiscsi_conn : pointer to beiscsi_conn
* @ params : pointer to offload_params structure
*/
static void beiscsi_set_params_for_offld ( struct beiscsi_conn * beiscsi_conn ,
struct beiscsi_offload_params * params )
{
struct iscsi_conn * conn = beiscsi_conn - > conn ;
struct iscsi_session * session = conn - > session ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , max_burst_length ,
params , session - > max_burst ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params ,
max_send_data_segment_length , params ,
conn - > max_xmit_dlength ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , first_burst_length ,
params , session - > first_burst ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , erl , params ,
session - > erl ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , dde , params ,
conn - > datadgst_en ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , hde , params ,
conn - > hdrdgst_en ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , ir2t , params ,
session - > initial_r2t_en ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , imd , params ,
session - > imm_data_en ) ;
2012-10-20 03:14:35 +04:00
AMAP_SET_BITS ( struct amap_beiscsi_offload_params ,
data_seq_inorder , params ,
session - > dataseq_inorder_en ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params ,
pdu_seq_inorder , params ,
session - > pdu_inorder_en ) ;
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , max_r2t , params ,
session - > max_r2t ) ;
2009-09-05 06:06:35 +04:00
AMAP_SET_BITS ( struct amap_beiscsi_offload_params , exp_statsn , params ,
( conn - > exp_statsn - 1 ) ) ;
2013-09-29 02:35:41 +04:00
AMAP_SET_BITS ( struct amap_beiscsi_offload_params ,
max_recv_data_segment_length , params ,
conn - > max_recv_dlength ) ;
2009-09-05 06:06:35 +04:00
}
/**
* beiscsi_conn_start - offload of session to chip
* @ cls_conn : pointer to beiscsi_conn
*/
int beiscsi_conn_start ( struct iscsi_cls_conn * cls_conn )
{
struct iscsi_conn * conn = cls_conn - > dd_data ;
struct beiscsi_conn * beiscsi_conn = conn - > dd_data ;
struct beiscsi_endpoint * beiscsi_ep ;
struct beiscsi_offload_params params ;
2013-09-29 02:35:58 +04:00
struct beiscsi_hba * phba ;
2009-09-05 06:06:35 +04:00
2013-09-29 02:35:58 +04:00
phba = ( ( struct beiscsi_conn * ) conn - > dd_data ) - > phba ;
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
2013-09-29 02:35:58 +04:00
return - EBUSY ;
}
2016-08-19 12:50:11 +03:00
beiscsi_log ( beiscsi_conn - > phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_conn_start \n " ) ;
2012-08-20 21:30:18 +04:00
2009-09-05 06:06:35 +04:00
memset ( & params , 0 , sizeof ( struct beiscsi_offload_params ) ) ;
beiscsi_ep = beiscsi_conn - > ep ;
if ( ! beiscsi_ep )
2012-08-20 21:30:18 +04:00
beiscsi_log ( beiscsi_conn - > phba , KERN_ERR ,
BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_conn_start , no beiscsi_ep \n " ) ;
2009-09-05 06:06:35 +04:00
beiscsi_conn - > login_in_progress = 0 ;
beiscsi_set_params_for_offld ( beiscsi_conn , & params ) ;
beiscsi_offload_connection ( beiscsi_conn , & params ) ;
iscsi_conn_start ( cls_conn ) ;
return 0 ;
}
/**
* beiscsi_get_cid - Allocate a cid
* @ phba : The phba instance
*/
static int beiscsi_get_cid ( struct beiscsi_hba * phba )
{
2013-09-29 02:35:49 +04:00
uint16_t cid_avlbl_ulp0 , cid_avlbl_ulp1 ;
2016-12-13 13:26:03 +03:00
unsigned short cid , cid_from_ulp ;
struct ulp_cid_info * cid_info ;
2013-09-29 02:35:49 +04:00
/* Find the ULP which has more CID available */
cid_avlbl_ulp0 = ( phba - > cid_array_info [ BEISCSI_ULP0 ] ) ?
BEISCSI_ULP0_AVLBL_CID ( phba ) : 0 ;
cid_avlbl_ulp1 = ( phba - > cid_array_info [ BEISCSI_ULP1 ] ) ?
BEISCSI_ULP1_AVLBL_CID ( phba ) : 0 ;
cid_from_ulp = ( cid_avlbl_ulp0 > cid_avlbl_ulp1 ) ?
BEISCSI_ULP0 : BEISCSI_ULP1 ;
2016-12-13 13:26:03 +03:00
/**
* If iSCSI protocol is loaded only on ULP 0 , and when cid_avlbl_ulp
* is ZERO for both , ULP 1 is returned .
* Check if ULP is loaded before getting new CID .
*/
if ( ! test_bit ( cid_from_ulp , ( void * ) & phba - > fw_config . ulp_supported ) )
return BE_INVALID_CID ;
cid_info = phba - > cid_array_info [ cid_from_ulp ] ;
cid = cid_info - > cid_array [ cid_info - > cid_alloc ] ;
if ( ! cid_info - > avlbl_cids | | cid = = BE_INVALID_CID ) {
__beiscsi_log ( phba , KERN_ERR ,
" BS_%d : failed to get cid: available %u:%u \n " ,
cid_info - > avlbl_cids , cid_info - > cid_free ) ;
return BE_INVALID_CID ;
2013-09-29 02:35:49 +04:00
}
2016-12-13 13:26:03 +03:00
/* empty the slot */
cid_info - > cid_array [ cid_info - > cid_alloc + + ] = BE_INVALID_CID ;
if ( cid_info - > cid_alloc = = BEISCSI_GET_CID_COUNT ( phba , cid_from_ulp ) )
cid_info - > cid_alloc = 0 ;
cid_info - > avlbl_cids - - ;
2009-09-05 06:06:35 +04:00
return cid ;
}
2010-06-09 12:30:08 +04:00
/**
* beiscsi_put_cid - Free the cid
* @ phba : The phba for which the cid is being freed
* @ cid : The cid to free
*/
static void beiscsi_put_cid ( struct beiscsi_hba * phba , unsigned short cid )
{
2013-09-29 02:35:49 +04:00
uint16_t cri_index = BE_GET_CRI_FROM_CID ( cid ) ;
2016-12-13 13:26:03 +03:00
struct hwi_wrb_context * pwrb_context ;
struct hwi_controller * phwi_ctrlr ;
struct ulp_cid_info * cid_info ;
uint16_t cid_post_ulp ;
2013-09-29 02:35:49 +04:00
phwi_ctrlr = phba - > phwi_ctrlr ;
pwrb_context = & phwi_ctrlr - > wrb_context [ cri_index ] ;
cid_post_ulp = pwrb_context - > ulp_num ;
cid_info = phba - > cid_array_info [ cid_post_ulp ] ;
2016-12-13 13:26:03 +03:00
/* fill only in empty slot */
if ( cid_info - > cid_array [ cid_info - > cid_free ] ! = BE_INVALID_CID ) {
__beiscsi_log ( phba , KERN_ERR ,
" BS_%d : failed to put cid %u: available %u:%u \n " ,
cid , cid_info - > avlbl_cids , cid_info - > cid_free ) ;
return ;
}
2013-09-29 02:35:49 +04:00
cid_info - > cid_array [ cid_info - > cid_free + + ] = cid ;
if ( cid_info - > cid_free = = BEISCSI_GET_CID_COUNT ( phba , cid_post_ulp ) )
cid_info - > cid_free = 0 ;
2016-12-13 13:26:03 +03:00
cid_info - > avlbl_cids + + ;
2010-06-09 12:30:08 +04:00
}
/**
* beiscsi_free_ep - free endpoint
* @ ep : pointer to iscsi endpoint structure
*/
static void beiscsi_free_ep ( struct beiscsi_endpoint * beiscsi_ep )
{
struct beiscsi_hba * phba = beiscsi_ep - > phba ;
2013-04-06 07:38:25 +04:00
struct beiscsi_conn * beiscsi_conn ;
2010-06-09 12:30:08 +04:00
beiscsi_put_cid ( phba , beiscsi_ep - > ep_cid ) ;
beiscsi_ep - > phba = NULL ;
2016-12-13 13:26:03 +03:00
/* clear this to track freeing in beiscsi_ep_disconnect */
phba - > ep_array [ BE_GET_CRI_FROM_CID ( beiscsi_ep - > ep_cid ) ] = NULL ;
2013-04-06 07:38:25 +04:00
/**
* Check if any connection resource allocated by driver
* is to be freed . This case occurs when target redirection
* or connection retry is done .
* */
if ( ! beiscsi_ep - > conn )
return ;
beiscsi_conn = beiscsi_ep - > conn ;
2016-12-13 13:26:03 +03:00
/**
* Break ep - > conn link here so that completions after
* this are ignored .
*/
beiscsi_ep - > conn = NULL ;
2013-04-06 07:38:25 +04:00
if ( beiscsi_conn - > login_in_progress ) {
2013-04-06 07:38:31 +04:00
beiscsi_free_mgmt_task_handles ( beiscsi_conn ,
beiscsi_conn - > task ) ;
2013-04-06 07:38:25 +04:00
beiscsi_conn - > login_in_progress = 0 ;
}
2010-06-09 12:30:08 +04:00
}
2009-09-05 06:06:35 +04:00
/**
* beiscsi_open_conn - Ask FW to open a TCP connection
* @ ep : endpoint to be used
* @ src_addr : The source IP address
* @ dst_addr : The Destination IP address
*
* Asks the FW to open a TCP connection
*/
static int beiscsi_open_conn ( struct iscsi_endpoint * ep ,
struct sockaddr * src_addr ,
struct sockaddr * dst_addr , int non_blocking )
{
struct beiscsi_endpoint * beiscsi_ep = ep - > dd_data ;
struct beiscsi_hba * phba = beiscsi_ep - > phba ;
2010-01-05 02:40:46 +03:00
struct tcp_connect_and_offload_out * ptcpcnct_out ;
2010-07-22 02:57:47 +04:00
struct be_dma_mem nonemb_cmd ;
2014-05-06 05:41:27 +04:00
unsigned int tag , req_memsize ;
2010-07-22 02:46:38 +04:00
int ret = - ENOMEM ;
2009-09-05 06:06:35 +04:00
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_open_conn \n " ) ;
2009-09-05 06:06:35 +04:00
beiscsi_ep - > ep_cid = beiscsi_get_cid ( phba ) ;
2016-12-13 13:26:03 +03:00
if ( beiscsi_ep - > ep_cid = = BE_INVALID_CID ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : No free cid available \n " ) ;
2009-09-05 06:06:35 +04:00
return ret ;
}
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_open_conn, ep_cid=%d \n " ,
beiscsi_ep - > ep_cid ) ;
2013-04-06 07:38:32 +04:00
phba - > ep_array [ BE_GET_CRI_FROM_CID
( beiscsi_ep - > ep_cid ) ] = ep ;
2009-09-05 06:06:35 +04:00
beiscsi_ep - > cid_vld = 0 ;
2014-05-06 05:41:27 +04:00
if ( is_chip_be2_be3r ( phba ) )
req_memsize = sizeof ( struct tcp_connect_and_offload_in ) ;
else
req_memsize = sizeof ( struct tcp_connect_and_offload_in_v1 ) ;
2018-10-10 19:22:24 +03:00
nonemb_cmd . va = dma_alloc_coherent ( & phba - > ctrl . pdev - > dev ,
2014-05-06 05:41:27 +04:00
req_memsize ,
2018-10-10 19:22:24 +03:00
& nonemb_cmd . dma , GFP_KERNEL ) ;
2010-07-22 02:57:47 +04:00
if ( nonemb_cmd . va = = NULL ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Failed to allocate memory for "
" mgmt_open_connection \n " ) ;
2013-04-06 07:38:32 +04:00
beiscsi_free_ep ( beiscsi_ep ) ;
2010-07-22 02:57:47 +04:00
return - ENOMEM ;
}
2014-05-06 05:41:27 +04:00
nonemb_cmd . size = req_memsize ;
2010-07-22 02:57:47 +04:00
memset ( nonemb_cmd . va , 0 , nonemb_cmd . size ) ;
tag = mgmt_open_connection ( phba , dst_addr , beiscsi_ep , & nonemb_cmd ) ;
2016-12-13 13:26:01 +03:00
if ( ! tag ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : mgmt_open_connection Failed for cid=%d \n " ,
beiscsi_ep - > ep_cid ) ;
2018-10-10 19:22:24 +03:00
dma_free_coherent ( & phba - > ctrl . pdev - > dev , nonemb_cmd . size ,
2010-07-22 02:57:47 +04:00
nonemb_cmd . va , nonemb_cmd . dma ) ;
2013-04-06 07:38:32 +04:00
beiscsi_free_ep ( beiscsi_ep ) ;
2010-07-22 02:52:27 +04:00
return - EAGAIN ;
2010-01-05 02:40:46 +03:00
}
2012-10-20 03:15:40 +04:00
2016-02-04 13:19:12 +03:00
ret = beiscsi_mccq_compl_wait ( phba , tag , NULL , & nonemb_cmd ) ;
2012-10-20 03:15:40 +04:00
if ( ret ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR ,
BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX ,
2012-10-20 03:15:40 +04:00
" BS_%d : mgmt_open_connection Failed " ) ;
2012-08-20 21:30:18 +04:00
2014-01-29 11:16:39 +04:00
if ( ret ! = - EBUSY )
2018-10-10 19:22:24 +03:00
dma_free_coherent ( & phba - > ctrl . pdev - > dev ,
nonemb_cmd . size , nonemb_cmd . va ,
nonemb_cmd . dma ) ;
2014-01-29 11:16:39 +04:00
2013-04-06 07:38:32 +04:00
beiscsi_free_ep ( beiscsi_ep ) ;
2014-01-29 11:16:39 +04:00
return ret ;
2010-01-05 02:40:46 +03:00
}
2012-10-20 03:15:40 +04:00
2013-04-06 07:38:23 +04:00
ptcpcnct_out = ( struct tcp_connect_and_offload_out * ) nonemb_cmd . va ;
2012-10-20 03:15:40 +04:00
beiscsi_ep = ep - > dd_data ;
beiscsi_ep - > fw_handle = ptcpcnct_out - > connection_handle ;
beiscsi_ep - > cid_vld = 1 ;
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : mgmt_open_connection Success \n " ) ;
2018-10-10 19:22:24 +03:00
dma_free_coherent ( & phba - > ctrl . pdev - > dev , nonemb_cmd . size ,
2010-07-22 02:57:47 +04:00
nonemb_cmd . va , nonemb_cmd . dma ) ;
2010-01-05 02:40:46 +03:00
return 0 ;
2009-09-05 06:06:35 +04:00
}
/**
* beiscsi_ep_connect - Ask chip to create TCP Conn
* @ scsi_host : Pointer to scsi_host structure
* @ dst_addr : The IP address of Target
* @ non_blocking : blocking or non - blocking call
*
* This routines first asks chip to create a connection and then allocates an EP
*/
struct iscsi_endpoint *
beiscsi_ep_connect ( struct Scsi_Host * shost , struct sockaddr * dst_addr ,
int non_blocking )
{
struct beiscsi_hba * phba ;
struct beiscsi_endpoint * beiscsi_ep ;
struct iscsi_endpoint * ep ;
int ret ;
2016-08-19 12:50:11 +03:00
if ( ! shost ) {
2009-09-05 06:06:35 +04:00
ret = - ENXIO ;
2016-08-19 12:50:11 +03:00
pr_err ( " beiscsi_ep_connect shost is NULL \n " ) ;
2009-09-05 06:06:35 +04:00
return ERR_PTR ( ret ) ;
}
2009-10-23 10:22:33 +04:00
2016-08-19 12:50:11 +03:00
phba = iscsi_host_priv ( shost ) ;
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2013-04-06 07:38:33 +04:00
ret = - EIO ;
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
2013-04-06 07:38:33 +04:00
return ERR_PTR ( ret ) ;
}
2016-08-19 12:50:11 +03:00
if ( ! test_bit ( BEISCSI_HBA_LINK_UP , & phba - > state ) ) {
2009-10-23 10:22:33 +04:00
ret = - EBUSY ;
2012-10-20 03:13:03 +04:00
beiscsi_log ( phba , KERN_WARNING , BEISCSI_LOG_CONFIG ,
" BS_%d : The Adapter Port state is Down!!! \n " ) ;
2009-10-23 10:22:33 +04:00
return ERR_PTR ( ret ) ;
}
2009-09-05 06:06:35 +04:00
ep = iscsi_create_endpoint ( sizeof ( struct beiscsi_endpoint ) ) ;
if ( ! ep ) {
ret = - ENOMEM ;
return ERR_PTR ( ret ) ;
}
beiscsi_ep = ep - > dd_data ;
beiscsi_ep - > phba = phba ;
2010-01-05 02:35:34 +03:00
beiscsi_ep - > openiscsi_ep = ep ;
2010-07-22 02:48:01 +04:00
ret = beiscsi_open_conn ( ep , NULL , dst_addr , non_blocking ) ;
if ( ret ) {
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_ERR , BEISCSI_LOG_CONFIG ,
" BS_%d : Failed in beiscsi_open_conn \n " ) ;
2009-09-05 06:06:35 +04:00
goto free_ep ;
}
return ep ;
free_ep :
2010-06-09 12:30:08 +04:00
iscsi_destroy_endpoint ( ep ) ;
2009-09-05 06:06:35 +04:00
return ERR_PTR ( ret ) ;
}
/**
* beiscsi_ep_poll - Poll to see if connection is established
* @ ep : endpoint to be used
* @ timeout_ms : timeout specified in millisecs
*
* Poll to see if TCP connection established
*/
int beiscsi_ep_poll ( struct iscsi_endpoint * ep , int timeout_ms )
{
struct beiscsi_endpoint * beiscsi_ep = ep - > dd_data ;
2012-08-20 21:30:18 +04:00
beiscsi_log ( beiscsi_ep - > phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : In beiscsi_ep_poll \n " ) ;
2009-09-05 06:06:35 +04:00
if ( beiscsi_ep - > cid_vld = = 1 )
return 1 ;
else
return 0 ;
}
2014-08-08 09:00:01 +04:00
/**
* beiscsi_flush_cq ( ) - Flush the CQ created .
* @ phba : ptr device priv structure .
*
* Before the connection resource are freed flush
* all the CQ enteries
* */
static void beiscsi_flush_cq ( struct beiscsi_hba * phba )
{
uint16_t i ;
struct be_eq_obj * pbe_eq ;
struct hwi_controller * phwi_ctrlr ;
struct hwi_context_memory * phwi_context ;
phwi_ctrlr = phba - > phwi_ctrlr ;
phwi_context = phwi_ctrlr - > phwi_ctxt ;
for ( i = 0 ; i < phba - > num_cpus ; i + + ) {
pbe_eq = & phwi_context - > be_eq [ i ] ;
2015-11-10 16:56:14 +03:00
irq_poll_disable ( & pbe_eq - > iopoll ) ;
2016-01-20 11:40:56 +03:00
beiscsi_process_cq ( pbe_eq , BE2_MAX_NUM_CQ_PROC ) ;
2015-11-10 16:56:14 +03:00
irq_poll_enable ( & pbe_eq - > iopoll ) ;
2014-08-08 09:00:01 +04:00
}
}
2009-09-05 06:06:35 +04:00
/**
2017-03-24 11:41:41 +03:00
* beiscsi_conn_close - Invalidate and upload connection
2009-09-05 06:06:35 +04:00
* @ ep : The iscsi endpoint
2017-03-24 11:41:41 +03:00
*
* Returns 0 on success , - 1 on failure .
2009-09-05 06:06:35 +04:00
*/
2017-03-24 11:41:41 +03:00
static int beiscsi_conn_close ( struct beiscsi_endpoint * beiscsi_ep )
2009-09-05 06:06:35 +04:00
{
struct beiscsi_hba * phba = beiscsi_ep - > phba ;
2017-03-24 11:41:41 +03:00
unsigned int tag , attempts ;
int ret ;
2009-09-05 06:06:35 +04:00
2017-03-24 11:41:41 +03:00
/**
* Without successfully invalidating and uploading connection
* driver can ' t reuse the CID so attempt more than once .
*/
attempts = 0 ;
while ( attempts + + < 3 ) {
tag = beiscsi_invalidate_cxn ( phba , beiscsi_ep ) ;
if ( tag ) {
ret = beiscsi_mccq_compl_wait ( phba , tag , NULL , NULL ) ;
if ( ! ret )
break ;
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : invalidate conn failed cid %d \n " ,
beiscsi_ep - > ep_cid ) ;
}
2009-09-05 06:06:35 +04:00
}
2012-10-20 03:15:40 +04:00
2017-03-24 11:41:41 +03:00
/* wait for all completions to arrive, then process them */
msleep ( 250 ) ;
/* flush CQ entries */
2014-08-08 09:00:01 +04:00
beiscsi_flush_cq ( phba ) ;
2017-03-24 11:41:41 +03:00
if ( attempts > 3 )
return - 1 ;
attempts = 0 ;
while ( attempts + + < 3 ) {
tag = beiscsi_upload_cxn ( phba , beiscsi_ep ) ;
if ( tag ) {
ret = beiscsi_mccq_compl_wait ( phba , tag , NULL , NULL ) ;
if ( ! ret )
break ;
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : upload conn failed cid %d \n " ,
beiscsi_ep - > ep_cid ) ;
}
}
if ( attempts > 3 )
return - 1 ;
return 0 ;
2009-09-05 06:06:35 +04:00
}
/**
2010-06-09 12:30:08 +04:00
* beiscsi_ep_disconnect - Tears down the TCP connection
* @ ep : endpoint to be used
*
* Tears down the TCP connection
2009-09-05 06:06:35 +04:00
*/
2010-06-09 12:30:08 +04:00
void beiscsi_ep_disconnect ( struct iscsi_endpoint * ep )
2009-09-05 06:06:35 +04:00
{
struct beiscsi_endpoint * beiscsi_ep ;
2017-03-24 11:41:41 +03:00
struct beiscsi_conn * beiscsi_conn ;
2010-06-09 12:30:08 +04:00
struct beiscsi_hba * phba ;
2016-12-13 13:26:03 +03:00
uint16_t cri_index ;
2009-09-05 06:06:35 +04:00
2010-06-09 12:30:08 +04:00
beiscsi_ep = ep - > dd_data ;
phba = beiscsi_ep - > phba ;
2012-08-20 21:30:18 +04:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
2016-12-13 13:26:03 +03:00
" BS_%d : In beiscsi_ep_disconnect for ep_cid = %u \n " ,
2012-08-20 21:30:18 +04:00
beiscsi_ep - > ep_cid ) ;
2010-06-09 12:30:08 +04:00
2016-12-13 13:26:03 +03:00
cri_index = BE_GET_CRI_FROM_CID ( beiscsi_ep - > ep_cid ) ;
if ( ! phba - > ep_array [ cri_index ] ) {
__beiscsi_log ( phba , KERN_ERR ,
" BS_%d : ep_array at %u cid %u empty \n " ,
cri_index ,
beiscsi_ep - > ep_cid ) ;
return ;
}
2012-08-20 21:30:55 +04:00
if ( beiscsi_ep - > conn ) {
beiscsi_conn = beiscsi_ep - > conn ;
iscsi_suspend_queue ( beiscsi_conn - > conn ) ;
2009-09-05 06:06:35 +04:00
}
2010-06-09 12:30:08 +04:00
2016-08-19 12:50:18 +03:00
if ( ! beiscsi_hba_is_online ( phba ) ) {
2016-08-19 12:50:11 +03:00
beiscsi_log ( phba , KERN_INFO , BEISCSI_LOG_CONFIG ,
" BS_%d : HBA in error 0x%lx \n " , phba - > state ) ;
2017-03-24 11:41:41 +03:00
} else {
/**
* Make CID available even if close fails .
* If not freed , FW might fail open using the CID .
*/
if ( beiscsi_conn_close ( beiscsi_ep ) < 0 )
__beiscsi_log ( phba , KERN_ERR ,
" BS_%d : close conn failed cid %d \n " ,
beiscsi_ep - > ep_cid ) ;
2009-09-05 06:06:35 +04:00
}
2010-06-09 12:30:08 +04:00
2010-01-05 02:35:34 +03:00
beiscsi_free_ep ( beiscsi_ep ) ;
2016-12-13 13:26:03 +03:00
if ( ! phba - > conn_table [ cri_index ] )
__beiscsi_log ( phba , KERN_ERR ,
2017-03-24 11:41:41 +03:00
" BS_%d : conn_table empty at %u: cid %u \n " ,
cri_index , beiscsi_ep - > ep_cid ) ;
2016-12-13 13:26:03 +03:00
phba - > conn_table [ cri_index ] = NULL ;
2010-06-09 12:30:08 +04:00
iscsi_destroy_endpoint ( beiscsi_ep - > openiscsi_ep ) ;
2009-09-05 06:06:35 +04:00
}
2011-07-25 22:48:42 +04:00
2016-08-19 12:50:06 +03:00
umode_t beiscsi_attr_is_visible ( int param_type , int param )
2011-07-25 22:48:42 +04:00
{
switch ( param_type ) {
2012-04-04 08:41:51 +04:00
case ISCSI_NET_PARAM :
switch ( param ) {
case ISCSI_NET_PARAM_IFACE_ENABLE :
case ISCSI_NET_PARAM_IPV4_ADDR :
case ISCSI_NET_PARAM_IPV4_SUBNET :
case ISCSI_NET_PARAM_IPV4_BOOTPROTO :
case ISCSI_NET_PARAM_IPV4_GW :
case ISCSI_NET_PARAM_IPV6_ADDR :
2012-08-20 21:30:43 +04:00
case ISCSI_NET_PARAM_VLAN_ID :
case ISCSI_NET_PARAM_VLAN_PRIORITY :
case ISCSI_NET_PARAM_VLAN_ENABLED :
2012-04-04 08:41:51 +04:00
return S_IRUGO ;
default :
return 0 ;
}
2011-07-25 22:48:45 +04:00
case ISCSI_HOST_PARAM :
switch ( param ) {
case ISCSI_HOST_PARAM_HWADDRESS :
2012-04-04 08:41:52 +04:00
case ISCSI_HOST_PARAM_INITIATOR_NAME :
case ISCSI_HOST_PARAM_PORT_STATE :
case ISCSI_HOST_PARAM_PORT_SPEED :
2011-07-25 22:48:45 +04:00
return S_IRUGO ;
default :
return 0 ;
}
2011-07-25 22:48:42 +04:00
case ISCSI_PARAM :
switch ( param ) {
case ISCSI_PARAM_MAX_RECV_DLENGTH :
case ISCSI_PARAM_MAX_XMIT_DLENGTH :
case ISCSI_PARAM_HDRDGST_EN :
case ISCSI_PARAM_DATADGST_EN :
case ISCSI_PARAM_CONN_ADDRESS :
case ISCSI_PARAM_CONN_PORT :
case ISCSI_PARAM_EXP_STATSN :
case ISCSI_PARAM_PERSISTENT_ADDRESS :
case ISCSI_PARAM_PERSISTENT_PORT :
case ISCSI_PARAM_PING_TMO :
case ISCSI_PARAM_RECV_TMO :
2011-07-25 22:48:43 +04:00
case ISCSI_PARAM_INITIAL_R2T_EN :
case ISCSI_PARAM_MAX_R2T :
case ISCSI_PARAM_IMM_DATA_EN :
case ISCSI_PARAM_FIRST_BURST :
case ISCSI_PARAM_MAX_BURST :
case ISCSI_PARAM_PDU_INORDER_EN :
case ISCSI_PARAM_DATASEQ_INORDER_EN :
case ISCSI_PARAM_ERL :
case ISCSI_PARAM_TARGET_NAME :
case ISCSI_PARAM_TPGT :
case ISCSI_PARAM_USERNAME :
case ISCSI_PARAM_PASSWORD :
case ISCSI_PARAM_USERNAME_IN :
case ISCSI_PARAM_PASSWORD_IN :
case ISCSI_PARAM_FAST_ABORT :
case ISCSI_PARAM_ABORT_TMO :
case ISCSI_PARAM_LU_RESET_TMO :
case ISCSI_PARAM_IFACE_NAME :
case ISCSI_PARAM_INITIATOR_NAME :
2011-07-25 22:48:42 +04:00
return S_IRUGO ;
default :
return 0 ;
}
}
return 0 ;
}