summaryrefslogtreecommitdiff
path: root/drivers/net/ethernet/freescale/dpa
diff options
context:
space:
mode:
authorIoana Radulescu <ruxandra.radulescu@freescale.com>2013-08-23 09:01:27 (GMT)
committerRivera Jose-B46482 <German.Rivera@freescale.com>2013-09-11 23:34:21 (GMT)
commit64ff8c982e3271f7849e8b1db8c2eef2d470a9c3 (patch)
tree5fcb498f6e1f55a74dd74ebe424b0d307591ba3b /drivers/net/ethernet/freescale/dpa
parent1ae3f770820021fe8a2ff8ec5dab2b2f0ce7b05c (diff)
downloadlinux-fsl-qoriq-64ff8c982e3271f7849e8b1db8c2eef2d470a9c3.tar.xz
dpaa_eth: Fix draining of buffer pools
When draining buffers in batches of eight, we must take into account the fact that BMan will return an error code if there are less than eight buffers left in the pool; when this happens, drain the remaining buffers one by one. And since we're at buffer pool cleanup, make sure allocated bpools get freed in case of errors inside the probe function. Signed-off-by: Ioana Radulescu <ruxandra.radulescu@freescale.com> Reviewed-on: http://git.am.freescale.net:8181/4191 Reviewed-by: Bucur Madalin-Cristian-B32716 <madalin.bucur@freescale.com> Change-Id: If264ca3dd4a8287bc5e5ee4e1c3a10ffe18663b7 Reviewed-on: http://git.am.freescale.net:8181/4657 Reviewed-by: Bogdan Hamciuc <bogdan.hamciuc@freescale.com> Tested-by: Review Code-CDREVIEW <CDREVIEW@freescale.com> Reviewed-by: Rivera Jose-B46482 <German.Rivera@freescale.com>
Diffstat (limited to 'drivers/net/ethernet/freescale/dpa')
-rw-r--r--drivers/net/ethernet/freescale/dpa/dpaa_eth.c4
-rw-r--r--drivers/net/ethernet/freescale/dpa/dpaa_eth_common.c20
2 files changed, 20 insertions, 4 deletions
diff --git a/drivers/net/ethernet/freescale/dpa/dpaa_eth.c b/drivers/net/ethernet/freescale/dpa/dpaa_eth.c
index 3a5ec61..bcb51fb 100644
--- a/drivers/net/ethernet/freescale/dpa/dpaa_eth.c
+++ b/drivers/net/ethernet/freescale/dpa/dpaa_eth.c
@@ -711,7 +711,7 @@ dpaa_eth_priv_probe(struct platform_device *_of_dev)
net_dev = alloc_etherdev_mq(sizeof(*priv), DPAA_ETH_TX_QUEUES);
if (!net_dev) {
dev_err(dev, "alloc_etherdev_mq() failed\n");
- return -ENOMEM;
+ goto alloc_etherdev_mq_failed;
}
/* Do this here, so we can be verbose early */
@@ -869,6 +869,8 @@ mac_probe_failed:
dev_set_drvdata(dev, NULL);
if (net_dev)
free_netdev(net_dev);
+alloc_etherdev_mq_failed:
+ devm_kfree(dev, dpa_bp);
return err;
}
diff --git a/drivers/net/ethernet/freescale/dpa/dpaa_eth_common.c b/drivers/net/ethernet/freescale/dpa/dpaa_eth_common.c
index 4c367bc..6906c07 100644
--- a/drivers/net/ethernet/freescale/dpa/dpaa_eth_common.c
+++ b/drivers/net/ethernet/freescale/dpa/dpaa_eth_common.c
@@ -474,6 +474,8 @@ int __cold dpa_remove(struct platform_device *of_dev)
free_percpu(priv->percpu_priv);
dpa_bp_free(priv, priv->dpa_bp);
+ devm_kfree(dev, priv->dpa_bp);
+
if (priv->buf_layout)
devm_kfree(dev, priv->buf_layout);
@@ -710,13 +712,25 @@ pdev_register_failed:
void dpa_bp_drain(struct dpa_bp *bp)
{
- int num;
+ int ret, num = 8;
do {
struct bm_buffer bmb[8];
int i;
- num = bman_acquire(bp->pool, bmb, 8, 0);
+ ret = bman_acquire(bp->pool, bmb, 8, 0);
+ if (ret < 0) {
+ if (num == 8) {
+ /* we have less than 8 buffers left;
+ * drain them one by one
+ */
+ num = 1;
+ continue;
+ } else {
+ /* Pool is fully drained */
+ break;
+ }
+ }
for (i = 0; i < num; i++) {
dma_addr_t addr = bm_buf_addr(&bmb[i]);
@@ -726,7 +740,7 @@ void dpa_bp_drain(struct dpa_bp *bp)
_dpa_bp_free_buf(phys_to_virt(addr));
}
- } while (num == 8);
+ } while (ret > 0);
}
static void __cold __attribute__((nonnull))