From: Greg Kroah-Hartman Date: Tue, 11 Apr 2023 14:01:56 +0000 (+0200) Subject: 6.1-stable patches X-Git-Tag: v5.15.107~19 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=27050adf48ab419443472b6b7b4e70af50828211;p=thirdparty%2Fkernel%2Fstable-queue.git 6.1-stable patches added patches: blk-throttle-fix-that-bps-of-child-could-exceed-bps-limited-in-parent.patch drm-amd-display-clear-mst-topology-if-it-fails-to-resume.patch drm-amdgpu-for-s0ix-skip-sdma-5.x-suspend-resume.patch drm-amdgpu-skip-psp-suspend-for-imu-enabled-asics-mode2-reset.patch drm-display-dp_mst-handle-old-new-payload-states-in-drm_dp_remove_payload.patch drm-i915-dp_mst-fix-payload-removal-during-output-disabling.patch drm-i915-fix-context-runtime-accounting.patch drm-i915-fix-race-condition-uaf-in-i915_perf_add_config_ioctl.patch drm-nouveau-disp-support-more-modes-by-checking-with-lower-bpc.patch drm-panfrost-fix-the-panfrost_mmu_map_fault_addr-error-path.patch maple_tree-fix-a-potential-concurrency-bug-in-rcu-mode.patch maple_tree-fix-get-wrong-data_end-in-mtree_lookup_walk.patch mm-hugetlb-fix-uffd-wr-protection-for-cow-optimization-path.patch mm-swap-fix-swap_info_struct-race-between-swapoff-and-get_swap_pages.patch mm-vmalloc-avoid-warn_alloc-noise-caused-by-fatal-signal.patch ring-buffer-fix-race-while-reader-and-writer-are-on-the-same-page.patch ublk-read-any-sqe-values-upfront.patch wifi-mt76-ignore-key-disable-commands.patch zsmalloc-document-freeable-stats.patch --- diff --git a/queue-6.1/blk-throttle-fix-that-bps-of-child-could-exceed-bps-limited-in-parent.patch b/queue-6.1/blk-throttle-fix-that-bps-of-child-could-exceed-bps-limited-in-parent.patch new file mode 100644 index 00000000000..b8d8d02c18c --- /dev/null +++ b/queue-6.1/blk-throttle-fix-that-bps-of-child-could-exceed-bps-limited-in-parent.patch @@ -0,0 +1,57 @@ +From 84aca0a7e039c8735abc0f89f3f48e9006c0dfc7 Mon Sep 17 00:00:00 2001 +From: Kemeng Shi +Date: Mon, 5 Dec 2022 19:57:02 +0800 +Subject: blk-throttle: Fix that bps of child could exceed bps limited in parent + +From: Kemeng Shi + +commit 84aca0a7e039c8735abc0f89f3f48e9006c0dfc7 upstream. + +Consider situation as following (on the default hierarchy): + HDD + | +root (bps limit: 4k) + | +child (bps limit :8k) + | +fio bs=8k +Rate of fio is supposed to be 4k, but result is 8k. Reason is as +following: +Size of single IO from fio is larger than bytes allowed in one +throtl_slice in child, so IOs are always queued in child group first. +When queued IOs in child are dispatched to parent group, BIO_BPS_THROTTLED +is set and these IOs will not be limited by tg_within_bps_limit anymore. +Fix this by only set BIO_BPS_THROTTLED when the bio traversed the entire +tree. + +There patch has no influence on situation which is not on the default +hierarchy as each group is a single root group without parent. + +Acked-by: Tejun Heo +Signed-off-by: Kemeng Shi +Link: https://lore.kernel.org/r/20221205115709.251489-3-shikemeng@huaweicloud.com +Signed-off-by: Jens Axboe +Cc: Khazhy Kumykov +Signed-off-by: Greg Kroah-Hartman +--- + block/blk-throttle.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/block/blk-throttle.c ++++ b/block/blk-throttle.c +@@ -1066,7 +1066,6 @@ static void tg_dispatch_one_bio(struct t + sq->nr_queued[rw]--; + + throtl_charge_bio(tg, bio); +- bio_set_flag(bio, BIO_BPS_THROTTLED); + + /* + * If our parent is another tg, we just need to transfer @bio to +@@ -1079,6 +1078,7 @@ static void tg_dispatch_one_bio(struct t + throtl_add_bio_tg(bio, &tg->qnode_on_parent[rw], parent_tg); + start_parent_slice_with_credit(tg, parent_tg, rw); + } else { ++ bio_set_flag(bio, BIO_BPS_THROTTLED); + throtl_qnode_add_bio(bio, &tg->qnode_on_parent[rw], + &parent_sq->queued[rw]); + BUG_ON(tg->td->nr_queued[rw] <= 0); diff --git a/queue-6.1/drm-amd-display-clear-mst-topology-if-it-fails-to-resume.patch b/queue-6.1/drm-amd-display-clear-mst-topology-if-it-fails-to-resume.patch new file mode 100644 index 00000000000..b4723cd70d9 --- /dev/null +++ b/queue-6.1/drm-amd-display-clear-mst-topology-if-it-fails-to-resume.patch @@ -0,0 +1,39 @@ +From 3f6752b4de41896c7f1609b1585db2080e8150d8 Mon Sep 17 00:00:00 2001 +From: Roman Li +Date: Thu, 1 Dec 2022 09:49:23 -0500 +Subject: drm/amd/display: Clear MST topology if it fails to resume + +From: Roman Li + +commit 3f6752b4de41896c7f1609b1585db2080e8150d8 upstream. + +[Why] +In case of failure to resume MST topology after suspend, an emtpty +mst tree prevents further mst hub detection on the same connector. +That causes the issue with MST hub hotplug after it's been unplug in +suspend. + +[How] +Stop topology manager on the connector after detecting DM_MST failure. + +Reviewed-by: Wayne Lin +Acked-by: Jasdeep Dhillon +Signed-off-by: Roman Li +Signed-off-by: Alex Deucher +Cc: "Limonciello, Mario" +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c ++++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +@@ -2175,6 +2175,8 @@ static int detect_mst_link_for_all_conne + DRM_ERROR("DM_MST: Failed to start MST\n"); + aconnector->dc_link->type = + dc_connection_single; ++ ret = dm_helpers_dp_mst_stop_top_mgr(aconnector->dc_link->ctx, ++ aconnector->dc_link); + break; + } + } diff --git a/queue-6.1/drm-amdgpu-for-s0ix-skip-sdma-5.x-suspend-resume.patch b/queue-6.1/drm-amdgpu-for-s0ix-skip-sdma-5.x-suspend-resume.patch new file mode 100644 index 00000000000..7e09cc4bf3a --- /dev/null +++ b/queue-6.1/drm-amdgpu-for-s0ix-skip-sdma-5.x-suspend-resume.patch @@ -0,0 +1,39 @@ +From 2a7798ea7390fd78f191c9e9bf68f5581d3b4a02 Mon Sep 17 00:00:00 2001 +From: Alex Deucher +Date: Fri, 2 Dec 2022 10:13:40 -0500 +Subject: drm/amdgpu: for S0ix, skip SDMA 5.x+ suspend/resume + +From: Alex Deucher + +commit 2a7798ea7390fd78f191c9e9bf68f5581d3b4a02 upstream. + +SDMA 5.x is part of the GFX block so it's controlled via +GFXOFF. Skip suspend as it should be handled the same +as GFX. + +v2: drop SDMA 4.x. That requires special handling. + +Reviewed-by: Mario Limonciello +Acked-by: Rajneesh Bhardwaj +Signed-off-by: Alex Deucher +Cc: "Limonciello, Mario" +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 ++++++ + 1 file changed, 6 insertions(+) + +--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c ++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +@@ -3034,6 +3034,12 @@ static int amdgpu_device_ip_suspend_phas + adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_MES)) + continue; + ++ /* SDMA 5.x+ is part of GFX power domain so it's covered by GFXOFF */ ++ if (adev->in_s0ix && ++ (adev->ip_versions[SDMA0_HWIP][0] >= IP_VERSION(5, 0, 0)) && ++ (adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_SDMA)) ++ continue; ++ + /* XXX handle errors */ + r = adev->ip_blocks[i].version->funcs->suspend(adev); + /* XXX handle errors */ diff --git a/queue-6.1/drm-amdgpu-skip-psp-suspend-for-imu-enabled-asics-mode2-reset.patch b/queue-6.1/drm-amdgpu-skip-psp-suspend-for-imu-enabled-asics-mode2-reset.patch new file mode 100644 index 00000000000..00ba92cb547 --- /dev/null +++ b/queue-6.1/drm-amdgpu-skip-psp-suspend-for-imu-enabled-asics-mode2-reset.patch @@ -0,0 +1,42 @@ +From e11c775030c5585370fda43035204bb5fa23b139 Mon Sep 17 00:00:00 2001 +From: Tim Huang +Date: Fri, 20 Jan 2023 22:27:32 +0800 +Subject: drm/amdgpu: skip psp suspend for IMU enabled ASICs mode2 reset + +From: Tim Huang + +commit e11c775030c5585370fda43035204bb5fa23b139 upstream. + +The psp suspend & resume should be skipped to avoid destroy +the TMR and reload FWs again for IMU enabled APU ASICs. + +Signed-off-by: Tim Huang +Acked-by: Alex Deucher +Reviewed-by: Mario Limonciello +Signed-off-by: Alex Deucher +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 12 ++++++++++++ + 1 file changed, 12 insertions(+) + +--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c ++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +@@ -3040,6 +3040,18 @@ static int amdgpu_device_ip_suspend_phas + (adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_SDMA)) + continue; + ++ /* Once swPSP provides the IMU, RLC FW binaries to TOS during cold-boot. ++ * These are in TMR, hence are expected to be reused by PSP-TOS to reload ++ * from this location and RLC Autoload automatically also gets loaded ++ * from here based on PMFW -> PSP message during re-init sequence. ++ * Therefore, the psp suspend & resume should be skipped to avoid destroy ++ * the TMR and reload FWs again for IMU enabled APU ASICs. ++ */ ++ if (amdgpu_in_reset(adev) && ++ (adev->flags & AMD_IS_APU) && adev->gfx.imu.funcs && ++ adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_PSP) ++ continue; ++ + /* XXX handle errors */ + r = adev->ip_blocks[i].version->funcs->suspend(adev); + /* XXX handle errors */ diff --git a/queue-6.1/drm-display-dp_mst-handle-old-new-payload-states-in-drm_dp_remove_payload.patch b/queue-6.1/drm-display-dp_mst-handle-old-new-payload-states-in-drm_dp_remove_payload.patch new file mode 100644 index 00000000000..8b665890326 --- /dev/null +++ b/queue-6.1/drm-display-dp_mst-handle-old-new-payload-states-in-drm_dp_remove_payload.patch @@ -0,0 +1,171 @@ +From e761cc20946a0094df71cb31a565a6a0d03bd8be Mon Sep 17 00:00:00 2001 +From: Imre Deak +Date: Mon, 6 Feb 2023 13:48:54 +0200 +Subject: drm/display/dp_mst: Handle old/new payload states in drm_dp_remove_payload() +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Imre Deak + +commit e761cc20946a0094df71cb31a565a6a0d03bd8be upstream. + +Atm, drm_dp_remove_payload() uses the same payload state to both get the +vc_start_slot required for the payload removal DPCD message and to +deduct time_slots from vc_start_slot of all payloads after the one being +removed. + +The above isn't always correct, as vc_start_slot must be the up-to-date +version contained in the new payload state, but time_slots must be the +one used when the payload was previously added, contained in the old +payload state. The new payload's time_slots can change vs. the old one +if the current atomic commit changes the corresponding mode. + +This patch let's drivers pass the old and new payload states to +drm_dp_remove_payload(), but keeps these the same for now in all drivers +not to change the behavior. A follow-up i915 patch will pass in that +driver the correct old and new states to the function. + +Cc: Lyude Paul +Cc: Ville Syrjälä +Cc: Ben Skeggs +Cc: Karol Herbst +Cc: Harry Wentland +Cc: Alex Deucher +Cc: Wayne Lin +Cc: stable@vger.kernel.org # 6.1 +Cc: dri-devel@lists.freedesktop.org +Reviewed-by: Ville Syrjälä +Reviewed-by: Lyude Paul +Acked-by: Lyude Paul +Acked-by: Daniel Vetter +Acked-by: Wayne Lin +Acked-by: Jani Nikula +Signed-off-by: Imre Deak +Link: https://patchwork.freedesktop.org/patch/msgid/20230206114856.2665066-2-imre.deak@intel.com +Hand modified for missing 8c7d980da9ba3eb67a1b40fd4b33bcf49397084b +Signed-off-by: Mario Limonciello +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c | 2 - + drivers/gpu/drm/display/drm_dp_mst_topology.c | 26 +++++++------- + drivers/gpu/drm/i915/display/intel_dp_mst.c | 4 +- + drivers/gpu/drm/nouveau/dispnv50/disp.c | 2 - + include/drm/display/drm_dp_mst_helper.h | 3 + + 5 files changed, 21 insertions(+), 16 deletions(-) + +--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c ++++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c +@@ -206,7 +206,7 @@ bool dm_helpers_dp_mst_write_payload_all + if (enable) + drm_dp_add_payload_part1(mst_mgr, mst_state, payload); + else +- drm_dp_remove_payload(mst_mgr, mst_state, payload); ++ drm_dp_remove_payload(mst_mgr, mst_state, payload, payload); + + /* mst_mgr->->payloads are VC payload notify MST branch using DPCD or + * AUX message. The sequence is slot 1-63 allocated sequence for each +--- a/drivers/gpu/drm/display/drm_dp_mst_topology.c ++++ b/drivers/gpu/drm/display/drm_dp_mst_topology.c +@@ -3342,7 +3342,8 @@ EXPORT_SYMBOL(drm_dp_add_payload_part1); + * drm_dp_remove_payload() - Remove an MST payload + * @mgr: Manager to use. + * @mst_state: The MST atomic state +- * @payload: The payload to write ++ * @old_payload: The payload with its old state ++ * @new_payload: The payload to write + * + * Removes a payload from an MST topology if it was successfully assigned a start slot. Also updates + * the starting time slots of all other payloads which would have been shifted towards the start of +@@ -3350,36 +3351,37 @@ EXPORT_SYMBOL(drm_dp_add_payload_part1); + */ + void drm_dp_remove_payload(struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_topology_state *mst_state, +- struct drm_dp_mst_atomic_payload *payload) ++ const struct drm_dp_mst_atomic_payload *old_payload, ++ struct drm_dp_mst_atomic_payload *new_payload) + { + struct drm_dp_mst_atomic_payload *pos; + bool send_remove = false; + + /* We failed to make the payload, so nothing to do */ +- if (payload->vc_start_slot == -1) ++ if (new_payload->vc_start_slot == -1) + return; + + mutex_lock(&mgr->lock); +- send_remove = drm_dp_mst_port_downstream_of_branch(payload->port, mgr->mst_primary); ++ send_remove = drm_dp_mst_port_downstream_of_branch(new_payload->port, mgr->mst_primary); + mutex_unlock(&mgr->lock); + + if (send_remove) +- drm_dp_destroy_payload_step1(mgr, mst_state, payload); ++ drm_dp_destroy_payload_step1(mgr, mst_state, new_payload); + else + drm_dbg_kms(mgr->dev, "Payload for VCPI %d not in topology, not sending remove\n", +- payload->vcpi); ++ new_payload->vcpi); + + list_for_each_entry(pos, &mst_state->payloads, next) { +- if (pos != payload && pos->vc_start_slot > payload->vc_start_slot) +- pos->vc_start_slot -= payload->time_slots; ++ if (pos != new_payload && pos->vc_start_slot > new_payload->vc_start_slot) ++ pos->vc_start_slot -= old_payload->time_slots; + } +- payload->vc_start_slot = -1; ++ new_payload->vc_start_slot = -1; + + mgr->payload_count--; +- mgr->next_start_slot -= payload->time_slots; ++ mgr->next_start_slot -= old_payload->time_slots; + +- if (payload->delete) +- drm_dp_mst_put_port_malloc(payload->port); ++ if (new_payload->delete) ++ drm_dp_mst_put_port_malloc(new_payload->port); + } + EXPORT_SYMBOL(drm_dp_remove_payload); + +--- a/drivers/gpu/drm/i915/display/intel_dp_mst.c ++++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c +@@ -366,6 +366,8 @@ static void intel_mst_disable_dp(struct + to_intel_connector(old_conn_state->connector); + struct drm_dp_mst_topology_state *mst_state = + drm_atomic_get_mst_topology_state(&state->base, &intel_dp->mst_mgr); ++ struct drm_dp_mst_atomic_payload *payload = ++ drm_atomic_get_mst_payload_state(mst_state, connector->port); + struct drm_i915_private *i915 = to_i915(connector->base.dev); + + drm_dbg_kms(&i915->drm, "active links %d\n", +@@ -374,7 +376,7 @@ static void intel_mst_disable_dp(struct + intel_hdcp_disable(intel_mst->connector); + + drm_dp_remove_payload(&intel_dp->mst_mgr, mst_state, +- drm_atomic_get_mst_payload_state(mst_state, connector->port)); ++ payload, payload); + + intel_audio_codec_disable(encoder, old_crtc_state, old_conn_state); + } +--- a/drivers/gpu/drm/nouveau/dispnv50/disp.c ++++ b/drivers/gpu/drm/nouveau/dispnv50/disp.c +@@ -1028,7 +1028,7 @@ nv50_msto_prepare(struct drm_atomic_stat + + // TODO: Figure out if we want to do a better job of handling VCPI allocation failures here? + if (msto->disabled) { +- drm_dp_remove_payload(mgr, mst_state, payload); ++ drm_dp_remove_payload(mgr, mst_state, payload, payload); + } else { + if (msto->enabled) + drm_dp_add_payload_part1(mgr, mst_state, payload); +--- a/include/drm/display/drm_dp_mst_helper.h ++++ b/include/drm/display/drm_dp_mst_helper.h +@@ -841,7 +841,8 @@ int drm_dp_add_payload_part2(struct drm_ + struct drm_dp_mst_atomic_payload *payload); + void drm_dp_remove_payload(struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_topology_state *mst_state, +- struct drm_dp_mst_atomic_payload *payload); ++ const struct drm_dp_mst_atomic_payload *old_payload, ++ struct drm_dp_mst_atomic_payload *new_payload); + + int drm_dp_check_act_status(struct drm_dp_mst_topology_mgr *mgr); + diff --git a/queue-6.1/drm-i915-dp_mst-fix-payload-removal-during-output-disabling.patch b/queue-6.1/drm-i915-dp_mst-fix-payload-removal-during-output-disabling.patch new file mode 100644 index 00000000000..246568d2465 --- /dev/null +++ b/queue-6.1/drm-i915-dp_mst-fix-payload-removal-during-output-disabling.patch @@ -0,0 +1,83 @@ +From eb50912ec931913e70640cecf75cb993fd26995f Mon Sep 17 00:00:00 2001 +From: Imre Deak +Date: Mon, 6 Feb 2023 13:48:56 +0200 +Subject: drm/i915/dp_mst: Fix payload removal during output disabling +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Imre Deak + +commit eb50912ec931913e70640cecf75cb993fd26995f upstream. + +Use the correct old/new topology and payload states in +intel_mst_disable_dp(). So far drm_atomic_get_mst_topology_state() it +used returned either the old state, in case the state was added already +earlier during the atomic check phase or otherwise the new state (but +the latter could fail, which can't be handled in the enable/disable +hooks). After the first patch in the patchset, the state should always +get added already during the check phase, so here we can get the +old/new states without a failure. + +drm_dp_remove_payload() should use time_slots from the old payload state +and vc_start_slot in the new one. It should update the new payload +states to reflect the sink's current payload table after the payload is +removed. Pass the new topology state and the old and new payload states +accordingly. + +This also fixes a problem where the payload allocations for multiple MST +streams on the same link got inconsistent after a few commits, as +during payload removal the old instead of the new payload state got +updated, so the subsequent enabling sequence and commits used a stale +payload state. + +v2: Constify the old payload state pointer. (Ville) + +Cc: Lyude Paul +Cc: Ville Syrjälä +Cc: stable@vger.kernel.org # 6.1 +Reviewed-by: Ville Syrjälä +Reviewed-by: Lyude Paul +Acked-by: Lyude Paul +Acked-by: Daniel Vetter +Acked-by: Wayne Lin +Acked-by: Jani Nikula +Signed-off-by: Imre Deak +Link: https://patchwork.freedesktop.org/patch/msgid/20230206114856.2665066-4-imre.deak@intel.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/i915/display/intel_dp_mst.c | 16 ++++++++++------ + 1 file changed, 10 insertions(+), 6 deletions(-) + +--- a/drivers/gpu/drm/i915/display/intel_dp_mst.c ++++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c +@@ -364,10 +364,14 @@ static void intel_mst_disable_dp(struct + struct intel_dp *intel_dp = &dig_port->dp; + struct intel_connector *connector = + to_intel_connector(old_conn_state->connector); +- struct drm_dp_mst_topology_state *mst_state = +- drm_atomic_get_mst_topology_state(&state->base, &intel_dp->mst_mgr); +- struct drm_dp_mst_atomic_payload *payload = +- drm_atomic_get_mst_payload_state(mst_state, connector->port); ++ struct drm_dp_mst_topology_state *old_mst_state = ++ drm_atomic_get_old_mst_topology_state(&state->base, &intel_dp->mst_mgr); ++ struct drm_dp_mst_topology_state *new_mst_state = ++ drm_atomic_get_new_mst_topology_state(&state->base, &intel_dp->mst_mgr); ++ const struct drm_dp_mst_atomic_payload *old_payload = ++ drm_atomic_get_mst_payload_state(old_mst_state, connector->port); ++ struct drm_dp_mst_atomic_payload *new_payload = ++ drm_atomic_get_mst_payload_state(new_mst_state, connector->port); + struct drm_i915_private *i915 = to_i915(connector->base.dev); + + drm_dbg_kms(&i915->drm, "active links %d\n", +@@ -375,8 +379,8 @@ static void intel_mst_disable_dp(struct + + intel_hdcp_disable(intel_mst->connector); + +- drm_dp_remove_payload(&intel_dp->mst_mgr, mst_state, +- payload, payload); ++ drm_dp_remove_payload(&intel_dp->mst_mgr, new_mst_state, ++ old_payload, new_payload); + + intel_audio_codec_disable(encoder, old_crtc_state, old_conn_state); + } diff --git a/queue-6.1/drm-i915-fix-context-runtime-accounting.patch b/queue-6.1/drm-i915-fix-context-runtime-accounting.patch new file mode 100644 index 00000000000..998f4a4b0bd --- /dev/null +++ b/queue-6.1/drm-i915-fix-context-runtime-accounting.patch @@ -0,0 +1,61 @@ +From dc3421560a67361442f33ec962fc6dd48895a0df Mon Sep 17 00:00:00 2001 +From: Tvrtko Ursulin +Date: Mon, 20 Mar 2023 15:14:23 +0000 +Subject: drm/i915: Fix context runtime accounting + +From: Tvrtko Ursulin + +commit dc3421560a67361442f33ec962fc6dd48895a0df upstream. + +When considering whether to mark one context as stopped and another as +started we need to look at whether the previous and new _contexts_ are +different and not just requests. Otherwise the software tracked context +start time was incorrectly updated to the most recent lite-restore time- +stamp, which was in some cases resulting in active time going backward, +until the context switch (typically the heartbeat pulse) would synchronise +with the hardware tracked context runtime. Easiest use case to observe +this behaviour was with a full screen clients with close to 100% engine +load. + +Signed-off-by: Tvrtko Ursulin +Fixes: bb6287cb1886 ("drm/i915: Track context current active time") +Cc: # v5.19+ +Reviewed-by: Matthew Auld +Link: https://patchwork.freedesktop.org/patch/msgid/20230320151423.1708436-1-tvrtko.ursulin@linux.intel.com +[tursulin: Fix spelling in commit msg.] +(cherry picked from commit b3e70051879c665acdd3a1ab50d0ed58d6a8001f) +Signed-off-by: Jani Nikula +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/i915/gt/intel_execlists_submission.c | 12 ++++++++++-- + 1 file changed, 10 insertions(+), 2 deletions(-) + +--- a/drivers/gpu/drm/i915/gt/intel_execlists_submission.c ++++ b/drivers/gpu/drm/i915/gt/intel_execlists_submission.c +@@ -2017,6 +2017,8 @@ process_csb(struct intel_engine_cs *engi + * inspecting the queue to see if we need to resumbit. + */ + if (*prev != *execlists->active) { /* elide lite-restores */ ++ struct intel_context *prev_ce = NULL, *active_ce = NULL; ++ + /* + * Note the inherent discrepancy between the HW runtime, + * recorded as part of the context switch, and the CPU +@@ -2028,9 +2030,15 @@ process_csb(struct intel_engine_cs *engi + * and correct overselves later when updating from HW. + */ + if (*prev) +- lrc_runtime_stop((*prev)->context); ++ prev_ce = (*prev)->context; + if (*execlists->active) +- lrc_runtime_start((*execlists->active)->context); ++ active_ce = (*execlists->active)->context; ++ if (prev_ce != active_ce) { ++ if (prev_ce) ++ lrc_runtime_stop(prev_ce); ++ if (active_ce) ++ lrc_runtime_start(active_ce); ++ } + new_timeslice(execlists); + } + diff --git a/queue-6.1/drm-i915-fix-race-condition-uaf-in-i915_perf_add_config_ioctl.patch b/queue-6.1/drm-i915-fix-race-condition-uaf-in-i915_perf_add_config_ioctl.patch new file mode 100644 index 00000000000..1ebf0beba8d --- /dev/null +++ b/queue-6.1/drm-i915-fix-race-condition-uaf-in-i915_perf_add_config_ioctl.patch @@ -0,0 +1,48 @@ +From dc30c011469165d57af9adac5baff7d767d20e5c Mon Sep 17 00:00:00 2001 +From: Min Li +Date: Tue, 28 Mar 2023 17:36:27 +0800 +Subject: drm/i915: fix race condition UAF in i915_perf_add_config_ioctl + +From: Min Li + +commit dc30c011469165d57af9adac5baff7d767d20e5c upstream. + +Userspace can guess the id value and try to race oa_config object creation +with config remove, resulting in a use-after-free if we dereference the +object after unlocking the metrics_lock. For that reason, unlocking the +metrics_lock must be done after we are done dereferencing the object. + +Signed-off-by: Min Li +Fixes: f89823c21224 ("drm/i915/perf: Implement I915_PERF_ADD/REMOVE_CONFIG interface") +Cc: # v4.14+ +Reviewed-by: Andi Shyti +Reviewed-by: Umesh Nerlige Ramappa +Signed-off-by: Tvrtko Ursulin +Link: https://patchwork.freedesktop.org/patch/msgid/20230328093627.5067-1-lm0963hack@gmail.com +[tursulin: Manually added stable tag.] +(cherry picked from commit 49f6f6483b652108bcb73accd0204a464b922395) +Signed-off-by: Jani Nikula +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/i915/i915_perf.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +--- a/drivers/gpu/drm/i915/i915_perf.c ++++ b/drivers/gpu/drm/i915/i915_perf.c +@@ -4270,13 +4270,13 @@ int i915_perf_add_config_ioctl(struct dr + err = oa_config->id; + goto sysfs_err; + } +- +- mutex_unlock(&perf->metrics_lock); ++ id = oa_config->id; + + drm_dbg(&perf->i915->drm, + "Added config %s id=%i\n", oa_config->uuid, oa_config->id); ++ mutex_unlock(&perf->metrics_lock); + +- return oa_config->id; ++ return id; + + sysfs_err: + mutex_unlock(&perf->metrics_lock); diff --git a/queue-6.1/drm-nouveau-disp-support-more-modes-by-checking-with-lower-bpc.patch b/queue-6.1/drm-nouveau-disp-support-more-modes-by-checking-with-lower-bpc.patch new file mode 100644 index 00000000000..56a627ed299 --- /dev/null +++ b/queue-6.1/drm-nouveau-disp-support-more-modes-by-checking-with-lower-bpc.patch @@ -0,0 +1,96 @@ +From 7f67aa097e875c87fba024e850cf405342300059 Mon Sep 17 00:00:00 2001 +From: Karol Herbst +Date: Fri, 31 Mar 2023 00:39:38 +0200 +Subject: drm/nouveau/disp: Support more modes by checking with lower bpc + +From: Karol Herbst + +commit 7f67aa097e875c87fba024e850cf405342300059 upstream. + +This allows us to advertise more modes especially on HDR displays. + +Fixes using 4K@60 modes on my TV and main display both using a HDMI to DP +adapter. Also fixes similar issues for users running into this. + +Cc: stable@vger.kernel.org # 5.10+ +Signed-off-by: Karol Herbst +Reviewed-by: Lyude Paul +Link: https://patchwork.freedesktop.org/patch/msgid/20230330223938.4025569-1-kherbst@redhat.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/nouveau/dispnv50/disp.c | 32 ++++++++++++++++++++++++++++++++ + drivers/gpu/drm/nouveau/nouveau_dp.c | 8 +++++--- + 2 files changed, 37 insertions(+), 3 deletions(-) + +--- a/drivers/gpu/drm/nouveau/dispnv50/disp.c ++++ b/drivers/gpu/drm/nouveau/dispnv50/disp.c +@@ -410,6 +410,35 @@ nv50_outp_atomic_check_view(struct drm_e + return 0; + } + ++static void ++nv50_outp_atomic_fix_depth(struct drm_encoder *encoder, struct drm_crtc_state *crtc_state) ++{ ++ struct nv50_head_atom *asyh = nv50_head_atom(crtc_state); ++ struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); ++ struct drm_display_mode *mode = &asyh->state.adjusted_mode; ++ unsigned int max_rate, mode_rate; ++ ++ switch (nv_encoder->dcb->type) { ++ case DCB_OUTPUT_DP: ++ max_rate = nv_encoder->dp.link_nr * nv_encoder->dp.link_bw; ++ ++ /* we don't support more than 10 anyway */ ++ asyh->or.bpc = min_t(u8, asyh->or.bpc, 10); ++ ++ /* reduce the bpc until it works out */ ++ while (asyh->or.bpc > 6) { ++ mode_rate = DIV_ROUND_UP(mode->clock * asyh->or.bpc * 3, 8); ++ if (mode_rate <= max_rate) ++ break; ++ ++ asyh->or.bpc -= 2; ++ } ++ break; ++ default: ++ break; ++ } ++} ++ + static int + nv50_outp_atomic_check(struct drm_encoder *encoder, + struct drm_crtc_state *crtc_state, +@@ -428,6 +457,9 @@ nv50_outp_atomic_check(struct drm_encode + if (crtc_state->mode_changed || crtc_state->connectors_changed) + asyh->or.bpc = connector->display_info.bpc; + ++ /* We might have to reduce the bpc */ ++ nv50_outp_atomic_fix_depth(encoder, crtc_state); ++ + return 0; + } + +--- a/drivers/gpu/drm/nouveau/nouveau_dp.c ++++ b/drivers/gpu/drm/nouveau/nouveau_dp.c +@@ -245,8 +245,6 @@ void nouveau_dp_irq(struct nouveau_drm * + } + + /* TODO: +- * - Use the minimum possible BPC here, once we add support for the max bpc +- * property. + * - Validate against the DP caps advertised by the GPU (we don't check these + * yet) + */ +@@ -258,7 +256,11 @@ nv50_dp_mode_valid(struct drm_connector + { + const unsigned int min_clock = 25000; + unsigned int max_rate, mode_rate, ds_max_dotclock, clock = mode->clock; +- const u8 bpp = connector->display_info.bpc * 3; ++ /* Check with the minmum bpc always, so we can advertise better modes. ++ * In particlar not doing this causes modes to be dropped on HDR ++ * displays as we might check with a bpc of 16 even. ++ */ ++ const u8 bpp = 6 * 3; + + if (mode->flags & DRM_MODE_FLAG_INTERLACE && !outp->caps.dp_interlace) + return MODE_NO_INTERLACE; diff --git a/queue-6.1/drm-panfrost-fix-the-panfrost_mmu_map_fault_addr-error-path.patch b/queue-6.1/drm-panfrost-fix-the-panfrost_mmu_map_fault_addr-error-path.patch new file mode 100644 index 00000000000..034c275d01d --- /dev/null +++ b/queue-6.1/drm-panfrost-fix-the-panfrost_mmu_map_fault_addr-error-path.patch @@ -0,0 +1,33 @@ +From 764a2ab9eb56e1200083e771aab16186836edf1d Mon Sep 17 00:00:00 2001 +From: Boris Brezillon +Date: Fri, 21 May 2021 11:38:11 +0200 +Subject: drm/panfrost: Fix the panfrost_mmu_map_fault_addr() error path + +From: Boris Brezillon + +commit 764a2ab9eb56e1200083e771aab16186836edf1d upstream. + +Make sure all bo->base.pages entries are either NULL or pointing to a +valid page before calling drm_gem_shmem_put_pages(). + +Reported-by: Tomeu Vizoso +Cc: +Fixes: 187d2929206e ("drm/panfrost: Add support for GPU heap allocations") +Signed-off-by: Boris Brezillon +Reviewed-by: Steven Price +Link: https://patchwork.freedesktop.org/patch/msgid/20210521093811.1018992-1-boris.brezillon@collabora.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/gpu/drm/panfrost/panfrost_mmu.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/gpu/drm/panfrost/panfrost_mmu.c ++++ b/drivers/gpu/drm/panfrost/panfrost_mmu.c +@@ -504,6 +504,7 @@ static int panfrost_mmu_map_fault_addr(s + if (IS_ERR(pages[i])) { + mutex_unlock(&bo->base.pages_lock); + ret = PTR_ERR(pages[i]); ++ pages[i] = NULL; + goto err_pages; + } + } diff --git a/queue-6.1/maple_tree-fix-a-potential-concurrency-bug-in-rcu-mode.patch b/queue-6.1/maple_tree-fix-a-potential-concurrency-bug-in-rcu-mode.patch new file mode 100644 index 00000000000..e909cad9f03 --- /dev/null +++ b/queue-6.1/maple_tree-fix-a-potential-concurrency-bug-in-rcu-mode.patch @@ -0,0 +1,82 @@ +From c45ea315a602d45569b08b93e9ab30f6a63a38aa Mon Sep 17 00:00:00 2001 +From: Peng Zhang +Date: Tue, 14 Mar 2023 20:42:03 +0800 +Subject: maple_tree: fix a potential concurrency bug in RCU mode + +From: Peng Zhang + +commit c45ea315a602d45569b08b93e9ab30f6a63a38aa upstream. + +There is a concurrency bug that may cause the wrong value to be loaded +when a CPU is modifying the maple tree. + +CPU1: +mtree_insert_range() + mas_insert() + mas_store_root() + ... + mas_root_expand() + ... + rcu_assign_pointer(mas->tree->ma_root, mte_mk_root(mas->node)); + ma_set_meta(node, maple_leaf_64, 0, slot); <---IP + +CPU2: +mtree_load() + mtree_lookup_walk() + ma_data_end(); + +When CPU1 is about to execute the instruction pointed to by IP, the +ma_data_end() executed by CPU2 may return the wrong end position, which +will cause the value loaded by mtree_load() to be wrong. + +An example of triggering the bug: + +Add mdelay(100) between rcu_assign_pointer() and ma_set_meta() in +mas_root_expand(). + +static DEFINE_MTREE(tree); +int work(void *p) { + unsigned long val; + for (int i = 0 ; i< 30; ++i) { + val = (unsigned long)mtree_load(&tree, 8); + mdelay(5); + pr_info("%lu",val); + } + return 0; +} + +mt_init_flags(&tree, MT_FLAGS_USE_RCU); +mtree_insert(&tree, 0, (void*)12345, GFP_KERNEL); +run_thread(work) +mtree_insert(&tree, 1, (void*)56789, GFP_KERNEL); + +In RCU mode, mtree_load() should always return the value before or after +the data structure is modified, and in this example mtree_load(&tree, 8) +may return 56789 which is not expected, it should always return NULL. Fix +it by put ma_set_meta() before rcu_assign_pointer(). + +Link: https://lkml.kernel.org/r/20230314124203.91572-4-zhangpeng.00@bytedance.com +Fixes: 54a611b60590 ("Maple Tree: add new data structure") +Signed-off-by: Peng Zhang +Reviewed-by: Liam R. Howlett +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + lib/maple_tree.c | 3 +-- + 1 file changed, 1 insertion(+), 2 deletions(-) + +--- a/lib/maple_tree.c ++++ b/lib/maple_tree.c +@@ -3654,10 +3654,9 @@ static inline int mas_root_expand(struct + slot++; + mas->depth = 1; + mas_set_height(mas); +- ++ ma_set_meta(node, maple_leaf_64, 0, slot); + /* swap the new root into the tree */ + rcu_assign_pointer(mas->tree->ma_root, mte_mk_root(mas->node)); +- ma_set_meta(node, maple_leaf_64, 0, slot); + return slot; + } + diff --git a/queue-6.1/maple_tree-fix-get-wrong-data_end-in-mtree_lookup_walk.patch b/queue-6.1/maple_tree-fix-get-wrong-data_end-in-mtree_lookup_walk.patch new file mode 100644 index 00000000000..ec9ff5d314f --- /dev/null +++ b/queue-6.1/maple_tree-fix-get-wrong-data_end-in-mtree_lookup_walk.patch @@ -0,0 +1,56 @@ +From ec07967d7523adb3670f9dfee0232e3bc868f3de Mon Sep 17 00:00:00 2001 +From: Peng Zhang +Date: Tue, 14 Mar 2023 20:42:01 +0800 +Subject: maple_tree: fix get wrong data_end in mtree_lookup_walk() + +From: Peng Zhang + +commit ec07967d7523adb3670f9dfee0232e3bc868f3de upstream. + +if (likely(offset > end)) + max = pivots[offset]; + +The above code should be changed to if (likely(offset < end)), which is +correct. This affects the correctness of ma_data_end(). Now it seems +that the final result will not be wrong, but it is best to change it. +This patch does not change the code as above, because it simplifies the +code by the way. + +Link: https://lkml.kernel.org/r/20230314124203.91572-1-zhangpeng.00@bytedance.com +Link: https://lkml.kernel.org/r/20230314124203.91572-2-zhangpeng.00@bytedance.com +Fixes: 54a611b60590 ("Maple Tree: add new data structure") +Signed-off-by: Peng Zhang +Reviewed-by: Liam R. Howlett +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + lib/maple_tree.c | 15 +++++---------- + 1 file changed, 5 insertions(+), 10 deletions(-) + +--- a/lib/maple_tree.c ++++ b/lib/maple_tree.c +@@ -3870,18 +3870,13 @@ static inline void *mtree_lookup_walk(st + end = ma_data_end(node, type, pivots, max); + if (unlikely(ma_dead_node(node))) + goto dead_node; +- +- if (pivots[offset] >= mas->index) +- goto next; +- + do { +- offset++; +- } while ((offset < end) && (pivots[offset] < mas->index)); +- +- if (likely(offset > end)) +- max = pivots[offset]; ++ if (pivots[offset] >= mas->index) { ++ max = pivots[offset]; ++ break; ++ } ++ } while (++offset < end); + +-next: + slots = ma_slots(node, type); + next = mt_slot(mas->tree, slots, offset); + if (unlikely(ma_dead_node(node))) diff --git a/queue-6.1/mm-hugetlb-fix-uffd-wr-protection-for-cow-optimization-path.patch b/queue-6.1/mm-hugetlb-fix-uffd-wr-protection-for-cow-optimization-path.patch new file mode 100644 index 00000000000..577d1288b55 --- /dev/null +++ b/queue-6.1/mm-hugetlb-fix-uffd-wr-protection-for-cow-optimization-path.patch @@ -0,0 +1,88 @@ +From 60d5b473d61be61ac315e544fcd6a8234a79500e Mon Sep 17 00:00:00 2001 +From: Peter Xu +Date: Tue, 21 Mar 2023 15:18:40 -0400 +Subject: mm/hugetlb: fix uffd wr-protection for CoW optimization path + +From: Peter Xu + +commit 60d5b473d61be61ac315e544fcd6a8234a79500e upstream. + +This patch fixes an issue that a hugetlb uffd-wr-protected mapping can be +writable even with uffd-wp bit set. It only happens with hugetlb private +mappings, when someone firstly wr-protects a missing pte (which will +install a pte marker), then a write to the same page without any prior +access to the page. + +Userfaultfd-wp trap for hugetlb was implemented in hugetlb_fault() before +reaching hugetlb_wp() to avoid taking more locks that userfault won't +need. However there's one CoW optimization path that can trigger +hugetlb_wp() inside hugetlb_no_page(), which will bypass the trap. + +This patch skips hugetlb_wp() for CoW and retries the fault if uffd-wp bit +is detected. The new path will only trigger in the CoW optimization path +because generic hugetlb_fault() (e.g. when a present pte was +wr-protected) will resolve the uffd-wp bit already. Also make sure +anonymous UNSHARE won't be affected and can still be resolved, IOW only +skip CoW not CoR. + +This patch will be needed for v5.19+ hence copy stable. + +[peterx@redhat.com: v2] + Link: https://lkml.kernel.org/r/ZBzOqwF2wrHgBVZb@x1n +[peterx@redhat.com: v3] + Link: https://lkml.kernel.org/r/20230324142620.2344140-1-peterx@redhat.com +Link: https://lkml.kernel.org/r/20230321191840.1897940-1-peterx@redhat.com +Fixes: 166f3ecc0daf ("mm/hugetlb: hook page faults for uffd write protection") +Signed-off-by: Peter Xu +Reported-by: Muhammad Usama Anjum +Tested-by: Muhammad Usama Anjum +Acked-by: David Hildenbrand +Reviewed-by: Mike Kravetz +Cc: Andrea Arcangeli +Cc: Axel Rasmussen +Cc: Mike Rapoport +Cc: Nadav Amit +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + mm/hugetlb.c | 14 ++++++++++++-- + 1 file changed, 12 insertions(+), 2 deletions(-) + +--- a/mm/hugetlb.c ++++ b/mm/hugetlb.c +@@ -5469,7 +5469,7 @@ static vm_fault_t hugetlb_wp(struct mm_s + struct page *pagecache_page, spinlock_t *ptl) + { + const bool unshare = flags & FAULT_FLAG_UNSHARE; +- pte_t pte; ++ pte_t pte = huge_ptep_get(ptep); + struct hstate *h = hstate_vma(vma); + struct page *old_page, *new_page; + int outside_reserve = 0; +@@ -5481,6 +5481,17 @@ static vm_fault_t hugetlb_wp(struct mm_s + VM_BUG_ON(!unshare && !(flags & FOLL_WRITE)); + + /* ++ * Never handle CoW for uffd-wp protected pages. It should be only ++ * handled when the uffd-wp protection is removed. ++ * ++ * Note that only the CoW optimization path (in hugetlb_no_page()) ++ * can trigger this, because hugetlb_fault() will always resolve ++ * uffd-wp bit first. ++ */ ++ if (!unshare && huge_pte_uffd_wp(pte)) ++ return 0; ++ ++ /* + * hugetlb does not support FOLL_FORCE-style write faults that keep the + * PTE mapped R/O such as maybe_mkwrite() would do. + */ +@@ -5495,7 +5506,6 @@ static vm_fault_t hugetlb_wp(struct mm_s + return 0; + } + +- pte = huge_ptep_get(ptep); + old_page = pte_page(pte); + + delayacct_wpcopy_start(); diff --git a/queue-6.1/mm-swap-fix-swap_info_struct-race-between-swapoff-and-get_swap_pages.patch b/queue-6.1/mm-swap-fix-swap_info_struct-race-between-swapoff-and-get_swap_pages.patch new file mode 100644 index 00000000000..4e34be0a2f8 --- /dev/null +++ b/queue-6.1/mm-swap-fix-swap_info_struct-race-between-swapoff-and-get_swap_pages.patch @@ -0,0 +1,119 @@ +From 6fe7d6b992113719e96744d974212df3fcddc76c Mon Sep 17 00:00:00 2001 +From: Rongwei Wang +Date: Tue, 4 Apr 2023 23:47:16 +0800 +Subject: mm/swap: fix swap_info_struct race between swapoff and get_swap_pages() + +From: Rongwei Wang + +commit 6fe7d6b992113719e96744d974212df3fcddc76c upstream. + +The si->lock must be held when deleting the si from the available list. +Otherwise, another thread can re-add the si to the available list, which +can lead to memory corruption. The only place we have found where this +happens is in the swapoff path. This case can be described as below: + +core 0 core 1 +swapoff + +del_from_avail_list(si) waiting + +try lock si->lock acquire swap_avail_lock + and re-add si into + swap_avail_head + +acquire si->lock but missing si already being added again, and continuing +to clear SWP_WRITEOK, etc. + +It can be easily found that a massive warning messages can be triggered +inside get_swap_pages() by some special cases, for example, we call +madvise(MADV_PAGEOUT) on blocks of touched memory concurrently, meanwhile, +run much swapon-swapoff operations (e.g. stress-ng-swap). + +However, in the worst case, panic can be caused by the above scene. In +swapoff(), the memory used by si could be kept in swap_info[] after +turning off a swap. This means memory corruption will not be caused +immediately until allocated and reset for a new swap in the swapon path. +A panic message caused: (with CONFIG_PLIST_DEBUG enabled) + +------------[ cut here ]------------ +top: 00000000e58a3003, n: 0000000013e75cda, p: 000000008cd4451a +prev: 0000000035b1e58a, n: 000000008cd4451a, p: 000000002150ee8d +next: 000000008cd4451a, n: 000000008cd4451a, p: 000000008cd4451a +WARNING: CPU: 21 PID: 1843 at lib/plist.c:60 plist_check_prev_next_node+0x50/0x70 +Modules linked in: rfkill(E) crct10dif_ce(E)... +CPU: 21 PID: 1843 Comm: stress-ng Kdump: ... 5.10.134+ +Hardware name: Alibaba Cloud ECS, BIOS 0.0.0 02/06/2015 +pstate: 60400005 (nZCv daif +PAN -UAO -TCO BTYPE=--) +pc : plist_check_prev_next_node+0x50/0x70 +lr : plist_check_prev_next_node+0x50/0x70 +sp : ffff0018009d3c30 +x29: ffff0018009d3c40 x28: ffff800011b32a98 +x27: 0000000000000000 x26: ffff001803908000 +x25: ffff8000128ea088 x24: ffff800011b32a48 +x23: 0000000000000028 x22: ffff001800875c00 +x21: ffff800010f9e520 x20: ffff001800875c00 +x19: ffff001800fdc6e0 x18: 0000000000000030 +x17: 0000000000000000 x16: 0000000000000000 +x15: 0736076307640766 x14: 0730073007380731 +x13: 0736076307640766 x12: 0730073007380731 +x11: 000000000004058d x10: 0000000085a85b76 +x9 : ffff8000101436e4 x8 : ffff800011c8ce08 +x7 : 0000000000000000 x6 : 0000000000000001 +x5 : ffff0017df9ed338 x4 : 0000000000000001 +x3 : ffff8017ce62a000 x2 : ffff0017df9ed340 +x1 : 0000000000000000 x0 : 0000000000000000 +Call trace: + plist_check_prev_next_node+0x50/0x70 + plist_check_head+0x80/0xf0 + plist_add+0x28/0x140 + add_to_avail_list+0x9c/0xf0 + _enable_swap_info+0x78/0xb4 + __do_sys_swapon+0x918/0xa10 + __arm64_sys_swapon+0x20/0x30 + el0_svc_common+0x8c/0x220 + do_el0_svc+0x2c/0x90 + el0_svc+0x1c/0x30 + el0_sync_handler+0xa8/0xb0 + el0_sync+0x148/0x180 +irq event stamp: 2082270 + +Now, si->lock locked before calling 'del_from_avail_list()' to make sure +other thread see the si had been deleted and SWP_WRITEOK cleared together, +will not reinsert again. + +This problem exists in versions after stable 5.10.y. + +Link: https://lkml.kernel.org/r/20230404154716.23058-1-rongwei.wang@linux.alibaba.com +Fixes: a2468cc9bfdff ("swap: choose swap device according to numa node") +Tested-by: Yongchen Yin +Signed-off-by: Rongwei Wang +Cc: Bagas Sanjaya +Cc: Matthew Wilcox (Oracle) +Cc: Aaron Lu +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + mm/swapfile.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/mm/swapfile.c ++++ b/mm/swapfile.c +@@ -679,6 +679,7 @@ static void __del_from_avail_list(struct + { + int nid; + ++ assert_spin_locked(&p->lock); + for_each_node(nid) + plist_del(&p->avail_lists[nid], &swap_avail_heads[nid]); + } +@@ -2428,8 +2429,8 @@ SYSCALL_DEFINE1(swapoff, const char __us + spin_unlock(&swap_lock); + goto out_dput; + } +- del_from_avail_list(p); + spin_lock(&p->lock); ++ del_from_avail_list(p); + if (p->prio < 0) { + struct swap_info_struct *si = p; + int nid; diff --git a/queue-6.1/mm-vmalloc-avoid-warn_alloc-noise-caused-by-fatal-signal.patch b/queue-6.1/mm-vmalloc-avoid-warn_alloc-noise-caused-by-fatal-signal.patch new file mode 100644 index 00000000000..94e91c77139 --- /dev/null +++ b/queue-6.1/mm-vmalloc-avoid-warn_alloc-noise-caused-by-fatal-signal.patch @@ -0,0 +1,122 @@ +From f349b15e183d6956f1b63d6ff57849ff10c7edd5 Mon Sep 17 00:00:00 2001 +From: Yafang Shao +Date: Thu, 30 Mar 2023 16:26:25 +0000 +Subject: mm: vmalloc: avoid warn_alloc noise caused by fatal signal + +From: Yafang Shao + +commit f349b15e183d6956f1b63d6ff57849ff10c7edd5 upstream. + +There're some suspicious warn_alloc on my test serer, for example, + +[13366.518837] warn_alloc: 81 callbacks suppressed +[13366.518841] test_verifier: vmalloc error: size 4096, page order 0, failed to allocate pages, mode:0x500dc2(GFP_HIGHUSER|__GFP_ZERO|__GFP_ACCOUNT), nodemask=(null),cpuset=/,mems_allowed=0-1 +[13366.522240] CPU: 30 PID: 722463 Comm: test_verifier Kdump: loaded Tainted: G W O 6.2.0+ #638 +[13366.524216] Call Trace: +[13366.524702] +[13366.525148] dump_stack_lvl+0x6c/0x80 +[13366.525712] dump_stack+0x10/0x20 +[13366.526239] warn_alloc+0x119/0x190 +[13366.526783] ? alloc_pages_bulk_array_mempolicy+0x9e/0x2a0 +[13366.527470] __vmalloc_area_node+0x546/0x5b0 +[13366.528066] __vmalloc_node_range+0xc2/0x210 +[13366.528660] __vmalloc_node+0x42/0x50 +[13366.529186] ? bpf_prog_realloc+0x53/0xc0 +[13366.529743] __vmalloc+0x1e/0x30 +[13366.530235] bpf_prog_realloc+0x53/0xc0 +[13366.530771] bpf_patch_insn_single+0x80/0x1b0 +[13366.531351] bpf_jit_blind_constants+0xe9/0x1c0 +[13366.531932] ? __free_pages+0xee/0x100 +[13366.532457] ? free_large_kmalloc+0x58/0xb0 +[13366.533002] bpf_int_jit_compile+0x8c/0x5e0 +[13366.533546] bpf_prog_select_runtime+0xb4/0x100 +[13366.534108] bpf_prog_load+0x6b1/0xa50 +[13366.534610] ? perf_event_task_tick+0x96/0xb0 +[13366.535151] ? security_capable+0x3a/0x60 +[13366.535663] __sys_bpf+0xb38/0x2190 +[13366.536120] ? kvm_clock_get_cycles+0x9/0x10 +[13366.536643] __x64_sys_bpf+0x1c/0x30 +[13366.537094] do_syscall_64+0x38/0x90 +[13366.537554] entry_SYSCALL_64_after_hwframe+0x72/0xdc +[13366.538107] RIP: 0033:0x7f78310f8e29 +[13366.538561] Code: 01 00 48 81 c4 80 00 00 00 e9 f1 fe ff ff 0f 1f 00 48 89 f8 48 89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 17 e0 2c 00 f7 d8 64 89 01 48 +[13366.540286] RSP: 002b:00007ffe2a61fff8 EFLAGS: 00000206 ORIG_RAX: 0000000000000141 +[13366.541031] RAX: ffffffffffffffda RBX: 0000000000000000 RCX: 00007f78310f8e29 +[13366.541749] RDX: 0000000000000080 RSI: 00007ffe2a6200b0 RDI: 0000000000000005 +[13366.542470] RBP: 00007ffe2a620010 R08: 00007ffe2a6202a0 R09: 00007ffe2a6200b0 +[13366.543183] R10: 00000000000f423e R11: 0000000000000206 R12: 0000000000407800 +[13366.543900] R13: 00007ffe2a620540 R14: 0000000000000000 R15: 0000000000000000 +[13366.544623] +[13366.545260] Mem-Info: +[13366.546121] active_anon:81319 inactive_anon:20733 isolated_anon:0 + active_file:69450 inactive_file:5624 isolated_file:0 + unevictable:0 dirty:10 writeback:0 + slab_reclaimable:69649 slab_unreclaimable:48930 + mapped:27400 shmem:12868 pagetables:4929 + sec_pagetables:0 bounce:0 + kernel_misc_reclaimable:0 + free:15870308 free_pcp:142935 free_cma:0 +[13366.551886] Node 0 active_anon:224836kB inactive_anon:33528kB active_file:175692kB inactive_file:13752kB unevictable:0kB isolated(anon):0kB isolated(file):0kB mapped:59248kB dirty:32kB writeback:0kB shmem:18252kB shmem_thp: 0kB shmem_pmdmapped: 0kB anon_thp: 0kB writeback_tmp:0kB kernel_stack:4616kB pagetables:10664kB sec_pagetables:0kB all_unreclaimable? no +[13366.555184] Node 1 active_anon:100440kB inactive_anon:49404kB active_file:102108kB inactive_file:8744kB unevictable:0kB isolated(anon):0kB isolated(file):0kB mapped:50352kB dirty:8kB writeback:0kB shmem:33220kB shmem_thp: 0kB shmem_pmdmapped: 0kB anon_thp: 0kB writeback_tmp:0kB kernel_stack:3896kB pagetables:9052kB sec_pagetables:0kB all_unreclaimable? no +[13366.558262] Node 0 DMA free:15360kB boost:0kB min:304kB low:380kB high:456kB reserved_highatomic:0KB active_anon:0kB inactive_anon:0kB active_file:0kB inactive_file:0kB unevictable:0kB writepending:0kB present:15992kB managed:15360kB mlocked:0kB bounce:0kB free_pcp:0kB local_pcp:0kB free_cma:0kB +[13366.560821] lowmem_reserve[]: 0 2735 31873 31873 31873 +[13366.561981] Node 0 DMA32 free:2790904kB boost:0kB min:56028kB low:70032kB high:84036kB reserved_highatomic:0KB active_anon:1936kB inactive_anon:20kB active_file:396kB inactive_file:344kB unevictable:0kB writepending:0kB present:3129200kB managed:2801520kB mlocked:0kB bounce:0kB free_pcp:5188kB local_pcp:0kB free_cma:0kB +[13366.565148] lowmem_reserve[]: 0 0 29137 29137 29137 +[13366.566168] Node 0 Normal free:28533824kB boost:0kB min:596740kB low:745924kB high:895108kB reserved_highatomic:28672KB active_anon:222900kB inactive_anon:33508kB active_file:175296kB inactive_file:13408kB unevictable:0kB writepending:32kB present:30408704kB managed:29837172kB mlocked:0kB bounce:0kB free_pcp:295724kB local_pcp:0kB free_cma:0kB +[13366.569485] lowmem_reserve[]: 0 0 0 0 0 +[13366.570416] Node 1 Normal free:32141144kB boost:0kB min:660504kB low:825628kB high:990752kB reserved_highatomic:69632KB active_anon:100440kB inactive_anon:49404kB active_file:102108kB inactive_file:8744kB unevictable:0kB writepending:8kB present:33554432kB managed:33025372kB mlocked:0kB bounce:0kB free_pcp:270880kB local_pcp:46860kB free_cma:0kB +[13366.573403] lowmem_reserve[]: 0 0 0 0 0 +[13366.574015] Node 0 DMA: 0*4kB 0*8kB 0*16kB 0*32kB 0*64kB 0*128kB 0*256kB 0*512kB 1*1024kB (U) 1*2048kB (M) 3*4096kB (M) = 15360kB +[13366.575474] Node 0 DMA32: 782*4kB (UME) 756*8kB (UME) 736*16kB (UME) 745*32kB (UME) 694*64kB (UME) 653*128kB (UME) 595*256kB (UME) 552*512kB (UME) 454*1024kB (UME) 347*2048kB (UME) 246*4096kB (UME) = 2790904kB +[13366.577442] Node 0 Normal: 33856*4kB (UMEH) 51815*8kB (UMEH) 42418*16kB (UMEH) 36272*32kB (UMEH) 22195*64kB (UMEH) 10296*128kB (UMEH) 7238*256kB (UMEH) 5638*512kB (UEH) 5337*1024kB (UMEH) 3506*2048kB (UMEH) 1470*4096kB (UME) = 28533784kB +[13366.580460] Node 1 Normal: 15776*4kB (UMEH) 37485*8kB (UMEH) 29509*16kB (UMEH) 21420*32kB (UMEH) 14818*64kB (UMEH) 13051*128kB (UMEH) 9918*256kB (UMEH) 7374*512kB (UMEH) 5397*1024kB (UMEH) 3887*2048kB (UMEH) 2002*4096kB (UME) = 32141240kB +[13366.583027] Node 0 hugepages_total=0 hugepages_free=0 hugepages_surp=0 hugepages_size=1048576kB +[13366.584380] Node 0 hugepages_total=0 hugepages_free=0 hugepages_surp=0 hugepages_size=2048kB +[13366.585702] Node 1 hugepages_total=0 hugepages_free=0 hugepages_surp=0 hugepages_size=1048576kB +[13366.587042] Node 1 hugepages_total=0 hugepages_free=0 hugepages_surp=0 hugepages_size=2048kB +[13366.588372] 87386 total pagecache pages +[13366.589266] 0 pages in swap cache +[13366.590327] Free swap = 0kB +[13366.591227] Total swap = 0kB +[13366.592142] 16777082 pages RAM +[13366.593057] 0 pages HighMem/MovableOnly +[13366.594037] 357226 pages reserved +[13366.594979] 0 pages hwpoisoned + +This failure really confuse me as there're still lots of available pages. +Finally I figured out it was caused by a fatal signal. When a process is +allocating memory via vm_area_alloc_pages(), it will break directly even +if it hasn't allocated the requested pages when it receives a fatal +signal. In that case, we shouldn't show this warn_alloc, as it is +useless. We only need to show this warning when there're really no enough +pages. + +Link: https://lkml.kernel.org/r/20230330162625.13604-1-laoar.shao@gmail.com +Signed-off-by: Yafang Shao +Reviewed-by: Lorenzo Stoakes +Cc: Christoph Hellwig +Cc: Uladzislau Rezki (Sony) +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + mm/vmalloc.c | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +--- a/mm/vmalloc.c ++++ b/mm/vmalloc.c +@@ -3056,9 +3056,11 @@ static void *__vmalloc_area_node(struct + * allocation request, free them via __vfree() if any. + */ + if (area->nr_pages != nr_small_pages) { +- warn_alloc(gfp_mask, NULL, +- "vmalloc error: size %lu, page order %u, failed to allocate pages", +- area->nr_pages * PAGE_SIZE, page_order); ++ /* vm_area_alloc_pages() can also fail due to a fatal signal */ ++ if (!fatal_signal_pending(current)) ++ warn_alloc(gfp_mask, NULL, ++ "vmalloc error: size %lu, page order %u, failed to allocate pages", ++ area->nr_pages * PAGE_SIZE, page_order); + goto fail; + } + diff --git a/queue-6.1/ring-buffer-fix-race-while-reader-and-writer-are-on-the-same-page.patch b/queue-6.1/ring-buffer-fix-race-while-reader-and-writer-are-on-the-same-page.patch new file mode 100644 index 00000000000..5fd3d793390 --- /dev/null +++ b/queue-6.1/ring-buffer-fix-race-while-reader-and-writer-are-on-the-same-page.patch @@ -0,0 +1,103 @@ +From 6455b6163d8c680366663cdb8c679514d55fc30c Mon Sep 17 00:00:00 2001 +From: Zheng Yejian +Date: Sat, 25 Mar 2023 10:12:47 +0800 +Subject: ring-buffer: Fix race while reader and writer are on the same page + +From: Zheng Yejian + +commit 6455b6163d8c680366663cdb8c679514d55fc30c upstream. + +When user reads file 'trace_pipe', kernel keeps printing following logs +that warn at "cpu_buffer->reader_page->read > rb_page_size(reader)" in +rb_get_reader_page(). It just looks like there's an infinite loop in +tracing_read_pipe(). This problem occurs several times on arm64 platform +when testing v5.10 and below. + + Call trace: + rb_get_reader_page+0x248/0x1300 + rb_buffer_peek+0x34/0x160 + ring_buffer_peek+0xbc/0x224 + peek_next_entry+0x98/0xbc + __find_next_entry+0xc4/0x1c0 + trace_find_next_entry_inc+0x30/0x94 + tracing_read_pipe+0x198/0x304 + vfs_read+0xb4/0x1e0 + ksys_read+0x74/0x100 + __arm64_sys_read+0x24/0x30 + el0_svc_common.constprop.0+0x7c/0x1bc + do_el0_svc+0x2c/0x94 + el0_svc+0x20/0x30 + el0_sync_handler+0xb0/0xb4 + el0_sync+0x160/0x180 + +Then I dump the vmcore and look into the problematic per_cpu ring_buffer, +I found that tail_page/commit_page/reader_page are on the same page while +reader_page->read is obviously abnormal: + tail_page == commit_page == reader_page == { + .write = 0x100d20, + .read = 0x8f9f4805, // Far greater than 0xd20, obviously abnormal!!! + .entries = 0x10004c, + .real_end = 0x0, + .page = { + .time_stamp = 0x857257416af0, + .commit = 0xd20, // This page hasn't been full filled. + // .data[0...0xd20] seems normal. + } + } + +The root cause is most likely the race that reader and writer are on the +same page while reader saw an event that not fully committed by writer. + +To fix this, add memory barriers to make sure the reader can see the +content of what is committed. Since commit a0fcaaed0c46 ("ring-buffer: Fix +race between reset page and reading page") has added the read barrier in +rb_get_reader_page(), here we just need to add the write barrier. + +Link: https://lore.kernel.org/linux-trace-kernel/20230325021247.2923907-1-zhengyejian1@huawei.com + +Cc: stable@vger.kernel.org +Fixes: 77ae365eca89 ("ring-buffer: make lockless") +Suggested-by: Steven Rostedt (Google) +Signed-off-by: Zheng Yejian +Signed-off-by: Steven Rostedt (Google) +Signed-off-by: Greg Kroah-Hartman +--- + kernel/trace/ring_buffer.c | 13 ++++++++++++- + 1 file changed, 12 insertions(+), 1 deletion(-) + +--- a/kernel/trace/ring_buffer.c ++++ b/kernel/trace/ring_buffer.c +@@ -3084,6 +3084,10 @@ rb_set_commit_to_write(struct ring_buffe + if (RB_WARN_ON(cpu_buffer, + rb_is_reader_page(cpu_buffer->tail_page))) + return; ++ /* ++ * No need for a memory barrier here, as the update ++ * of the tail_page did it for this page. ++ */ + local_set(&cpu_buffer->commit_page->page->commit, + rb_page_write(cpu_buffer->commit_page)); + rb_inc_page(&cpu_buffer->commit_page); +@@ -3093,6 +3097,8 @@ rb_set_commit_to_write(struct ring_buffe + while (rb_commit_index(cpu_buffer) != + rb_page_write(cpu_buffer->commit_page)) { + ++ /* Make sure the readers see the content of what is committed. */ ++ smp_wmb(); + local_set(&cpu_buffer->commit_page->page->commit, + rb_page_write(cpu_buffer->commit_page)); + RB_WARN_ON(cpu_buffer, +@@ -4672,7 +4678,12 @@ rb_get_reader_page(struct ring_buffer_pe + + /* + * Make sure we see any padding after the write update +- * (see rb_reset_tail()) ++ * (see rb_reset_tail()). ++ * ++ * In addition, a writer may be writing on the reader page ++ * if the page has not been fully filled, so the read barrier ++ * is also needed to make sure we see the content of what is ++ * committed by the writer (see rb_set_commit_to_write()). + */ + smp_rmb(); + diff --git a/queue-6.1/series b/queue-6.1/series index aaf5b0b489e..bd8427111f9 100644 --- a/queue-6.1/series +++ b/queue-6.1/series @@ -126,3 +126,22 @@ tracing-osnoise-fix-notify-new-tracing_max_latency.patch tracing-free-error-logs-of-tracing-instances.patch asoc-hdac_hdmi-use-set_stream-instead-of-set_tdm_slots.patch tracing-synthetic-make-lastcmd_mutex-static.patch +zsmalloc-document-freeable-stats.patch +mm-vmalloc-avoid-warn_alloc-noise-caused-by-fatal-signal.patch +wifi-mt76-ignore-key-disable-commands.patch +ublk-read-any-sqe-values-upfront.patch +drm-panfrost-fix-the-panfrost_mmu_map_fault_addr-error-path.patch +drm-nouveau-disp-support-more-modes-by-checking-with-lower-bpc.patch +drm-i915-fix-context-runtime-accounting.patch +drm-i915-fix-race-condition-uaf-in-i915_perf_add_config_ioctl.patch +ring-buffer-fix-race-while-reader-and-writer-are-on-the-same-page.patch +mm-swap-fix-swap_info_struct-race-between-swapoff-and-get_swap_pages.patch +mm-hugetlb-fix-uffd-wr-protection-for-cow-optimization-path.patch +maple_tree-fix-get-wrong-data_end-in-mtree_lookup_walk.patch +maple_tree-fix-a-potential-concurrency-bug-in-rcu-mode.patch +blk-throttle-fix-that-bps-of-child-could-exceed-bps-limited-in-parent.patch +drm-amd-display-clear-mst-topology-if-it-fails-to-resume.patch +drm-amdgpu-for-s0ix-skip-sdma-5.x-suspend-resume.patch +drm-amdgpu-skip-psp-suspend-for-imu-enabled-asics-mode2-reset.patch +drm-display-dp_mst-handle-old-new-payload-states-in-drm_dp_remove_payload.patch +drm-i915-dp_mst-fix-payload-removal-during-output-disabling.patch diff --git a/queue-6.1/ublk-read-any-sqe-values-upfront.patch b/queue-6.1/ublk-read-any-sqe-values-upfront.patch new file mode 100644 index 00000000000..6793fe14d3f --- /dev/null +++ b/queue-6.1/ublk-read-any-sqe-values-upfront.patch @@ -0,0 +1,65 @@ +From 8c68ae3b22fa6fb2dbe83ef955ff10936503d28e Mon Sep 17 00:00:00 2001 +From: Jens Axboe +Date: Wed, 5 Apr 2023 20:00:46 -0600 +Subject: ublk: read any SQE values upfront + +From: Jens Axboe + +commit 8c68ae3b22fa6fb2dbe83ef955ff10936503d28e upstream. + +Since SQE memory is shared with userspace, we should only be reading it +once. We cannot read it multiple times, particularly when it's read once +for validation and then read again for the actual use. + +ublk_ch_uring_cmd() is safe when called as a retry operation, as the +memory backing is stable at that point. But for normal issue, we want +to ensure that we only read ublksrv_io_cmd once. Wrap the function in +a helper that reads the value into an on-stack copy of the struct. + +Cc: stable@vger.kernel.org # 6.0+ +Reviewed-by: Ming Lei +Signed-off-by: Jens Axboe +Signed-off-by: Greg Kroah-Hartman +--- + drivers/block/ublk_drv.c | 22 ++++++++++++++++++++-- + 1 file changed, 20 insertions(+), 2 deletions(-) + +--- a/drivers/block/ublk_drv.c ++++ b/drivers/block/ublk_drv.c +@@ -1202,9 +1202,10 @@ static void ublk_handle_need_get_data(st + ublk_queue_cmd(ubq, req); + } + +-static int ublk_ch_uring_cmd(struct io_uring_cmd *cmd, unsigned int issue_flags) ++static int __ublk_ch_uring_cmd(struct io_uring_cmd *cmd, ++ unsigned int issue_flags, ++ struct ublksrv_io_cmd *ub_cmd) + { +- struct ublksrv_io_cmd *ub_cmd = (struct ublksrv_io_cmd *)cmd->cmd; + struct ublk_device *ub = cmd->file->private_data; + struct ublk_queue *ubq; + struct ublk_io *io; +@@ -1306,6 +1307,23 @@ static int ublk_ch_uring_cmd(struct io_u + return -EIOCBQUEUED; + } + ++static int ublk_ch_uring_cmd(struct io_uring_cmd *cmd, unsigned int issue_flags) ++{ ++ struct ublksrv_io_cmd *ub_src = (struct ublksrv_io_cmd *) cmd->cmd; ++ struct ublksrv_io_cmd ub_cmd; ++ ++ /* ++ * Not necessary for async retry, but let's keep it simple and always ++ * copy the values to avoid any potential reuse. ++ */ ++ ub_cmd.q_id = READ_ONCE(ub_src->q_id); ++ ub_cmd.tag = READ_ONCE(ub_src->tag); ++ ub_cmd.result = READ_ONCE(ub_src->result); ++ ub_cmd.addr = READ_ONCE(ub_src->addr); ++ ++ return __ublk_ch_uring_cmd(cmd, issue_flags, &ub_cmd); ++} ++ + static const struct file_operations ublk_ch_fops = { + .owner = THIS_MODULE, + .open = ublk_ch_open, diff --git a/queue-6.1/wifi-mt76-ignore-key-disable-commands.patch b/queue-6.1/wifi-mt76-ignore-key-disable-commands.patch new file mode 100644 index 00000000000..fd386746cb5 --- /dev/null +++ b/queue-6.1/wifi-mt76-ignore-key-disable-commands.patch @@ -0,0 +1,317 @@ +From e6db67fa871dee37d22701daba806bfcd4d9df49 Mon Sep 17 00:00:00 2001 +From: Felix Fietkau +Date: Thu, 30 Mar 2023 11:12:59 +0200 +Subject: wifi: mt76: ignore key disable commands + +From: Felix Fietkau + +commit e6db67fa871dee37d22701daba806bfcd4d9df49 upstream. + +This helps avoid cleartext leakage of already queued or powersave buffered +packets, when a reassoc triggers the key deletion. + +Cc: stable@vger.kernel.org +Signed-off-by: Felix Fietkau +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230330091259.61378-1-nbd@nbd.name +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/wireless/mediatek/mt76/mt7603/main.c | 10 +-- + drivers/net/wireless/mediatek/mt76/mt7615/mac.c | 70 ++++++--------------- + drivers/net/wireless/mediatek/mt76/mt7615/main.c | 15 ++-- + drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h | 6 - + drivers/net/wireless/mediatek/mt76/mt76x02_util.c | 18 ++--- + drivers/net/wireless/mediatek/mt76/mt7915/main.c | 13 +-- + drivers/net/wireless/mediatek/mt76/mt7921/main.c | 13 +-- + 7 files changed, 56 insertions(+), 89 deletions(-) + +--- a/drivers/net/wireless/mediatek/mt76/mt7603/main.c ++++ b/drivers/net/wireless/mediatek/mt76/mt7603/main.c +@@ -512,15 +512,15 @@ mt7603_set_key(struct ieee80211_hw *hw, + !(key->flags & IEEE80211_KEY_FLAG_PAIRWISE)) + return -EOPNOTSUPP; + +- if (cmd == SET_KEY) { +- key->hw_key_idx = wcid->idx; +- wcid->hw_key_idx = idx; +- } else { ++ if (cmd != SET_KEY) { + if (idx == wcid->hw_key_idx) + wcid->hw_key_idx = -1; + +- key = NULL; ++ return 0; + } ++ ++ key->hw_key_idx = wcid->idx; ++ wcid->hw_key_idx = idx; + mt76_wcid_key_setup(&dev->mt76, wcid, key); + + return mt7603_wtbl_set_key(dev, wcid->idx, key); +--- a/drivers/net/wireless/mediatek/mt76/mt7615/mac.c ++++ b/drivers/net/wireless/mediatek/mt76/mt7615/mac.c +@@ -1180,8 +1180,7 @@ EXPORT_SYMBOL_GPL(mt7615_mac_set_rates); + static int + mt7615_mac_wtbl_update_key(struct mt7615_dev *dev, struct mt76_wcid *wcid, + struct ieee80211_key_conf *key, +- enum mt76_cipher_type cipher, u16 cipher_mask, +- enum set_key_cmd cmd) ++ enum mt76_cipher_type cipher, u16 cipher_mask) + { + u32 addr = mt7615_mac_wtbl_addr(dev, wcid->idx) + 30 * 4; + u8 data[32] = {}; +@@ -1190,27 +1189,18 @@ mt7615_mac_wtbl_update_key(struct mt7615 + return -EINVAL; + + mt76_rr_copy(dev, addr, data, sizeof(data)); +- if (cmd == SET_KEY) { +- if (cipher == MT_CIPHER_TKIP) { +- /* Rx/Tx MIC keys are swapped */ +- memcpy(data, key->key, 16); +- memcpy(data + 16, key->key + 24, 8); +- memcpy(data + 24, key->key + 16, 8); +- } else { +- if (cipher_mask == BIT(cipher)) +- memcpy(data, key->key, key->keylen); +- else if (cipher != MT_CIPHER_BIP_CMAC_128) +- memcpy(data, key->key, 16); +- if (cipher == MT_CIPHER_BIP_CMAC_128) +- memcpy(data + 16, key->key, 16); +- } ++ if (cipher == MT_CIPHER_TKIP) { ++ /* Rx/Tx MIC keys are swapped */ ++ memcpy(data, key->key, 16); ++ memcpy(data + 16, key->key + 24, 8); ++ memcpy(data + 24, key->key + 16, 8); + } else { ++ if (cipher_mask == BIT(cipher)) ++ memcpy(data, key->key, key->keylen); ++ else if (cipher != MT_CIPHER_BIP_CMAC_128) ++ memcpy(data, key->key, 16); + if (cipher == MT_CIPHER_BIP_CMAC_128) +- memset(data + 16, 0, 16); +- else if (cipher_mask) +- memset(data, 0, 16); +- if (!cipher_mask) +- memset(data, 0, sizeof(data)); ++ memcpy(data + 16, key->key, 16); + } + + mt76_wr_copy(dev, addr, data, sizeof(data)); +@@ -1221,7 +1211,7 @@ mt7615_mac_wtbl_update_key(struct mt7615 + static int + mt7615_mac_wtbl_update_pk(struct mt7615_dev *dev, struct mt76_wcid *wcid, + enum mt76_cipher_type cipher, u16 cipher_mask, +- int keyidx, enum set_key_cmd cmd) ++ int keyidx) + { + u32 addr = mt7615_mac_wtbl_addr(dev, wcid->idx), w0, w1; + +@@ -1240,9 +1230,7 @@ mt7615_mac_wtbl_update_pk(struct mt7615_ + else + w0 &= ~MT_WTBL_W0_RX_IK_VALID; + +- if (cmd == SET_KEY && +- (cipher != MT_CIPHER_BIP_CMAC_128 || +- cipher_mask == BIT(cipher))) { ++ if (cipher != MT_CIPHER_BIP_CMAC_128 || cipher_mask == BIT(cipher)) { + w0 &= ~MT_WTBL_W0_KEY_IDX; + w0 |= FIELD_PREP(MT_WTBL_W0_KEY_IDX, keyidx); + } +@@ -1259,19 +1247,10 @@ mt7615_mac_wtbl_update_pk(struct mt7615_ + + static void + mt7615_mac_wtbl_update_cipher(struct mt7615_dev *dev, struct mt76_wcid *wcid, +- enum mt76_cipher_type cipher, u16 cipher_mask, +- enum set_key_cmd cmd) ++ enum mt76_cipher_type cipher, u16 cipher_mask) + { + u32 addr = mt7615_mac_wtbl_addr(dev, wcid->idx); + +- if (!cipher_mask) { +- mt76_clear(dev, addr + 2 * 4, MT_WTBL_W2_KEY_TYPE); +- return; +- } +- +- if (cmd != SET_KEY) +- return; +- + if (cipher == MT_CIPHER_BIP_CMAC_128 && + cipher_mask & ~BIT(MT_CIPHER_BIP_CMAC_128)) + return; +@@ -1282,8 +1261,7 @@ mt7615_mac_wtbl_update_cipher(struct mt7 + + int __mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, + struct mt76_wcid *wcid, +- struct ieee80211_key_conf *key, +- enum set_key_cmd cmd) ++ struct ieee80211_key_conf *key) + { + enum mt76_cipher_type cipher; + u16 cipher_mask = wcid->cipher; +@@ -1293,19 +1271,14 @@ int __mt7615_mac_wtbl_set_key(struct mt7 + if (cipher == MT_CIPHER_NONE) + return -EOPNOTSUPP; + +- if (cmd == SET_KEY) +- cipher_mask |= BIT(cipher); +- else +- cipher_mask &= ~BIT(cipher); +- +- mt7615_mac_wtbl_update_cipher(dev, wcid, cipher, cipher_mask, cmd); +- err = mt7615_mac_wtbl_update_key(dev, wcid, key, cipher, cipher_mask, +- cmd); ++ cipher_mask |= BIT(cipher); ++ mt7615_mac_wtbl_update_cipher(dev, wcid, cipher, cipher_mask); ++ err = mt7615_mac_wtbl_update_key(dev, wcid, key, cipher, cipher_mask); + if (err < 0) + return err; + + err = mt7615_mac_wtbl_update_pk(dev, wcid, cipher, cipher_mask, +- key->keyidx, cmd); ++ key->keyidx); + if (err < 0) + return err; + +@@ -1316,13 +1289,12 @@ int __mt7615_mac_wtbl_set_key(struct mt7 + + int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, + struct mt76_wcid *wcid, +- struct ieee80211_key_conf *key, +- enum set_key_cmd cmd) ++ struct ieee80211_key_conf *key) + { + int err; + + spin_lock_bh(&dev->mt76.lock); +- err = __mt7615_mac_wtbl_set_key(dev, wcid, key, cmd); ++ err = __mt7615_mac_wtbl_set_key(dev, wcid, key); + spin_unlock_bh(&dev->mt76.lock); + + return err; +--- a/drivers/net/wireless/mediatek/mt76/mt7615/main.c ++++ b/drivers/net/wireless/mediatek/mt76/mt7615/main.c +@@ -391,18 +391,17 @@ static int mt7615_set_key(struct ieee802 + + if (cmd == SET_KEY) + *wcid_keyidx = idx; +- else if (idx == *wcid_keyidx) +- *wcid_keyidx = -1; +- else ++ else { ++ if (idx == *wcid_keyidx) ++ *wcid_keyidx = -1; + goto out; ++ } + +- mt76_wcid_key_setup(&dev->mt76, wcid, +- cmd == SET_KEY ? key : NULL); +- ++ mt76_wcid_key_setup(&dev->mt76, wcid, key); + if (mt76_is_mmio(&dev->mt76)) +- err = mt7615_mac_wtbl_set_key(dev, wcid, key, cmd); ++ err = mt7615_mac_wtbl_set_key(dev, wcid, key); + else +- err = __mt7615_mac_wtbl_set_key(dev, wcid, key, cmd); ++ err = __mt7615_mac_wtbl_set_key(dev, wcid, key); + + out: + mt7615_mutex_release(dev); +--- a/drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h ++++ b/drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h +@@ -482,11 +482,9 @@ int mt7615_mac_write_txwi(struct mt7615_ + void mt7615_mac_set_timing(struct mt7615_phy *phy); + int __mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, + struct mt76_wcid *wcid, +- struct ieee80211_key_conf *key, +- enum set_key_cmd cmd); ++ struct ieee80211_key_conf *key); + int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, struct mt76_wcid *wcid, +- struct ieee80211_key_conf *key, +- enum set_key_cmd cmd); ++ struct ieee80211_key_conf *key); + void mt7615_mac_reset_work(struct work_struct *work); + u32 mt7615_mac_get_sta_tid_sn(struct mt7615_dev *dev, int wcid, u8 tid); + +--- a/drivers/net/wireless/mediatek/mt76/mt76x02_util.c ++++ b/drivers/net/wireless/mediatek/mt76/mt76x02_util.c +@@ -455,20 +455,20 @@ int mt76x02_set_key(struct ieee80211_hw + msta = sta ? (struct mt76x02_sta *)sta->drv_priv : NULL; + wcid = msta ? &msta->wcid : &mvif->group_wcid; + +- if (cmd == SET_KEY) { +- key->hw_key_idx = wcid->idx; +- wcid->hw_key_idx = idx; +- if (key->flags & IEEE80211_KEY_FLAG_RX_MGMT) { +- key->flags |= IEEE80211_KEY_FLAG_SW_MGMT_TX; +- wcid->sw_iv = true; +- } +- } else { ++ if (cmd != SET_KEY) { + if (idx == wcid->hw_key_idx) { + wcid->hw_key_idx = -1; + wcid->sw_iv = false; + } + +- key = NULL; ++ return 0; ++ } ++ ++ key->hw_key_idx = wcid->idx; ++ wcid->hw_key_idx = idx; ++ if (key->flags & IEEE80211_KEY_FLAG_RX_MGMT) { ++ key->flags |= IEEE80211_KEY_FLAG_SW_MGMT_TX; ++ wcid->sw_iv = true; + } + mt76_wcid_key_setup(&dev->mt76, wcid, key); + +--- a/drivers/net/wireless/mediatek/mt76/mt7915/main.c ++++ b/drivers/net/wireless/mediatek/mt76/mt7915/main.c +@@ -393,16 +393,15 @@ static int mt7915_set_key(struct ieee802 + mt7915_mcu_add_bss_info(phy, vif, true); + } + +- if (cmd == SET_KEY) ++ if (cmd == SET_KEY) { + *wcid_keyidx = idx; +- else if (idx == *wcid_keyidx) +- *wcid_keyidx = -1; +- else ++ } else { ++ if (idx == *wcid_keyidx) ++ *wcid_keyidx = -1; + goto out; ++ } + +- mt76_wcid_key_setup(&dev->mt76, wcid, +- cmd == SET_KEY ? key : NULL); +- ++ mt76_wcid_key_setup(&dev->mt76, wcid, key); + err = mt76_connac_mcu_add_key(&dev->mt76, vif, &msta->bip, + key, MCU_EXT_CMD(STA_REC_UPDATE), + &msta->wcid, cmd); +--- a/drivers/net/wireless/mediatek/mt76/mt7921/main.c ++++ b/drivers/net/wireless/mediatek/mt76/mt7921/main.c +@@ -464,16 +464,15 @@ static int mt7921_set_key(struct ieee802 + + mt7921_mutex_acquire(dev); + +- if (cmd == SET_KEY) ++ if (cmd == SET_KEY) { + *wcid_keyidx = idx; +- else if (idx == *wcid_keyidx) +- *wcid_keyidx = -1; +- else ++ } else { ++ if (idx == *wcid_keyidx) ++ *wcid_keyidx = -1; + goto out; ++ } + +- mt76_wcid_key_setup(&dev->mt76, wcid, +- cmd == SET_KEY ? key : NULL); +- ++ mt76_wcid_key_setup(&dev->mt76, wcid, key); + err = mt76_connac_mcu_add_key(&dev->mt76, vif, &msta->bip, + key, MCU_UNI_CMD(STA_REC_UPDATE), + &msta->wcid, cmd); diff --git a/queue-6.1/zsmalloc-document-freeable-stats.patch b/queue-6.1/zsmalloc-document-freeable-stats.patch new file mode 100644 index 00000000000..616d35bb43f --- /dev/null +++ b/queue-6.1/zsmalloc-document-freeable-stats.patch @@ -0,0 +1,34 @@ +From 618a8a917dbf5830e2064d2fa0568940eb5d2584 Mon Sep 17 00:00:00 2001 +From: Sergey Senozhatsky +Date: Sat, 25 Mar 2023 11:46:31 +0900 +Subject: zsmalloc: document freeable stats + +From: Sergey Senozhatsky + +commit 618a8a917dbf5830e2064d2fa0568940eb5d2584 upstream. + +When freeable class stat was added to classes file (back in 2016) we +forgot to update zsmalloc documentation. Fix that. + +Link: https://lkml.kernel.org/r/20230325024631.2817153-3-senozhatsky@chromium.org +Fixes: 1120ed548394 ("mm/zsmalloc: add `freeable' column to pool stat") +Signed-off-by: Sergey Senozhatsky +Cc: Minchan Kim +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + Documentation/mm/zsmalloc.rst | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/Documentation/mm/zsmalloc.rst ++++ b/Documentation/mm/zsmalloc.rst +@@ -68,6 +68,8 @@ pages_used + the number of pages allocated for the class + pages_per_zspage + the number of 0-order pages to make a zspage ++freeable ++ the approximate number of pages class compaction can free + + We assign a zspage to ZS_ALMOST_EMPTY fullness group when n <= N / f, where +