Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 340417
b: refs/heads/master
c: f25b119
h: refs/heads/master
i:
  340415: a5e7aac
v: v3
  • Loading branch information
Padmanabh Ratnakar authored and David S. Miller committed Oct 22, 2012
1 parent 374f3aa commit 06b1fa6
Show file tree
Hide file tree
Showing 6 changed files with 174 additions and 3 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: a85e998681624ac85d423f34e833f95dffdd2a3c
refs/heads/master: f25b119c6c19bbe70a27f7e439ef26ed8acd42ea
1 change: 1 addition & 0 deletions trunk/drivers/net/ethernet/emulex/benet/be.h
Original file line number Diff line number Diff line change
Expand Up @@ -390,6 +390,7 @@ struct be_adapter {

struct delayed_work func_recovery_work;
u32 flags;
u32 cmd_privileges;
/* Ethtool knobs and info */
char fw_ver[FW_VER_LEN];
int if_handle; /* Used to configure filtering */
Expand Down
105 changes: 105 additions & 0 deletions trunk/drivers/net/ethernet/emulex/benet/be_cmds.c
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,55 @@
#include "be.h"
#include "be_cmds.h"

static struct be_cmd_priv_map cmd_priv_map[] = {
{
OPCODE_ETH_ACPI_WOL_MAGIC_CONFIG,
CMD_SUBSYSTEM_ETH,
BE_PRIV_LNKMGMT | BE_PRIV_VHADM |
BE_PRIV_DEVCFG | BE_PRIV_DEVSEC
},
{
OPCODE_COMMON_GET_FLOW_CONTROL,
CMD_SUBSYSTEM_COMMON,
BE_PRIV_LNKQUERY | BE_PRIV_VHADM |
BE_PRIV_DEVCFG | BE_PRIV_DEVSEC
},
{
OPCODE_COMMON_SET_FLOW_CONTROL,
CMD_SUBSYSTEM_COMMON,
BE_PRIV_LNKMGMT | BE_PRIV_VHADM |
BE_PRIV_DEVCFG | BE_PRIV_DEVSEC
},
{
OPCODE_ETH_GET_PPORT_STATS,
CMD_SUBSYSTEM_ETH,
BE_PRIV_LNKMGMT | BE_PRIV_VHADM |
BE_PRIV_DEVCFG | BE_PRIV_DEVSEC
},
{
OPCODE_COMMON_GET_PHY_DETAILS,
CMD_SUBSYSTEM_COMMON,
BE_PRIV_LNKMGMT | BE_PRIV_VHADM |
BE_PRIV_DEVCFG | BE_PRIV_DEVSEC
}
};

static bool be_cmd_allowed(struct be_adapter *adapter, u8 opcode,
u8 subsystem)
{
int i;
int num_entries = sizeof(cmd_priv_map)/sizeof(struct be_cmd_priv_map);
u32 cmd_privileges = adapter->cmd_privileges;

for (i = 0; i < num_entries; i++)
if (opcode == cmd_priv_map[i].opcode &&
subsystem == cmd_priv_map[i].subsystem)
if (!(cmd_privileges & cmd_priv_map[i].priv_mask))
return false;

return true;
}

static inline void *embedded_payload(struct be_mcc_wrb *wrb)
{
return wrb->payload.embedded_payload;
Expand Down Expand Up @@ -1332,6 +1381,10 @@ int lancer_cmd_get_pport_stats(struct be_adapter *adapter,
struct lancer_cmd_req_pport_stats *req;
int status = 0;

if (!be_cmd_allowed(adapter, OPCODE_ETH_GET_PPORT_STATS,
CMD_SUBSYSTEM_ETH))
return -EPERM;

spin_lock_bh(&adapter->mcc_lock);

wrb = wrb_from_mccq(adapter);
Expand Down Expand Up @@ -1711,6 +1764,10 @@ int be_cmd_set_flow_control(struct be_adapter *adapter, u32 tx_fc, u32 rx_fc)
struct be_cmd_req_set_flow_control *req;
int status;

if (!be_cmd_allowed(adapter, OPCODE_COMMON_SET_FLOW_CONTROL,
CMD_SUBSYSTEM_COMMON))
return -EPERM;

spin_lock_bh(&adapter->mcc_lock);

wrb = wrb_from_mccq(adapter);
Expand Down Expand Up @@ -1740,6 +1797,10 @@ int be_cmd_get_flow_control(struct be_adapter *adapter, u32 *tx_fc, u32 *rx_fc)
struct be_cmd_req_get_flow_control *req;
int status;

if (!be_cmd_allowed(adapter, OPCODE_COMMON_GET_FLOW_CONTROL,
CMD_SUBSYSTEM_COMMON))
return -EPERM;

spin_lock_bh(&adapter->mcc_lock);

wrb = wrb_from_mccq(adapter);
Expand Down Expand Up @@ -2306,6 +2367,10 @@ int be_cmd_get_phy_info(struct be_adapter *adapter)
struct be_dma_mem cmd;
int status;

if (!be_cmd_allowed(adapter, OPCODE_COMMON_GET_PHY_DETAILS,
CMD_SUBSYSTEM_COMMON))
return -EPERM;

spin_lock_bh(&adapter->mcc_lock);

wrb = wrb_from_mccq(adapter);
Expand Down Expand Up @@ -2465,6 +2530,42 @@ int be_cmd_req_native_mode(struct be_adapter *adapter)
return status;
}

/* Get privilege(s) for a function */
int be_cmd_get_fn_privileges(struct be_adapter *adapter, u32 *privilege,
u32 domain)
{
struct be_mcc_wrb *wrb;
struct be_cmd_req_get_fn_privileges *req;
int status;

spin_lock_bh(&adapter->mcc_lock);

wrb = wrb_from_mccq(adapter);
if (!wrb) {
status = -EBUSY;
goto err;
}

req = embedded_payload(wrb);

be_wrb_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON,
OPCODE_COMMON_GET_FN_PRIVILEGES, sizeof(*req),
wrb, NULL);

req->hdr.domain = domain;

status = be_mcc_notify_wait(adapter);
if (!status) {
struct be_cmd_resp_get_fn_privileges *resp =
embedded_payload(wrb);
*privilege = le32_to_cpu(resp->privilege_mask);
}

err:
spin_unlock_bh(&adapter->mcc_lock);
return status;
}

/* Uses synchronous MCCQ */
int be_cmd_get_mac_from_list(struct be_adapter *adapter, u8 *mac,
bool *pmac_id_active, u32 *pmac_id, u8 domain)
Expand Down Expand Up @@ -2682,6 +2783,10 @@ int be_cmd_get_acpi_wol_cap(struct be_adapter *adapter)
int payload_len = sizeof(*req);
struct be_dma_mem cmd;

if (!be_cmd_allowed(adapter, OPCODE_ETH_ACPI_WOL_MAGIC_CONFIG,
CMD_SUBSYSTEM_ETH))
return -EPERM;

memset(&cmd, 0, sizeof(struct be_dma_mem));
cmd.size = sizeof(struct be_cmd_resp_acpi_wol_magic_config_v1);
cmd.va = pci_alloc_consistent(adapter->pdev, cmd.size,
Expand Down
43 changes: 43 additions & 0 deletions trunk/drivers/net/ethernet/emulex/benet/be_cmds.h
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,7 @@ struct be_mcc_mailbox {
#define OPCODE_COMMON_GET_PROFILE_CONFIG 164
#define OPCODE_COMMON_SET_PROFILE_CONFIG 165
#define OPCODE_COMMON_SET_HSW_CONFIG 153
#define OPCODE_COMMON_GET_FN_PRIVILEGES 170
#define OPCODE_COMMON_READ_OBJECT 171
#define OPCODE_COMMON_WRITE_OBJECT 172

Expand Down Expand Up @@ -1432,6 +1433,41 @@ struct be_cmd_resp_set_func_cap {
u8 rsvd[212];
};

/*********************** Function Privileges ***********************/
enum {
BE_PRIV_DEFAULT = 0x1,
BE_PRIV_LNKQUERY = 0x2,
BE_PRIV_LNKSTATS = 0x4,
BE_PRIV_LNKMGMT = 0x8,
BE_PRIV_LNKDIAG = 0x10,
BE_PRIV_UTILQUERY = 0x20,
BE_PRIV_FILTMGMT = 0x40,
BE_PRIV_IFACEMGMT = 0x80,
BE_PRIV_VHADM = 0x100,
BE_PRIV_DEVCFG = 0x200,
BE_PRIV_DEVSEC = 0x400
};
#define MAX_PRIVILEGES (BE_PRIV_VHADM | BE_PRIV_DEVCFG | \
BE_PRIV_DEVSEC)
#define MIN_PRIVILEGES BE_PRIV_DEFAULT

struct be_cmd_priv_map {
u8 opcode;
u8 subsystem;
u32 priv_mask;
};

struct be_cmd_req_get_fn_privileges {
struct be_cmd_req_hdr hdr;
u32 rsvd;
};

struct be_cmd_resp_get_fn_privileges {
struct be_cmd_resp_hdr hdr;
u32 privilege_mask;
};


/******************** GET/SET_MACLIST **************************/
#define BE_MAX_MAC 64
struct be_cmd_req_get_mac_list {
Expand Down Expand Up @@ -1766,6 +1802,11 @@ struct be_cmd_resp_set_profile_config {
struct be_cmd_req_hdr hdr;
};

static inline bool check_privilege(struct be_adapter *adapter, u32 flags)
{
return flags & adapter->cmd_privileges ? true : false;
}

extern int be_pci_fnum_get(struct be_adapter *adapter);
extern int be_fw_wait_ready(struct be_adapter *adapter);
extern int be_cmd_mac_addr_query(struct be_adapter *adapter, u8 *mac_addr,
Expand Down Expand Up @@ -1862,6 +1903,8 @@ extern int be_cmd_get_cntl_attributes(struct be_adapter *adapter);
extern int be_cmd_req_native_mode(struct be_adapter *adapter);
extern int be_cmd_get_reg_len(struct be_adapter *adapter, u32 *log_size);
extern void be_cmd_get_regs(struct be_adapter *adapter, u32 buf_len, void *buf);
extern int be_cmd_get_fn_privileges(struct be_adapter *adapter,
u32 *privilege, u32 domain);
extern int be_cmd_get_mac_from_list(struct be_adapter *adapter, u8 *mac,
bool *pmac_id_active, u32 *pmac_id,
u8 domain);
Expand Down
7 changes: 7 additions & 0 deletions trunk/drivers/net/ethernet/emulex/benet/be_ethtool.c
Original file line number Diff line number Diff line change
Expand Up @@ -261,6 +261,9 @@ be_get_reg_len(struct net_device *netdev)
struct be_adapter *adapter = netdev_priv(netdev);
u32 log_size = 0;

if (!check_privilege(adapter, MAX_PRIVILEGES))
return 0;

if (be_physfn(adapter)) {
if (lancer_chip(adapter))
log_size = lancer_cmd_get_file_len(adapter,
Expand Down Expand Up @@ -787,6 +790,10 @@ static int
be_get_eeprom_len(struct net_device *netdev)
{
struct be_adapter *adapter = netdev_priv(netdev);

if (!check_privilege(adapter, MAX_PRIVILEGES))
return 0;

if (lancer_chip(adapter)) {
if (be_physfn(adapter))
return lancer_cmd_get_file_len(adapter,
Expand Down
19 changes: 17 additions & 2 deletions trunk/drivers/net/ethernet/emulex/benet/be_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -2745,6 +2745,11 @@ static void be_setup_init(struct be_adapter *adapter)
adapter->be3_native = false;
adapter->promiscuous = false;
adapter->eq_next_idx = 0;

if (be_physfn(adapter))
adapter->cmd_privileges = MAX_PRIVILEGES;
else
adapter->cmd_privileges = MIN_PRIVILEGES;
}

static int be_get_mac_addr(struct be_adapter *adapter, u8 *mac, u32 if_handle,
Expand Down Expand Up @@ -2917,6 +2922,13 @@ static int be_setup(struct be_adapter *adapter)
if (status)
goto err;

be_cmd_get_fn_privileges(adapter, &adapter->cmd_privileges, 0);
/* In UMC mode FW does not return right privileges.
* Override with correct privilege equivalent to PF.
*/
if (be_is_mc(adapter))
adapter->cmd_privileges = MAX_PRIVILEGES;

en_flags = BE_IF_FLAGS_UNTAGGED | BE_IF_FLAGS_BROADCAST |
BE_IF_FLAGS_MULTICAST | BE_IF_FLAGS_PASS_L3L4_ERRORS;

Expand Down Expand Up @@ -2973,8 +2985,8 @@ static int be_setup(struct be_adapter *adapter)
dev_warn(dev, "device doesn't support SRIOV\n");
}

be_cmd_get_phy_info(adapter);
if (be_pause_supported(adapter))
status = be_cmd_get_phy_info(adapter);
if (!status && be_pause_supported(adapter))
adapter->phy.fc_autoneg = 1;

schedule_delayed_work(&adapter->work, msecs_to_jiffies(1000));
Expand Down Expand Up @@ -3711,6 +3723,9 @@ u32 be_get_fw_log_level(struct be_adapter *adapter)
u32 level = 0;
int j;

if (lancer_chip(adapter))
return 0;

memset(&extfat_cmd, 0, sizeof(struct be_dma_mem));
extfat_cmd.size = sizeof(struct be_cmd_resp_get_ext_fat_caps);
extfat_cmd.va = pci_alloc_consistent(adapter->pdev, extfat_cmd.size,
Expand Down

0 comments on commit 06b1fa6

Please sign in to comment.