From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 0519F31A072 for ; Thu, 26 Mar 2026 21:58:05 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1774562286; cv=none; b=dlmRnPlpJaRxJNQ6W9x0Sl406hUPIPYxk/shSi3cuyhTkiBwv/uWfSqNOh01TVrL2S084Hfhpn4Ot+g6YeXKYEgbTzoQ5zoPWOY0isCOIso3KiDN46Hy0eBlMNtYPdIlGlNymigav1/yeQM9IXXro5vYp5DKKc14TysjnnsmJTk= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1774562286; c=relaxed/simple; bh=qkLJcVWRuoxDtOd4Mc/0vtTK56aPHxNVu27G63U6aKs=; h=Date:Message-ID:From:To:Cc:Subject:References:MIME-Version: Content-Type; b=uQUoGkcSb7BTwT3W7+Wnzvv1uu23gkVZvtXotuqxVPveacrvbnrTOCXT7nj6eNJK5kdsVHhl9z50ty0j42gbH8AuyweMwYkcUIKU025k1jeQ4YhTwvA9urcnIJL0wYzGBpcXa434jxF+Bq6TgXOUPEr5l9B3xYXud9VY5CVHNHA= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=fIDOpvXm; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="fIDOpvXm" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 62731C116C6; Thu, 26 Mar 2026 21:58:04 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1774562285; bh=qkLJcVWRuoxDtOd4Mc/0vtTK56aPHxNVu27G63U6aKs=; h=Date:From:To:Cc:Subject:References:From; b=fIDOpvXmoyAI2atCf6319HAvGTeIJD0lKSNpX8WJv2P3ToUJmbZcfdLs4ko7OrZqC HSlZW3zyjmYykuP+k1TSOXcGH3ErkeI+1Yl8j9Ib6lkHpbbieJgth2C4Yajpq7kgYZ oamrq3dFvsbuWcN1XLnPRQ4m33QIqv2ucJn3v4F7+gNi+J5ZbF/KiosfMkGzROPyIM 9ZChIucH/BPexr27po0PQRTBLQeUETMGDE9BqolrMvInX4ARfrBh4KtyOIPXDeJR65 1MErb3Fpu5AG2kpnlIFRbOt6J5o/Mq+DVmnXB2HOqR8TKvfRlYiN99mVDartRDZTKO aGr2psa6cvbtg== Date: Thu, 26 Mar 2026 22:57:59 +0100 Message-ID: <20260326215037.119195934@kernel.org> User-Agent: quilt/0.68 From: Thomas Gleixner To: LKML Cc: x86@kernel.org, Michael Kelley , Jan Kiszka , Kieran Bingham , Florian Fainelli , Dmitry Ilvokhin , Radu Rendec Subject: [patch V3 13/14] genirq/proc: Runtime size the chip name References: <20260326214345.019130211@kernel.org> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 The chip name column in the /proc/interrupt output is 8 characters and right aligned, which causes visual clutter due to the fixed length and the alignment. Many interrupt chips, e.g. PCI/MSI[X] have way longer names. Update the length when a chip is assigned to an interrupt and utilize this information for the output. Align it left so all chip names start at the begin of the column. Update the GDB script as well. Signed-off-by: Thomas Gleixner Cc: Jan Kiszka Cc: Kieran Bingham Cc: Florian Fainelli --- V3: New patch --- kernel/irq/chip.c | 6 ++++-- kernel/irq/internals.h | 8 ++------ kernel/irq/irqdomain.c | 3 +++ kernel/irq/proc.c | 33 ++++++++++++++++++++++++++++----- kernel/irq/proc.h | 9 +++++++++ scripts/gdb/linux/interrupts.py | 25 ++++++++++++++++--------- 6 files changed, 62 insertions(+), 22 deletions(-) --- a/kernel/irq/chip.c +++ b/kernel/irq/chip.c @@ -46,9 +46,11 @@ int irq_set_chip(unsigned int irq, const scoped_irqdesc->irq_data.chip = (struct irq_chip *)(chip ?: &no_irq_chip); ret = 0; } - /* For !CONFIG_SPARSE_IRQ make the irq show up in allocated_irqs. */ - if (!ret) + if (!ret) { + /* For !CONFIG_SPARSE_IRQ make the irq show up in allocated_irqs. */ irq_mark_irq(irq); + irq_proc_update_chip(chip); + } return ret; } EXPORT_SYMBOL(irq_set_chip); --- a/kernel/irq/internals.h +++ b/kernel/irq/internals.h @@ -12,6 +12,8 @@ #include #include +#include "proc.h" + #ifdef CONFIG_SPARSE_IRQ # define MAX_SPARSE_IRQS INT_MAX #else @@ -149,12 +151,6 @@ static inline void unregister_handler_pr static inline void irq_proc_update_valid(struct irq_desc *desc) { } #endif -#if defined(CONFIG_PROC_FS) && defined(CONFIG_GENERIC_IRQ_SHOW) -void irq_proc_calc_prec(void); -#else -static inline void irq_proc_calc_prec(void) { } -#endif - struct irq_desc *irq_find_desc_at_or_after(unsigned int offset); extern bool irq_can_set_affinity_usr(unsigned int irq); --- a/kernel/irq/irqdomain.c +++ b/kernel/irq/irqdomain.c @@ -20,6 +20,8 @@ #include #include +#include "proc.h" + static LIST_HEAD(irq_domain_list); static DEFINE_MUTEX(irq_domain_mutex); @@ -1532,6 +1534,7 @@ int irq_domain_set_hwirq_and_chip(struct irq_data->chip = (struct irq_chip *)(chip ? chip : &no_irq_chip); irq_data->chip_data = chip_data; + irq_proc_update_chip(chip); return 0; } EXPORT_SYMBOL_GPL(irq_domain_set_hwirq_and_chip); --- a/kernel/irq/proc.c +++ b/kernel/irq/proc.c @@ -456,10 +456,14 @@ int __weak arch_show_interrupts(struct s return 0; } +static DEFINE_RAW_SPINLOCK(irq_proc_constraints_lock); + static struct irq_proc_constraints { unsigned int num_prec; + unsigned int chip_width; } irq_proc_constraints __read_mostly = { .num_prec = 3, + .chip_width = 8, }; #ifndef ACTUAL_NR_IRQS @@ -472,7 +476,23 @@ void irq_proc_calc_prec(void) for (prec = 3, n = 1000; prec < 10 && n <= total_nr_irqs; ++prec) n *= 10; - WRITE_ONCE(irq_proc_constraints.num_prec, prec); + + guard(raw_spinlock_irqsave)(&irq_proc_constraints_lock); + if (prec > irq_proc_constraints.num_prec) + WRITE_ONCE(irq_proc_constraints.num_prec, prec); +} + +void irq_proc_update_chip(const struct irq_chip *chip) +{ + unsigned int len = chip && chip->name ? strlen(chip->name) : 0; + + if (!len || len <= READ_ONCE(irq_proc_constraints.chip_width)) + return; + + /* Can be invoked from interrupt disabled contexts */ + guard(raw_spinlock_irqsave)(&irq_proc_constraints_lock); + if (len > irq_proc_constraints.chip_width) + WRITE_ONCE(irq_proc_constraints.chip_width, len); } #define ZSTR1 " 0" @@ -513,6 +533,7 @@ void irq_proc_emit_counts(struct seq_fil int show_interrupts(struct seq_file *p, void *v) { + unsigned int chip_width = READ_ONCE(irq_proc_constraints.chip_width); unsigned int prec = READ_ONCE(irq_proc_constraints.num_prec); int i = *(loff_t *) v, j; struct irqaction *action; @@ -548,18 +569,20 @@ int show_interrupts(struct seq_file *p, irq_proc_emit_counts(p, &desc->kstat_irqs->cnt); else irq_proc_emit_zero_counts(p, num_online_cpus()); - seq_putc(p, ' '); + + /* Enforce a visual gap */ + seq_write(p, " ", 2); guard(raw_spinlock_irq)(&desc->lock); if (desc->irq_data.chip) { if (desc->irq_data.chip->irq_print_chip) desc->irq_data.chip->irq_print_chip(&desc->irq_data, p); else if (desc->irq_data.chip->name) - seq_printf(p, "%8s", desc->irq_data.chip->name); + seq_printf(p, "%-*s", chip_width, desc->irq_data.chip->name); else - seq_printf(p, "%8s", "-"); + seq_printf(p, "%-*s", chip_width, "-"); } else { - seq_printf(p, "%8s", "None"); + seq_printf(p, "%-*s", chip_width, "None"); } seq_putc(p, ' '); --- /dev/null +++ b/kernel/irq/proc.h @@ -0,0 +1,9 @@ +/* SPDX-License-Identifier: GPL-2.0 */ + +#if defined(CONFIG_PROC_FS) && defined(CONFIG_GENERIC_IRQ_SHOW) +void irq_proc_calc_prec(void); +void irq_proc_update_chip(const struct irq_chip *chip); +#else +static inline void irq_proc_calc_prec(void) { } +static inline void irq_proc_update_chip(const struct irq_chip *chip) { } +#endif --- a/scripts/gdb/linux/interrupts.py +++ b/scripts/gdb/linux/interrupts.py @@ -20,7 +20,7 @@ irq_desc_type = utils.CachedType("struct def irqd_is_level(desc): return desc['irq_data']['common']['state_use_accessors'] & constants.LX_IRQD_LEVEL -def show_irq_desc(prec, irq): +def show_irq_desc(prec, chip_width, irq): text = "" desc = mapletree.mtree_load(gdb.parse_and_eval("&sparse_irqs"), irq) @@ -48,7 +48,7 @@ irq_desc_type = utils.CachedType("struct count = cpus.per_cpu(desc['kstat_irqs'], cpu)['cnt'] else: count = 0 - text += "%10u" % (count) + text += "%10u " % (count) name = "None" if desc['irq_data']['chip']: @@ -58,7 +58,7 @@ irq_desc_type = utils.CachedType("struct else: name = "-" - text += " %8s" % (name) + text += " %-*s" % (chip_width, name) if desc['irq_data']['domain']: text += " %*lu" % (prec, desc['irq_data']['hwirq']) @@ -179,11 +179,18 @@ irq_desc_type = utils.CachedType("struct def invoke(self, arg, from_tty): nr_irqs = gdb.parse_and_eval("total_nr_irqs") - prec = 3 - j = 1000 - while prec < 10 and j <= nr_irqs: - prec += 1 - j *= 10 + constr = utils.gdb_eval_or_none('irq_proc_constraints') + + if constr: + prec = int(constr['num_prec']) + chip_width = int(constr['chip_width']) + else: + prec = 3 + j = 1000 + while prec < 10 and j <= nr_irqs: + prec += 1 + j *= 10 + chip_width = 8 gdb.write("%*s" % (prec + 8, "")) for cpu in cpus.each_online_cpu(): @@ -194,7 +201,7 @@ irq_desc_type = utils.CachedType("struct raise gdb.GdbError("Unable to find the sparse IRQ tree, is CONFIG_SPARSE_IRQ enabled?") for irq in range(nr_irqs): - gdb.write(show_irq_desc(prec, irq)) + gdb.write(show_irq_desc(prec, chip_width, irq)) gdb.write(arch_show_interrupts(prec))