[PATCH 1/5] Revert "firewire: core: use mutex to coordinate concurrent calls to flush completions"

From: Takashi Sakamoto
Date: Thu Sep 12 2024 - 09:30:59 EST


This reverts commit d9605d67562505e27dcc0f71af418118d3db91e5, since this
commit is on the following reverted changes.

Signed-off-by: Takashi Sakamoto <o-takashi@xxxxxxxxxxxxx>
---
drivers/firewire/core-iso.c | 11 ++---------
drivers/firewire/ohci.c | 37 +++++++++++++++++++++++--------------
include/linux/firewire.h | 1 -
3 files changed, 25 insertions(+), 24 deletions(-)

diff --git a/drivers/firewire/core-iso.c b/drivers/firewire/core-iso.c
index 1405d2e9cb2c..9f41c78878ad 100644
--- a/drivers/firewire/core-iso.c
+++ b/drivers/firewire/core-iso.c
@@ -157,7 +157,6 @@ struct fw_iso_context *fw_iso_context_create(struct fw_card *card,
ctx->callback.sc = callback;
ctx->callback_data = callback_data;
INIT_WORK(&ctx->work, flush_completions_work);
- mutex_init(&ctx->flushing_completions_mutex);

trace_isoc_outbound_allocate(ctx, channel, speed);
trace_isoc_inbound_single_allocate(ctx, channel, header_size);
@@ -174,8 +173,6 @@ void fw_iso_context_destroy(struct fw_iso_context *ctx)
trace_isoc_inbound_multiple_destroy(ctx);

ctx->card->driver->free_iso_context(ctx);
-
- mutex_destroy(&ctx->flushing_completions_mutex);
}
EXPORT_SYMBOL(fw_iso_context_destroy);

@@ -229,7 +226,7 @@ EXPORT_SYMBOL(fw_iso_context_queue_flush);
* to process the context asynchronously, fw_iso_context_schedule_flush_completions() is available
* instead.
*
- * Context: Process context due to mutex_trylock().
+ * Context: Process context.
*/
int fw_iso_context_flush_completions(struct fw_iso_context *ctx)
{
@@ -237,11 +234,7 @@ int fw_iso_context_flush_completions(struct fw_iso_context *ctx)
trace_isoc_inbound_single_flush_completions(ctx);
trace_isoc_inbound_multiple_flush_completions(ctx);

- scoped_cond_guard(mutex_try, /* nothing to do */, &ctx->flushing_completions_mutex) {
- return ctx->card->driver->flush_iso_completions(ctx);
- }
-
- return 0;
+ return ctx->card->driver->flush_iso_completions(ctx);
}
EXPORT_SYMBOL(fw_iso_context_flush_completions);

diff --git a/drivers/firewire/ohci.c b/drivers/firewire/ohci.c
index b182998a77f4..02ff0363d3ad 100644
--- a/drivers/firewire/ohci.c
+++ b/drivers/firewire/ohci.c
@@ -166,6 +166,7 @@ struct iso_context {
struct context context;
void *header;
size_t header_length;
+ unsigned long flushing_completions;
u32 mc_buffer_bus;
u16 mc_completed;
u16 last_timestamp;
@@ -3578,23 +3579,31 @@ static void ohci_flush_queue_iso(struct fw_iso_context *base)
static int ohci_flush_iso_completions(struct fw_iso_context *base)
{
struct iso_context *ctx = container_of(base, struct iso_context, base);
+ int ret = 0;

- // Note that tasklet softIRQ is not used to process isochronous context anymore.
- context_tasklet((unsigned long)&ctx->context);
+ if (!test_and_set_bit_lock(0, &ctx->flushing_completions)) {
+ // Note that tasklet softIRQ is not used to process isochronous context anymore.
+ context_tasklet((unsigned long)&ctx->context);

- switch (base->type) {
- case FW_ISO_CONTEXT_TRANSMIT:
- case FW_ISO_CONTEXT_RECEIVE:
- if (ctx->header_length != 0)
- flush_iso_completions(ctx, FW_ISO_CONTEXT_COMPLETIONS_CAUSE_FLUSH);
- return 0;
- case FW_ISO_CONTEXT_RECEIVE_MULTICHANNEL:
- if (ctx->mc_completed != 0)
- flush_ir_buffer_fill(ctx);
- return 0;
- default:
- return -ENOSYS;
+ switch (base->type) {
+ case FW_ISO_CONTEXT_TRANSMIT:
+ case FW_ISO_CONTEXT_RECEIVE:
+ if (ctx->header_length != 0)
+ flush_iso_completions(ctx, FW_ISO_CONTEXT_COMPLETIONS_CAUSE_FLUSH);
+ break;
+ case FW_ISO_CONTEXT_RECEIVE_MULTICHANNEL:
+ if (ctx->mc_completed != 0)
+ flush_ir_buffer_fill(ctx);
+ break;
+ default:
+ ret = -ENOSYS;
+ }
+
+ clear_bit_unlock(0, &ctx->flushing_completions);
+ smp_mb__after_atomic();
}
+
+ return ret;
}

static const struct fw_card_driver ohci_driver = {
diff --git a/include/linux/firewire.h b/include/linux/firewire.h
index 19e8c5f9537c..f815d12deda0 100644
--- a/include/linux/firewire.h
+++ b/include/linux/firewire.h
@@ -512,7 +512,6 @@ union fw_iso_callback {
struct fw_iso_context {
struct fw_card *card;
struct work_struct work;
- struct mutex flushing_completions_mutex;
int type;
int channel;
int speed;
--
2.43.0