Commit 195ef57f authored by Alex Elder's avatar Alex Elder Committed by David S. Miller

net: ipa: do not clear interrupt in gsi_channel_start()

In gsi_channel_start() there is harmless-looking comment "Clear the
channel's event ring interrupt in case it's pending".  The intent
was to avoid getting spurious interrupts when first bringing up a
channel.

However we now use channel stop/start to implement suspend and
resume, and an interrupt pending at the time we resume is actually
something we don't want to ignore.

The very first time we bring up the channel we do not expect an
interrupt to be pending, and even if it were, the effect would
simply be to schedule NAPI on that channel, which would find nothing
to do, which is not a problem.

Stop clearing any pending IEOB interrupt in gsi_channel_start().
That leaves one caller of the trivial function gsi_isr_ieob_clear().
Get rid of that function and just open-code it in gsi_isr_ieob()
instead.

This fixes a problem where suspend/resume IPA v4.2 would get stuck
when resuming after a suspend.
Signed-off-by: default avatarAlex Elder <elder@linaro.org>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent a4f48458
...@@ -238,11 +238,6 @@ static void gsi_irq_ieob_enable(struct gsi *gsi, u32 evt_ring_id) ...@@ -238,11 +238,6 @@ static void gsi_irq_ieob_enable(struct gsi *gsi, u32 evt_ring_id)
iowrite32(val, gsi->virt + GSI_CNTXT_SRC_IEOB_IRQ_MSK_OFFSET); iowrite32(val, gsi->virt + GSI_CNTXT_SRC_IEOB_IRQ_MSK_OFFSET);
} }
static void gsi_isr_ieob_clear(struct gsi *gsi, u32 mask)
{
iowrite32(mask, gsi->virt + GSI_CNTXT_SRC_IEOB_IRQ_CLR_OFFSET);
}
static void gsi_irq_ieob_disable(struct gsi *gsi, u32 evt_ring_id) static void gsi_irq_ieob_disable(struct gsi *gsi, u32 evt_ring_id)
{ {
u32 val; u32 val;
...@@ -777,7 +772,6 @@ static void gsi_channel_deprogram(struct gsi_channel *channel) ...@@ -777,7 +772,6 @@ static void gsi_channel_deprogram(struct gsi_channel *channel)
int gsi_channel_start(struct gsi *gsi, u32 channel_id) int gsi_channel_start(struct gsi *gsi, u32 channel_id)
{ {
struct gsi_channel *channel = &gsi->channel[channel_id]; struct gsi_channel *channel = &gsi->channel[channel_id];
u32 evt_ring_id = channel->evt_ring_id;
int ret; int ret;
mutex_lock(&gsi->mutex); mutex_lock(&gsi->mutex);
...@@ -786,9 +780,6 @@ int gsi_channel_start(struct gsi *gsi, u32 channel_id) ...@@ -786,9 +780,6 @@ int gsi_channel_start(struct gsi *gsi, u32 channel_id)
mutex_unlock(&gsi->mutex); mutex_unlock(&gsi->mutex);
/* Clear the channel's event ring interrupt in case it's pending */
gsi_isr_ieob_clear(gsi, BIT(evt_ring_id));
gsi_channel_thaw(channel); gsi_channel_thaw(channel);
return ret; return ret;
...@@ -1093,7 +1084,7 @@ static void gsi_isr_ieob(struct gsi *gsi) ...@@ -1093,7 +1084,7 @@ static void gsi_isr_ieob(struct gsi *gsi)
u32 event_mask; u32 event_mask;
event_mask = ioread32(gsi->virt + GSI_CNTXT_SRC_IEOB_IRQ_OFFSET); event_mask = ioread32(gsi->virt + GSI_CNTXT_SRC_IEOB_IRQ_OFFSET);
gsi_isr_ieob_clear(gsi, event_mask); iowrite32(event_mask, gsi->virt + GSI_CNTXT_SRC_IEOB_IRQ_CLR_OFFSET);
while (event_mask) { while (event_mask) {
u32 evt_ring_id = __ffs(event_mask); u32 evt_ring_id = __ffs(event_mask);
......
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