Commit ab526eaa authored by David S. Miller's avatar David S. Miller

Merge branch 'dpaa-cleanups'

Sean Anderson says:

====================
net: dpaa: Cleanups in preparation for phylink conversion (part 2)

This series contains several cleanup patches for dpaa/fman. While they
are intended to prepare for a phylink conversion, they stand on their
own. This series was originally submitted as part of [1].

[1] https://lore.kernel.org/netdev/20220715215954.1449214-1-sean.anderson@seco.com

Changes in v5:
- Reduce line length of tgec_config
- Reduce line length of qman_update_cgr_safe
- Rebase onto net-next/master

Changes in v4:
- weer -> were
- tricy -> tricky
- Use mac_dev for calling change_addr
- qman_cgr_create -> qman_create_cgr

Changes in v2:
- Fix prototype for dtsec_initialization
- Fix warning if sizeof(void *) != sizeof(resource_size_t)
- Specify type of mac_dev for exception_cb
- Add helper for sanity checking cgr ops
- Add CGR update function
- Adjust queue depth on rate change
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 36f9b474 ef2a8d54
...@@ -197,12 +197,15 @@ static int dpaa_rx_extra_headroom; ...@@ -197,12 +197,15 @@ static int dpaa_rx_extra_headroom;
#define dpaa_get_max_mtu() \ #define dpaa_get_max_mtu() \
(dpaa_max_frm - (VLAN_ETH_HLEN + ETH_FCS_LEN)) (dpaa_max_frm - (VLAN_ETH_HLEN + ETH_FCS_LEN))
static void dpaa_eth_cgr_set_speed(struct mac_device *mac_dev, int speed);
static int dpaa_netdev_init(struct net_device *net_dev, static int dpaa_netdev_init(struct net_device *net_dev,
const struct net_device_ops *dpaa_ops, const struct net_device_ops *dpaa_ops,
u16 tx_timeout) u16 tx_timeout)
{ {
struct dpaa_priv *priv = netdev_priv(net_dev); struct dpaa_priv *priv = netdev_priv(net_dev);
struct device *dev = net_dev->dev.parent; struct device *dev = net_dev->dev.parent;
struct mac_device *mac_dev = priv->mac_dev;
struct dpaa_percpu_priv *percpu_priv; struct dpaa_percpu_priv *percpu_priv;
const u8 *mac_addr; const u8 *mac_addr;
int i, err; int i, err;
...@@ -216,10 +219,10 @@ static int dpaa_netdev_init(struct net_device *net_dev, ...@@ -216,10 +219,10 @@ static int dpaa_netdev_init(struct net_device *net_dev,
} }
net_dev->netdev_ops = dpaa_ops; net_dev->netdev_ops = dpaa_ops;
mac_addr = priv->mac_dev->addr; mac_addr = mac_dev->addr;
net_dev->mem_start = priv->mac_dev->res->start; net_dev->mem_start = (unsigned long)mac_dev->vaddr;
net_dev->mem_end = priv->mac_dev->res->end; net_dev->mem_end = (unsigned long)mac_dev->vaddr_end;
net_dev->min_mtu = ETH_MIN_MTU; net_dev->min_mtu = ETH_MIN_MTU;
net_dev->max_mtu = dpaa_get_max_mtu(); net_dev->max_mtu = dpaa_get_max_mtu();
...@@ -246,7 +249,7 @@ static int dpaa_netdev_init(struct net_device *net_dev, ...@@ -246,7 +249,7 @@ static int dpaa_netdev_init(struct net_device *net_dev,
eth_hw_addr_set(net_dev, mac_addr); eth_hw_addr_set(net_dev, mac_addr);
} else { } else {
eth_hw_addr_random(net_dev); eth_hw_addr_random(net_dev);
err = priv->mac_dev->change_addr(priv->mac_dev->fman_mac, err = mac_dev->change_addr(mac_dev->fman_mac,
(const enet_addr_t *)net_dev->dev_addr); (const enet_addr_t *)net_dev->dev_addr);
if (err) { if (err) {
dev_err(dev, "Failed to set random MAC address\n"); dev_err(dev, "Failed to set random MAC address\n");
...@@ -261,6 +264,9 @@ static int dpaa_netdev_init(struct net_device *net_dev, ...@@ -261,6 +264,9 @@ static int dpaa_netdev_init(struct net_device *net_dev,
net_dev->needed_headroom = priv->tx_headroom; net_dev->needed_headroom = priv->tx_headroom;
net_dev->watchdog_timeo = msecs_to_jiffies(tx_timeout); net_dev->watchdog_timeo = msecs_to_jiffies(tx_timeout);
mac_dev->net_dev = net_dev;
mac_dev->update_speed = dpaa_eth_cgr_set_speed;
/* start without the RUNNING flag, phylib controls it later */ /* start without the RUNNING flag, phylib controls it later */
netif_carrier_off(net_dev); netif_carrier_off(net_dev);
...@@ -290,10 +296,7 @@ static int dpaa_stop(struct net_device *net_dev) ...@@ -290,10 +296,7 @@ static int dpaa_stop(struct net_device *net_dev)
if (mac_dev->phy_dev) if (mac_dev->phy_dev)
phy_stop(mac_dev->phy_dev); phy_stop(mac_dev->phy_dev);
err = mac_dev->disable(mac_dev->fman_mac); mac_dev->disable(mac_dev->fman_mac);
if (err < 0)
netif_err(priv, ifdown, net_dev, "mac_dev->disable() = %d\n",
err);
for (i = 0; i < ARRAY_SIZE(mac_dev->port); i++) { for (i = 0; i < ARRAY_SIZE(mac_dev->port); i++) {
error = fman_port_disable(mac_dev->port[i]); error = fman_port_disable(mac_dev->port[i]);
...@@ -828,10 +831,10 @@ static int dpaa_eth_cgr_init(struct dpaa_priv *priv) ...@@ -828,10 +831,10 @@ static int dpaa_eth_cgr_init(struct dpaa_priv *priv)
initcgr.we_mask = cpu_to_be16(QM_CGR_WE_CSCN_EN | QM_CGR_WE_CS_THRES); initcgr.we_mask = cpu_to_be16(QM_CGR_WE_CSCN_EN | QM_CGR_WE_CS_THRES);
initcgr.cgr.cscn_en = QM_CGR_EN; initcgr.cgr.cscn_en = QM_CGR_EN;
/* Set different thresholds based on the MAC speed. /* Set different thresholds based on the configured MAC speed.
* This may turn suboptimal if the MAC is reconfigured at a speed * This may turn suboptimal if the MAC is reconfigured at another
* lower than its max, e.g. if a dTSEC later negotiates a 100Mbps link. * speed, so MACs must call dpaa_eth_cgr_set_speed in their adjust_link
* In such cases, we ought to reconfigure the threshold, too. * callback.
*/ */
if (priv->mac_dev->if_support & SUPPORTED_10000baseT_Full) if (priv->mac_dev->if_support & SUPPORTED_10000baseT_Full)
cs_th = DPAA_CS_THRESHOLD_10G; cs_th = DPAA_CS_THRESHOLD_10G;
...@@ -860,6 +863,31 @@ static int dpaa_eth_cgr_init(struct dpaa_priv *priv) ...@@ -860,6 +863,31 @@ static int dpaa_eth_cgr_init(struct dpaa_priv *priv)
return err; return err;
} }
static void dpaa_eth_cgr_set_speed(struct mac_device *mac_dev, int speed)
{
struct net_device *net_dev = mac_dev->net_dev;
struct dpaa_priv *priv = netdev_priv(net_dev);
struct qm_mcc_initcgr opts = { };
u32 cs_th;
int err;
opts.we_mask = cpu_to_be16(QM_CGR_WE_CS_THRES);
switch (speed) {
case SPEED_10000:
cs_th = DPAA_CS_THRESHOLD_10G;
break;
case SPEED_1000:
default:
cs_th = DPAA_CS_THRESHOLD_1G;
break;
}
qm_cgr_cs_thres_set64(&opts.cgr.cs_thres, cs_th, 1);
err = qman_update_cgr_safe(&priv->cgr_data.cgr, &opts);
if (err)
netdev_err(net_dev, "could not update speed: %d\n", err);
}
static inline void dpaa_setup_ingress(const struct dpaa_priv *priv, static inline void dpaa_setup_ingress(const struct dpaa_priv *priv,
struct dpaa_fq *fq, struct dpaa_fq *fq,
const struct qman_fq *template) const struct qman_fq *template)
......
...@@ -18,7 +18,7 @@ static ssize_t dpaa_eth_show_addr(struct device *dev, ...@@ -18,7 +18,7 @@ static ssize_t dpaa_eth_show_addr(struct device *dev,
if (mac_dev) if (mac_dev)
return sprintf(buf, "%llx", return sprintf(buf, "%llx",
(unsigned long long)mac_dev->res->start); (unsigned long long)mac_dev->vaddr);
else else
return sprintf(buf, "none"); return sprintf(buf, "none");
} }
......
...@@ -8,27 +8,10 @@ ...@@ -8,27 +8,10 @@
#include "fman_mac.h" #include "fman_mac.h"
struct fman_mac *dtsec_config(struct fman_mac_params *params); struct mac_device;
int dtsec_set_promiscuous(struct fman_mac *dtsec, bool new_val);
int dtsec_modify_mac_address(struct fman_mac *dtsec, const enet_addr_t *enet_addr); int dtsec_initialization(struct mac_device *mac_dev,
int dtsec_adjust_link(struct fman_mac *dtsec, struct device_node *mac_node,
u16 speed); struct fman_mac_params *params);
int dtsec_restart_autoneg(struct fman_mac *dtsec);
int dtsec_cfg_max_frame_len(struct fman_mac *dtsec, u16 new_val);
int dtsec_cfg_pad_and_crc(struct fman_mac *dtsec, bool new_val);
int dtsec_enable(struct fman_mac *dtsec);
int dtsec_disable(struct fman_mac *dtsec);
int dtsec_init(struct fman_mac *dtsec);
int dtsec_free(struct fman_mac *dtsec);
int dtsec_accept_rx_pause_frames(struct fman_mac *dtsec, bool en);
int dtsec_set_tx_pause_frames(struct fman_mac *dtsec, u8 priority,
u16 pause_time, u16 thresh_time);
int dtsec_set_exception(struct fman_mac *dtsec,
enum fman_mac_exceptions exception, bool enable);
int dtsec_add_hash_mac_address(struct fman_mac *dtsec, enet_addr_t *eth_addr);
int dtsec_del_hash_mac_address(struct fman_mac *dtsec, enet_addr_t *eth_addr);
int dtsec_get_version(struct fman_mac *dtsec, u32 *mac_version);
int dtsec_set_allmulti(struct fman_mac *dtsec, bool enable);
int dtsec_set_tstamp(struct fman_mac *dtsec, bool enable);
#endif /* __DTSEC_H */ #endif /* __DTSEC_H */
...@@ -41,6 +41,7 @@ ...@@ -41,6 +41,7 @@
#include <linux/if_ether.h> #include <linux/if_ether.h>
struct fman_mac; struct fman_mac;
struct mac_device;
/* Ethernet Address */ /* Ethernet Address */
typedef u8 enet_addr_t[ETH_ALEN]; typedef u8 enet_addr_t[ETH_ALEN];
...@@ -158,30 +159,23 @@ struct eth_hash_entry { ...@@ -158,30 +159,23 @@ struct eth_hash_entry {
struct list_head node; struct list_head node;
}; };
typedef void (fman_mac_exception_cb)(void *dev_id, typedef void (fman_mac_exception_cb)(struct mac_device *dev_id,
enum fman_mac_exceptions exceptions); enum fman_mac_exceptions exceptions);
/* FMan MAC config input */ /* FMan MAC config input */
struct fman_mac_params { struct fman_mac_params {
/* Base of memory mapped FM MAC registers */
void __iomem *base_addr;
/* MAC address of device; First octet is sent first */
enet_addr_t addr;
/* MAC ID; numbering of dTSEC and 1G-mEMAC: /* MAC ID; numbering of dTSEC and 1G-mEMAC:
* 0 - FM_MAX_NUM_OF_1G_MACS; * 0 - FM_MAX_NUM_OF_1G_MACS;
* numbering of 10G-MAC (TGEC) and 10G-mEMAC: * numbering of 10G-MAC (TGEC) and 10G-mEMAC:
* 0 - FM_MAX_NUM_OF_10G_MACS * 0 - FM_MAX_NUM_OF_10G_MACS
*/ */
u8 mac_id; u8 mac_id;
/* PHY interface */
phy_interface_t phy_if;
/* Note that the speed should indicate the maximum rate that /* Note that the speed should indicate the maximum rate that
* this MAC should support rather than the actual speed; * this MAC should support rather than the actual speed;
*/ */
u16 max_speed; u16 max_speed;
/* A handle to the FM object this port related to */ /* A handle to the FM object this port related to */
void *fm; void *fm;
void *dev_id; /* device cookie used by the exception cbs */
fman_mac_exception_cb *event_cb; /* MDIO Events Callback Routine */ fman_mac_exception_cb *event_cb; /* MDIO Events Callback Routine */
fman_mac_exception_cb *exception_cb;/* Exception Callback Routine */ fman_mac_exception_cb *exception_cb;/* Exception Callback Routine */
/* SGMII/QSGII interface with 1000BaseX auto-negotiation between MAC /* SGMII/QSGII interface with 1000BaseX auto-negotiation between MAC
...@@ -190,8 +184,6 @@ struct fman_mac_params { ...@@ -190,8 +184,6 @@ struct fman_mac_params {
* synchronize with far-end phy at 10Mbps, 100Mbps or 1000Mbps * synchronize with far-end phy at 10Mbps, 100Mbps or 1000Mbps
*/ */
bool basex_if; bool basex_if;
/* Pointer to TBI/PCS PHY node, used for TBI/PCS PHY access */
struct device_node *internal_phy_node;
}; };
struct eth_hash_t { struct eth_hash_t {
......
...@@ -11,26 +11,10 @@ ...@@ -11,26 +11,10 @@
#include <linux/netdevice.h> #include <linux/netdevice.h>
#include <linux/phy_fixed.h> #include <linux/phy_fixed.h>
struct fman_mac *memac_config(struct fman_mac_params *params); struct mac_device;
int memac_set_promiscuous(struct fman_mac *memac, bool new_val);
int memac_modify_mac_address(struct fman_mac *memac, const enet_addr_t *enet_addr); int memac_initialization(struct mac_device *mac_dev,
int memac_adjust_link(struct fman_mac *memac, u16 speed); struct device_node *mac_node,
int memac_cfg_max_frame_len(struct fman_mac *memac, u16 new_val); struct fman_mac_params *params);
int memac_cfg_reset_on_init(struct fman_mac *memac, bool enable);
int memac_cfg_fixed_link(struct fman_mac *memac,
struct fixed_phy_status *fixed_link);
int memac_enable(struct fman_mac *memac);
int memac_disable(struct fman_mac *memac);
int memac_init(struct fman_mac *memac);
int memac_free(struct fman_mac *memac);
int memac_accept_rx_pause_frames(struct fman_mac *memac, bool en);
int memac_set_tx_pause_frames(struct fman_mac *memac, u8 priority,
u16 pause_time, u16 thresh_time);
int memac_set_exception(struct fman_mac *memac,
enum fman_mac_exceptions exception, bool enable);
int memac_add_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr);
int memac_del_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr);
int memac_set_allmulti(struct fman_mac *memac, bool enable);
int memac_set_tstamp(struct fman_mac *memac, bool enable);
#endif /* __MEMAC_H */ #endif /* __MEMAC_H */
...@@ -7,6 +7,7 @@ ...@@ -7,6 +7,7 @@
#include "fman_tgec.h" #include "fman_tgec.h"
#include "fman.h" #include "fman.h"
#include "mac.h"
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/bitrev.h> #include <linux/bitrev.h>
...@@ -179,7 +180,7 @@ struct fman_mac { ...@@ -179,7 +180,7 @@ struct fman_mac {
/* MAC address of device; */ /* MAC address of device; */
u64 addr; u64 addr;
u16 max_speed; u16 max_speed;
void *dev_id; /* device cookie used by the exception cbs */ struct mac_device *dev_id; /* device cookie used by the exception cbs */
fman_mac_exception_cb *exception_cb; fman_mac_exception_cb *exception_cb;
fman_mac_exception_cb *event_cb; fman_mac_exception_cb *event_cb;
/* pointer to driver's global address hash table */ /* pointer to driver's global address hash table */
...@@ -392,7 +393,7 @@ static bool is_init_done(struct tgec_cfg *cfg) ...@@ -392,7 +393,7 @@ static bool is_init_done(struct tgec_cfg *cfg)
return false; return false;
} }
int tgec_enable(struct fman_mac *tgec) static int tgec_enable(struct fman_mac *tgec)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
u32 tmp; u32 tmp;
...@@ -407,22 +408,19 @@ int tgec_enable(struct fman_mac *tgec) ...@@ -407,22 +408,19 @@ int tgec_enable(struct fman_mac *tgec)
return 0; return 0;
} }
int tgec_disable(struct fman_mac *tgec) static void tgec_disable(struct fman_mac *tgec)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
u32 tmp; u32 tmp;
if (!is_init_done(tgec->cfg)) WARN_ON_ONCE(!is_init_done(tgec->cfg));
return -EINVAL;
tmp = ioread32be(&regs->command_config); tmp = ioread32be(&regs->command_config);
tmp &= ~(CMD_CFG_RX_EN | CMD_CFG_TX_EN); tmp &= ~(CMD_CFG_RX_EN | CMD_CFG_TX_EN);
iowrite32be(tmp, &regs->command_config); iowrite32be(tmp, &regs->command_config);
return 0;
} }
int tgec_set_promiscuous(struct fman_mac *tgec, bool new_val) static int tgec_set_promiscuous(struct fman_mac *tgec, bool new_val)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
u32 tmp; u32 tmp;
...@@ -440,18 +438,9 @@ int tgec_set_promiscuous(struct fman_mac *tgec, bool new_val) ...@@ -440,18 +438,9 @@ int tgec_set_promiscuous(struct fman_mac *tgec, bool new_val)
return 0; return 0;
} }
int tgec_cfg_max_frame_len(struct fman_mac *tgec, u16 new_val) static int tgec_set_tx_pause_frames(struct fman_mac *tgec,
{ u8 __maybe_unused priority, u16 pause_time,
if (is_init_done(tgec->cfg)) u16 __maybe_unused thresh_time)
return -EINVAL;
tgec->cfg->max_frame_length = new_val;
return 0;
}
int tgec_set_tx_pause_frames(struct fman_mac *tgec, u8 __maybe_unused priority,
u16 pause_time, u16 __maybe_unused thresh_time)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
...@@ -463,7 +452,7 @@ int tgec_set_tx_pause_frames(struct fman_mac *tgec, u8 __maybe_unused priority, ...@@ -463,7 +452,7 @@ int tgec_set_tx_pause_frames(struct fman_mac *tgec, u8 __maybe_unused priority,
return 0; return 0;
} }
int tgec_accept_rx_pause_frames(struct fman_mac *tgec, bool en) static int tgec_accept_rx_pause_frames(struct fman_mac *tgec, bool en)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
u32 tmp; u32 tmp;
...@@ -481,7 +470,8 @@ int tgec_accept_rx_pause_frames(struct fman_mac *tgec, bool en) ...@@ -481,7 +470,8 @@ int tgec_accept_rx_pause_frames(struct fman_mac *tgec, bool en)
return 0; return 0;
} }
int tgec_modify_mac_address(struct fman_mac *tgec, const enet_addr_t *p_enet_addr) static int tgec_modify_mac_address(struct fman_mac *tgec,
const enet_addr_t *p_enet_addr)
{ {
if (!is_init_done(tgec->cfg)) if (!is_init_done(tgec->cfg))
return -EINVAL; return -EINVAL;
...@@ -492,7 +482,8 @@ int tgec_modify_mac_address(struct fman_mac *tgec, const enet_addr_t *p_enet_add ...@@ -492,7 +482,8 @@ int tgec_modify_mac_address(struct fman_mac *tgec, const enet_addr_t *p_enet_add
return 0; return 0;
} }
int tgec_add_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr) static int tgec_add_hash_mac_address(struct fman_mac *tgec,
enet_addr_t *eth_addr)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
struct eth_hash_entry *hash_entry; struct eth_hash_entry *hash_entry;
...@@ -529,7 +520,7 @@ int tgec_add_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr) ...@@ -529,7 +520,7 @@ int tgec_add_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr)
return 0; return 0;
} }
int tgec_set_allmulti(struct fman_mac *tgec, bool enable) static int tgec_set_allmulti(struct fman_mac *tgec, bool enable)
{ {
u32 entry; u32 entry;
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
...@@ -552,7 +543,7 @@ int tgec_set_allmulti(struct fman_mac *tgec, bool enable) ...@@ -552,7 +543,7 @@ int tgec_set_allmulti(struct fman_mac *tgec, bool enable)
return 0; return 0;
} }
int tgec_set_tstamp(struct fman_mac *tgec, bool enable) static int tgec_set_tstamp(struct fman_mac *tgec, bool enable)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
u32 tmp; u32 tmp;
...@@ -572,7 +563,8 @@ int tgec_set_tstamp(struct fman_mac *tgec, bool enable) ...@@ -572,7 +563,8 @@ int tgec_set_tstamp(struct fman_mac *tgec, bool enable)
return 0; return 0;
} }
int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr) static int tgec_del_hash_mac_address(struct fman_mac *tgec,
enet_addr_t *eth_addr)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
struct eth_hash_entry *hash_entry = NULL; struct eth_hash_entry *hash_entry = NULL;
...@@ -609,20 +601,15 @@ int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr) ...@@ -609,20 +601,15 @@ int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr)
return 0; return 0;
} }
int tgec_get_version(struct fman_mac *tgec, u32 *mac_version) static void tgec_adjust_link(struct mac_device *mac_dev)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct phy_device *phy_dev = mac_dev->phy_dev;
if (!is_init_done(tgec->cfg))
return -EINVAL;
*mac_version = ioread32be(&regs->tgec_id); mac_dev->update_speed(mac_dev, phy_dev->speed);
return 0;
} }
int tgec_set_exception(struct fman_mac *tgec, static int tgec_set_exception(struct fman_mac *tgec,
enum fman_mac_exceptions exception, bool enable) enum fman_mac_exceptions exception, bool enable)
{ {
struct tgec_regs __iomem *regs = tgec->regs; struct tgec_regs __iomem *regs = tgec->regs;
u32 bit_mask = 0; u32 bit_mask = 0;
...@@ -648,7 +635,7 @@ int tgec_set_exception(struct fman_mac *tgec, ...@@ -648,7 +635,7 @@ int tgec_set_exception(struct fman_mac *tgec,
return 0; return 0;
} }
int tgec_init(struct fman_mac *tgec) static int tgec_init(struct fman_mac *tgec)
{ {
struct tgec_cfg *cfg; struct tgec_cfg *cfg;
enet_addr_t eth_addr; enet_addr_t eth_addr;
...@@ -731,7 +718,7 @@ int tgec_init(struct fman_mac *tgec) ...@@ -731,7 +718,7 @@ int tgec_init(struct fman_mac *tgec)
return 0; return 0;
} }
int tgec_free(struct fman_mac *tgec) static int tgec_free(struct fman_mac *tgec)
{ {
free_init_resources(tgec); free_init_resources(tgec);
...@@ -741,13 +728,12 @@ int tgec_free(struct fman_mac *tgec) ...@@ -741,13 +728,12 @@ int tgec_free(struct fman_mac *tgec)
return 0; return 0;
} }
struct fman_mac *tgec_config(struct fman_mac_params *params) static struct fman_mac *tgec_config(struct mac_device *mac_dev,
struct fman_mac_params *params)
{ {
struct fman_mac *tgec; struct fman_mac *tgec;
struct tgec_cfg *cfg; struct tgec_cfg *cfg;
void __iomem *base_addr;
base_addr = params->base_addr;
/* allocate memory for the UCC GETH data structure. */ /* allocate memory for the UCC GETH data structure. */
tgec = kzalloc(sizeof(*tgec), GFP_KERNEL); tgec = kzalloc(sizeof(*tgec), GFP_KERNEL);
if (!tgec) if (!tgec)
...@@ -765,8 +751,8 @@ struct fman_mac *tgec_config(struct fman_mac_params *params) ...@@ -765,8 +751,8 @@ struct fman_mac *tgec_config(struct fman_mac_params *params)
set_dflts(cfg); set_dflts(cfg);
tgec->regs = base_addr; tgec->regs = mac_dev->vaddr;
tgec->addr = ENET_ADDR_TO_UINT64(params->addr); tgec->addr = ENET_ADDR_TO_UINT64(mac_dev->addr);
tgec->max_speed = params->max_speed; tgec->max_speed = params->max_speed;
tgec->mac_id = params->mac_id; tgec->mac_id = params->mac_id;
tgec->exceptions = (TGEC_IMASK_MDIO_SCAN_EVENT | tgec->exceptions = (TGEC_IMASK_MDIO_SCAN_EVENT |
...@@ -786,7 +772,7 @@ struct fman_mac *tgec_config(struct fman_mac_params *params) ...@@ -786,7 +772,7 @@ struct fman_mac *tgec_config(struct fman_mac_params *params)
TGEC_IMASK_RX_ALIGN_ER); TGEC_IMASK_RX_ALIGN_ER);
tgec->exception_cb = params->exception_cb; tgec->exception_cb = params->exception_cb;
tgec->event_cb = params->event_cb; tgec->event_cb = params->event_cb;
tgec->dev_id = params->dev_id; tgec->dev_id = mac_dev;
tgec->fm = params->fm; tgec->fm = params->fm;
/* Save FMan revision */ /* Save FMan revision */
...@@ -794,3 +780,52 @@ struct fman_mac *tgec_config(struct fman_mac_params *params) ...@@ -794,3 +780,52 @@ struct fman_mac *tgec_config(struct fman_mac_params *params)
return tgec; return tgec;
} }
int tgec_initialization(struct mac_device *mac_dev,
struct device_node *mac_node,
struct fman_mac_params *params)
{
int err;
struct fman_mac *tgec;
mac_dev->set_promisc = tgec_set_promiscuous;
mac_dev->change_addr = tgec_modify_mac_address;
mac_dev->add_hash_mac_addr = tgec_add_hash_mac_address;
mac_dev->remove_hash_mac_addr = tgec_del_hash_mac_address;
mac_dev->set_tx_pause = tgec_set_tx_pause_frames;
mac_dev->set_rx_pause = tgec_accept_rx_pause_frames;
mac_dev->set_exception = tgec_set_exception;
mac_dev->set_allmulti = tgec_set_allmulti;
mac_dev->set_tstamp = tgec_set_tstamp;
mac_dev->set_multi = fman_set_multi;
mac_dev->adjust_link = tgec_adjust_link;
mac_dev->enable = tgec_enable;
mac_dev->disable = tgec_disable;
mac_dev->fman_mac = tgec_config(mac_dev, params);
if (!mac_dev->fman_mac) {
err = -EINVAL;
goto _return;
}
tgec = mac_dev->fman_mac;
tgec->cfg->max_frame_length = fman_get_max_frm();
err = tgec_init(tgec);
if (err < 0)
goto _return_fm_mac_free;
/* For 10G MAC, disable Tx ECC exception */
err = tgec_set_exception(tgec, FM_MAC_EX_10G_TX_ECC_ER, false);
if (err < 0)
goto _return_fm_mac_free;
pr_info("FMan XGEC version: 0x%08x\n",
ioread32be(&tgec->regs->tgec_id));
goto _return;
_return_fm_mac_free:
tgec_free(mac_dev->fman_mac);
_return:
return err;
}
...@@ -8,23 +8,10 @@ ...@@ -8,23 +8,10 @@
#include "fman_mac.h" #include "fman_mac.h"
struct fman_mac *tgec_config(struct fman_mac_params *params); struct mac_device;
int tgec_set_promiscuous(struct fman_mac *tgec, bool new_val);
int tgec_modify_mac_address(struct fman_mac *tgec, const enet_addr_t *enet_addr); int tgec_initialization(struct mac_device *mac_dev,
int tgec_cfg_max_frame_len(struct fman_mac *tgec, u16 new_val); struct device_node *mac_node,
int tgec_enable(struct fman_mac *tgec); struct fman_mac_params *params);
int tgec_disable(struct fman_mac *tgec);
int tgec_init(struct fman_mac *tgec);
int tgec_free(struct fman_mac *tgec);
int tgec_accept_rx_pause_frames(struct fman_mac *tgec, bool en);
int tgec_set_tx_pause_frames(struct fman_mac *tgec, u8 priority,
u16 pause_time, u16 thresh_time);
int tgec_set_exception(struct fman_mac *tgec,
enum fman_mac_exceptions exception, bool enable);
int tgec_add_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr);
int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr);
int tgec_get_version(struct fman_mac *tgec, u32 *mac_version);
int tgec_set_allmulti(struct fman_mac *tgec, bool enable);
int tgec_set_tstamp(struct fman_mac *tgec, bool enable);
#endif /* __TGEC_H */ #endif /* __TGEC_H */
This diff is collapsed.
...@@ -19,14 +19,16 @@ struct fman_mac; ...@@ -19,14 +19,16 @@ struct fman_mac;
struct mac_priv_s; struct mac_priv_s;
struct mac_device { struct mac_device {
void __iomem *vaddr;
void __iomem *vaddr_end;
struct device *dev; struct device *dev;
struct resource *res;
u8 addr[ETH_ALEN]; u8 addr[ETH_ALEN];
struct fman_port *port[2]; struct fman_port *port[2];
u32 if_support; u32 if_support;
struct phy_device *phy_dev; struct phy_device *phy_dev;
phy_interface_t phy_if; phy_interface_t phy_if;
struct device_node *phy_node; struct device_node *phy_node;
struct net_device *net_dev;
bool autoneg_pause; bool autoneg_pause;
bool rx_pause_req; bool rx_pause_req;
...@@ -37,7 +39,7 @@ struct mac_device { ...@@ -37,7 +39,7 @@ struct mac_device {
bool allmulti; bool allmulti;
int (*enable)(struct fman_mac *mac_dev); int (*enable)(struct fman_mac *mac_dev);
int (*disable)(struct fman_mac *mac_dev); void (*disable)(struct fman_mac *mac_dev);
void (*adjust_link)(struct mac_device *mac_dev); void (*adjust_link)(struct mac_device *mac_dev);
int (*set_promisc)(struct fman_mac *mac_dev, bool enable); int (*set_promisc)(struct fman_mac *mac_dev, bool enable);
int (*change_addr)(struct fman_mac *mac_dev, const enet_addr_t *enet_addr); int (*change_addr)(struct fman_mac *mac_dev, const enet_addr_t *enet_addr);
...@@ -55,6 +57,8 @@ struct mac_device { ...@@ -55,6 +57,8 @@ struct mac_device {
int (*remove_hash_mac_addr)(struct fman_mac *mac_dev, int (*remove_hash_mac_addr)(struct fman_mac *mac_dev,
enet_addr_t *eth_addr); enet_addr_t *eth_addr);
void (*update_speed)(struct mac_device *mac_dev, int speed);
struct fman_mac *fman_mac; struct fman_mac *fman_mac;
struct mac_priv_s *priv; struct mac_priv_s *priv;
}; };
...@@ -71,8 +75,6 @@ int fman_set_mac_active_pause(struct mac_device *mac_dev, bool rx, bool tx); ...@@ -71,8 +75,6 @@ int fman_set_mac_active_pause(struct mac_device *mac_dev, bool rx, bool tx);
void fman_get_pause_cfg(struct mac_device *mac_dev, bool *rx_pause, void fman_get_pause_cfg(struct mac_device *mac_dev, bool *rx_pause,
bool *tx_pause); bool *tx_pause);
int set_fman_mac_params(struct mac_device *mac_dev,
struct fman_mac_params *params);
int fman_set_multi(struct net_device *net_dev, struct mac_device *mac_dev); int fman_set_multi(struct net_device *net_dev, struct mac_device *mac_dev);
#endif /* __MAC_H */ #endif /* __MAC_H */
...@@ -2483,13 +2483,8 @@ int qman_create_cgr(struct qman_cgr *cgr, u32 flags, ...@@ -2483,13 +2483,8 @@ int qman_create_cgr(struct qman_cgr *cgr, u32 flags,
} }
EXPORT_SYMBOL(qman_create_cgr); EXPORT_SYMBOL(qman_create_cgr);
int qman_delete_cgr(struct qman_cgr *cgr) static struct qman_portal *qman_cgr_get_affine_portal(struct qman_cgr *cgr)
{ {
unsigned long irqflags;
struct qm_mcr_querycgr cgr_state;
struct qm_mcc_initcgr local_opts;
int ret = 0;
struct qman_cgr *i;
struct qman_portal *p = get_affine_portal(); struct qman_portal *p = get_affine_portal();
if (cgr->chan != p->config->channel) { if (cgr->chan != p->config->channel) {
...@@ -2497,10 +2492,25 @@ int qman_delete_cgr(struct qman_cgr *cgr) ...@@ -2497,10 +2492,25 @@ int qman_delete_cgr(struct qman_cgr *cgr)
dev_err(p->config->dev, "CGR not owned by current portal"); dev_err(p->config->dev, "CGR not owned by current portal");
dev_dbg(p->config->dev, " create 0x%x, delete 0x%x\n", dev_dbg(p->config->dev, " create 0x%x, delete 0x%x\n",
cgr->chan, p->config->channel); cgr->chan, p->config->channel);
put_affine_portal();
ret = -EINVAL; return NULL;
goto put_portal;
} }
return p;
}
int qman_delete_cgr(struct qman_cgr *cgr)
{
unsigned long irqflags;
struct qm_mcr_querycgr cgr_state;
struct qm_mcc_initcgr local_opts;
int ret = 0;
struct qman_cgr *i;
struct qman_portal *p = qman_cgr_get_affine_portal(cgr);
if (!p)
return -EINVAL;
memset(&local_opts, 0, sizeof(struct qm_mcc_initcgr)); memset(&local_opts, 0, sizeof(struct qm_mcc_initcgr));
spin_lock_irqsave(&p->cgr_lock, irqflags); spin_lock_irqsave(&p->cgr_lock, irqflags);
list_del(&cgr->node); list_del(&cgr->node);
...@@ -2528,7 +2538,6 @@ int qman_delete_cgr(struct qman_cgr *cgr) ...@@ -2528,7 +2538,6 @@ int qman_delete_cgr(struct qman_cgr *cgr)
list_add(&cgr->node, &p->cgr_cbs); list_add(&cgr->node, &p->cgr_cbs);
release_lock: release_lock:
spin_unlock_irqrestore(&p->cgr_lock, irqflags); spin_unlock_irqrestore(&p->cgr_lock, irqflags);
put_portal:
put_affine_portal(); put_affine_portal();
return ret; return ret;
} }
...@@ -2559,6 +2568,54 @@ void qman_delete_cgr_safe(struct qman_cgr *cgr) ...@@ -2559,6 +2568,54 @@ void qman_delete_cgr_safe(struct qman_cgr *cgr)
} }
EXPORT_SYMBOL(qman_delete_cgr_safe); EXPORT_SYMBOL(qman_delete_cgr_safe);
static int qman_update_cgr(struct qman_cgr *cgr, struct qm_mcc_initcgr *opts)
{
int ret;
unsigned long irqflags;
struct qman_portal *p = qman_cgr_get_affine_portal(cgr);
if (!p)
return -EINVAL;
spin_lock_irqsave(&p->cgr_lock, irqflags);
ret = qm_modify_cgr(cgr, 0, opts);
spin_unlock_irqrestore(&p->cgr_lock, irqflags);
put_affine_portal();
return ret;
}
struct update_cgr_params {
struct qman_cgr *cgr;
struct qm_mcc_initcgr *opts;
int ret;
};
static void qman_update_cgr_smp_call(void *p)
{
struct update_cgr_params *params = p;
params->ret = qman_update_cgr(params->cgr, params->opts);
}
int qman_update_cgr_safe(struct qman_cgr *cgr, struct qm_mcc_initcgr *opts)
{
struct update_cgr_params params = {
.cgr = cgr,
.opts = opts,
};
preempt_disable();
if (qman_cgr_cpus[cgr->cgrid] != smp_processor_id())
smp_call_function_single(qman_cgr_cpus[cgr->cgrid],
qman_update_cgr_smp_call, &params,
true);
else
params.ret = qman_update_cgr(cgr, opts);
preempt_enable();
return params.ret;
}
EXPORT_SYMBOL(qman_update_cgr_safe);
/* Cleanup FQs */ /* Cleanup FQs */
static int _qm_mr_consume_and_match_verb(struct qm_portal *p, int v) static int _qm_mr_consume_and_match_verb(struct qm_portal *p, int v)
......
...@@ -1171,6 +1171,15 @@ int qman_delete_cgr(struct qman_cgr *cgr); ...@@ -1171,6 +1171,15 @@ int qman_delete_cgr(struct qman_cgr *cgr);
*/ */
void qman_delete_cgr_safe(struct qman_cgr *cgr); void qman_delete_cgr_safe(struct qman_cgr *cgr);
/**
* qman_update_cgr_safe - Modifies a congestion group object from any CPU
* @cgr: the 'cgr' object to modify
* @opts: state of the CGR settings
*
* This will select the proper CPU and modify the CGR settings.
*/
int qman_update_cgr_safe(struct qman_cgr *cgr, struct qm_mcc_initcgr *opts);
/** /**
* qman_query_cgr_congested - Queries CGR's congestion status * qman_query_cgr_congested - Queries CGR's congestion status
* @cgr: the 'cgr' object to query * @cgr: the 'cgr' object to query
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment