From nobody Fri Oct 3 23:08:23 2025 Received: from galois.linutronix.de (Galois.linutronix.de [193.142.43.55]) (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 D997C2EFDBB for ; Sat, 23 Aug 2025 16:39:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=193.142.43.55 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755967195; cv=none; b=ScDVJ08oRIBC8UXFZn4DJ1DD7dwz9UISOGEq+/rzZz+ZYO4Wi2Rbdq6X63z4Czf8NIIfDjD4oq9ah8xdErjwUx+Q6jWS1lTccsbb6cw4hRhVTvljipp7R/HsPHFuia9Uk9f5srtrdUp8Ru3ym+chuF7exjTv2hXHKegxAumY5Rs= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755967195; c=relaxed/simple; bh=ib147srNtRaGfMjNJX6VP8Nrd59NNxlfgAx9sJK6GmM=; h=Message-ID:From:To:Cc:Subject:References:MIME-Version: Content-Type:Date; b=kNQfvGmlMo8VlTNkQ7hfGeA8XGky6b6vHUVrHKarBCDWtm34aBLcUcnBgwyMtxHb3KOepqxz0+15mwCnKeIz2+QRYl4TK4lu0oMKeaVURiVLxGBRGJpGR9G0wtJNtoymyzd429Ts3ia+952hJoET7CVEkren+mCxhLDAXvCb3dA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=linutronix.de; spf=pass smtp.mailfrom=linutronix.de; dkim=pass (2048-bit key) header.d=linutronix.de header.i=@linutronix.de header.b=2ztJn4vo; dkim=permerror (0-bit key) header.d=linutronix.de header.i=@linutronix.de header.b=ua3Gw0jp; arc=none smtp.client-ip=193.142.43.55 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=linutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=linutronix.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=linutronix.de header.i=@linutronix.de header.b="2ztJn4vo"; dkim=permerror (0-bit key) header.d=linutronix.de header.i=@linutronix.de header.b="ua3Gw0jp" Message-ID: <20250823161654.421576400@linutronix.de> DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linutronix.de; s=2020; t=1755967192; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: references:references; bh=GN7N/WjuobM3/hdkgPG84P+YkkU3yzsHrdvAdHmio98=; b=2ztJn4vomKVRfle7FKcGlnOJiijZNyTamAaoWz7sBv2UQMgoI3Q7jXaCCCV/CbO+NMLQHz ll5l62uxG4I+mh2w3qSSNR/YxPXdMObH7BakpMFUUc9CJPP8zWst9SLusk/5FYW8B/nVzo 8dd0t4ESiJAaxj5jNVkHEx8Y5kVRTTNRMJQKV1I/pKrXppqLokH4Fyc0kt5+eUQekCA7Gq qoHDxh2NrFGTWHWJ0wbWCYrkNt1wf5/2Lxl1Qxs9x9F0+KdMD8heg65zNSfdt/J6hvQovi zvzz2lJFs5FDHlMMp35mNfoUvBbe4pg8vz0PoKQnCzcZqh7lBHohsMR1zYfpvQ== DKIM-Signature: v=1; a=ed25519-sha256; c=relaxed/relaxed; d=linutronix.de; s=2020e; t=1755967192; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: references:references; bh=GN7N/WjuobM3/hdkgPG84P+YkkU3yzsHrdvAdHmio98=; b=ua3Gw0jpMOxUfC3Cu4w1bUhpHhBj0jR67V/b2m9X5swCzHQmhsP1jUyA7eFYdhDm+aCxri P+f29T/zeFcPzSDw== From: Thomas Gleixner To: LKML Cc: Jens Axboe , Peter Zijlstra , Mathieu Desnoyers , "Paul E. McKenney" , Boqun Feng , Paolo Bonzini , Sean Christopherson , Wei Liu , Dexuan Cui , x86@kernel.org, Arnd Bergmann , Heiko Carstens , Christian Borntraeger , Sven Schnelle , Huacai Chen , Paul Walmsley , Palmer Dabbelt Subject: [patch V2 18/37] rseq: Provide static branch for runtime debugging References: <20250823161326.635281786@linutronix.de> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Date: Sat, 23 Aug 2025 18:39:50 +0200 (CEST) Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Config based debug is rarely turned on and is not available easily when things go wrong. Provide a static branch to allow permanent integration of debug mechanisms along with the usual toggles in Kconfig, command line and debugfs. Requested-by: Peter Zijlstra Signed-off-by: Thomas Gleixner Reviewed-by: Mathieu Desnoyers --- Documentation/admin-guide/kernel-parameters.txt | 4 + include/linux/rseq_entry.h | 3=20 init/Kconfig | 14 ++++ kernel/rseq.c | 73 +++++++++++++++++++= +++-- 4 files changed, 90 insertions(+), 4 deletions(-) --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -6443,6 +6443,10 @@ Memory area to be used by remote processor image, managed by CMA. =20 + rseq_debug=3D [KNL] Enable or disable restartable sequence + debug mode. Defaults to CONFIG_RSEQ_DEBUG_DEFAULT_ENABLE. + Format: + rt_group_sched=3D [KNL] Enable or disable SCHED_RR/FIFO group scheduling when CONFIG_RT_GROUP_SCHED=3Dy. Defaults to !CONFIG_RT_GROUP_SCHED_DEFAULT_DISABLED. --- a/include/linux/rseq_entry.h +++ b/include/linux/rseq_entry.h @@ -34,6 +34,7 @@ DECLARE_PER_CPU(struct rseq_stats, rseq_ #endif /* !CONFIG_RSEQ_STATS */ =20 #ifdef CONFIG_RSEQ +#include #include =20 #include @@ -66,6 +67,8 @@ static inline void rseq_trace_ip_fixup(u unsigned long offset, unsigned long abort_ip) { } #endif /* !CONFIG_TRACEPOINT */ =20 +DECLARE_STATIC_KEY_MAYBE(CONFIG_RSEQ_DEBUG_DEFAULT_ENABLE, rseq_debug_enab= led); + static __always_inline void rseq_note_user_irq_entry(void) { if (IS_ENABLED(CONFIG_GENERIC_IRQ_ENTRY)) --- a/init/Kconfig +++ b/init/Kconfig @@ -1893,10 +1893,24 @@ config RSEQ_STATS =20 If unsure, say N. =20 +config RSEQ_DEBUG_DEFAULT_ENABLE + default n + bool "Enable restartable sequences debug mode by default" if EXPERT + depends on RSEQ + help + This enables the static branch for debug mode of restartable + sequences. + + This also can be controlled on the kernel command line via the + command line parameter "rseq_debug=3D0/1" and through debugfs. + + If unsure, say N. + config DEBUG_RSEQ default n bool "Enable debugging of rseq() system call" if EXPERT depends on RSEQ && DEBUG_KERNEL + select RSEQ_DEBUG_DEFAULT_ENABLE help Enable extra debugging checks for the rseq system call. =20 --- a/kernel/rseq.c +++ b/kernel/rseq.c @@ -95,6 +95,27 @@ RSEQ_CS_FLAG_NO_RESTART_ON_SIGNAL | \ RSEQ_CS_FLAG_NO_RESTART_ON_MIGRATE) =20 +DEFINE_STATIC_KEY_MAYBE(CONFIG_RSEQ_DEBUG_DEFAULT_ENABLE, rseq_debug_enabl= ed); + +static inline void rseq_control_debug(bool on) +{ + if (on) + static_branch_enable(&rseq_debug_enabled); + else + static_branch_disable(&rseq_debug_enabled); +} + +static int __init rseq_setup_debug(char *str) +{ + bool on; + + if (kstrtobool(str, &on)) + return -EINVAL; + rseq_control_debug(on); + return 0; +} +__setup("rseq_debug=3D", rseq_setup_debug); + #ifdef CONFIG_TRACEPOINTS /* * Out of line, so the actual update functions can be in a header to be @@ -112,10 +133,11 @@ void __rseq_trace_ip_fixup(unsigned long } #endif /* CONFIG_TRACEPOINTS */ =20 +#ifdef CONFIG_DEBUG_FS #ifdef CONFIG_RSEQ_STATS DEFINE_PER_CPU(struct rseq_stats, rseq_stats); =20 -static int rseq_debug_show(struct seq_file *m, void *p) +static int rseq_stats_show(struct seq_file *m, void *p) { struct rseq_stats stats =3D { }; unsigned int cpu; @@ -140,14 +162,56 @@ static int rseq_debug_show(struct seq_fi return 0; } =20 +static int rseq_stats_open(struct inode *inode, struct file *file) +{ + return single_open(file, rseq_stats_show, inode->i_private); +} + +static const struct file_operations stat_ops =3D { + .open =3D rseq_stats_open, + .read =3D seq_read, + .llseek =3D seq_lseek, + .release =3D single_release, +}; + +static int __init rseq_stats_init(struct dentry *root_dir) +{ + debugfs_create_file("stats", 0444, root_dir, NULL, &stat_ops); + return 0; +} +#else +static inline void rseq_stats_init(struct dentry *root_dir) { } +#endif /* CONFIG_RSEQ_STATS */ + +static int rseq_debug_show(struct seq_file *m, void *p) +{ + bool on =3D static_branch_unlikely(&rseq_debug_enabled); + + seq_printf(m, "%d\n", on); + return 0; +} + +static ssize_t rseq_debug_write(struct file *file, const char __user *ubuf, + size_t count, loff_t *ppos) +{ + bool on; + + if (kstrtobool_from_user(ubuf, count, &on)) + return -EINVAL; + + rseq_control_debug(on); + return count; +} + static int rseq_debug_open(struct inode *inode, struct file *file) { return single_open(file, rseq_debug_show, inode->i_private); } =20 -static const struct file_operations dfs_ops =3D { +static const struct file_operations debug_ops =3D { .open =3D rseq_debug_open, .read =3D seq_read, + .write =3D rseq_debug_write, .llseek =3D seq_lseek, .release =3D single_release, }; @@ -156,11 +220,12 @@ static int __init rseq_debugfs_init(void { struct dentry *root_dir =3D debugfs_create_dir("rseq", NULL); =20 - debugfs_create_file("stats", 0444, root_dir, NULL, &dfs_ops); + debugfs_create_file("debug", 0644, root_dir, NULL, &debug_ops); + rseq_stats_init(root_dir); return 0; } __initcall(rseq_debugfs_init); -#endif /* CONFIG_RSEQ_STATS */ +#endif /* CONFIG_DEBUG_FS */ =20 #ifdef CONFIG_DEBUG_RSEQ static struct rseq *rseq_kernel_fields(struct task_struct *t)