diff options
Diffstat (limited to 'target/linux/layerscape/patches-4.4/7216-dpaa2-evb-Fix-interrupt-handling.patch')
-rw-r--r-- | target/linux/layerscape/patches-4.4/7216-dpaa2-evb-Fix-interrupt-handling.patch | 69 |
1 files changed, 69 insertions, 0 deletions
diff --git a/target/linux/layerscape/patches-4.4/7216-dpaa2-evb-Fix-interrupt-handling.patch b/target/linux/layerscape/patches-4.4/7216-dpaa2-evb-Fix-interrupt-handling.patch new file mode 100644 index 0000000000..d3d976af98 --- /dev/null +++ b/target/linux/layerscape/patches-4.4/7216-dpaa2-evb-Fix-interrupt-handling.patch @@ -0,0 +1,69 @@ +From 4efb592d8a931669df5df04bedcae8cbc85c3700 Mon Sep 17 00:00:00 2001 +From: Razvan Stefanescu <razvan.stefanescu@freescale.com> +Date: Wed, 17 Feb 2016 16:31:01 +0200 +Subject: [PATCH 216/226] dpaa2-evb: Fix interrupt handling + +Mask only the events handled by the driver - DPDMUX_IRQ_EVENT_LINK_CHANGED. + +Use clear-on-read mechanism for the interrupt status and avoid calling +dpdmux_clear_irq_status(). Status contains the events handled (only link +state change for the moment) and masks the first 16-bits, as they are used +to store the interface ID that generated the event. + +Signed-off-by: Razvan Stefanescu <razvan.stefanescu@freescale.com> +--- + drivers/staging/fsl-dpaa2/evb/evb.c | 20 ++++++++++---------- + 1 file changed, 10 insertions(+), 10 deletions(-) + +--- a/drivers/staging/fsl-dpaa2/evb/evb.c ++++ b/drivers/staging/fsl-dpaa2/evb/evb.c +@@ -151,7 +151,9 @@ static irqreturn_t _evb_irq0_handler_thr + struct fsl_mc_io *io = priv->mc_io; + uint16_t token = priv->mux_handle; + int irq_index = DPDMUX_IRQ_INDEX_IF; +- uint32_t status = 0, clear = 0; ++ ++ /* Mask the events and the if_id reserved bits to be cleared on read */ ++ uint32_t status = DPDMUX_IRQ_EVENT_LINK_CHANGED | 0xFFFF0000; + int err; + + /* Sanity check */ +@@ -163,23 +165,21 @@ static irqreturn_t _evb_irq0_handler_thr + err = dpdmux_get_irq_status(io, 0, token, irq_index, &status); + if (unlikely(err)) { + netdev_err(netdev, "Can't get irq status (err %d)", err); +- clear = 0xffffffff; ++ err = dpdmux_clear_irq_status(io, 0, token, irq_index, ++ 0xFFFFFFFF); ++ if (unlikely(err)) ++ netdev_err(netdev, "Can't clear irq status (err %d)", ++ err); + goto out; + } + +- /* FIXME clear irq status */ +- + if (status & DPDMUX_IRQ_EVENT_LINK_CHANGED) { +- clear |= DPDMUX_IRQ_EVENT_LINK_CHANGED; +- + err = evb_links_state_update(priv); + if (unlikely(err)) + goto out; + } ++ + out: +- err = dpdmux_clear_irq_status(io, 0, token, irq_index, clear); +- if (unlikely(err)) +- netdev_err(netdev, "Can't clear irq status (err %d)", err); + return IRQ_HANDLED; + } + +@@ -191,7 +191,7 @@ static int evb_setup_irqs(struct fsl_mc_ + int err = 0; + struct fsl_mc_device_irq *irq; + const int irq_index = DPDMUX_IRQ_INDEX_IF; +- uint32_t mask = ~0x0u; /* FIXME: unmask handled irqs */ ++ uint32_t mask = DPDMUX_IRQ_EVENT_LINK_CHANGED; + + err = fsl_mc_allocate_irqs(evb_dev); + if (unlikely(err)) { |