]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
firewire: core: add helper function to retire descriptors
authorTakashi Sakamoto <o-takashi@sakamocchi.jp>
Thu, 12 Sep 2024 13:30:36 +0000 (22:30 +0900)
committerTakashi Sakamoto <o-takashi@sakamocchi.jp>
Thu, 12 Sep 2024 13:30:36 +0000 (22:30 +0900)
Both IR/IT contexts use the same code to retire completed descriptors
as AT context uses.

This commit adds a helper function to reduce the duplicated codes.

Link: https://lore.kernel.org/r/20240912133038.238786-4-o-takashi@sakamocchi.jp
Signed-off-by: Takashi Sakamoto <o-takashi@sakamocchi.jp>
drivers/firewire/ohci.c

index 3a911cfb5ff31a4bd1a31cf984d061b6def53f5b..4af4c9af4fe4a8d17d82975a7a2d509571f8f778 100644 (file)
@@ -1141,9 +1141,8 @@ static struct descriptor *find_branch_descriptor(struct descriptor *d, int z)
                return d + z - 1;
 }
 
-static void context_tasklet(unsigned long data)
+static void context_retire_descriptors(struct context *ctx)
 {
-       struct context *ctx = (struct context *) data;
        struct descriptor *d, *last;
        u32 address;
        int z;
@@ -1182,45 +1181,19 @@ static void context_tasklet(unsigned long data)
        }
 }
 
+static void context_tasklet(unsigned long data)
+{
+       struct context *ctx = (struct context *) data;
+
+       context_retire_descriptors(ctx);
+}
+
 static void ohci_isoc_context_work(struct work_struct *work)
 {
        struct fw_iso_context *base = container_of(work, struct fw_iso_context, work);
        struct iso_context *isoc_ctx = container_of(base, struct iso_context, base);
-       struct context *ctx = &isoc_ctx->context;
-       struct descriptor *d, *last;
-       u32 address;
-       int z;
-       struct descriptor_buffer *desc;
-
-       desc = list_entry(ctx->buffer_list.next, struct descriptor_buffer, list);
-       last = ctx->last;
-       while (last->branch_address != 0) {
-               struct descriptor_buffer *old_desc = desc;
-
-               address = le32_to_cpu(last->branch_address);
-               z = address & 0xf;
-               address &= ~0xf;
-               ctx->current_bus = address;
-
-               // If the branch address points to a buffer outside of the current buffer, advance
-               // to the next buffer.
-               if (address < desc->buffer_bus || address >= desc->buffer_bus + desc->used)
-                       desc = list_entry(desc->list.next, struct descriptor_buffer, list);
-               d = desc->buffer + (address - desc->buffer_bus) / sizeof(*d);
-               last = find_branch_descriptor(d, z);
-
-               if (!ctx->callback(ctx, d, last))
-                       break;
 
-               if (old_desc != desc) {
-                       // If we've advanced to the next buffer, move the previous buffer to the
-                       // free list.
-                       old_desc->used = 0;
-                       guard(spinlock_irqsave)(&ctx->ohci->lock);
-                       list_move_tail(&old_desc->list, &ctx->buffer_list);
-               }
-               ctx->last = last;
-       }
+       context_retire_descriptors(&isoc_ctx->context);
 }
 
 /*