Merge branch 'qlcnic-next'
Shahed Shaikh says: ==================== qlcnic: Re-factoring and enhancements This patch series includes following changes - * Re-factored firmware minidump template header handling * Support to make 8 vNIC mode application to work with 16 vNIC mode * Enhance error message logging when adapter is in failed state and when adapter lock access fails. * Allow vlan0 traffic * update MAINTAINERS Please apply this series to net-next. ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
Коммит
8bfdfbc188
|
@ -7038,13 +7038,8 @@ F: Documentation/networking/LICENSE.qla3xxx
|
|||
F: drivers/net/ethernet/qlogic/qla3xxx.*
|
||||
|
||||
QLOGIC QLCNIC (1/10)Gb ETHERNET DRIVER
|
||||
M: Himanshu Madhani <himanshu.madhani@qlogic.com>
|
||||
M: Rajesh Borundia <rajesh.borundia@qlogic.com>
|
||||
M: Shahed Shaikh <shahed.shaikh@qlogic.com>
|
||||
M: Jitendra Kalsaria <jitendra.kalsaria@qlogic.com>
|
||||
M: Sony Chacko <sony.chacko@qlogic.com>
|
||||
M: Sucheta Chakraborty <sucheta.chakraborty@qlogic.com>
|
||||
M: linux-driver@qlogic.com
|
||||
M: Dept-HSGLinuxNICDev@qlogic.com
|
||||
L: netdev@vger.kernel.org
|
||||
S: Supported
|
||||
F: drivers/net/ethernet/qlogic/qlcnic/
|
||||
|
|
|
@ -38,8 +38,8 @@
|
|||
|
||||
#define _QLCNIC_LINUX_MAJOR 5
|
||||
#define _QLCNIC_LINUX_MINOR 3
|
||||
#define _QLCNIC_LINUX_SUBVERSION 55
|
||||
#define QLCNIC_LINUX_VERSIONID "5.3.55"
|
||||
#define _QLCNIC_LINUX_SUBVERSION 56
|
||||
#define QLCNIC_LINUX_VERSIONID "5.3.56"
|
||||
#define QLCNIC_DRV_IDC_VER 0x01
|
||||
#define QLCNIC_DRIVER_VERSION ((_QLCNIC_LINUX_MAJOR << 16) |\
|
||||
(_QLCNIC_LINUX_MINOR << 8) | (_QLCNIC_LINUX_SUBVERSION))
|
||||
|
@ -394,7 +394,7 @@ struct qlcnic_nic_intr_coalesce {
|
|||
u32 timer_out;
|
||||
};
|
||||
|
||||
struct qlcnic_dump_template_hdr {
|
||||
struct qlcnic_83xx_dump_template_hdr {
|
||||
u32 type;
|
||||
u32 offset;
|
||||
u32 size;
|
||||
|
@ -411,15 +411,42 @@ struct qlcnic_dump_template_hdr {
|
|||
u32 rsvd[0];
|
||||
};
|
||||
|
||||
struct qlcnic_82xx_dump_template_hdr {
|
||||
u32 type;
|
||||
u32 offset;
|
||||
u32 size;
|
||||
u32 cap_mask;
|
||||
u32 num_entries;
|
||||
u32 version;
|
||||
u32 timestamp;
|
||||
u32 checksum;
|
||||
u32 drv_cap_mask;
|
||||
u32 sys_info[3];
|
||||
u32 saved_state[16];
|
||||
u32 cap_sizes[8];
|
||||
u32 rsvd[7];
|
||||
u32 capabilities;
|
||||
u32 rsvd1[0];
|
||||
};
|
||||
|
||||
struct qlcnic_fw_dump {
|
||||
u8 clr; /* flag to indicate if dump is cleared */
|
||||
bool enable; /* enable/disable dump */
|
||||
u32 size; /* total size of the dump */
|
||||
u32 cap_mask; /* Current capture mask */
|
||||
void *data; /* dump data area */
|
||||
struct qlcnic_dump_template_hdr *tmpl_hdr;
|
||||
void *tmpl_hdr;
|
||||
dma_addr_t phys_addr;
|
||||
void *dma_buffer;
|
||||
bool use_pex_dma;
|
||||
/* Read only elements which are common between 82xx and 83xx
|
||||
* template header. Update these values immediately after we read
|
||||
* template header from Firmware
|
||||
*/
|
||||
u32 tmpl_hdr_size;
|
||||
u32 version;
|
||||
u32 num_entries;
|
||||
u32 offset;
|
||||
};
|
||||
|
||||
/*
|
||||
|
@ -1769,6 +1796,12 @@ struct qlcnic_hardware_ops {
|
|||
struct qlcnic_host_tx_ring *);
|
||||
void (*disable_tx_intr) (struct qlcnic_adapter *,
|
||||
struct qlcnic_host_tx_ring *);
|
||||
u32 (*get_saved_state)(void *, u32);
|
||||
void (*set_saved_state)(void *, u32, u32);
|
||||
void (*cache_tmpl_hdr_values)(struct qlcnic_fw_dump *);
|
||||
u32 (*get_cap_size)(void *, int);
|
||||
void (*set_sys_info)(void *, int, u32);
|
||||
void (*store_cap_mask)(void *, u32);
|
||||
};
|
||||
|
||||
extern struct qlcnic_nic_template qlcnic_vf_ops;
|
||||
|
@ -2007,6 +2040,42 @@ static inline void qlcnic_read_phys_port_id(struct qlcnic_adapter *adapter)
|
|||
adapter->ahw->hw_ops->read_phys_port_id(adapter);
|
||||
}
|
||||
|
||||
static inline u32 qlcnic_get_saved_state(struct qlcnic_adapter *adapter,
|
||||
void *t_hdr, u32 index)
|
||||
{
|
||||
return adapter->ahw->hw_ops->get_saved_state(t_hdr, index);
|
||||
}
|
||||
|
||||
static inline void qlcnic_set_saved_state(struct qlcnic_adapter *adapter,
|
||||
void *t_hdr, u32 index, u32 value)
|
||||
{
|
||||
adapter->ahw->hw_ops->set_saved_state(t_hdr, index, value);
|
||||
}
|
||||
|
||||
static inline void qlcnic_cache_tmpl_hdr_values(struct qlcnic_adapter *adapter,
|
||||
struct qlcnic_fw_dump *fw_dump)
|
||||
{
|
||||
adapter->ahw->hw_ops->cache_tmpl_hdr_values(fw_dump);
|
||||
}
|
||||
|
||||
static inline u32 qlcnic_get_cap_size(struct qlcnic_adapter *adapter,
|
||||
void *tmpl_hdr, int index)
|
||||
{
|
||||
return adapter->ahw->hw_ops->get_cap_size(tmpl_hdr, index);
|
||||
}
|
||||
|
||||
static inline void qlcnic_set_sys_info(struct qlcnic_adapter *adapter,
|
||||
void *tmpl_hdr, int idx, u32 value)
|
||||
{
|
||||
adapter->ahw->hw_ops->set_sys_info(tmpl_hdr, idx, value);
|
||||
}
|
||||
|
||||
static inline void qlcnic_store_cap_mask(struct qlcnic_adapter *adapter,
|
||||
void *tmpl_hdr, u32 mask)
|
||||
{
|
||||
adapter->ahw->hw_ops->store_cap_mask(tmpl_hdr, mask);
|
||||
}
|
||||
|
||||
static inline void qlcnic_dev_request_reset(struct qlcnic_adapter *adapter,
|
||||
u32 key)
|
||||
{
|
||||
|
|
|
@ -203,7 +203,12 @@ static struct qlcnic_hardware_ops qlcnic_83xx_hw_ops = {
|
|||
.disable_sds_intr = qlcnic_83xx_disable_sds_intr,
|
||||
.enable_tx_intr = qlcnic_83xx_enable_tx_intr,
|
||||
.disable_tx_intr = qlcnic_83xx_disable_tx_intr,
|
||||
|
||||
.get_saved_state = qlcnic_83xx_get_saved_state,
|
||||
.set_saved_state = qlcnic_83xx_set_saved_state,
|
||||
.cache_tmpl_hdr_values = qlcnic_83xx_cache_tmpl_hdr_values,
|
||||
.get_cap_size = qlcnic_83xx_get_cap_size,
|
||||
.set_sys_info = qlcnic_83xx_set_sys_info,
|
||||
.store_cap_mask = qlcnic_83xx_store_cap_mask,
|
||||
};
|
||||
|
||||
static struct qlcnic_nic_template qlcnic_83xx_ops = {
|
||||
|
|
|
@ -308,6 +308,8 @@ struct qlc_83xx_reset {
|
|||
#define QLC_83XX_IDC_FLASH_PARAM_ADDR 0x3e8020
|
||||
|
||||
struct qlcnic_adapter;
|
||||
struct qlcnic_fw_dump;
|
||||
|
||||
struct qlc_83xx_idc {
|
||||
int (*state_entry) (struct qlcnic_adapter *);
|
||||
u64 sec_counter;
|
||||
|
@ -650,4 +652,10 @@ int qlcnic_83xx_check_vnic_state(struct qlcnic_adapter *);
|
|||
void qlcnic_83xx_aer_stop_poll_work(struct qlcnic_adapter *);
|
||||
int qlcnic_83xx_aer_reset(struct qlcnic_adapter *);
|
||||
void qlcnic_83xx_aer_start_poll_work(struct qlcnic_adapter *);
|
||||
u32 qlcnic_83xx_get_saved_state(void *, u32);
|
||||
void qlcnic_83xx_set_saved_state(void *, u32, u32);
|
||||
void qlcnic_83xx_cache_tmpl_hdr_values(struct qlcnic_fw_dump *);
|
||||
u32 qlcnic_83xx_get_cap_size(void *, int);
|
||||
void qlcnic_83xx_set_sys_info(void *, int, u32);
|
||||
void qlcnic_83xx_store_cap_mask(void *, u32);
|
||||
#endif
|
||||
|
|
|
@ -1639,14 +1639,14 @@ qlcnic_get_dump_flag(struct net_device *netdev, struct ethtool_dump *dump)
|
|||
}
|
||||
|
||||
if (fw_dump->clr)
|
||||
dump->len = fw_dump->tmpl_hdr->size + fw_dump->size;
|
||||
dump->len = fw_dump->tmpl_hdr_size + fw_dump->size;
|
||||
else
|
||||
dump->len = 0;
|
||||
|
||||
if (!qlcnic_check_fw_dump_state(adapter))
|
||||
dump->flag = ETH_FW_DUMP_DISABLE;
|
||||
else
|
||||
dump->flag = fw_dump->tmpl_hdr->drv_cap_mask;
|
||||
dump->flag = fw_dump->cap_mask;
|
||||
|
||||
dump->version = adapter->fw_version;
|
||||
return 0;
|
||||
|
@ -1671,9 +1671,10 @@ qlcnic_get_dump_data(struct net_device *netdev, struct ethtool_dump *dump,
|
|||
netdev_info(netdev, "Dump not available\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Copy template header first */
|
||||
copy_sz = fw_dump->tmpl_hdr->size;
|
||||
hdr_ptr = (u32 *) fw_dump->tmpl_hdr;
|
||||
copy_sz = fw_dump->tmpl_hdr_size;
|
||||
hdr_ptr = (u32 *)fw_dump->tmpl_hdr;
|
||||
data = buffer;
|
||||
for (i = 0; i < copy_sz/sizeof(u32); i++)
|
||||
*data++ = cpu_to_le32(*hdr_ptr++);
|
||||
|
@ -1681,7 +1682,7 @@ qlcnic_get_dump_data(struct net_device *netdev, struct ethtool_dump *dump,
|
|||
/* Copy captured dump data */
|
||||
memcpy(buffer + copy_sz, fw_dump->data, fw_dump->size);
|
||||
dump->len = copy_sz + fw_dump->size;
|
||||
dump->flag = fw_dump->tmpl_hdr->drv_cap_mask;
|
||||
dump->flag = fw_dump->cap_mask;
|
||||
|
||||
/* Free dump area once data has been captured */
|
||||
vfree(fw_dump->data);
|
||||
|
@ -1703,7 +1704,11 @@ static int qlcnic_set_dump_mask(struct qlcnic_adapter *adapter, u32 mask)
|
|||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
fw_dump->tmpl_hdr->drv_cap_mask = mask;
|
||||
fw_dump->cap_mask = mask;
|
||||
|
||||
/* Store new capture mask in template header as well*/
|
||||
qlcnic_store_cap_mask(adapter, fw_dump->tmpl_hdr, mask);
|
||||
|
||||
netdev_info(netdev, "Driver mask changed to: 0x%x\n", mask);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -317,9 +317,7 @@ static void qlcnic_write_window_reg(u32 addr, void __iomem *bar0, u32 data)
|
|||
int
|
||||
qlcnic_pcie_sem_lock(struct qlcnic_adapter *adapter, int sem, u32 id_reg)
|
||||
{
|
||||
int timeout = 0;
|
||||
int err = 0;
|
||||
u32 done = 0;
|
||||
int timeout = 0, err = 0, done = 0;
|
||||
|
||||
while (!done) {
|
||||
done = QLCRD32(adapter, QLCNIC_PCIE_REG(PCIE_SEM_LOCK(sem)),
|
||||
|
@ -327,10 +325,20 @@ qlcnic_pcie_sem_lock(struct qlcnic_adapter *adapter, int sem, u32 id_reg)
|
|||
if (done == 1)
|
||||
break;
|
||||
if (++timeout >= QLCNIC_PCIE_SEM_TIMEOUT) {
|
||||
dev_err(&adapter->pdev->dev,
|
||||
"Failed to acquire sem=%d lock; holdby=%d\n",
|
||||
sem,
|
||||
id_reg ? QLCRD32(adapter, id_reg, &err) : -1);
|
||||
if (id_reg) {
|
||||
done = QLCRD32(adapter, id_reg, &err);
|
||||
if (done != -1)
|
||||
dev_err(&adapter->pdev->dev,
|
||||
"Failed to acquire sem=%d lock held by=%d\n",
|
||||
sem, done);
|
||||
else
|
||||
dev_err(&adapter->pdev->dev,
|
||||
"Failed to acquire sem=%d lock",
|
||||
sem);
|
||||
} else {
|
||||
dev_err(&adapter->pdev->dev,
|
||||
"Failed to acquire sem=%d lock", sem);
|
||||
}
|
||||
return -EIO;
|
||||
}
|
||||
msleep(1);
|
||||
|
|
|
@ -161,6 +161,7 @@ struct qlcnic_host_sds_ring;
|
|||
struct qlcnic_host_tx_ring;
|
||||
struct qlcnic_hardware_context;
|
||||
struct qlcnic_adapter;
|
||||
struct qlcnic_fw_dump;
|
||||
|
||||
int qlcnic_82xx_hw_read_wx_2M(struct qlcnic_adapter *adapter, ulong, int *);
|
||||
int qlcnic_82xx_hw_write_wx_2M(struct qlcnic_adapter *, ulong, u32);
|
||||
|
@ -213,4 +214,11 @@ int qlcnic_82xx_shutdown(struct pci_dev *);
|
|||
int qlcnic_82xx_resume(struct qlcnic_adapter *);
|
||||
void qlcnic_clr_all_drv_state(struct qlcnic_adapter *adapter, u8 failed);
|
||||
void qlcnic_fw_poll_work(struct work_struct *work);
|
||||
|
||||
u32 qlcnic_82xx_get_saved_state(void *, u32);
|
||||
void qlcnic_82xx_set_saved_state(void *, u32, u32);
|
||||
void qlcnic_82xx_cache_tmpl_hdr_values(struct qlcnic_fw_dump *);
|
||||
u32 qlcnic_82xx_get_cap_size(void *, int);
|
||||
void qlcnic_82xx_set_sys_info(void *, int, u32);
|
||||
void qlcnic_82xx_store_cap_mask(void *, u32);
|
||||
#endif /* __QLCNIC_HW_H_ */
|
||||
|
|
|
@ -90,7 +90,6 @@ static void qlcnic_82xx_io_resume(struct pci_dev *);
|
|||
static void qlcnic_82xx_set_mac_filter_count(struct qlcnic_adapter *);
|
||||
static pci_ers_result_t qlcnic_82xx_io_error_detected(struct pci_dev *,
|
||||
pci_channel_state_t);
|
||||
|
||||
static u32 qlcnic_vlan_tx_check(struct qlcnic_adapter *adapter)
|
||||
{
|
||||
struct qlcnic_hardware_context *ahw = adapter->ahw;
|
||||
|
@ -561,6 +560,12 @@ static struct qlcnic_hardware_ops qlcnic_hw_ops = {
|
|||
.disable_sds_intr = qlcnic_82xx_disable_sds_intr,
|
||||
.enable_tx_intr = qlcnic_82xx_enable_tx_intr,
|
||||
.disable_tx_intr = qlcnic_82xx_disable_tx_intr,
|
||||
.get_saved_state = qlcnic_82xx_get_saved_state,
|
||||
.set_saved_state = qlcnic_82xx_set_saved_state,
|
||||
.cache_tmpl_hdr_values = qlcnic_82xx_cache_tmpl_hdr_values,
|
||||
.get_cap_size = qlcnic_82xx_get_cap_size,
|
||||
.set_sys_info = qlcnic_82xx_set_sys_info,
|
||||
.store_cap_mask = qlcnic_82xx_store_cap_mask,
|
||||
};
|
||||
|
||||
static int qlcnic_check_multi_tx_capability(struct qlcnic_adapter *adapter)
|
||||
|
@ -2445,8 +2450,8 @@ qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||
if (err) {
|
||||
switch (err) {
|
||||
case -ENOTRECOVERABLE:
|
||||
dev_err(&pdev->dev, "Adapter initialization failed due to a faulty hardware. Please reboot\n");
|
||||
dev_err(&pdev->dev, "If reboot doesn't help, please replace the adapter with new one and return the faulty adapter for repair\n");
|
||||
dev_err(&pdev->dev, "Adapter initialization failed due to a faulty hardware\n");
|
||||
dev_err(&pdev->dev, "Please replace the adapter with new one and return the faulty adapter for repair\n");
|
||||
goto err_out_free_hw;
|
||||
case -ENOMEM:
|
||||
dev_err(&pdev->dev, "Adapter initialization failed. Please reboot\n");
|
||||
|
|
|
@ -211,6 +211,107 @@ enum qlcnic_minidump_opcode {
|
|||
QLCNIC_DUMP_RDEND = 255
|
||||
};
|
||||
|
||||
inline u32 qlcnic_82xx_get_saved_state(void *t_hdr, u32 index)
|
||||
{
|
||||
struct qlcnic_82xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
return hdr->saved_state[index];
|
||||
}
|
||||
|
||||
inline void qlcnic_82xx_set_saved_state(void *t_hdr, u32 index,
|
||||
u32 value)
|
||||
{
|
||||
struct qlcnic_82xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
hdr->saved_state[index] = value;
|
||||
}
|
||||
|
||||
void qlcnic_82xx_cache_tmpl_hdr_values(struct qlcnic_fw_dump *fw_dump)
|
||||
{
|
||||
struct qlcnic_82xx_dump_template_hdr *hdr;
|
||||
|
||||
hdr = fw_dump->tmpl_hdr;
|
||||
fw_dump->tmpl_hdr_size = hdr->size;
|
||||
fw_dump->version = hdr->version;
|
||||
fw_dump->num_entries = hdr->num_entries;
|
||||
fw_dump->offset = hdr->offset;
|
||||
|
||||
hdr->drv_cap_mask = hdr->cap_mask;
|
||||
fw_dump->cap_mask = hdr->cap_mask;
|
||||
}
|
||||
|
||||
inline u32 qlcnic_82xx_get_cap_size(void *t_hdr, int index)
|
||||
{
|
||||
struct qlcnic_82xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
return hdr->cap_sizes[index];
|
||||
}
|
||||
|
||||
void qlcnic_82xx_set_sys_info(void *t_hdr, int idx, u32 value)
|
||||
{
|
||||
struct qlcnic_82xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
hdr->sys_info[idx] = value;
|
||||
}
|
||||
|
||||
void qlcnic_82xx_store_cap_mask(void *tmpl_hdr, u32 mask)
|
||||
{
|
||||
struct qlcnic_82xx_dump_template_hdr *hdr = tmpl_hdr;
|
||||
|
||||
hdr->drv_cap_mask = mask;
|
||||
}
|
||||
|
||||
inline u32 qlcnic_83xx_get_saved_state(void *t_hdr, u32 index)
|
||||
{
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
return hdr->saved_state[index];
|
||||
}
|
||||
|
||||
inline void qlcnic_83xx_set_saved_state(void *t_hdr, u32 index,
|
||||
u32 value)
|
||||
{
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
hdr->saved_state[index] = value;
|
||||
}
|
||||
|
||||
void qlcnic_83xx_cache_tmpl_hdr_values(struct qlcnic_fw_dump *fw_dump)
|
||||
{
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr;
|
||||
|
||||
hdr = fw_dump->tmpl_hdr;
|
||||
fw_dump->tmpl_hdr_size = hdr->size;
|
||||
fw_dump->version = hdr->version;
|
||||
fw_dump->num_entries = hdr->num_entries;
|
||||
fw_dump->offset = hdr->offset;
|
||||
|
||||
hdr->drv_cap_mask = hdr->cap_mask;
|
||||
fw_dump->cap_mask = hdr->cap_mask;
|
||||
}
|
||||
|
||||
inline u32 qlcnic_83xx_get_cap_size(void *t_hdr, int index)
|
||||
{
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
return hdr->cap_sizes[index];
|
||||
}
|
||||
|
||||
void qlcnic_83xx_set_sys_info(void *t_hdr, int idx, u32 value)
|
||||
{
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr = t_hdr;
|
||||
|
||||
hdr->sys_info[idx] = value;
|
||||
}
|
||||
|
||||
void qlcnic_83xx_store_cap_mask(void *tmpl_hdr, u32 mask)
|
||||
{
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr;
|
||||
|
||||
hdr = tmpl_hdr;
|
||||
hdr->drv_cap_mask = mask;
|
||||
}
|
||||
|
||||
struct qlcnic_dump_operations {
|
||||
enum qlcnic_minidump_opcode opcode;
|
||||
u32 (*handler)(struct qlcnic_adapter *, struct qlcnic_dump_entry *,
|
||||
|
@ -238,11 +339,11 @@ static u32 qlcnic_dump_crb(struct qlcnic_adapter *adapter,
|
|||
static u32 qlcnic_dump_ctrl(struct qlcnic_adapter *adapter,
|
||||
struct qlcnic_dump_entry *entry, __le32 *buffer)
|
||||
{
|
||||
int i, k, timeout = 0;
|
||||
u32 addr, data;
|
||||
u8 no_ops;
|
||||
void *hdr = adapter->ahw->fw_dump.tmpl_hdr;
|
||||
struct __ctrl *ctr = &entry->region.ctrl;
|
||||
struct qlcnic_dump_template_hdr *t_hdr = adapter->ahw->fw_dump.tmpl_hdr;
|
||||
int i, k, timeout = 0;
|
||||
u32 addr, data, temp;
|
||||
u8 no_ops;
|
||||
|
||||
addr = ctr->addr;
|
||||
no_ops = ctr->no_ops;
|
||||
|
@ -285,29 +386,42 @@ static u32 qlcnic_dump_ctrl(struct qlcnic_adapter *adapter,
|
|||
}
|
||||
break;
|
||||
case QLCNIC_DUMP_RD_SAVE:
|
||||
if (ctr->index_a)
|
||||
addr = t_hdr->saved_state[ctr->index_a];
|
||||
temp = ctr->index_a;
|
||||
if (temp)
|
||||
addr = qlcnic_get_saved_state(adapter,
|
||||
hdr,
|
||||
temp);
|
||||
data = qlcnic_ind_rd(adapter, addr);
|
||||
t_hdr->saved_state[ctr->index_v] = data;
|
||||
qlcnic_set_saved_state(adapter, hdr,
|
||||
ctr->index_v, data);
|
||||
break;
|
||||
case QLCNIC_DUMP_WRT_SAVED:
|
||||
if (ctr->index_v)
|
||||
data = t_hdr->saved_state[ctr->index_v];
|
||||
temp = ctr->index_v;
|
||||
if (temp)
|
||||
data = qlcnic_get_saved_state(adapter,
|
||||
hdr,
|
||||
temp);
|
||||
else
|
||||
data = ctr->val1;
|
||||
if (ctr->index_a)
|
||||
addr = t_hdr->saved_state[ctr->index_a];
|
||||
|
||||
temp = ctr->index_a;
|
||||
if (temp)
|
||||
addr = qlcnic_get_saved_state(adapter,
|
||||
hdr,
|
||||
temp);
|
||||
qlcnic_ind_wr(adapter, addr, data);
|
||||
break;
|
||||
case QLCNIC_DUMP_MOD_SAVE_ST:
|
||||
data = t_hdr->saved_state[ctr->index_v];
|
||||
data = qlcnic_get_saved_state(adapter, hdr,
|
||||
ctr->index_v);
|
||||
data <<= ctr->shl_val;
|
||||
data >>= ctr->shr_val;
|
||||
if (ctr->val2)
|
||||
data &= ctr->val2;
|
||||
data |= ctr->val3;
|
||||
data += ctr->val1;
|
||||
t_hdr->saved_state[ctr->index_v] = data;
|
||||
qlcnic_set_saved_state(adapter, hdr,
|
||||
ctr->index_v, data);
|
||||
break;
|
||||
default:
|
||||
dev_info(&adapter->pdev->dev,
|
||||
|
@ -544,7 +658,7 @@ out:
|
|||
static int qlcnic_start_pex_dma(struct qlcnic_adapter *adapter,
|
||||
struct __mem *mem)
|
||||
{
|
||||
struct qlcnic_dump_template_hdr *tmpl_hdr;
|
||||
struct qlcnic_83xx_dump_template_hdr *tmpl_hdr;
|
||||
struct device *dev = &adapter->pdev->dev;
|
||||
u32 dma_no, dma_base_addr, temp_addr;
|
||||
int i, ret, dma_sts;
|
||||
|
@ -596,7 +710,7 @@ static u32 qlcnic_read_memory_pexdma(struct qlcnic_adapter *adapter,
|
|||
struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
|
||||
u32 temp, dma_base_addr, size = 0, read_size = 0;
|
||||
struct qlcnic_pex_dma_descriptor *dma_descr;
|
||||
struct qlcnic_dump_template_hdr *tmpl_hdr;
|
||||
struct qlcnic_83xx_dump_template_hdr *tmpl_hdr;
|
||||
struct device *dev = &adapter->pdev->dev;
|
||||
dma_addr_t dma_phys_addr;
|
||||
void *dma_buffer;
|
||||
|
@ -938,8 +1052,8 @@ static int
|
|||
qlcnic_fw_flash_get_minidump_temp_size(struct qlcnic_adapter *adapter,
|
||||
struct qlcnic_cmd_args *cmd)
|
||||
{
|
||||
struct qlcnic_dump_template_hdr tmp_hdr;
|
||||
u32 size = sizeof(struct qlcnic_dump_template_hdr) / sizeof(u32);
|
||||
struct qlcnic_83xx_dump_template_hdr tmp_hdr;
|
||||
u32 size = sizeof(tmp_hdr) / sizeof(u32);
|
||||
int ret = 0;
|
||||
|
||||
if (qlcnic_82xx_check(adapter))
|
||||
|
@ -1027,17 +1141,19 @@ free_mem:
|
|||
return err;
|
||||
}
|
||||
|
||||
#define QLCNIC_TEMPLATE_VERSION (0x20001)
|
||||
|
||||
int qlcnic_fw_cmd_get_minidump_temp(struct qlcnic_adapter *adapter)
|
||||
{
|
||||
int err;
|
||||
u32 temp_size = 0;
|
||||
u32 version, csum, *tmp_buf;
|
||||
struct qlcnic_hardware_context *ahw;
|
||||
struct qlcnic_dump_template_hdr *tmpl_hdr;
|
||||
struct qlcnic_fw_dump *fw_dump;
|
||||
u32 version, csum, *tmp_buf;
|
||||
u8 use_flash_temp = 0;
|
||||
u32 temp_size = 0;
|
||||
int err;
|
||||
|
||||
ahw = adapter->ahw;
|
||||
|
||||
fw_dump = &ahw->fw_dump;
|
||||
err = qlcnic_fw_get_minidump_temp_size(adapter, &version, &temp_size,
|
||||
&use_flash_temp);
|
||||
if (err) {
|
||||
|
@ -1046,11 +1162,11 @@ int qlcnic_fw_cmd_get_minidump_temp(struct qlcnic_adapter *adapter)
|
|||
return -EIO;
|
||||
}
|
||||
|
||||
ahw->fw_dump.tmpl_hdr = vzalloc(temp_size);
|
||||
if (!ahw->fw_dump.tmpl_hdr)
|
||||
fw_dump->tmpl_hdr = vzalloc(temp_size);
|
||||
if (!fw_dump->tmpl_hdr)
|
||||
return -ENOMEM;
|
||||
|
||||
tmp_buf = (u32 *)ahw->fw_dump.tmpl_hdr;
|
||||
tmp_buf = (u32 *)fw_dump->tmpl_hdr;
|
||||
if (use_flash_temp)
|
||||
goto flash_temp;
|
||||
|
||||
|
@ -1065,8 +1181,8 @@ flash_temp:
|
|||
dev_err(&adapter->pdev->dev,
|
||||
"Failed to get minidump template header %d\n",
|
||||
err);
|
||||
vfree(ahw->fw_dump.tmpl_hdr);
|
||||
ahw->fw_dump.tmpl_hdr = NULL;
|
||||
vfree(fw_dump->tmpl_hdr);
|
||||
fw_dump->tmpl_hdr = NULL;
|
||||
return -EIO;
|
||||
}
|
||||
}
|
||||
|
@ -1076,21 +1192,22 @@ flash_temp:
|
|||
if (csum) {
|
||||
dev_err(&adapter->pdev->dev,
|
||||
"Template header checksum validation failed\n");
|
||||
vfree(ahw->fw_dump.tmpl_hdr);
|
||||
ahw->fw_dump.tmpl_hdr = NULL;
|
||||
vfree(fw_dump->tmpl_hdr);
|
||||
fw_dump->tmpl_hdr = NULL;
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
tmpl_hdr = ahw->fw_dump.tmpl_hdr;
|
||||
tmpl_hdr->drv_cap_mask = tmpl_hdr->cap_mask;
|
||||
qlcnic_cache_tmpl_hdr_values(adapter, fw_dump);
|
||||
|
||||
dev_info(&adapter->pdev->dev,
|
||||
"Default minidump capture mask 0x%x\n",
|
||||
tmpl_hdr->cap_mask);
|
||||
fw_dump->cap_mask);
|
||||
|
||||
if ((tmpl_hdr->version & 0xfffff) >= 0x20001)
|
||||
ahw->fw_dump.use_pex_dma = true;
|
||||
if (qlcnic_83xx_check(adapter) &&
|
||||
(fw_dump->version & 0xfffff) >= QLCNIC_TEMPLATE_VERSION)
|
||||
fw_dump->use_pex_dma = true;
|
||||
else
|
||||
ahw->fw_dump.use_pex_dma = false;
|
||||
fw_dump->use_pex_dma = false;
|
||||
|
||||
qlcnic_enable_fw_dump_state(adapter);
|
||||
|
||||
|
@ -1099,21 +1216,22 @@ flash_temp:
|
|||
|
||||
int qlcnic_dump_fw(struct qlcnic_adapter *adapter)
|
||||
{
|
||||
__le32 *buffer;
|
||||
u32 ocm_window;
|
||||
char mesg[64];
|
||||
char *msg[] = {mesg, NULL};
|
||||
int i, k, ops_cnt, ops_index, dump_size = 0;
|
||||
u32 entry_offset, dump, no_entries, buf_offset = 0;
|
||||
struct qlcnic_dump_entry *entry;
|
||||
struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
|
||||
struct qlcnic_dump_template_hdr *tmpl_hdr = fw_dump->tmpl_hdr;
|
||||
static const struct qlcnic_dump_operations *fw_dump_ops;
|
||||
struct qlcnic_83xx_dump_template_hdr *hdr_83xx;
|
||||
u32 entry_offset, dump, no_entries, buf_offset = 0;
|
||||
int i, k, ops_cnt, ops_index, dump_size = 0;
|
||||
struct device *dev = &adapter->pdev->dev;
|
||||
struct qlcnic_hardware_context *ahw;
|
||||
void *temp_buffer;
|
||||
struct qlcnic_dump_entry *entry;
|
||||
void *temp_buffer, *tmpl_hdr;
|
||||
u32 ocm_window;
|
||||
__le32 *buffer;
|
||||
char mesg[64];
|
||||
char *msg[] = {mesg, NULL};
|
||||
|
||||
ahw = adapter->ahw;
|
||||
tmpl_hdr = fw_dump->tmpl_hdr;
|
||||
|
||||
/* Return if we don't have firmware dump template header */
|
||||
if (!tmpl_hdr)
|
||||
|
@ -1133,8 +1251,9 @@ int qlcnic_dump_fw(struct qlcnic_adapter *adapter)
|
|||
netif_info(adapter->ahw, drv, adapter->netdev, "Take FW dump\n");
|
||||
/* Calculate the size for dump data area only */
|
||||
for (i = 2, k = 1; (i & QLCNIC_DUMP_MASK_MAX); i <<= 1, k++)
|
||||
if (i & tmpl_hdr->drv_cap_mask)
|
||||
dump_size += tmpl_hdr->cap_sizes[k];
|
||||
if (i & fw_dump->cap_mask)
|
||||
dump_size += qlcnic_get_cap_size(adapter, tmpl_hdr, k);
|
||||
|
||||
if (!dump_size)
|
||||
return -EIO;
|
||||
|
||||
|
@ -1144,10 +1263,10 @@ int qlcnic_dump_fw(struct qlcnic_adapter *adapter)
|
|||
|
||||
buffer = fw_dump->data;
|
||||
fw_dump->size = dump_size;
|
||||
no_entries = tmpl_hdr->num_entries;
|
||||
entry_offset = tmpl_hdr->offset;
|
||||
tmpl_hdr->sys_info[0] = QLCNIC_DRIVER_VERSION;
|
||||
tmpl_hdr->sys_info[1] = adapter->fw_version;
|
||||
no_entries = fw_dump->num_entries;
|
||||
entry_offset = fw_dump->offset;
|
||||
qlcnic_set_sys_info(adapter, tmpl_hdr, 0, QLCNIC_DRIVER_VERSION);
|
||||
qlcnic_set_sys_info(adapter, tmpl_hdr, 1, adapter->fw_version);
|
||||
|
||||
if (fw_dump->use_pex_dma) {
|
||||
temp_buffer = dma_alloc_coherent(dev, QLC_PEX_DMA_READ_SIZE,
|
||||
|
@ -1163,16 +1282,17 @@ int qlcnic_dump_fw(struct qlcnic_adapter *adapter)
|
|||
ops_cnt = ARRAY_SIZE(qlcnic_fw_dump_ops);
|
||||
fw_dump_ops = qlcnic_fw_dump_ops;
|
||||
} else {
|
||||
hdr_83xx = tmpl_hdr;
|
||||
ops_cnt = ARRAY_SIZE(qlcnic_83xx_fw_dump_ops);
|
||||
fw_dump_ops = qlcnic_83xx_fw_dump_ops;
|
||||
ocm_window = tmpl_hdr->ocm_wnd_reg[adapter->ahw->pci_func];
|
||||
tmpl_hdr->saved_state[QLC_83XX_OCM_INDEX] = ocm_window;
|
||||
tmpl_hdr->saved_state[QLC_83XX_PCI_INDEX] = ahw->pci_func;
|
||||
ocm_window = hdr_83xx->ocm_wnd_reg[ahw->pci_func];
|
||||
hdr_83xx->saved_state[QLC_83XX_OCM_INDEX] = ocm_window;
|
||||
hdr_83xx->saved_state[QLC_83XX_PCI_INDEX] = ahw->pci_func;
|
||||
}
|
||||
|
||||
for (i = 0; i < no_entries; i++) {
|
||||
entry = (void *)tmpl_hdr + entry_offset;
|
||||
if (!(entry->hdr.mask & tmpl_hdr->drv_cap_mask)) {
|
||||
entry = tmpl_hdr + entry_offset;
|
||||
if (!(entry->hdr.mask & fw_dump->cap_mask)) {
|
||||
entry->hdr.flags |= QLCNIC_DUMP_SKIP;
|
||||
entry_offset += entry->hdr.offset;
|
||||
continue;
|
||||
|
@ -1209,8 +1329,9 @@ int qlcnic_dump_fw(struct qlcnic_adapter *adapter)
|
|||
|
||||
fw_dump->clr = 1;
|
||||
snprintf(mesg, sizeof(mesg), "FW_DUMP=%s", adapter->netdev->name);
|
||||
dev_info(dev, "%s: Dump data %d bytes captured, template header size %d bytes\n",
|
||||
adapter->netdev->name, fw_dump->size, tmpl_hdr->size);
|
||||
netdev_info(adapter->netdev,
|
||||
"Dump data %d bytes captured, template header size %d bytes\n",
|
||||
fw_dump->size, fw_dump->tmpl_hdr_size);
|
||||
/* Send a udev event to notify availability of FW dump */
|
||||
kobject_uevent_env(&dev->kobj, KOBJ_CHANGE, msg);
|
||||
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
#define QLC_MAC_STAR_DEL 7
|
||||
#define QLC_VF_FLOOD_BIT BIT_16
|
||||
#define QLC_FLOOD_MODE 0x5
|
||||
#define QLC_SRIOV_ALLOW_VLAN0 BIT_19
|
||||
|
||||
static int qlcnic_sriov_pf_get_vport_handle(struct qlcnic_adapter *, u8);
|
||||
|
||||
|
@ -337,8 +338,11 @@ static int qlcnic_sriov_pf_cfg_vlan_filtering(struct qlcnic_adapter *adapter,
|
|||
return err;
|
||||
|
||||
cmd.req.arg[1] = 0x4;
|
||||
if (enable)
|
||||
if (enable) {
|
||||
cmd.req.arg[1] |= BIT_16;
|
||||
if (qlcnic_84xx_check(adapter))
|
||||
cmd.req.arg[1] |= QLC_SRIOV_ALLOW_VLAN0;
|
||||
}
|
||||
|
||||
err = qlcnic_issue_cmd(adapter, &cmd);
|
||||
if (err)
|
||||
|
|
|
@ -350,33 +350,15 @@ static ssize_t qlcnic_sysfs_write_mem(struct file *filp, struct kobject *kobj,
|
|||
return size;
|
||||
}
|
||||
|
||||
static u32 qlcnic_get_pci_func_count(struct qlcnic_adapter *adapter)
|
||||
{
|
||||
struct qlcnic_hardware_context *ahw = adapter->ahw;
|
||||
u32 count = 0;
|
||||
|
||||
if (!(adapter->flags & QLCNIC_ESWITCH_ENABLED))
|
||||
return ahw->total_nic_func;
|
||||
|
||||
if (ahw->total_pci_func <= QLC_DEFAULT_VNIC_COUNT)
|
||||
count = QLC_DEFAULT_VNIC_COUNT;
|
||||
else
|
||||
count = ahw->max_vnic_func;
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
int qlcnic_is_valid_nic_func(struct qlcnic_adapter *adapter, u8 pci_func)
|
||||
{
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < pci_func_count; i++) {
|
||||
for (i = 0; i < adapter->ahw->max_vnic_func; i++) {
|
||||
if (adapter->npars[i].pci_func == pci_func)
|
||||
return i;
|
||||
}
|
||||
|
||||
return -1;
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
static int validate_pm_config(struct qlcnic_adapter *adapter,
|
||||
|
@ -464,23 +446,21 @@ static ssize_t qlcnic_sysfs_read_pm_config(struct file *filp,
|
|||
{
|
||||
struct device *dev = container_of(kobj, struct device, kobj);
|
||||
struct qlcnic_adapter *adapter = dev_get_drvdata(dev);
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
struct qlcnic_pm_func_cfg *pm_cfg;
|
||||
int i, pm_cfg_size;
|
||||
u8 pci_func;
|
||||
u32 count;
|
||||
int i;
|
||||
|
||||
pm_cfg_size = pci_func_count * sizeof(*pm_cfg);
|
||||
if (size != pm_cfg_size)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
memset(buf, 0, pm_cfg_size);
|
||||
memset(buf, 0, size);
|
||||
pm_cfg = (struct qlcnic_pm_func_cfg *)buf;
|
||||
|
||||
for (i = 0; i < pci_func_count; i++) {
|
||||
count = size / sizeof(struct qlcnic_pm_func_cfg);
|
||||
for (i = 0; i < adapter->ahw->total_nic_func; i++) {
|
||||
pci_func = adapter->npars[i].pci_func;
|
||||
if (!adapter->npars[i].active)
|
||||
if (pci_func >= count) {
|
||||
dev_dbg(dev, "%s: Total nic functions[%d], App sent function count[%d]\n",
|
||||
__func__, adapter->ahw->total_nic_func, count);
|
||||
continue;
|
||||
|
||||
}
|
||||
if (!adapter->npars[i].eswitch_status)
|
||||
continue;
|
||||
|
||||
|
@ -494,7 +474,6 @@ static ssize_t qlcnic_sysfs_read_pm_config(struct file *filp,
|
|||
static int validate_esw_config(struct qlcnic_adapter *adapter,
|
||||
struct qlcnic_esw_func_cfg *esw_cfg, int count)
|
||||
{
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
struct qlcnic_hardware_context *ahw = adapter->ahw;
|
||||
int i, ret;
|
||||
u32 op_mode;
|
||||
|
@ -507,7 +486,7 @@ static int validate_esw_config(struct qlcnic_adapter *adapter,
|
|||
|
||||
for (i = 0; i < count; i++) {
|
||||
pci_func = esw_cfg[i].pci_func;
|
||||
if (pci_func >= pci_func_count)
|
||||
if (pci_func >= ahw->max_vnic_func)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
if (adapter->ahw->op_mode == QLCNIC_MGMT_FUNC)
|
||||
|
@ -642,23 +621,21 @@ static ssize_t qlcnic_sysfs_read_esw_config(struct file *file,
|
|||
{
|
||||
struct device *dev = container_of(kobj, struct device, kobj);
|
||||
struct qlcnic_adapter *adapter = dev_get_drvdata(dev);
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
struct qlcnic_esw_func_cfg *esw_cfg;
|
||||
size_t esw_cfg_size;
|
||||
u8 i, pci_func;
|
||||
u8 pci_func;
|
||||
u32 count;
|
||||
int i;
|
||||
|
||||
esw_cfg_size = pci_func_count * sizeof(*esw_cfg);
|
||||
if (size != esw_cfg_size)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
memset(buf, 0, esw_cfg_size);
|
||||
memset(buf, 0, size);
|
||||
esw_cfg = (struct qlcnic_esw_func_cfg *)buf;
|
||||
|
||||
for (i = 0; i < pci_func_count; i++) {
|
||||
count = size / sizeof(struct qlcnic_esw_func_cfg);
|
||||
for (i = 0; i < adapter->ahw->total_nic_func; i++) {
|
||||
pci_func = adapter->npars[i].pci_func;
|
||||
if (!adapter->npars[i].active)
|
||||
if (pci_func >= count) {
|
||||
dev_dbg(dev, "%s: Total nic functions[%d], App sent function count[%d]\n",
|
||||
__func__, adapter->ahw->total_nic_func, count);
|
||||
continue;
|
||||
|
||||
}
|
||||
if (!adapter->npars[i].eswitch_status)
|
||||
continue;
|
||||
|
||||
|
@ -741,23 +718,24 @@ static ssize_t qlcnic_sysfs_read_npar_config(struct file *file,
|
|||
{
|
||||
struct device *dev = container_of(kobj, struct device, kobj);
|
||||
struct qlcnic_adapter *adapter = dev_get_drvdata(dev);
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
struct qlcnic_npar_func_cfg *np_cfg;
|
||||
struct qlcnic_info nic_info;
|
||||
size_t np_cfg_size;
|
||||
int i, ret;
|
||||
|
||||
np_cfg_size = pci_func_count * sizeof(*np_cfg);
|
||||
if (size != np_cfg_size)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
u32 count;
|
||||
|
||||
memset(&nic_info, 0, sizeof(struct qlcnic_info));
|
||||
memset(buf, 0, np_cfg_size);
|
||||
memset(buf, 0, size);
|
||||
np_cfg = (struct qlcnic_npar_func_cfg *)buf;
|
||||
|
||||
for (i = 0; i < pci_func_count; i++) {
|
||||
count = size / sizeof(struct qlcnic_npar_func_cfg);
|
||||
for (i = 0; i < adapter->ahw->total_nic_func; i++) {
|
||||
if (qlcnic_is_valid_nic_func(adapter, i) < 0)
|
||||
continue;
|
||||
if (adapter->npars[i].pci_func >= count) {
|
||||
dev_dbg(dev, "%s: Total nic functions[%d], App sent function count[%d]\n",
|
||||
__func__, adapter->ahw->total_nic_func, count);
|
||||
continue;
|
||||
}
|
||||
ret = qlcnic_get_nic_info(adapter, &nic_info, i);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
@ -783,7 +761,6 @@ static ssize_t qlcnic_sysfs_get_port_stats(struct file *file,
|
|||
{
|
||||
struct device *dev = container_of(kobj, struct device, kobj);
|
||||
struct qlcnic_adapter *adapter = dev_get_drvdata(dev);
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
struct qlcnic_esw_statistics port_stats;
|
||||
int ret;
|
||||
|
||||
|
@ -793,7 +770,7 @@ static ssize_t qlcnic_sysfs_get_port_stats(struct file *file,
|
|||
if (size != sizeof(struct qlcnic_esw_statistics))
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
if (offset >= pci_func_count)
|
||||
if (offset >= adapter->ahw->max_vnic_func)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
memset(&port_stats, 0, size);
|
||||
|
@ -884,13 +861,12 @@ static ssize_t qlcnic_sysfs_clear_port_stats(struct file *file,
|
|||
|
||||
struct device *dev = container_of(kobj, struct device, kobj);
|
||||
struct qlcnic_adapter *adapter = dev_get_drvdata(dev);
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
int ret;
|
||||
|
||||
if (qlcnic_83xx_check(adapter))
|
||||
return QLC_STATUS_UNSUPPORTED_CMD;
|
||||
|
||||
if (offset >= pci_func_count)
|
||||
if (offset >= adapter->ahw->max_vnic_func)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
ret = qlcnic_clear_esw_stats(adapter, QLCNIC_STATS_PORT, offset,
|
||||
|
@ -914,17 +890,12 @@ static ssize_t qlcnic_sysfs_read_pci_config(struct file *file,
|
|||
{
|
||||
struct device *dev = container_of(kobj, struct device, kobj);
|
||||
struct qlcnic_adapter *adapter = dev_get_drvdata(dev);
|
||||
u32 pci_func_count = qlcnic_get_pci_func_count(adapter);
|
||||
struct qlcnic_pci_func_cfg *pci_cfg;
|
||||
struct qlcnic_pci_info *pci_info;
|
||||
size_t pci_cfg_sz;
|
||||
int i, ret;
|
||||
u32 count;
|
||||
|
||||
pci_cfg_sz = pci_func_count * sizeof(*pci_cfg);
|
||||
if (size != pci_cfg_sz)
|
||||
return QL_STATUS_INVALID_PARAM;
|
||||
|
||||
pci_info = kcalloc(pci_func_count, sizeof(*pci_info), GFP_KERNEL);
|
||||
pci_info = kcalloc(size, sizeof(*pci_info), GFP_KERNEL);
|
||||
if (!pci_info)
|
||||
return -ENOMEM;
|
||||
|
||||
|
@ -935,7 +906,8 @@ static ssize_t qlcnic_sysfs_read_pci_config(struct file *file,
|
|||
}
|
||||
|
||||
pci_cfg = (struct qlcnic_pci_func_cfg *)buf;
|
||||
for (i = 0; i < pci_func_count; i++) {
|
||||
count = size / sizeof(struct qlcnic_pci_func_cfg);
|
||||
for (i = 0; i < count; i++) {
|
||||
pci_cfg[i].pci_func = pci_info[i].id;
|
||||
pci_cfg[i].func_type = pci_info[i].type;
|
||||
pci_cfg[i].func_state = 0;
|
||||
|
|
Загрузка…
Ссылка в новой задаче