From: Greg Kroah-Hartman Date: Sat, 28 Jan 2023 09:29:01 +0000 (+0100) Subject: 6.1-stable patches X-Git-Tag: v5.10.166~53 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=13782956f27d0828b26186341239513e83a5e47f;p=thirdparty%2Fkernel%2Fstable-queue.git 6.1-stable patches added patches: cifs-fix-oops-due-to-uncleared-server-smbd_conn-in-reconnect.patch ftrace-export-ftrace_free_filter-to-modules.patch ftrace-scripts-update-the-instructions-for-ftrace-bisect.sh.patch module-don-t-wait-for-going-modules.patch trace_events_hist-add-check-for-return-value-of-create_hist_field.patch tracing-make-sure-trace_printk-can-output-as-soon-as-it-can-be-used.patch --- diff --git a/queue-6.1/cifs-fix-oops-due-to-uncleared-server-smbd_conn-in-reconnect.patch b/queue-6.1/cifs-fix-oops-due-to-uncleared-server-smbd_conn-in-reconnect.patch new file mode 100644 index 00000000000..64a0734729f --- /dev/null +++ b/queue-6.1/cifs-fix-oops-due-to-uncleared-server-smbd_conn-in-reconnect.patch @@ -0,0 +1,37 @@ +From b7ab9161cf5ddc42a288edf9d1a61f3bdffe17c7 Mon Sep 17 00:00:00 2001 +From: David Howells +Date: Wed, 25 Jan 2023 14:02:13 +0000 +Subject: cifs: Fix oops due to uncleared server->smbd_conn in reconnect + +From: David Howells + +commit b7ab9161cf5ddc42a288edf9d1a61f3bdffe17c7 upstream. + +In smbd_destroy(), clear the server->smbd_conn pointer after freeing the +smbd_connection struct that it points to so that reconnection doesn't get +confused. + +Fixes: 8ef130f9ec27 ("CIFS: SMBD: Implement function to destroy a SMB Direct connection") +Cc: stable@vger.kernel.org +Reviewed-by: Paulo Alcantara (SUSE) +Acked-by: Tom Talpey +Signed-off-by: David Howells +Cc: Long Li +Cc: Pavel Shilovsky +Cc: Ronnie Sahlberg +Signed-off-by: Steve French +Signed-off-by: Greg Kroah-Hartman +--- + fs/cifs/smbdirect.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/fs/cifs/smbdirect.c ++++ b/fs/cifs/smbdirect.c +@@ -1405,6 +1405,7 @@ void smbd_destroy(struct TCP_Server_Info + destroy_workqueue(info->workqueue); + log_rdma_event(INFO, "rdma session destroyed\n"); + kfree(info); ++ server->smbd_conn = NULL; + } + + /* diff --git a/queue-6.1/ftrace-export-ftrace_free_filter-to-modules.patch b/queue-6.1/ftrace-export-ftrace_free_filter-to-modules.patch new file mode 100644 index 00000000000..9ea88447327 --- /dev/null +++ b/queue-6.1/ftrace-export-ftrace_free_filter-to-modules.patch @@ -0,0 +1,128 @@ +From 8be9fbd5345da52f4a74f7f81d55ff9fa0a2958e Mon Sep 17 00:00:00 2001 +From: Mark Rutland +Date: Tue, 3 Jan 2023 12:49:11 +0000 +Subject: ftrace: Export ftrace_free_filter() to modules + +From: Mark Rutland + +commit 8be9fbd5345da52f4a74f7f81d55ff9fa0a2958e upstream. + +Setting filters on an ftrace ops results in some memory being allocated +for the filter hashes, which must be freed before the ops can be freed. +This can be done by removing every individual element of the hash by +calling ftrace_set_filter_ip() or ftrace_set_filter_ips() with `remove` +set, but this is somewhat error prone as it's easy to forget to remove +an element. + +Make it easier to clean this up by exporting ftrace_free_filter(), which +can be used to clean up all of the filter hashes after an ftrace_ops has +been unregistered. + +Using this, fix the ftrace-direct* samples to free hashes prior to being +unloaded. All other code either removes individual filters explicitly or +is built-in and already calls ftrace_free_filter(). + +Link: https://lkml.kernel.org/r/20230103124912.2948963-3-mark.rutland@arm.com + +Cc: stable@vger.kernel.org +Cc: Florent Revest +Cc: Masami Hiramatsu +Fixes: e1067a07cfbc ("ftrace/samples: Add module to test multi direct modify interface") +Fixes: 5fae941b9a6f ("ftrace/samples: Add multi direct interface test module") +Reviewed-by: Masami Hiramatsu (Google) +Reviewed-by: Steven Rostedt (Google) +Signed-off-by: Mark Rutland +Signed-off-by: Steven Rostedt (Google) +Signed-off-by: Greg Kroah-Hartman +--- + kernel/trace/ftrace.c | 23 ++++++++++++++++++++++- + samples/ftrace/ftrace-direct-multi-modify.c | 1 + + samples/ftrace/ftrace-direct-multi.c | 1 + + 3 files changed, 24 insertions(+), 1 deletion(-) + +--- a/kernel/trace/ftrace.c ++++ b/kernel/trace/ftrace.c +@@ -1248,12 +1248,17 @@ static void free_ftrace_hash_rcu(struct + call_rcu(&hash->rcu, __free_ftrace_hash_rcu); + } + ++/** ++ * ftrace_free_filter - remove all filters for an ftrace_ops ++ * @ops - the ops to remove the filters from ++ */ + void ftrace_free_filter(struct ftrace_ops *ops) + { + ftrace_ops_init(ops); + free_ftrace_hash(ops->func_hash->filter_hash); + free_ftrace_hash(ops->func_hash->notrace_hash); + } ++EXPORT_SYMBOL_GPL(ftrace_free_filter); + + static struct ftrace_hash *alloc_ftrace_hash(int size_bits) + { +@@ -5828,6 +5833,10 @@ EXPORT_SYMBOL_GPL(modify_ftrace_direct_m + * + * Filters denote which functions should be enabled when tracing is enabled + * If @ip is NULL, it fails to update filter. ++ * ++ * This can allocate memory which must be freed before @ops can be freed, ++ * either by removing each filtered addr or by using ++ * ftrace_free_filter(@ops). + */ + int ftrace_set_filter_ip(struct ftrace_ops *ops, unsigned long ip, + int remove, int reset) +@@ -5847,7 +5856,11 @@ EXPORT_SYMBOL_GPL(ftrace_set_filter_ip); + * + * Filters denote which functions should be enabled when tracing is enabled + * If @ips array or any ip specified within is NULL , it fails to update filter. +- */ ++ * ++ * This can allocate memory which must be freed before @ops can be freed, ++ * either by removing each filtered addr or by using ++ * ftrace_free_filter(@ops). ++*/ + int ftrace_set_filter_ips(struct ftrace_ops *ops, unsigned long *ips, + unsigned int cnt, int remove, int reset) + { +@@ -5889,6 +5902,10 @@ ftrace_set_regex(struct ftrace_ops *ops, + * + * Filters denote which functions should be enabled when tracing is enabled. + * If @buf is NULL and reset is set, all functions will be enabled for tracing. ++ * ++ * This can allocate memory which must be freed before @ops can be freed, ++ * either by removing each filtered addr or by using ++ * ftrace_free_filter(@ops). + */ + int ftrace_set_filter(struct ftrace_ops *ops, unsigned char *buf, + int len, int reset) +@@ -5908,6 +5925,10 @@ EXPORT_SYMBOL_GPL(ftrace_set_filter); + * Notrace Filters denote which functions should not be enabled when tracing + * is enabled. If @buf is NULL and reset is set, all functions will be enabled + * for tracing. ++ * ++ * This can allocate memory which must be freed before @ops can be freed, ++ * either by removing each filtered addr or by using ++ * ftrace_free_filter(@ops). + */ + int ftrace_set_notrace(struct ftrace_ops *ops, unsigned char *buf, + int len, int reset) +--- a/samples/ftrace/ftrace-direct-multi-modify.c ++++ b/samples/ftrace/ftrace-direct-multi-modify.c +@@ -149,6 +149,7 @@ static void __exit ftrace_direct_multi_e + { + kthread_stop(simple_tsk); + unregister_ftrace_direct_multi(&direct, my_tramp); ++ ftrace_free_filter(&direct); + } + + module_init(ftrace_direct_multi_init); +--- a/samples/ftrace/ftrace-direct-multi.c ++++ b/samples/ftrace/ftrace-direct-multi.c +@@ -77,6 +77,7 @@ static int __init ftrace_direct_multi_in + static void __exit ftrace_direct_multi_exit(void) + { + unregister_ftrace_direct_multi(&direct, (unsigned long) my_tramp); ++ ftrace_free_filter(&direct); + } + + module_init(ftrace_direct_multi_init); diff --git a/queue-6.1/ftrace-scripts-update-the-instructions-for-ftrace-bisect.sh.patch b/queue-6.1/ftrace-scripts-update-the-instructions-for-ftrace-bisect.sh.patch new file mode 100644 index 00000000000..a312fcc1a27 --- /dev/null +++ b/queue-6.1/ftrace-scripts-update-the-instructions-for-ftrace-bisect.sh.patch @@ -0,0 +1,98 @@ +From 7ae4ba7195b1bac04a4210a499da9d8c63b0ba9c Mon Sep 17 00:00:00 2001 +From: "Steven Rostedt (Google)" +Date: Mon, 23 Jan 2023 11:22:52 -0500 +Subject: ftrace/scripts: Update the instructions for ftrace-bisect.sh + +From: Steven Rostedt (Google) + +commit 7ae4ba7195b1bac04a4210a499da9d8c63b0ba9c upstream. + +The instructions for the ftrace-bisect.sh script, which is used to find +what function is being traced that is causing a kernel crash, and possibly +a triple fault reboot, uses the old method. In 5.1, a new feature was +added that let the user write in the index into available_filter_functions +that maps to the function a user wants to set in set_ftrace_filter (or +set_ftrace_notrace). This takes O(1) to set, as suppose to writing a +function name, which takes O(n) (where n is the number of functions in +available_filter_functions). + +The ftrace-bisect.sh requires setting half of the functions in +available_filter_functions, which is O(n^2) using the name method to enable +and can take several minutes to complete. The number method is O(n) which +takes less than a second to complete. Using the number method for any +kernel 5.1 and after is the proper way to do the bisect. + +Update the usage to reflect the new change, as well as using the +/sys/kernel/tracing path instead of the obsolete debugfs path. + +Link: https://lkml.kernel.org/r/20230123112252.022003dd@gandalf.local.home + +Cc: stable@vger.kernel.org +Cc: Masami Hiramatsu +Acked-by: Mark Rutland +Fixes: f79b3f338564e ("ftrace: Allow enabling of filters via index of available_filter_functions") +Signed-off-by: Steven Rostedt (Google) +Signed-off-by: Greg Kroah-Hartman +--- + scripts/tracing/ftrace-bisect.sh | 34 ++++++++++++++++++++++++++-------- + 1 file changed, 26 insertions(+), 8 deletions(-) + +--- a/scripts/tracing/ftrace-bisect.sh ++++ b/scripts/tracing/ftrace-bisect.sh +@@ -12,7 +12,7 @@ + # (note, if this is a problem with function_graph tracing, then simply + # replace "function" with "function_graph" in the following steps). + # +-# # cd /sys/kernel/debug/tracing ++# # cd /sys/kernel/tracing + # # echo schedule > set_ftrace_filter + # # echo function > current_tracer + # +@@ -20,22 +20,40 @@ + # + # # echo nop > current_tracer + # +-# # cat available_filter_functions > ~/full-file ++# Starting with v5.1 this can be done with numbers, making it much faster: ++# ++# The old (slow) way, for kernels before v5.1. ++# ++# [old-way] # cat available_filter_functions > ~/full-file ++# ++# [old-way] *** Note *** this process will take several minutes to update the ++# [old-way] filters. Setting multiple functions is an O(n^2) operation, and we ++# [old-way] are dealing with thousands of functions. So go have coffee, talk ++# [old-way] with your coworkers, read facebook. And eventually, this operation ++# [old-way] will end. ++# ++# The new way (using numbers) is an O(n) operation, and usually takes less than a second. ++# ++# seq `wc -l available_filter_functions | cut -d' ' -f1` > ~/full-file ++# ++# This will create a sequence of numbers that match the functions in ++# available_filter_functions, and when echoing in a number into the ++# set_ftrace_filter file, it will enable the corresponding function in ++# O(1) time. Making enabling all functions O(n) where n is the number of ++# functions to enable. ++# ++# For either the new or old way, the rest of the operations remain the same. ++# + # # ftrace-bisect ~/full-file ~/test-file ~/non-test-file + # # cat ~/test-file > set_ftrace_filter + # +-# *** Note *** this will take several minutes. Setting multiple functions is +-# an O(n^2) operation, and we are dealing with thousands of functions. So go +-# have coffee, talk with your coworkers, read facebook. And eventually, this +-# operation will end. +-# + # # echo function > current_tracer + # + # If it crashes, we know that ~/test-file has a bad function. + # + # Reboot back to test kernel. + # +-# # cd /sys/kernel/debug/tracing ++# # cd /sys/kernel/tracing + # # mv ~/test-file ~/full-file + # + # If it didn't crash. diff --git a/queue-6.1/module-don-t-wait-for-going-modules.patch b/queue-6.1/module-don-t-wait-for-going-modules.patch new file mode 100644 index 00000000000..9567c1d7c41 --- /dev/null +++ b/queue-6.1/module-don-t-wait-for-going-modules.patch @@ -0,0 +1,111 @@ +From 0254127ab977e70798707a7a2b757c9f3c971210 Mon Sep 17 00:00:00 2001 +From: Petr Pavlu +Date: Mon, 5 Dec 2022 11:35:57 +0100 +Subject: module: Don't wait for GOING modules + +From: Petr Pavlu + +commit 0254127ab977e70798707a7a2b757c9f3c971210 upstream. + +During a system boot, it can happen that the kernel receives a burst of +requests to insert the same module but loading it eventually fails +during its init call. For instance, udev can make a request to insert +a frequency module for each individual CPU when another frequency module +is already loaded which causes the init function of the new module to +return an error. + +Since commit 6e6de3dee51a ("kernel/module.c: Only return -EEXIST for +modules that have finished loading"), the kernel waits for modules in +MODULE_STATE_GOING state to finish unloading before making another +attempt to load the same module. + +This creates unnecessary work in the described scenario and delays the +boot. In the worst case, it can prevent udev from loading drivers for +other devices and might cause timeouts of services waiting on them and +subsequently a failed boot. + +This patch attempts a different solution for the problem 6e6de3dee51a +was trying to solve. Rather than waiting for the unloading to complete, +it returns a different error code (-EBUSY) for modules in the GOING +state. This should avoid the error situation that was described in +6e6de3dee51a (user space attempting to load a dependent module because +the -EEXIST error code would suggest to user space that the first module +had been loaded successfully), while avoiding the delay situation too. + +This has been tested on linux-next since December 2022 and passes +all kmod selftests except test 0009 with module compression enabled +but it has been confirmed that this issue has existed and has gone +unnoticed since prior to this commit and can also be reproduced without +module compression with a simple usleep(5000000) on tools/modprobe.c [0]. +These failures are caused by hitting the kernel mod_concurrent_max and can +happen either due to a self inflicted kernel module auto-loead DoS somehow +or on a system with large CPU count and each CPU count incorrectly triggering +many module auto-loads. Both of those issues need to be fixed in-kernel. + +[0] https://lore.kernel.org/all/Y9A4fiobL6IHp%2F%2FP@bombadil.infradead.org/ + +Fixes: 6e6de3dee51a ("kernel/module.c: Only return -EEXIST for modules that have finished loading") +Co-developed-by: Martin Wilck +Signed-off-by: Martin Wilck +Signed-off-by: Petr Pavlu +Cc: stable@vger.kernel.org +Reviewed-by: Petr Mladek +[mcgrof: enhance commit log with testing and kmod test result interpretation ] +Signed-off-by: Luis Chamberlain +Signed-off-by: Greg Kroah-Hartman +--- + kernel/module/main.c | 26 +++++++++++++++++++++----- + 1 file changed, 21 insertions(+), 5 deletions(-) + +--- a/kernel/module/main.c ++++ b/kernel/module/main.c +@@ -2386,7 +2386,8 @@ static bool finished_loading(const char + sched_annotate_sleep(); + mutex_lock(&module_mutex); + mod = find_module_all(name, strlen(name), true); +- ret = !mod || mod->state == MODULE_STATE_LIVE; ++ ret = !mod || mod->state == MODULE_STATE_LIVE ++ || mod->state == MODULE_STATE_GOING; + mutex_unlock(&module_mutex); + + return ret; +@@ -2562,20 +2563,35 @@ static int add_unformed_module(struct mo + + mod->state = MODULE_STATE_UNFORMED; + +-again: + mutex_lock(&module_mutex); + old = find_module_all(mod->name, strlen(mod->name), true); + if (old != NULL) { +- if (old->state != MODULE_STATE_LIVE) { ++ if (old->state == MODULE_STATE_COMING ++ || old->state == MODULE_STATE_UNFORMED) { + /* Wait in case it fails to load. */ + mutex_unlock(&module_mutex); + err = wait_event_interruptible(module_wq, + finished_loading(mod->name)); + if (err) + goto out_unlocked; +- goto again; ++ ++ /* The module might have gone in the meantime. */ ++ mutex_lock(&module_mutex); ++ old = find_module_all(mod->name, strlen(mod->name), ++ true); + } +- err = -EEXIST; ++ ++ /* ++ * We are here only when the same module was being loaded. Do ++ * not try to load it again right now. It prevents long delays ++ * caused by serialized module load failures. It might happen ++ * when more devices of the same type trigger load of ++ * a particular module. ++ */ ++ if (old && old->state == MODULE_STATE_LIVE) ++ err = -EEXIST; ++ else ++ err = -EBUSY; + goto out; + } + mod_update_bounds(mod); diff --git a/queue-6.1/series b/queue-6.1/series index 4deec8c46a1..db5c6403881 100644 --- a/queue-6.1/series +++ b/queue-6.1/series @@ -207,3 +207,9 @@ vfio-type1-respect-iommu-reserved-regions-in-vfio_te.patch scsi-hpsa-fix-allocation-size-for-scsi_host_alloc.patch kvm-vfio-fix-potential-deadlock-on-vfio-group_lock.patch nfsd-don-t-free-files-unconditionally-in-__nfsd_file.patch +module-don-t-wait-for-going-modules.patch +ftrace-export-ftrace_free_filter-to-modules.patch +tracing-make-sure-trace_printk-can-output-as-soon-as-it-can-be-used.patch +trace_events_hist-add-check-for-return-value-of-create_hist_field.patch +ftrace-scripts-update-the-instructions-for-ftrace-bisect.sh.patch +cifs-fix-oops-due-to-uncleared-server-smbd_conn-in-reconnect.patch diff --git a/queue-6.1/trace_events_hist-add-check-for-return-value-of-create_hist_field.patch b/queue-6.1/trace_events_hist-add-check-for-return-value-of-create_hist_field.patch new file mode 100644 index 00000000000..a5c399c73db --- /dev/null +++ b/queue-6.1/trace_events_hist-add-check-for-return-value-of-create_hist_field.patch @@ -0,0 +1,37 @@ +From 8b152e9150d07a885f95e1fd401fc81af202d9a4 Mon Sep 17 00:00:00 2001 +From: Natalia Petrova +Date: Wed, 11 Jan 2023 15:04:09 +0300 +Subject: trace_events_hist: add check for return value of 'create_hist_field' + +From: Natalia Petrova + +commit 8b152e9150d07a885f95e1fd401fc81af202d9a4 upstream. + +Function 'create_hist_field' is called recursively at +trace_events_hist.c:1954 and can return NULL-value that's why we have +to check it to avoid null pointer dereference. + +Found by Linux Verification Center (linuxtesting.org) with SVACE. + +Link: https://lkml.kernel.org/r/20230111120409.4111-1-n.petrova@fintech.ru + +Cc: stable@vger.kernel.org +Fixes: 30350d65ac56 ("tracing: Add variable support to hist triggers") +Signed-off-by: Natalia Petrova +Signed-off-by: Steven Rostedt (Google) +Signed-off-by: Greg Kroah-Hartman +--- + kernel/trace/trace_events_hist.c | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/kernel/trace/trace_events_hist.c ++++ b/kernel/trace/trace_events_hist.c +@@ -1975,6 +1975,8 @@ static struct hist_field *create_hist_fi + hist_field->fn_num = flags & HIST_FIELD_FL_LOG2 ? HIST_FIELD_FN_LOG2 : + HIST_FIELD_FN_BUCKET; + hist_field->operands[0] = create_hist_field(hist_data, field, fl, NULL); ++ if (!hist_field->operands[0]) ++ goto free; + hist_field->size = hist_field->operands[0]->size; + hist_field->type = kstrdup_const(hist_field->operands[0]->type, GFP_KERNEL); + if (!hist_field->type) diff --git a/queue-6.1/tracing-make-sure-trace_printk-can-output-as-soon-as-it-can-be-used.patch b/queue-6.1/tracing-make-sure-trace_printk-can-output-as-soon-as-it-can-be-used.patch new file mode 100644 index 00000000000..9352f7c0915 --- /dev/null +++ b/queue-6.1/tracing-make-sure-trace_printk-can-output-as-soon-as-it-can-be-used.patch @@ -0,0 +1,80 @@ +From 3bb06eb6e9acf7c4a3e1b5bc87aed398ff8e2253 Mon Sep 17 00:00:00 2001 +From: "Steven Rostedt (Google)" +Date: Wed, 4 Jan 2023 16:14:12 -0500 +Subject: tracing: Make sure trace_printk() can output as soon as it can be used + +From: Steven Rostedt (Google) + +commit 3bb06eb6e9acf7c4a3e1b5bc87aed398ff8e2253 upstream. + +Currently trace_printk() can be used as soon as early_trace_init() is +called from start_kernel(). But if a crash happens, and +"ftrace_dump_on_oops" is set on the kernel command line, all you get will +be: + + [ 0.456075] -0 0dN.2. 347519us : Unknown type 6 + [ 0.456075] -0 0dN.2. 353141us : Unknown type 6 + [ 0.456075] -0 0dN.2. 358684us : Unknown type 6 + +This is because the trace_printk() event (type 6) hasn't been registered +yet. That gets done via an early_initcall(), which may be early, but not +early enough. + +Instead of registering the trace_printk() event (and other ftrace events, +which are not trace events) via an early_initcall(), have them registered at +the same time that trace_printk() can be used. This way, if there is a +crash before early_initcall(), then the trace_printk()s will actually be +useful. + +Link: https://lkml.kernel.org/r/20230104161412.019f6c55@gandalf.local.home + +Cc: stable@vger.kernel.org +Cc: Masami Hiramatsu +Fixes: e725c731e3bb1 ("tracing: Split tracing initialization into two for early initialization") +Reported-by: "Joel Fernandes (Google)" +Tested-by: Joel Fernandes (Google) +Signed-off-by: Steven Rostedt (Google) +Signed-off-by: Greg Kroah-Hartman +--- + kernel/trace/trace.c | 2 ++ + kernel/trace/trace.h | 1 + + kernel/trace/trace_output.c | 3 +-- + 3 files changed, 4 insertions(+), 2 deletions(-) + +--- a/kernel/trace/trace.c ++++ b/kernel/trace/trace.c +@@ -10291,6 +10291,8 @@ void __init early_trace_init(void) + static_key_enable(&tracepoint_printk_key.key); + } + tracer_alloc_buffers(); ++ ++ init_events(); + } + + void __init trace_init(void) +--- a/kernel/trace/trace.h ++++ b/kernel/trace/trace.h +@@ -1490,6 +1490,7 @@ extern void trace_event_enable_cmd_recor + extern void trace_event_enable_tgid_record(bool enable); + + extern int event_trace_init(void); ++extern int init_events(void); + extern int event_trace_add_tracer(struct dentry *parent, struct trace_array *tr); + extern int event_trace_del_tracer(struct trace_array *tr); + extern void __trace_early_add_events(struct trace_array *tr); +--- a/kernel/trace/trace_output.c ++++ b/kernel/trace/trace_output.c +@@ -1568,7 +1568,7 @@ static struct trace_event *events[] __in + NULL + }; + +-__init static int init_events(void) ++__init int init_events(void) + { + struct trace_event *event; + int i, ret; +@@ -1581,4 +1581,3 @@ __init static int init_events(void) + + return 0; + } +-early_initcall(init_events);