From 74014c9a85207bb3b0093b531fb79c48801aa73c Mon Sep 17 00:00:00 2001 From: Oussama Ghorbel <ghorbel@gmail.com> Date: Mon, 28 Nov 2016 16:00:51 +0100 Subject: [PATCH 1/2] arm: add stat support to fiq This patch allows drivers that uses fiq to have a stat on the execution number of the fiq handler. For that three APIs has been defined: - fiq_kstat_enable: this function enables fiq stat and allocates required memory for it - fiq_kstat_disable: this function disable fiq stat and free its allocated memory - fiq_kstat_this_cpu_inc: This function increments the fiq stat counter of the current CPU running the fiq handler A driver may call fiq_kstat_enable at its initialization to enable fiq stat and then call fiq_kstat_this_cpu_inc from the fiq handler When the fiq stat is enabled by a driver, then /proc/interrupts shows the fiq entry as the following example: FIQ: 0 21642080 0 0 usb_fiq If the fiq stat is not enabled, the content will be similar to the old one as the following example: FIQ: usb_fiq The fiq name will be always written on the first column after the last CPU column Signed-off-by: Oussama Ghorbel <ghorbel@gmail.com> --- arch/arm/include/asm/fiq.h | 10 ++++++++++ arch/arm/kernel/fiq.c | 31 +++++++++++++++++++++++++++---- 2 files changed, 37 insertions(+), 4 deletions(-) Index: linux-rpi-4.18.4-test/arch/arm/include/asm/fiq.h =================================================================== @ linux-rpi-4.18.4-test/arch/arm/include/asm/fiq.h:35 @ struct fiq_handler { /* data for the relinquish/reacquire functions */ void *dev_id; + /* fiq stats percpu */ + unsigned int __percpu *fiq_kstat; }; extern int claim_fiq(struct fiq_handler *f); @ linux-rpi-4.18.4-test/arch/arm/include/asm/fiq.h:59 @ static inline void get_fiq_regs(struct p __get_fiq_regs(®s->ARM_r8); } +extern int fiq_kstat_enable(struct fiq_handler *fh); +extern void fiq_kstat_disable(struct fiq_handler *fh); + +static inline void fiq_kstat_this_cpu_inc(struct fiq_handler *fh) +{ + __this_cpu_inc(*fh->fiq_kstat); +} + #endif Index: linux-rpi-4.18.4-test/arch/arm/kernel/fiq.c =================================================================== --- linux-rpi-4.18.4-test.orig/arch/arm/kernel/fiq.c +++ linux-rpi-4.18.4-test/arch/arm/kernel/fiq.c @ linux-rpi-4.18.4-test/arch/arm/include/asm/fiq.h:89 @ static struct fiq_handler *current_fiq = int show_fiq_list(struct seq_file *p, int prec) { - if (current_fiq != &default_owner) - seq_printf(p, "%*s: %s\n", prec, "FIQ", - current_fiq->name); + int j; + if (current_fiq == &default_owner) + return 0; + seq_printf(p, "%*s: ", prec, "FIQ"); + for_each_online_cpu(j) { + if (current_fiq->fiq_kstat) + seq_printf(p, "%10u ", + *per_cpu_ptr(current_fiq->fiq_kstat, j)); + else + seq_printf(p, "%10s ", ""); + } + seq_printf(p, " %s\n", current_fiq->name); return 0; } @ linux-rpi-4.18.4-test/arch/arm/include/asm/fiq.h:179 @ void __init init_FIQ(int start) get_fiq_regs(&dfl_fiq_regs); fiq_start = start; } + +int fiq_kstat_enable(struct fiq_handler *fh) +{ + fh->fiq_kstat = alloc_percpu(unsigned int); + return fh->fiq_kstat != 0 ? 0 : 1; +} +EXPORT_SYMBOL(fiq_kstat_enable); + +void fiq_kstat_disable(struct fiq_handler *fh) +{ + free_percpu(fh->fiq_kstat); + fh->fiq_kstat = NULL; +} +EXPORT_SYMBOL(fiq_kstat_disable);