aboutsummaryrefslogtreecommitdiffstats
path: root/target
diff options
context:
space:
mode:
authorGabor Juhos <juhosg@openwrt.org>2013-12-20 11:41:20 +0000
committerGabor Juhos <juhosg@openwrt.org>2013-12-20 11:41:20 +0000
commit35d601f974050feb5463a171ab90940c0ebe8ac9 (patch)
tree0ef43836f05dea6067314e9abf9eb0611dacd9a7 /target
parent9e7d77de2de40cd6783b0db84b8554012fe3c85b (diff)
downloadupstream-35d601f974050feb5463a171ab90940c0ebe8ac9.tar.gz
upstream-35d601f974050feb5463a171ab90940c0ebe8ac9.tar.bz2
upstream-35d601f974050feb5463a171ab90940c0ebe8ac9.zip
ar71xx: ag71xx: calculate max frame len register value from the MTU
Set the MAX_FRAME_LEN register to zero in ag71xx_hw_init() and write the correct value into that from the ag71xx_open() and ag71xx_fast_reset() functions. Also recalculate the RX buffer size based on the actual maximum frame length value to optimize memory allocation. Additionaly, disallow to change the MTU value while the interface it running. Signed-off-by: Gabor Juhos <juhosg@openwrt.org> SVN-Revision: 39147
Diffstat (limited to 'target')
-rw-r--r--target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c18
1 files changed, 15 insertions, 3 deletions
diff --git a/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c b/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c
index ce05c10882..715c1cef1b 100644
--- a/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c
+++ b/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c
@@ -438,8 +438,8 @@ static void ag71xx_hw_setup(struct ag71xx *ag)
ag71xx_sb(ag, AG71XX_REG_MAC_CFG2,
MAC_CFG2_PAD_CRC_EN | MAC_CFG2_LEN_CHECK);
- /* setup max frame length */
- ag71xx_wr(ag, AG71XX_REG_MAC_MFL, ag->max_frame_len);
+ /* setup max frame length to zero */
+ ag71xx_wr(ag, AG71XX_REG_MAC_MFL, 0);
/* setup FIFO configuration registers */
ag71xx_wr(ag, AG71XX_REG_FIFO_CFG0, FIFO_CFG0_INIT);
@@ -508,6 +508,10 @@ static void ag71xx_fast_reset(struct ag71xx *ag)
ag71xx_dma_reset(ag);
ag71xx_hw_setup(ag);
+ /* setup max frame length */
+ ag71xx_wr(ag, AG71XX_REG_MAC_MFL,
+ ag71xx_max_frame_len(ag->dev->mtu));
+
ag71xx_wr(ag, AG71XX_REG_RX_DESC, rx_ds);
ag71xx_wr(ag, AG71XX_REG_TX_DESC, tx_ds);
ag71xx_wr(ag, AG71XX_REG_MII_CFG, mii_reg);
@@ -612,9 +616,14 @@ void ag71xx_link_adjust(struct ag71xx *ag)
static int ag71xx_open(struct net_device *dev)
{
struct ag71xx *ag = netdev_priv(dev);
+ unsigned int max_frame_len;
int ret;
- ag->rx_buf_size = ag->max_frame_len + NET_SKB_PAD + NET_IP_ALIGN;
+ max_frame_len = ag71xx_max_frame_len(dev->mtu);
+ ag->rx_buf_size = max_frame_len + NET_SKB_PAD + NET_IP_ALIGN;
+
+ /* setup max frame length */
+ ag71xx_wr(ag, AG71XX_REG_MAC_MFL, max_frame_len);
ret = ag71xx_rings_init(ag);
if (ret)
@@ -1063,6 +1072,9 @@ static int ag71xx_change_mtu(struct net_device *dev, int new_mtu)
if (new_mtu < 68 || max_frame_len > ag->max_frame_len)
return -EINVAL;
+ if (netif_running(dev))
+ return -EBUSY;
+
dev->mtu = new_mtu;
return 0;
}