aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/qlcnic/qlcnic_ctx.c
diff options
context:
space:
mode:
authorRajesh Borundia <rajesh.borundia@qlogic.com>2010-08-19 01:08:25 -0400
committerDavid S. Miller <davem@davemloft.net>2010-08-19 19:52:38 -0400
commit4e8acb011f0e9e86e29b53ff051e699ba0c5726d (patch)
treea8f74029aa29ce99403f283a6c33368bda0762b9 /drivers/net/qlcnic/qlcnic_ctx.c
parent251b036a22f530aff26cf70f5cdb0cf64a072e46 (diff)
qlcnic: configure port on eswitch
o Nic partition capable devices has embedded switch, this needs to support various features like external switch. Signed-off-by: Rajesh Borundia <rajesh.borundia@qlogic.com> Signed-off-by: Amit Kumar Salecha <amit.salecha@qlogic.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/qlcnic/qlcnic_ctx.c')
-rw-r--r--drivers/net/qlcnic/qlcnic_ctx.c174
1 files changed, 130 insertions, 44 deletions
diff --git a/drivers/net/qlcnic/qlcnic_ctx.c b/drivers/net/qlcnic/qlcnic_ctx.c
index 57c9b09bd16a..74ae3b0a5ea8 100644
--- a/drivers/net/qlcnic/qlcnic_ctx.c
+++ b/drivers/net/qlcnic/qlcnic_ctx.c
@@ -813,9 +813,8 @@ int qlcnic_get_eswitch_capabilities(struct qlcnic_adapter *adapter, u8 port,
813 arg2 = QLCRD32(adapter, QLCNIC_ARG2_CRB_OFFSET); 813 arg2 = QLCRD32(adapter, QLCNIC_ARG2_CRB_OFFSET);
814 814
815 eswitch->port = arg1 & 0xf; 815 eswitch->port = arg1 & 0xf;
816 eswitch->active_vports = LSB(arg2); 816 eswitch->max_ucast_filters = LSW(arg2);
817 eswitch->max_ucast_filters = MSB(arg2); 817 eswitch->max_active_vlans = MSW(arg2) & 0xfff;
818 eswitch->max_active_vlans = LSB(MSW(arg2));
819 if (arg1 & BIT_6) 818 if (arg1 & BIT_6)
820 eswitch->flags |= QLCNIC_SWITCH_VLAN_FILTERING; 819 eswitch->flags |= QLCNIC_SWITCH_VLAN_FILTERING;
821 if (arg1 & BIT_7) 820 if (arg1 & BIT_7)
@@ -943,47 +942,6 @@ int qlcnic_config_port_mirroring(struct qlcnic_adapter *adapter, u8 id,
943 return err; 942 return err;
944} 943}
945 944
946/* Configure eSwitch port */
947int qlcnic_config_switch_port(struct qlcnic_adapter *adapter, u8 id,
948 int vlan_tagging, u8 discard_tagged, u8 promsc_mode,
949 u8 mac_learn, u8 pci_func, u16 vlan_id)
950{
951 int err = -EIO;
952 u32 arg1;
953 struct qlcnic_eswitch *eswitch;
954
955 if (adapter->op_mode != QLCNIC_MGMT_FUNC)
956 return err;
957
958 eswitch = &adapter->eswitch[id];
959 if (!(eswitch->flags & QLCNIC_SWITCH_ENABLE))
960 return err;
961
962 arg1 = eswitch->port | (discard_tagged ? BIT_4 : 0);
963 arg1 |= (promsc_mode ? BIT_6 : 0) | (mac_learn ? BIT_7 : 0);
964 arg1 |= pci_func << 8;
965 if (vlan_tagging)
966 arg1 |= BIT_5 | (vlan_id << 16);
967
968 err = qlcnic_issue_cmd(adapter,
969 adapter->ahw.pci_func,
970 adapter->fw_hal_version,
971 arg1,
972 0,
973 0,
974 QLCNIC_CDRP_CMD_CONFIGURE_ESWITCH);
975
976 if (err != QLCNIC_RCODE_SUCCESS) {
977 dev_err(&adapter->pdev->dev,
978 "Failed to configure eswitch port%d\n", eswitch->port);
979 } else {
980 dev_info(&adapter->pdev->dev,
981 "Configured eSwitch for port %d\n", eswitch->port);
982 }
983
984 return err;
985}
986
987int qlcnic_get_port_stats(struct qlcnic_adapter *adapter, const u8 func, 945int qlcnic_get_port_stats(struct qlcnic_adapter *adapter, const u8 func,
988 const u8 rx_tx, struct __qlcnic_esw_statistics *esw_stats) { 946 const u8 rx_tx, struct __qlcnic_esw_statistics *esw_stats) {
989 947
@@ -1108,3 +1066,131 @@ err_ret:
1108 "rx_ctx=%d\n", func_esw, port, rx_tx); 1066 "rx_ctx=%d\n", func_esw, port, rx_tx);
1109 return -EIO; 1067 return -EIO;
1110} 1068}
1069
1070static int
1071__qlcnic_get_eswitch_port_config(struct qlcnic_adapter *adapter,
1072 u32 *arg1, u32 *arg2)
1073{
1074 int err = -EIO;
1075 u8 pci_func;
1076 pci_func = (*arg1 >> 8);
1077 err = qlcnic_issue_cmd(adapter,
1078 adapter->ahw.pci_func,
1079 adapter->fw_hal_version,
1080 *arg1,
1081 0,
1082 0,
1083 QLCNIC_CDRP_CMD_GET_ESWITCH_PORT_CONFIG);
1084
1085 if (err == QLCNIC_RCODE_SUCCESS) {
1086 *arg1 = QLCRD32(adapter, QLCNIC_ARG1_CRB_OFFSET);
1087 *arg2 = QLCRD32(adapter, QLCNIC_ARG2_CRB_OFFSET);
1088 dev_info(&adapter->pdev->dev,
1089 "eSwitch port config for pci func%d\n", pci_func);
1090 } else {
1091 dev_err(&adapter->pdev->dev,
1092 "Failed to get eswitch port config%d\n", pci_func);
1093 }
1094 return err;
1095}
1096/* Configure eSwitch port
1097op_mode = 0 for setting default port behavior
1098op_mode = 1 for setting vlan id
1099op_mode = 2 for deleting vlan id
1100op_type = 0 for vlan_id
1101op_type = 1 for port vlan_id
1102*/
1103int qlcnic_config_switch_port(struct qlcnic_adapter *adapter,
1104 struct qlcnic_esw_func_cfg *esw_cfg)
1105{
1106 int err = -EIO;
1107 u32 arg1, arg2 = 0;
1108 u8 pci_func;
1109
1110 if (adapter->op_mode != QLCNIC_MGMT_FUNC)
1111 return err;
1112 pci_func = esw_cfg->pci_func;
1113 arg1 = (adapter->npars[pci_func].phy_port & BIT_0);
1114 arg1 |= (pci_func << 8);
1115
1116 if (__qlcnic_get_eswitch_port_config(adapter, &arg1, &arg2))
1117 return err;
1118 arg1 &= ~(0x0ff << 8);
1119 arg1 |= (pci_func << 8);
1120 arg1 &= ~(BIT_2 | BIT_3);
1121 switch (esw_cfg->op_mode) {
1122 case QLCNIC_PORT_DEFAULTS:
1123 arg1 |= (BIT_4 | BIT_6 | BIT_7);
1124 arg2 |= (BIT_0 | BIT_1);
1125 if (adapter->capabilities & QLCNIC_FW_CAPABILITY_TSO)
1126 arg2 |= (BIT_2 | BIT_3);
1127 if (!(esw_cfg->discard_tagged))
1128 arg1 &= ~BIT_4;
1129 if (!(esw_cfg->promisc_mode))
1130 arg1 &= ~BIT_6;
1131 if (!(esw_cfg->mac_learning))
1132 arg1 &= ~BIT_7;
1133 if (!(esw_cfg->mac_anti_spoof))
1134 arg2 &= ~BIT_0;
1135 if (!(esw_cfg->offload_flags & BIT_0))
1136 arg2 &= ~(BIT_1 | BIT_2 | BIT_3);
1137 if (!(esw_cfg->offload_flags & BIT_1))
1138 arg2 &= ~BIT_2;
1139 if (!(esw_cfg->offload_flags & BIT_2))
1140 arg2 &= ~BIT_3;
1141 break;
1142 case QLCNIC_ADD_VLAN:
1143 arg1 |= (BIT_2 | BIT_5);
1144 arg1 |= (esw_cfg->vlan_id << 16);
1145 break;
1146 case QLCNIC_DEL_VLAN:
1147 arg1 |= (BIT_3 | BIT_5);
1148 arg1 &= ~(0x0ffff << 16);
1149 default:
1150 return err;
1151 }
1152
1153 err = qlcnic_issue_cmd(adapter,
1154 adapter->ahw.pci_func,
1155 adapter->fw_hal_version,
1156 arg1,
1157 arg2,
1158 0,
1159 QLCNIC_CDRP_CMD_CONFIGURE_ESWITCH);
1160
1161 if (err != QLCNIC_RCODE_SUCCESS) {
1162 dev_err(&adapter->pdev->dev,
1163 "Failed to configure eswitch port%d\n", pci_func);
1164 } else {
1165 dev_info(&adapter->pdev->dev,
1166 "Configured eSwitch for port %d\n", pci_func);
1167 }
1168
1169 return err;
1170}
1171
1172int
1173qlcnic_get_eswitch_port_config(struct qlcnic_adapter *adapter,
1174 struct qlcnic_esw_func_cfg *esw_cfg)
1175{
1176 u32 arg1, arg2;
1177 u8 phy_port;
1178 if (adapter->op_mode == QLCNIC_MGMT_FUNC)
1179 phy_port = adapter->npars[esw_cfg->pci_func].phy_port;
1180 else
1181 phy_port = adapter->physical_port;
1182 arg1 = phy_port;
1183 arg1 |= (esw_cfg->pci_func << 8);
1184 if (__qlcnic_get_eswitch_port_config(adapter, &arg1, &arg2))
1185 return -EIO;
1186
1187 esw_cfg->discard_tagged = !!(arg1 & BIT_4);
1188 esw_cfg->host_vlan_tag = !!(arg1 & BIT_5);
1189 esw_cfg->promisc_mode = !!(arg1 & BIT_6);
1190 esw_cfg->mac_learning = !!(arg1 & BIT_7);
1191 esw_cfg->vlan_id = LSW(arg1 >> 16);
1192 esw_cfg->mac_anti_spoof = (arg2 & 0x1);
1193 esw_cfg->offload_flags = ((arg2 >> 1) & 0x7);
1194
1195 return 0;
1196}