summaryrefslogtreecommitdiff
AgeCommit message (Collapse)Author
2026-06-03Bluetooth: RFCOMM: validate skb length in MCC handlersSeungJu Cheon
The RFCOMM MCC handlers cast skb->data to protocol-specific structs without validating skb->len first. A malicious remote device can send truncated MCC frames and trigger out-of-bounds reads in these handlers. Fix this by using skb_pull_data() to validate and access the required data before dereferencing it. rfcomm_recv_rpn() requires special handling since ETSI TS 07.10 allows 1-byte RPN requests. Handle this by validating only the DLCI byte first, and validating the full struct only when len > 1. Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2") Suggested-by: Muhammad Bilal <meatuni001@gmail.com> Signed-off-by: SeungJu Cheon <suunj1331@gmail.com> Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
2026-06-03Bluetooth: MGMT: validate advertising TLV before type checksZhang Cen
tlv_data_is_valid() reads each advertising data field length from data[i], then inspects data[i + 1] for managed EIR types before checking that the current field still fits inside the supplied buffer. A malformed field whose length byte is the last byte of the buffer can therefore make the parser read one byte past the advertising data. KASAN reported the following when a malformed MGMT_OP_ADD_ADVERTISING request reached that path: BUG: KASAN: vmalloc-out-of-bounds in tlv_data_is_valid() Read of size 1 Call trace: tlv_data_is_valid() add_advertising() hci_mgmt_cmd() hci_sock_sendmsg() Move the existing element-length check before any type-octet inspection so each non-empty element is proven to contain its type byte before the parser looks at data[i + 1]. Fixes: 2bb36870e8cb ("Bluetooth: Unify advertising instance flags check") Reviewed-by: Paul Menzel <pmenzel@molgen.mpg.de> Signed-off-by: Zhang Cen <rollkingzzc@gmail.com> Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
2026-06-03Bluetooth: RFCOMM: hold listener socket in rfcomm_connect_ind()Zhang Cen
rfcomm_get_sock_by_channel() scans rfcomm_sk_list under the list lock, but returns the selected listener after dropping that lock without taking a reference. rfcomm_connect_ind() then locks the listener, queues a child socket on it, and may notify it after unlocking it. The buggy scenario involves two paths, with each column showing the order within that path: rfcomm_connect_ind(): listener close: 1. Find parent in 1. close() enters rfcomm_get_sock_by_channel() rfcomm_sock_release(). 2. Drop rfcomm_sk_list.lock 2. rfcomm_sock_shutdown() without pinning parent. closes the listener. 3. Call lock_sock(parent) and 3. rfcomm_sock_kill() bt_accept_enqueue(parent, unlinks and puts parent. sk, true). 4. Read parent flags and may 4. parent can be freed. call sk_state_change(). If close wins the race, parent can be freed before rfcomm_connect_ind() reaches lock_sock(), bt_accept_enqueue(), or the deferred-setup callback. Take a reference on the listener before leaving rfcomm_sk_list.lock. After lock_sock() succeeds, recheck that it is still in BT_LISTEN before queueing a child, cache the deferred-setup bit while the parent is locked, and drop the reference after the last parent use. KASAN reported a slab-use-after-free in lock_sock_nested() from rfcomm_connect_ind(), with the freeing stack going through rfcomm_sock_kill() and rfcomm_sock_release(). Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2") Signed-off-by: Zhang Cen <rollkingzzc@gmail.com> Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
2026-06-03x86/virt/seamldr: Abort updates after a failed stepChao Gao
A TDX module update is a multi-step process, and any step can fail. The current update flow continues to later steps after an error. Continuing after a failure can cause the TDX module to enter an unrecoverable state. But certain failures during the initial module shutdown step should simply return an error to userspace, so the update can be retried cleanly. To preserve that recoverability, one option would be to abort the update only for those failures, since they occur before any TDX module state is changed. But special-casing specific failures in specific steps would complicate the do-while() update loop for no benefit. Simply abort update on any failure, at any step. Track failures for each step, stop the update loop once a failure is observed, and do not advance the state machine to the next step. [ dhansen: style nits ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Xu Yilun <yilun.xu@linux.intel.com> Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Link: https://lore.kernel.org/linux-coco/aQFmOZCdw64z14cJ@google.com/ # [1] Link: https://patch.msgid.link/20260520133909.409394-16-chao.gao@intel.com
2026-06-03x86/virt/seamldr: Introduce skeleton for TDX module updatesChao Gao
tl;dr: Use stop_machine() and a state machine based on the "MULTI_STOP" pattern to implement core TDX module update logic. Long version: TDX module updates require careful synchronization with other TDX operations. The requirements are (#1/#2 reflect current behavior that must be preserved): 1. SEAMCALLs need to be callable from both process and IRQ contexts. 2. SEAMCALLs need to be able to run concurrently across CPUs 3. During updates, only update-related SEAMCALLs are permitted; all other SEAMCALLs shouldn't be called. 4. During updates, all online CPUs must participate in the update work. No single lock primitive satisfies all requirements. For instance, rwlock_t handles #1/#2 but fails #4: CPUs spinning with IRQs disabled cannot be directed to perform update work. Use stop_machine() as it is the only well-understood mechanism that can meet all requirements. And TDX module updates consist of several steps (See Intel Trust Domain Extensions (Intel TDX) Module Base Architecture Specification, Chapter "TD-Preserving TDX module Update"). Ordering requirements between steps mandate lockstep synchronization across all CPUs. multi_cpu_stop() provides a good example of executing a multi-step task in lockstep across CPUs, but it does not synchronize the individual steps inside the callback itself. Implement a similar state machine as the skeleton for TDX module updates. Each state represents one step in the update flow, and the state advances only after all CPUs acknowledge completion of the current step. This acknowledgment mechanism provides the required lockstep execution. The update flow is intentionally simpler than multi_cpu_stop() in two ways: a) use a spinlock to protect the control data instead of atomic_t and explicit memory barriers. b) omit touch_nmi_watchdog() and rcu_momentary_eqs(), which exist there for debugging and are not strictly needed for this update flow Potential alternative to stop_machine() ======================================= An alternative approach is to lock all KVM entry points and kick all vCPUs. Here, KVM entry points refer to KVM VM/vCPU ioctl entry points, implemented in KVM common code (virt/kvm). Adding a locking mechanism there would affect all architectures KVM supports. And to lock only TDX vCPUs, new logic would be needed to identify TDX vCPUs, which the KVM common code currently lacks. This would add significant complexity and maintenance overhead to KVM for this TDX-specific use case, so don't take this approach. [ dhansen: normal changelog/style munging ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Xu Yilun <yilun.xu@linux.intel.com> Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Rick Edgecombe <rick.p.edgecombe@intel.com> Link: https://patch.msgid.link/20260520133909.409394-15-chao.gao@intel.com
2026-06-03x86/virt/seamldr: Allocate and populate a module update requestChao Gao
There are two important ABIs here: 'struct tdx_image' - The on-disk and in-memory format for a TDX module update image. 'struct seamldr_params' - The in-memory ABI passed to the TDX module loader. Points to a single 'struct tdx_image' broken up into 4k pages. Userspace supplies the update image in 'struct tdx_image' format. The image consists of a header followed by a sigstruct and the module binary. P-SEAMLDR, however, consumes 'struct seamldr_params' rather than the image directly. Parse the 'struct tdx_image' provided by userspace and populate a matching 'struct seamldr_params'. The 'tdx_image' ABI is versioned. Two public versions exist today: 0x100 and 0x200. This kernel only accepts 0x200. The older 0x100 format is being deprecated and is intentionally not supported here. Future versions of the module might be able to use the same ABIs (user/kernel and kernel/SEAMLDR) but they will not be able to use this kernel code. Reject module images without that specific version. This ensures that the kernel is able to understand the passed-in format. Validate the 'struct tdx_image' header before using it, because the header is consumed solely by the kernel to locate the sigstruct and module within the image. Do not validate the payload itself. The sigstruct and module pages are passed through to P-SEAMLDR, which validates them as part of the update. sigstruct_pages_pa_list currently has only one entry, but it will grow to four pages in the future. Keep it as an array for symmetry with module_pages_pa_list and for extensibility. [ dhansen: normal changelog clarification/munging ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-14-chao.gao@intel.com
2026-06-03coco/tdx-host: Implement firmware upload sysfs ABI for TDX module updatesChao Gao
tl;dr: Select fw_upload for doing TDX module updates. The process of selecting among available update images is complicated and nuanced. Punt the selection process out to userspace. One existing userspace implementation today is the script in the Intel TDX Module Binaries repository[1]. Long Version: The kernel supports two primary firmware update mechanisms: 1. request_firmware() - used by microcode, SEV firmware, hundreds of other drivers 2. 'struct fw_upload' - used by CXL, FPGA updates, dozens of others The key difference between is that request_firmware() loads a named file from the filesystem where the filename is kernel-controlled, while fw_upload accepts firmware data directly from userspace. TDX module firmware update selection policy is too complex for the kernel. Leave it to userspace and use fw_upload. Add a skeleton fw_upload implementation to be fleshed out in subsequent patches. Refactor the sysfs visiblity attribute function so it can be used as a more generic flag for the presence of viable runtime update support. Why fw_upload instead of request_firmware()? ============================================ Selecting a TDX module update image is not a simple "load the latest" decision. Userspace needs to choose an image that is compatible with both the platform and the currently running module. Some constraints are hard requirements: a. Module version series are platform-specific. For example, the 1.5.x series runs on Sapphire Rapids but not Granite Rapids, which needs 2.0.x. b. Updates are also constrained by version distance. A 1.5.6 module might permit updates to 1.5.7 but not to 1.5.50. There may also be userspace policy choices: c. Decide the update direction: upgrade or downgrade d. Choose whether to optimize for fewer updates or smaller version steps, for example, 1.2.3=>1.2.5 versus 1.2.3=>1.2.4=>1.2.5. Given that complexity, leave module selection to userspace and use fw_upload. 1. https://github.com/intel/confidential-computing.tdx.tdx-module.binaries/blob/main/version_select_and_load.py [ dhansen: add version script link, add more explanation of code moves, fix some minor whitespace issues ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Link: https://lore.kernel.org/kvm/01fc8946-eb84-46fa-9458-f345dd3f6033@intel.com/ Link: https://patch.msgid.link/20260520133909.409394-13-chao.gao@intel.com
2026-06-03coco/tdx-host: Don't expose P-SEAMLDR information on CPUs with erratumChao Gao
TDX-capable CPUs clobber the current VMCS on P-SEAMLDR calls. Clearing the current VMCS behind KVM's back breaks KVM. Future CPUs will fix this by preserving the current VMCS across P-SEAMLDR calls. A future specification update will describe the VMCS-clearing behavior as an erratum and to state that it does not occur when IA32_VMX_BASIC[60] is set. Add a CPU bug bit and refuse to expose P-SEAMLDR information on affected CPUs. Use a CPU bug bit to stay consistent with X86_BUG_TDX_PW_MCE. As a bonus, the bug bit is visible to userspace, which allows userspace to determine why these sysfs files are not exposed, and it can also be checked by other kernel components in the future if needed. == Alternatives == Two workarounds were considered but both were rejected: 1. Save/restore the current VMCS around P-SEAMLDR calls. This produces ugly assembly code [1] and doesn't play well with #MCE or #NMI if they need to use the current VMCS. 2. Move KVM's VMCS tracking logic to the TDX core code, which would break the boundary between KVM and the TDX core code [2]. [ dhansen: comment and changelog munging. Add seamldr_call() bug check. ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Rick Edgecombe <rick.p.edgecombe@intel.com> Reviewed-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://lore.kernel.org/kvm/fedb3192-e68c-423c-93b2-a4dc2f964148@intel.com/ # [1] Link: https://lore.kernel.org/kvm/aYIXFmT-676oN6j0@google.com/ # [2] Link: https://patch.msgid.link/20260520133909.409394-12-chao.gao@intel.com
2026-06-03coco/tdx-host: Expose P-SEAMLDR information via sysfsChao Gao
TDX module updates require userspace to select the appropriate module to load. Expose necessary information to facilitate this decision. Two values are needed: - P-SEAMLDR version: for compatibility checks between TDX module and P-SEAMLDR - num_remaining_updates: indicates how many updates can be performed Expose them as tdx-host device attributes visible only when updates are supported. Note that the underlying P-SEAMLDR attributes are available regardless of update support; this only restricts their visibility to userspace. Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-11-chao.gao@intel.com
2026-06-03x86/virt/seamldr: Add a helper to retrieve P-SEAMLDR informationChao Gao
P-SEAMLDR reports its state via SEAMLDR.INFO, including its version and the number of remaining runtime updates. This information is useful for userspace. For example, userspace can use the P-SEAMLDR version to determine whether a candidate TDX module is compatible with the running loader, and can use the remaining update count to determine whether another runtime update is still possible. Add a helper to retrieve P-SEAMLDR information in preparation for exposing P-SEAMLDR version and other necessary information to userspace. Export the new kAPI for use by the "tdx_host" device. Note that there are two distinct P-SEAMLDR APIs with similar names: "SEAMLDR.INFO" is metadata about the loader. It's metadata for the update process. "SEAMLDR.SEAMINFO" is metadata about SEAM mode. It is for the module init process, not for the update process. Use SEAMLDR.INFO here. For details, see "Intel Trust Domain Extensions - SEAM Loader (SEAMLDR) Interface Specification". Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Xiaoyao Li <xiaoyao.li@intel.com> Reviewed-by: Rick Edgecombe <rick.p.edgecombe@intel.com> Reviewed-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-10-chao.gao@intel.com
2026-06-03x86/virt/seamldr: Introduce a wrapper for P-SEAMLDR SEAMCALLsChao Gao
The TDX architecture uses the "SEAMCALL" instruction to communicate with SEAM mode software. Right now, the only SEAM mode software that the kernel communicates with is the TDX module. But, there is actually another component that runs in SEAM mode but it is separate from the TDX module: the persistent SEAM loader or "P-SEAMLDR". Right now, the only component that communicates with it is the BIOS which loads the TDX module itself at boot. But, to support updating the TDX module, the kernel now needs to be able to talk to it. P-SEAMLDR SEAMCALLs differ from TDX module SEAMCALLs in areas such as concurrency requirements. Add a P-SEAMLDR wrapper to handle these differences and prepare for implementing concrete functions. Use seamcall_prerr() (not '_ret') because current P-SEAMLDR calls do not use any output registers other than RAX. Note: Despite the similar name, the NP-SEAMLDR ("Non-Persistent") (ACM) invoked exclusively by the BIOS at boot rather than a component running in SEAM mode. The kernel cannot call it at runtime. It exposes no SEAMCALL interface. Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Binbin Wu <binbin.wu@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Xiaoyao Li <xiaoyao.li@intel.com> Reviewed-by: Rick Edgecombe <rick.p.edgecombe@intel.com> Reviewed-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://cdrdv2.intel.com/v1/dl/getContent/733582 # [1] Link: https://patch.msgid.link/20260520133909.409394-9-chao.gao@intel.com
2026-06-03coco/tdx-host: Expose TDX module versionChao Gao
For TDX module updates, userspace needs to select compatible update versions based on the current module version. For example, the 1.5.x series runs on Sapphire Rapids but not Granite Rapids, which needs 2.0.x. Updates are also constrained by version distance, so a 1.5.6 module might permit updates to 1.5.7 but not to 1.5.20. Start the process of punting the version selection logic to userspace. Expose the TDX module version in the new faux device. Define TDX_VERSION_FMT macro for the TDX version format since it will be used multiple times. Also convert an existing print statement to use it. == Background == For posterity, here's what other firmware mechanisms do: 1. AMD SEV leverages an existing PCI device for the PSP to expose metadata. TDX uses a faux device as it doesn't have PCI device in its architecture. 2. Microcode uses per-CPU virtual devices to report microcode revisions because CPUs can have different revisions. But, there is only a single TDX module, so exposing the TDX module version through a global TDX faux device is appropriate 3. ARM's CCA implementation isn't in-tree yet, but will likely follow a similar faux device approach, though it's unclear whether they need to expose firmware version information [ dhansen: trim changelog ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Binbin Wu <binbin.wu@linux.intel.com> Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com> Reviewed-by: Xu Yilun <yilun.xu@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Xiaoyao Li <xiaoyao.li@intel.com> Reviewed-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://lore.kernel.org/all/2025073035-bulginess-rematch-b92e@gregkh/ # [1] Link: https://patch.msgid.link/20260520133909.409394-8-chao.gao@intel.com
2026-06-03coco/tdx-host: Introduce a "tdx_host" deviceChao Gao
TDX depends on a platform firmware module that runs on the CPU. Unlike other CoCo architectures, TDX has no hardware "device" running the show, just a blob on the CPU. Create a virtual device to anchor interactions with this platform firmware. This lets later code: - expose metadata: TDX module version, seamldr version, to userspace as device attributes - implement firmware uploader APIs (which are tied to a device) to support TDX module runtime updates Use a faux device because the TDX module is singular within the system and has no platform resources. Using a faux device eliminates the need to create a stub bus. The call to tdx_get_sysinfo() ensures that the TDX module is ready to provide services. Note that AMD has a PCI device for the PSP for SEV and ARM CCA will likely have a faux device [1]. Thanks to Dan and Yilun for all the help on this one. [ dhansen: trim changelog ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Jonathan Cameron <jonathan.cameron@huawei.com> Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com> Reviewed-by: Xu Yilun <yilun.xu@linux.intel.com> Reviewed-by: Kai Huang <kai.huang@intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Xiaoyao Li <xiaoyao.li@intel.com> Link: https://lore.kernel.org/all/2025073035-bulginess-rematch-b92e@gregkh/ # [1] Link: https://patch.msgid.link/20260520133909.409394-7-chao.gao@intel.com
2026-06-03x86/virt/tdx: Move low level SEAMCALL helpers out of <asm/tdx.h>Kai Huang
TDX host core code implements three seamcall*() helpers to make SEAMCALLs to the TDX module. Currently, they are implemented in <asm/tdx.h> and are exposed to other kernel code which includes <asm/tdx.h>. However, other than the TDX host core, seamcall*() are not expected to be used by other kernel code directly. For instance, for all SEAMCALLs that are used by KVM, the TDX host core exports a wrapper function for each of them. Move seamcall*() and related code out of <asm/tdx.h> and make them only visible to TDX host core. Since TDX host core tdx.c is already very heavy, don't put low level seamcall*() code there but to a new dedicated "seamcall_internal.h". Also, currently tdx.c has seamcall_prerr*() helpers which additionally print error message when calling seamcall*() fails. Move them to "seamcall_internal.h" as well. In such way all low level SEAMCALL helpers are in a dedicated place, which is much more readable. Copy the copyright notice from the original files and consolidate the date ranges to: Copyright (C) 2021-2023 Intel Corporation Signed-off-by: Kai Huang <kai.huang@intel.com> Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com> Reviewed-by: Binbin Wu <binbin.wu@linux.intel.com> Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com> Reviewed-by: Kiryl Shutsemau (Meta) <kas@kernel.org> Reviewed-by: Xiaoyao Li <xiaoyao.li@intel.com> Reviewed-by: Vishal Annapurve <vannapurve@google.com> Acked-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-6-chao.gao@intel.com
2026-06-03x86/virt/tdx: Move TDX_FEATURES0 bits to asm/tdx.hChao Gao
Future changes will add support for new TDX features exposed as TDX_FEATURES0 bits. The presence of these features will need to be checked outside of arch/x86/virt. The feature query helpers and the TDX_FEATURES0 defines they reference will need to live in the widely accessible asm/tdx.h header. Move the existing TDX_FEATURES0 to asm/tdx.h so that they can all be kept together. Opportunistically switch to BIT_ULL() since TDX_FEATURES0 is 64-bit. No functional change intended. [ dhansen: grammar fixups ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://lore.kernel.org/kvm/20260427152854.101171-17-chao.gao@intel.com/ # [1] Link: https://lore.kernel.org/kvm/20251121005125.417831-16-rick.p.edgecombe@intel.com/ # [2] Link: https://patch.msgid.link/20260520133909.409394-5-chao.gao@intel.com
2026-06-03x86/virt/tdx: Consolidate TDX global initialization statesChao Gao
The kernel uses several global flags to guard one-time TDX initialization flows and prevent them from being repeated. When the TDX module is updated, all of those states must be reset so that the module can be initialized again. Today those states are kept as separate global variables, which makes the reset path awkward and easy to miss when a new state is added. Group the states into a single structure so they can be reset together, for example with memset(), and so a newly added state won't be missed. Drop the __ro_after_init annotation from tdx_module_initialized because the other two states do not have it. And with TDX module update support, all the states need to be writable at runtime. Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-4-chao.gao@intel.com
2026-06-03x86/virt/tdx: Move TDX global initialization states to file scopeChao Gao
TDX module global initialization is executed only once. The first call caches both the result and the "done" state, and later callers reuse the saved result. A lock protects that cached states. Those states and the lock are currently kept as function-local statics because they are used only by try_init_module_global(). TDX module updates need to reset the cached states so TDX global initialization can be run again after an update. That will add another access site in the same file. Move the cached states to file scope so it is accessible outside try_init_module_global(), and move the lock along with the states it protects. No functional change intended. Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-3-chao.gao@intel.com
2026-06-03x86/virt/tdx: Clarify try_init_module_global() result cachingChao Gao
TDX module global initialization is executed only once. The first call caches both the return code and the "done" state in static function variables. Later callers read the variables. A lock protects the saved state and serializes callers. These variables will soon be moved to a global structure. Prepare for that by treating the variables as a unit. Assign them together and limit accesses to while the lock is held. [ dhansen: mostly rewrite changelog ] Signed-off-by: Chao Gao <chao.gao@intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Link: https://patch.msgid.link/20260520133909.409394-2-chao.gao@intel.com
2026-06-03Merge branch 'kvm-ghcb-for-7.2' into HEADPaolo Bonzini
Merge the final part of the GHCB 7.2 fixes at https://lore.kernel.org/kvm/20260529183549.1104619-1-pbonzini@redhat.com/. Patches 1-17 have already been included in Linux 7.1; these are minor cleanups, and fixes for behaviors that are suboptimal or contradicting the specification. Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Remove sometimes-used function-scoped "ret" from #VMGEXIT handlerSean Christopherson
Now that only two case-statements actually need a local "ret" variable, refactor sev_handle_vmgexit() to have all flows return directly when possible, and bury "ret" as "r" in the two paths that need to propagate a return value from a helper. No functional change intended. Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-25-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-25-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Turn sev_es_validate_vmgexit() into a dedicated predicateSean Christopherson
Now that sev_es_validate_vmgexit() is only responsible for checking that all required GHCB fields are marked valid, turn it into a predicate whose name reflects exactly that. No functional change intended. Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-24-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-24-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Handle unknown #VMGEXIT reasons in sev_handle_vmgexit()Sean Christopherson
Handle unknown #VMGEXIT reasons in sev_handle_vmgexit(), not in sev_es_validate_vmgexit(). This makes it _much_ more obvious that KVM simply funnels "legacy" exits to the standard SVM interception handlers, and is the final preparatory change needed to reduce the scope of sev_es_validate_vmgexit(). No functional change intended. Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-23-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-23-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Return INVALID_INPUT, not MISSING_INPUT, for bad GUEST_REQUEST ↵Sean Christopherson
input(s) Return INVALID_INPUT, not MISSING_INPUT, if the guest provides an unaligned address for a GUEST_REQUEST, and/or attempts to use the same page for the source and destination. The inputs are obviously invalid, not missing. Opportunistically move the checks out of sev_es_validate_vmgexit(), to continue the march towards reducing the scope of the helper, and to help guide future changes into correctly handling bad input. Fixes: 88caf544c930 ("KVM: SEV: Provide support for SNP_GUEST_REQUEST NAE event") Fixes: 74458e4859d8 ("KVM: SEV: Provide support for SNP_EXTENDED_GUEST_REQUEST NAE event") Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-22-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-22-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Return INVALID_EVENT for SNP-only #VMGEXIT from non-SNP guestSean Christopherson
Signal INVALID_EVENT, not MISSING_INPUT, if a non-SNP guest attempts to invoke an SNP-only #VMGEXIT. Opportunistically move the checks out of sev_es_validate_vmgexit() to continue the march towards making said helper a predicate whose sole purpose is to verify the guest has marked required GHCB fields as valid. Fixes: e366f92ea99e ("KVM: SEV: Support SEV-SNP AP Creation NAE event") Fixes: 9b54e248d264 ("KVM: SEV: Add support to handle Page State Change VMGEXIT") Fixes: 88caf544c930 ("KVM: SEV: Provide support for SNP_GUEST_REQUEST NAE event") Fixes: 74458e4859d8 ("KVM: SEV: Provide support for SNP_EXTENDED_GUEST_REQUEST NAE event") Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-21-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-21-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Move GHCB "usage" check out of sev_es_validate_vmgexit()Sean Christopherson
Move the check to verify the guest's requested GHCB out of sev_es_validate_vmgexit() as the first step towards making said helper a predicate whose sole purpose is to verify the guest has marked required GHCB fields as valid. Using a single "validate" helper sounds good on paper, but in practice it's difficult to verify that KVM is performing the necessary sanity checks (the usage of state is far removed from the relevant checks), makes it difficult to understand that "legacy" exits are simply routed to KVM's existing exit handlers, and most importantly, has directly contributed to a number of bugs as adding case-statements to the validation subtly removes them from the default path that rejects unknown exit codes with INVALID_EVENT. Deliberately extract the usage code check first so as to preserve the order of KVM's checks, even though future code extraction will technically fix bugs. No functional change intended. Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-20-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-20-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Don't terminate SNP VMs on #VMGEXIT without a registered GHCBSean Christopherson
If the guest attempts a non-MSR #VMGEXIT without the registered GHCB, return a GHCB_HV_RESP_MALFORMED_INPUT+GHCB_ERR_NOT_REGISTERED error to the guest instead of exiting KVM_RUN with -EINVAL (and in likelihood killing the VM). KVM has already mapped the requested GHCB, i.e. can cleanly report an error, and so exiting with -EINVAL is completely unjustified. Fixes: 0c76b1d08280 ("KVM: SEV: Add support to handle GHCB GPA register VMGEXIT") Cc: stable@vger.kernel.org Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-19-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-19-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03gpu: nova-core: gsp: enable FSP boot pathAlexandre Courbot
Now that all the elements are in place, enable the FSP boot path so Hopper and Blackwell can boot. Reviewed-by: Eliot Courtney <ecourtney@nvidia.com> Link: https://patch.msgid.link/20260603-b4-blackwell-v13-9-d9f3a06939e0@nvidia.com Signed-off-by: Alexandre Courbot <acourbot@nvidia.com>
2026-06-03gpu: nova-core: add non-sec2 unload pathEliot Courtney
For non-sec2 it is only required to wait for GSP falcon to halt. This is because GSP does the main work of unloading on GPUs not using sec2. Signed-off-by: Eliot Courtney <ecourtney@nvidia.com> [ jhubbard: use Result instead of Result<()> in the UnloadBundle impl ] Signed-off-by: John Hubbard <jhubbard@nvidia.com> Link: https://patch.msgid.link/20260603-b4-blackwell-v13-8-d9f3a06939e0@nvidia.com Signed-off-by: Alexandre Courbot <acourbot@nvidia.com>
2026-06-03gpu: nova-core: Hopper/Blackwell: add GSP lockdown release pollingJohn Hubbard
On Hopper and Blackwell, FSP boots GSP with hardware lockdown enabled. After FSP Chain of Trust completes, the driver must poll for lockdown release before proceeding with GSP initialization. Add the register bit and helper functions needed for this polling. Signed-off-by: John Hubbard <jhubbard@nvidia.com> Link: https://patch.msgid.link/20260603-b4-blackwell-v13-7-d9f3a06939e0@nvidia.com [acourbot: fix `lockdown_released` logic and add explanatory comments.] Signed-off-by: Alexandre Courbot <acourbot@nvidia.com>
2026-06-03gpu: nova-core: Hopper/Blackwell: add FSP Chain of Trust bootJohn Hubbard
Build and send the Chain of Trust message to FSP, bundling the DMA-coherent boot parameters that FSP reads at boot time. Signed-off-by: John Hubbard <jhubbard@nvidia.com> Link: https://patch.msgid.link/20260603-b4-blackwell-v13-6-d9f3a06939e0@nvidia.com [acourbot: rename `frts_offset` to `frts_vidmem_offset`.] [acourbot: add note about frts_sysmem_* CoT members.] Co-developed-by: Alexandre Courbot <acourbot@nvidia.com> Signed-off-by: Alexandre Courbot <acourbot@nvidia.com>
2026-06-03Merge tag 'kvm-s390-master-7.1-3' of ↵Paolo Bonzini
https://git.kernel.org/pub/scm/linux/kernel/git/kvms390/linux into HEAD KVM: s390: More gmap and vsie fixes
2026-06-03KVM: SEV: Unmap and unpin the GHCB as needed on vCPU freeSean Christopherson
Unmap and unpin the GHCB as needed when freeing a vCPU. If the VM is destroyed after mapping+pinning the GHCB on #VMGEXIT, without re-running the vCPU, KVM will effectively leak the GHCB and any mappings created for the GHCB. Fixes: 291bd20d5d88 ("KVM: SVM: Add initial support for a VMGEXIT VMEXIT") Cc: stable@vger.kernel.org Tested-by: Michael Roth <michael.roth@amd.com> Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-18-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-18-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Decouple the need to sync the GHCB SA from the need to free the SASean Christopherson
Decouple synchronizing the GHCB SA from freeing/unpinning the SA, so that the free/unpin path can be reused when freeing a vCPU. Opportunistically add a WARN to harden KVM against stomping over (and thus leaking) an already-allocated scratch area. Cc: stable@vger.kernel.org Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-17-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-17-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Move sev_free_vcpu() down below sev_es_unmap_ghcb()Sean Christopherson
Relocate sev_free_vcpu() down in sev.c so that it's definition comes after sev_es_unmap_ghcb(). This will allow sharing unmap functionality between the two functions without needing a forward declaration (or weird placement of the common code). No functional change intended. Cc: stable@vger.kernel.org Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-16-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-16-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: Don't WARN if memory is dirtied without a vCPU when the VM is dyingSean Christopherson
When marking a page dirty, complain about not having a running/loaded vCPU if and only if the VM is still alive, i.e. its refcount is non-zero. This will allow fixing a memory leak for x86 SEV-ES guests without hitting what is effectively a false positive on the WARN. For some SEV-ES VM-Exits, KVM keeps a writable mapping of a guest page across an exit to userspace, and typically unmaps the page on the next KVM_RUN. But if userspace never calls KVM_RUN after such an exit, then KVM needs to unmap the page when the vCPU is destroyed, which in turn triggers the WARN about not having a running vCPU. Alternatively, SEV-ES could temporarily load the vCPU to suppress the WARN, as is done in nested_vmx_free_vcpu() (but for completely unrelated reasons; suppressing WARN from nested_put_vmcs12_pages() is pure happenstance). But loading a vCPU during destruction is gross (ideally nVMX code would be cleaned up), risks complicating the SEV-ES code (KVM would need to ensure the temporarily load()+put() only runs when the vCPU isn't already loaded), and is ultimately pointless. The motivation for the WARN is to guard against KVM dirtying guest memory without pushing the corresponding GFN to the active vCPU's dirty ring, e.g. to ensure userspace doesn't miss a dirty page. But for the VM's refcount to reach zero, there can't be _any_ userspace mappings to the dirty ring, as mapping the dirty ring requires doing mmap() on the vCPU FD. I.e. if userspace had a valid mapping for the dirty ring, then the vCPU file and thus the owning VM would still be alive. And so since userspace can't possibly reach the dirty ring, whether or not KVM technically "misses" a push to the dirty ring is irrelevant. Reported-by: Michael Roth <michael.roth@amd.com> Cc: stable@vger.kernel.org Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-15-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-15-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Read start/end indices of PSC requests exactly once per #VMGEXITSean Christopherson
Rework Page State Change (PSC) handling to read the guest-provided start and end indices exactly once, at the beginning of the request. Re-reading the indices is "fine", _if_ the guest is well-behaved. KVM _should_ be safe against concurrent guest modification of the indices, but there is zero reason to introduce unnecessary risk. Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-14-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-14-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Add an anonymous "psc" struct to track current PSC metadataSean Christopherson
Add a "psc" struct to vcpu_sev_es_state to avoid having to prefix all of the fields with "psc_". Take advantage of the code churn to opportunistically rename local variables to "guest_psc" to make it more obvious that the buffer is guest data, and more importantly, guest accessible! Opportunistically rename inflight => batch_size as well, because there can really only be one operation in-flight (per-vCPU), i.e. "inflight" _looks_ like a boolean, but in actuality is an integer tracking how many pages are being handled by the current operation. No functional change intended. Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-13-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-13-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03KVM: SEV: Make it more obvious when KVM is writing back the current PSC indexSean Christopherson
Increment the guest-visible "cur_entry" index outside of the for-loop when processing Page State Change entries, and add a comment to make it more obvious which code is operating on trusted data, and which code is touching guest-accessible data. No functional change intended. Reviewed-by: Tom Lendacky <thomas.lendacky@amd.com> Reviewed-by: Michael Roth <michael.roth@amd.com> Signed-off-by: Sean Christopherson <seanjc@google.com> Message-ID: <20260501202250.2115252-12-seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Message-ID: <20260529183549.1104619-12-pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2026-06-03fs/ntfs3: validate lcns_follow in log_replay conversionKonstantin Komarov
log_replay() converts DIR_PAGE_ENTRY_32 records into DIR_PAGE_ENTRY records when replaying version 0 restart tables. During this conversion, the memmove() length is derived directly from the on-disk lcns_follow field: memmove(&dp->vcn, &dp0->vcn_low, 2 * sizeof(u64) + le32_to_cpu(dp->lcns_follow) * sizeof(u64)); check_rstbl() validates restart table structure, but does not constrain per-entry lcns_follow values relative to the entry size. A malformed filesystem image can provide an oversized lcns_follow value, causing the conversion memmove() to access memory beyond the bounds of the allocated restart table buffer. The same field is later used to bound iteration over page_lcns[], so validating lcns_follow during conversion also prevents downstream out-of-bounds access from the same malformed metadata. Compute the maximum valid lcns_follow from the already-validated restart table entry size and reject entries that exceed this bound. Reuse the existing t16/t32 scratch variables already declared in log_replay() to avoid introducing new declarations. Fixes: b46acd6a6a62 ("fs/ntfs3: Add NTFS journal") Cc: stable@vger.kernel.org Signed-off-by: Pavitra Jha <jhapavitra98@gmail.com> [almaz.alexandrovich@paragon-software.com: fixed the conflicts] Signed-off-by: Konstantin Komarov <almaz.alexandrovich@paragon-software.com>
2026-06-03fs/ntfs3: bound copy_lcns dp->page_lcns[] index in analysis passMichael Bommarito
In log_replay()'s analysis pass, after find_dp() returns a valid DIR_PAGE_ENTRY for the (target_attr, target_vcn) tuple, the copy_lcns block walks lrh->lcns_follow further entries: t16 = le16_to_cpu(lrh->lcns_follow); for (i = 0; i < t16; i++) { size_t j = (size_t)(le64_to_cpu(lrh->target_vcn) - le64_to_cpu(dp->vcn)); dp->page_lcns[j + i] = lrh->page_lcns[i]; } find_dp() only validates that target_vcn falls within [dp->vcn, dp->vcn + dp->lcns_follow), i.e., that the FIRST cluster is covered. The walk through the further entries is not bounded against dp->lcns_follow. For a malformed LRH where target_vcn = dp->vcn + dp->lcns_follow - 1 and lrh->lcns_follow > 1, the i > 0 writes overflow the dp's allocated page_lcns[] array. Add the missing j + lrh->lcns_follow <= dp->lcns_follow guard. Reproduced under UML+KASAN on mainline 8d90b09e6741 as a slab-out-of-bounds write of size 8 from log_replay+0x68d4 on the mount path. This is distinct from Pavitra Jha's 2026-05-02 patch ("fs/ntfs3: validate lcns_follow in log_replay conversion", <20260502154252.164586-1-jhapavitra98@gmail.com>) which addresses the separate version-0 dirty-page-table conversion path's memmove(&dp->vcn, ...) call. The two fixes are complementary; both should land. Fixes: b46acd6a6a62 ("fs/ntfs3: Add NTFS journal") Cc: stable@vger.kernel.org Assisted-by: Claude:claude-opus-4-7 Signed-off-by: Michael Bommarito <michael.bommarito@gmail.com> [almaz.alexandrovich@paragon-software.com: clang-formatted the changes, fixed conflicts] Signed-off-by: Konstantin Komarov <almaz.alexandrovich@paragon-software.com>
2026-06-03fs/ntfs3: bound DeleteIndexEntryAllocation memmove lengthKonstantin Komarov
In do_action()'s DeleteIndexEntryAllocation case, e->size comes from an on-disk INDEX_BUFFER entry. When e->size makes e + e->size point past hdr + hdr->used, PtrOffset(e1, Add2Ptr(hdr, used)) returns a negative ptrdiff_t that is silently cast to a quasi-infinite size_t when passed to memmove(). The memmove then walks past the destination buffer. The sibling DeleteIndexEntryRoot case at fslog.c:3540-3543 already carries the corresponding guard: if (PtrOffset(e1, Add2Ptr(hdr, used)) < esize || Add2Ptr(e, esize) > Add2Ptr(lrh, rec_len) || used + esize > le32_to_cpu(hdr->total)) { goto dirty_vol; } Apply the same shape to the allocation-path case. Also reject esize == 0: memmove(e, e, ...) is a no-op and leaves hdr->used unchanged, hiding a malformed entry from the existing check_index_header() walk. Reproduced under UML+KASAN on mainline 8d90b09e6741 by mounting a crafted NTFS image: the unguarded memmove takes a length of 0xffffffffffffff00 and the kernel oopses in memmove+0x81/0x1a0 on the do_action+0x36a2 frame. Fixes: b46acd6a6a62 ("fs/ntfs3: Add NTFS journal") Cc: stable@vger.kernel.org Assisted-by: Claude:claude-opus-4-7 Signed-off-by: Michael Bommarito <michael.bommarito@gmail.com> [almaz.alexandrovich@paragon-software.com: clang-formatted the changes] Signed-off-by: Konstantin Komarov <almaz.alexandrovich@paragon-software.com>
2026-06-03fs/ntfs3: bound attr_off in UpdateResidentValue against data_offKonstantin Komarov
In do_action()'s UpdateResidentValue case (fslog.c:3307), lrh->attr_off and lrh->redo_len come from the on-disk LRH. When they satisfy aoff + dlen < attr->res.data_off, the assignment attr->res.data_size = cpu_to_le32(aoff + dlen - data_off); underflows to ~4 GiB (e.g. 0xFFFFFFF9 when aoff=0x10, dlen=1, data_off=0x18). Subsequent code that reads attr->res.data_size to walk the resident attribute payload would then read up to 4 GiB past the 1024-byte MFT record allocation. The existing mi_enum_attr() defense in fs/ntfs3/record.c:287 catches the corrupted data_size on the next attribute walk and fails the mount, but only on the path that walks all attributes. A read site that picks an attribute by name and reads its data_size without re-validating is not covered. Validate aoff against data_off and asize at the source. Reproduced under UML+KASAN on mainline 8d90b09e6741 via pr_warn-only probe: with aoff=0x10 and data_off=0x18, the post-assignment data_size is 0xfffffff9 (mount then fails at -22 from mi_enum_attr). Fixes: b46acd6a6a62 ("fs/ntfs3: Add NTFS journal") Cc: stable@vger.kernel.org Assisted-by: Claude:claude-opus-4-7 Signed-off-by: Michael Bommarito <michael.bommarito@gmail.com> [almaz.alexandrovich@paragon-software.com: clang-formatted the changes] Signed-off-by: Konstantin Komarov <almaz.alexandrovich@paragon-software.com>
2026-06-03ext4: improve str2hashbuf by processing 4-byte chunks and removing function ↵Guan-Chun Wu
pointers The original byte-by-byte implementation with modulo checks is less efficient. Refactor str2hashbuf_unsigned() and str2hashbuf_signed() to process input in explicit 4-byte chunks instead of using a modulus-based loop to emit words byte by byte. Additionally, the use of function pointers for selecting the appropriate str2hashbuf implementation has been removed. Instead, the functions are directly invoked based on the hash type, eliminating the overhead of dynamic function calls. Performance test (x86_64, Intel Core i7-10700 @ 2.90GHz, average over 10000 runs, using kernel module for testing): len | orig_s | new_s | orig_u | new_u ----+--------+-------+--------+------- 1 | 70 | 71 | 63 | 63 8 | 68 | 64 | 64 | 62 32 | 75 | 70 | 75 | 63 64 | 96 | 71 | 100 | 68 255 | 192 | 108 | 187 | 84 This change improves performance, especially for larger input sizes. Signed-off-by: Guan-Chun Wu <409411716@gms.tku.edu.tw> Link: https://patch.msgid.link/20260531080019.3794809-3-409411716@gms.tku.edu.tw Signed-off-by: Theodore Ts'o <tytso@mit.edu>
2026-06-03ext4: add Kunit coverage for directory hash computationGuan-Chun Wu
Introduce Kunit tests for fs/ext4/hash.c to verify ext4fs_dirhash() across the legacy, half-MD4, and TEA hash variants. The tests cover empty, seeded hashing, and non-ASCII name handling. They also verify error paths, including invalid hash versions and SipHash without a configured key, and check that the signed and unsigned hash variants differ on non-ASCII input as expected. When CONFIG_UNICODE is enabled, the tests further verify casefolded-name hashing and the fallback behavior for invalid input. Co-developed-by: Chen Hao Yu <edward062254@gmail.com> Signed-off-by: Chen Hao Yu <edward062254@gmail.com> Signed-off-by: Guan-Chun Wu <409411716@gms.tku.edu.tw> Link: https://patch.msgid.link/20260531080019.3794809-2-409411716@gms.tku.edu.tw Signed-off-by: Theodore Ts'o <tytso@mit.edu>
2026-06-03dma-debug: fix physical address retrieval in debug_dma_sync_sg_for_deviceLi RongQing
In debug_dma_sync_sg_for_device(), when iterating over a scatterlist, the debug entry population mistakenly uses the head of the scatterlist 'sg' to fetch the physical address via sg_phys(), instead of using the current iterator variable 's'. This causes dma-debug to track the physical address of the very first scatterlist entry for all subsequent entries in the list. Fix this by passing the correct loop iterator 's' to sg_phys() Fixes: 9d4f645a1fd49ee ("dma-debug: store a phys_addr_t in struct dma_debug_entry") Signed-off-by: Li RongQing <lirongqing@baidu.com> Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com> Link: https://lore.kernel.org/r/20260603123708.1665-1-lirongqing@baidu.com
2026-06-03ext4: fast commit: export snapshot stats in fc_infoLi Chen
Snapshot-based fast commit can fall back when the commit-time snapshot cannot be built (e.g. extent status cache misses). It is useful to quantify the updates-locked window and to see why snapshotting failed. Add best-effort snapshot counters to the ext4 superblock and extend /proc/fs/ext4/<sb_id>/fc_info to report the number of snapshotted inodes and ranges, snapshot failure reasons, and the average/max time spent with journal updates locked. Signed-off-by: Li Chen <chenl311@chinatelecom.cn> Link: https://patch.msgid.link/20260515091829.194810-8-me@linux.beauty Signed-off-by: Theodore Ts'o <tytso@mit.edu>
2026-06-03ext4: fast commit: add lock_updates tracepointLi Chen
Commit-time fast commit snapshots run under jbd2_journal_lock_updates(), so it is useful to quantify the time spent with updates locked and to understand why snapshotting can fail. Add a new tracepoint, ext4_fc_lock_updates, reporting the time spent in the updates-locked window along with the number of snapshotted inodes and ranges. Record the first snapshot failure reason in a stable snap_err field for tooling. Signed-off-by: Li Chen <chenl311@chinatelecom.cn> Reviewed-by: Steven Rostedt (Google) <rostedt@goodmis.org> Link: https://patch.msgid.link/20260515091829.194810-7-me@linux.beauty Signed-off-by: Theodore Ts'o <tytso@mit.edu>
2026-06-03ext4: fast commit: avoid i_data_sem by dropping ext4_map_blocks() in snapshotsLi Chen
Commit-time snapshots run under jbd2_journal_lock_updates(), so the work done there must stay bounded. The snapshot path still used ext4_map_blocks() to build data ranges. This can take i_data_sem and pulls the mapping code into the snapshot logic. Build inode data range snapshots from the extent status tree instead. The extent status tree is a cache, not an authoritative source. If the needed information is missing or unstable (e.g. delayed allocation), treat the transaction as fast commit ineligible and fall back to full commit. Also cap the number of inodes and ranges snapshotted per fast commit and allocate range records from a dedicated slab cache. The inode pointer array is allocated outside the updates-locked window. Testing: QEMU/KVM guest, virtio-pmem + dax, ext4 -O fast_commit, mounted dax,noatime. Ran python3 500x {4K write + fsync}, fallocate 256M, and python3 500x {creat + fsync(dir)} without lockdep splats or errors. Signed-off-by: Li Chen <chenl311@chinatelecom.cn> Link: https://patch.msgid.link/20260515091829.194810-6-me@linux.beauty Signed-off-by: Theodore Ts'o <tytso@mit.edu>
2026-06-03ext4: fast commit: avoid self-deadlock in inode snapshottingLi Chen
ext4_fc_snapshot_inodes() used igrab()/iput() to pin inodes while building commit-time snapshots. With ext4_fc_del() waiting for EXT4_STATE_FC_COMMITTING, iput() can trigger ext4_clear_inode()->ext4_fc_del() in the commit thread and deadlock waiting for the fast commit to finish. ext4_fc_del() also has to re-check EXT4_STATE_FC_COMMITTING after waiting on EXT4_STATE_FC_FLUSHING_DATA. The commit thread clears FLUSHING_DATA before it sets COMMITTING, so a waiter woken from the flush wait must not delete the inode based on an old COMMITTING check. Avoid taking extra references. Collect inode pointers under s_fc_lock and rely on EXT4_STATE_FC_COMMITTING to pin inodes until ext4_fc_cleanup() clears the bit. Also set EXT4_STATE_FC_COMMITTING for create-only inodes referenced from the dentry update queue, and wake up waiters when ext4_fc_cleanup() clears the bit. Signed-off-by: Li Chen <chenl311@chinatelecom.cn> Link: https://patch.msgid.link/20260515091829.194810-5-me@linux.beauty Signed-off-by: Theodore Ts'o <tytso@mit.edu>
2026-06-03ext4: fast commit: avoid waiting for FC_COMMITTINGLi Chen
ext4_fc_track_inode() can be called while holding i_data_sem (e.g. fallocate). Waiting for EXT4_STATE_FC_COMMITTING in that case risks an ABBA deadlock: i_data_sem -> wait(FC_COMMITTING) vs FC_COMMITTING -> wait(i_data_sem) in the commit task. Now that fast commit snapshots inode state at commit time, updates during log writing do not need to block. Drop the wait and lockdep assertion in ext4_fc_track_inode(), and make ext4_fc_del() wait for FC_COMMITTING so an inode cannot be removed while the commit thread is still using it. When an inode is modified during a fast commit, mark it with EXT4_STATE_FC_REQUEUE so cleanup keeps it queued for the next fast commit. This is needed because jbd2_fc_end_commit() invokes the cleanup callback with tid == 0, so tid-based requeue logic would requeue every inode. Testing: tracepoint ext4:ext4_fc_commit_stop with two fsyncs in the same transaction. nblks is the number of journal blocks written for that fast commit. Before this change, the second fsync still wrote almost the same fast commit log (nblks 10->9), because tid == 0 in jbd2_fc_end_commit() caused the tid-based requeue logic to keep all inodes queued. After this change, only inodes modified during the commit are requeued, and the second fsync wrote a nearly empty fast commit (nblks 10->1). Signed-off-by: Li Chen <chenl311@chinatelecom.cn> Link: https://patch.msgid.link/20260515091829.194810-4-me@linux.beauty Signed-off-by: Theodore Ts'o <tytso@mit.edu>