linux/drivers/net/ethernet/intel/i40e/i40e_dcb_nl.c
Neerav Parikh 8279e49531 i40e: Change some messages from info to debug only
There are several error messages that have been printing when there is
no functional issue. These messages should be available at debug message
level only.

Change-ID: Id91e47bf942c483563995f30d8705fa53acd5aa3
Signed-off-by: Neerav Parikh <neerav.parikh@intel.com>
Signed-off-by: Catherine Sullivan <catherine.sullivan@intel.com>
Signed-off-by: Shannon Nelson <shannon.nelson@intel.com>
Tested-by: Andrew Bowers <andrewx.bowers@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
2015-10-15 01:58:41 -07:00

321 lines
8.5 KiB
C

/*******************************************************************************
*
* Intel Ethernet Controller XL710 Family Linux Driver
* Copyright(c) 2013 - 2014 Intel Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
* version 2, as published by the Free Software Foundation.
*
* This program is distributed in the hope it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*
* The full GNU General Public License is included in this distribution in
* the file called "COPYING".
*
* Contact Information:
* e1000-devel Mailing List <e1000-devel@lists.sourceforge.net>
* Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
*
******************************************************************************/
#ifdef CONFIG_I40E_DCB
#include "i40e.h"
#include <net/dcbnl.h>
/**
* i40e_get_pfc_delay - retrieve PFC Link Delay
* @hw: pointer to hardware struct
* @delay: holds the PFC Link delay value
*
* Returns PFC Link Delay from the PRTDCB_GENC.PFCLDA
**/
static void i40e_get_pfc_delay(struct i40e_hw *hw, u16 *delay)
{
u32 val;
val = rd32(hw, I40E_PRTDCB_GENC);
*delay = (u16)((val & I40E_PRTDCB_GENC_PFCLDA_MASK) >>
I40E_PRTDCB_GENC_PFCLDA_SHIFT);
}
/**
* i40e_dcbnl_ieee_getets - retrieve local IEEE ETS configuration
* @netdev: the corresponding netdev
* @ets: structure to hold the ETS information
*
* Returns local IEEE ETS configuration
**/
static int i40e_dcbnl_ieee_getets(struct net_device *dev,
struct ieee_ets *ets)
{
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
struct i40e_dcbx_config *dcbxcfg;
struct i40e_hw *hw = &pf->hw;
if (!(pf->dcbx_cap & DCB_CAP_DCBX_VER_IEEE))
return -EINVAL;
dcbxcfg = &hw->local_dcbx_config;
ets->willing = dcbxcfg->etscfg.willing;
ets->ets_cap = dcbxcfg->etscfg.maxtcs;
ets->cbs = dcbxcfg->etscfg.cbs;
memcpy(ets->tc_tx_bw, dcbxcfg->etscfg.tcbwtable,
sizeof(ets->tc_tx_bw));
memcpy(ets->tc_rx_bw, dcbxcfg->etscfg.tcbwtable,
sizeof(ets->tc_rx_bw));
memcpy(ets->tc_tsa, dcbxcfg->etscfg.tsatable,
sizeof(ets->tc_tsa));
memcpy(ets->prio_tc, dcbxcfg->etscfg.prioritytable,
sizeof(ets->prio_tc));
memcpy(ets->tc_reco_bw, dcbxcfg->etsrec.tcbwtable,
sizeof(ets->tc_reco_bw));
memcpy(ets->tc_reco_tsa, dcbxcfg->etsrec.tsatable,
sizeof(ets->tc_reco_tsa));
memcpy(ets->reco_prio_tc, dcbxcfg->etscfg.prioritytable,
sizeof(ets->reco_prio_tc));
return 0;
}
/**
* i40e_dcbnl_ieee_getpfc - retrieve local IEEE PFC configuration
* @netdev: the corresponding netdev
* @ets: structure to hold the PFC information
*
* Returns local IEEE PFC configuration
**/
static int i40e_dcbnl_ieee_getpfc(struct net_device *dev,
struct ieee_pfc *pfc)
{
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
struct i40e_dcbx_config *dcbxcfg;
struct i40e_hw *hw = &pf->hw;
int i;
if (!(pf->dcbx_cap & DCB_CAP_DCBX_VER_IEEE))
return -EINVAL;
dcbxcfg = &hw->local_dcbx_config;
pfc->pfc_cap = dcbxcfg->pfc.pfccap;
pfc->pfc_en = dcbxcfg->pfc.pfcenable;
pfc->mbc = dcbxcfg->pfc.mbc;
i40e_get_pfc_delay(hw, &pfc->delay);
/* Get Requests/Indicatiosn */
for (i = 0; i < I40E_MAX_TRAFFIC_CLASS; i++) {
pfc->requests[i] = pf->stats.priority_xoff_tx[i];
pfc->indications[i] = pf->stats.priority_xoff_rx[i];
}
return 0;
}
/**
* i40e_dcbnl_getdcbx - retrieve current DCBx capability
* @netdev: the corresponding netdev
*
* Returns DCBx capability features
**/
static u8 i40e_dcbnl_getdcbx(struct net_device *dev)
{
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
return pf->dcbx_cap;
}
/**
* i40e_dcbnl_get_perm_hw_addr - MAC address used by DCBx
* @netdev: the corresponding netdev
*
* Returns the SAN MAC address used for LLDP exchange
**/
static void i40e_dcbnl_get_perm_hw_addr(struct net_device *dev,
u8 *perm_addr)
{
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
int i, j;
memset(perm_addr, 0xff, MAX_ADDR_LEN);
for (i = 0; i < dev->addr_len; i++)
perm_addr[i] = pf->hw.mac.perm_addr[i];
for (j = 0; j < dev->addr_len; j++, i++)
perm_addr[i] = pf->hw.mac.san_addr[j];
}
static const struct dcbnl_rtnl_ops dcbnl_ops = {
.ieee_getets = i40e_dcbnl_ieee_getets,
.ieee_getpfc = i40e_dcbnl_ieee_getpfc,
.getdcbx = i40e_dcbnl_getdcbx,
.getpermhwaddr = i40e_dcbnl_get_perm_hw_addr,
};
/**
* i40e_dcbnl_set_all - set all the apps and ieee data from DCBx config
* @vsi: the corresponding vsi
*
* Set up all the IEEE APPs in the DCBNL App Table and generate event for
* other settings
**/
void i40e_dcbnl_set_all(struct i40e_vsi *vsi)
{
struct net_device *dev = vsi->netdev;
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
struct i40e_dcbx_config *dcbxcfg;
struct i40e_hw *hw = &pf->hw;
struct dcb_app sapp;
u8 prio, tc_map;
int i;
/* DCB not enabled */
if (!(pf->flags & I40E_FLAG_DCB_ENABLED))
return;
/* MFP mode but not an iSCSI PF so return */
if ((pf->flags & I40E_FLAG_MFP_ENABLED) && !(pf->hw.func_caps.iscsi))
return;
dcbxcfg = &hw->local_dcbx_config;
/* Set up all the App TLVs if DCBx is negotiated */
for (i = 0; i < dcbxcfg->numapps; i++) {
prio = dcbxcfg->app[i].priority;
tc_map = BIT(dcbxcfg->etscfg.prioritytable[prio]);
/* Add APP only if the TC is enabled for this VSI */
if (tc_map & vsi->tc_config.enabled_tc) {
sapp.selector = dcbxcfg->app[i].selector;
sapp.protocol = dcbxcfg->app[i].protocolid;
sapp.priority = prio;
dcb_ieee_setapp(dev, &sapp);
}
}
/* Notify user-space of the changes */
dcbnl_ieee_notify(dev, RTM_SETDCB, DCB_CMD_IEEE_SET, 0, 0);
}
/**
* i40e_dcbnl_vsi_del_app - Delete APP for given VSI
* @vsi: the corresponding vsi
* @app: APP to delete
*
* Delete given APP from the DCBNL APP table for given
* VSI
**/
static int i40e_dcbnl_vsi_del_app(struct i40e_vsi *vsi,
struct i40e_dcb_app_priority_table *app)
{
struct net_device *dev = vsi->netdev;
struct dcb_app sapp;
if (!dev)
return -EINVAL;
sapp.selector = app->selector;
sapp.protocol = app->protocolid;
sapp.priority = app->priority;
return dcb_ieee_delapp(dev, &sapp);
}
/**
* i40e_dcbnl_del_app - Delete APP on all VSIs
* @pf: the corresponding PF
* @app: APP to delete
*
* Delete given APP from all the VSIs for given PF
**/
static void i40e_dcbnl_del_app(struct i40e_pf *pf,
struct i40e_dcb_app_priority_table *app)
{
int v, err;
for (v = 0; v < pf->num_alloc_vsi; v++) {
if (pf->vsi[v] && pf->vsi[v]->netdev) {
err = i40e_dcbnl_vsi_del_app(pf->vsi[v], app);
dev_dbg(&pf->pdev->dev, "Deleting app for VSI seid=%d err=%d sel=%d proto=0x%x prio=%d\n",
pf->vsi[v]->seid, err, app->selector,
app->protocolid, app->priority);
}
}
}
/**
* i40e_dcbnl_find_app - Search APP in given DCB config
* @cfg: DCBX configuration data
* @app: APP to search for
*
* Find given APP in the DCB configuration
**/
static bool i40e_dcbnl_find_app(struct i40e_dcbx_config *cfg,
struct i40e_dcb_app_priority_table *app)
{
int i;
for (i = 0; i < cfg->numapps; i++) {
if (app->selector == cfg->app[i].selector &&
app->protocolid == cfg->app[i].protocolid &&
app->priority == cfg->app[i].priority)
return true;
}
return false;
}
/**
* i40e_dcbnl_flush_apps - Delete all removed APPs
* @pf: the corresponding PF
* @old_cfg: old DCBX configuration data
* @new_cfg: new DCBX configuration data
*
* Find and delete all APPs that are not present in the passed
* DCB configuration
**/
void i40e_dcbnl_flush_apps(struct i40e_pf *pf,
struct i40e_dcbx_config *old_cfg,
struct i40e_dcbx_config *new_cfg)
{
struct i40e_dcb_app_priority_table app;
int i;
/* MFP mode but not an iSCSI PF so return */
if ((pf->flags & I40E_FLAG_MFP_ENABLED) && !(pf->hw.func_caps.iscsi))
return;
for (i = 0; i < old_cfg->numapps; i++) {
app = old_cfg->app[i];
/* The APP is not available anymore delete it */
if (!i40e_dcbnl_find_app(new_cfg, &app))
i40e_dcbnl_del_app(pf, &app);
}
}
/**
* i40e_dcbnl_setup - DCBNL setup
* @vsi: the corresponding vsi
*
* Set up DCBNL ops and initial APP TLVs
**/
void i40e_dcbnl_setup(struct i40e_vsi *vsi)
{
struct net_device *dev = vsi->netdev;
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
/* Not DCB capable */
if (!(pf->flags & I40E_FLAG_DCB_CAPABLE))
return;
dev->dcbnl_ops = &dcbnl_ops;
/* Set initial IEEE DCB settings */
i40e_dcbnl_set_all(vsi);
}
#endif /* CONFIG_I40E_DCB */