From nobody Wed Dec 17 12:34:25 2025 Received: from 6.mo581.mail-out.ovh.net (6.mo581.mail-out.ovh.net [188.165.39.218]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 1461D2DC771 for ; Thu, 1 May 2025 00:01:35 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=188.165.39.218 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746057700; cv=none; b=SeQoo0l+FNORPF/kzTacN3MDzM04PEcR8BrGlx3uCBB1L1Db0R+YtI1BeFIx6XuibRMoNvZLGfwua2M5k58U2V9vZ+6gJ8MZ7X2gmACeeO+2xN3ey/QVg+BdtW9MPqW1QCFzItHBxQt+WFRvjXJod9yPQeDbegc1xoZEs5mbEoU= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746057700; c=relaxed/simple; bh=R6IceUwMr0LDFa2629e3oGBZ3BcVaeTj7CZ0L8ipPHM=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Yk/rqDX9dUGfChHkvLIk6N6eg5NRVvhSXs5/Q4ARj/55wYsdxKhb6Umd36+m65K+fibrPZixsaxdTllT8W0+CAzBX/tfr7oVZi2/rGkYan9t0OgJHeGq8Ffy1LHRy+uLYGSrHHPJZFbIlO8TJlPCEFEo2H5nPbehCCi8zzM5zzg= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=eYRStlys; arc=none smtp.client-ip=188.165.39.218 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="eYRStlys" Received: from director5.ghost.mail-out.ovh.net (unknown [10.109.148.49]) by mo581.mail-out.ovh.net (Postfix) with ESMTP id 4ZnshM00Xvz1KrG for ; Wed, 30 Apr 2025 22:45:06 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-lsxl9 (unknown [10.110.188.136]) by director5.ghost.mail-out.ovh.net (Postfix) with ESMTPS id A6E571FD1E; Wed, 30 Apr 2025 22:45:06 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.106]) by ghost-submission-5b5ff79f4f-lsxl9 with ESMTPSA id zNP6HvKnEmhEPgsA7JqBbA (envelope-from ); Wed, 30 Apr 2025 22:45:06 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-106R006e662464a-a362-49e1-98a7-ed03813e7455, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com Subject: [RFC PATCH v2 1/9] Documentation/x86: update Secure Launch for AMD SKINIT Date: Thu, 1 May 2025 01:44:43 +0300 Message-ID: X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12101735152036918428 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: 0 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleefucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucenucfjughrpefhvfevufffkffojghfggfgsedtkeertdertddtnecuhfhrohhmpefuvghrghhiihcuffhmhihtrhhukhcuoehsvghrghhiihdrughmhihtrhhukhesfehmuggvsgdrtghomheqnecuggftrfgrthhtvghrnhephfelgfdtleejhefhffeileetgfffjeekueejudegieekieekvefhgeevtdelffehnecuffhomhgrihhnpehtrhgvnhgthhgsohhothdrohhrghdprghmugdrtghomhdpghhithhhuhgsrdgtohhmpdhfohhsuggvmhdrohhrghenucfkphepuddvjedrtddrtddruddpudejiedrudduuddrudekuddrudejkedpfeejrdehledrudegvddruddtieenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehkedumgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=JuWliCcAsReBMdU+nYOowwU7TndfwJwkdSza/u3yJXQ=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053107; v=1; b=eYRStlysuOo+/q+RdvWt3UH2J7ocC0t7u2I3DySr15q70NgkKutCMMHLsXqnYGEToY44JjnV UM8qvO/gRkUqZXVbqIQlPW5Z9crGNac1bWjLx60GJdZp/SlDTzHEqNHifHViUPQvYBzYXhzLBOx 1CEj4VNZqz8YRSSyGP08RIyKidjnJp0WtH8HzRt9J5IUAMnkE6nZUk1KHxHfgDgsh4FNhrWWSrU A5AviAs3ONB14f9v0ijpXOJg34uDRH/GR9P5unXn7DEDbbfyxumhUIsXXNCueKbK6rN2uhjdf0X ODTiXyqQOIJDZOXuGGEJFkI01gfR2cErG4pZA36eY52mQ== Content-Type: text/plain; charset="utf-8" * Switch ACM to DCE where not talking exclusively about Intel TXT * Switch MLE to DLME where not talking exclusively about Intel TXT * Add information about Secure Loader * Update information about Secure Launch to account for AMD SKINIT Signed-off-by: Sergii Dmytruk --- .../secure_launch_details.rst | 83 ++++++++++++++++--- .../secure_launch_overview.rst | 61 +++++++++----- 2 files changed, 113 insertions(+), 31 deletions(-) diff --git a/Documentation/security/launch-integrity/secure_launch_details.= rst b/Documentation/security/launch-integrity/secure_launch_details.rst index c58fa3a6a607..0936c29fd113 100644 --- a/Documentation/security/launch-integrity/secure_launch_details.rst +++ b/Documentation/security/launch-integrity/secure_launch_details.rst @@ -18,13 +18,13 @@ The settings to enable Secure Launch using Kconfig are = under:: A kernel with this option enabled can still be booted using other supported methods. =20 -To reduce the Trusted Computing Base (TCB) of the MLE [1]_, the build +To reduce the Trusted Computing Base (TCB) of the DLME [1]_, the build configuration should be pared down as narrowly as one's use case allows. Fewer drivers (less active hardware) and features reduce the attack surfac= e. -As an example in the extreme, the MLE could only have local disk access wi= th no +As an example in the extreme, the DLME could only have local disk access w= ith no other hardware supports except optional network access for remote attestat= ion. =20 -It is also desirable, if possible, to embed the initrd used with the MLE k= ernel +It is also desirable, if possible, to embed the initrd used with the DLME = kernel image to reduce complexity. =20 The following are important configuration necessities to always consider: @@ -39,7 +39,8 @@ other instabilities at boot. Even in cases where Secure L= aunch and KASLR work together, it is still recommended that KASLR be disabled to avoid introduc= ing security concerns with unprotected kernel memory. =20 -If possible, a kernel being used as an MLE should be built with KASLR disa= bled:: +If possible, a kernel being used as an DLME should be built with KASLR +disabled:: =20 "Processor type and features" --> "Build a relocatable kernel" --> @@ -64,7 +65,7 @@ IOMMU Configuration =20 When doing a Secure Launch, the IOMMU should always be enabled and the dri= vers loaded. However, IOMMU passthrough mode should never be used. This leaves = the -MLE completely exposed to DMA after the PMRs [2]_ are disabled. The current +DLME completely exposed to DMA after the PMRs [2]_ are disabled. The curre= nt default mode is to use IOMMU in lazy translated mode, but strict translated mode, is the preferred IOMMU mode and this should be selected in the build configuration:: @@ -109,9 +110,9 @@ Intel TXT Interface =20 The primary interfaces between the various components in TXT are the TXT M= MIO registers and the TXT heap. The MMIO register banks are described in Appen= dix B -of the TXT MLE [1]_ Development Guide. +of the TXT MLE Development Guide. =20 -The TXT heap is described in Appendix C of the TXT MLE [1]_ Development +The TXT heap is described in Appendix C of the TXT MLE Development Guide. Most of the TXT heap is predefined in the specification. The heap is initialized by firmware and the pre-launch environment and is subsequently= used by the SINIT ACM. One section, called the OS to MLE Data Table, is reserve= d for @@ -571,10 +572,68 @@ An error occurred in the Secure Launch module while m= apping the Secure Launch Resource table. The underlying issue is memremap() failure, most likely du= e to a resource shortage. =20 +AMD SKINIT Interface +=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D + +This DRTM comes in two flavours: with DRTM service running in PSP/ASP and +without one. The DRTM service effectively extends basic functionality of t= he +SKINIT instruction providing stronger security guarantees at the cost of m= ore +complicated programming interface. + +As of the end of 2024 the DRTM service is available on Milan/Genoa platfor= ms +running suitable firmware releases. When firmware doesn't provide the serv= ice, +simpler DRTM process is used. + +Basic SKINIT DRTM workflow is straightforward in its design. It defines on= ly +the bare minimum necessary to perform the DRTM and to pass some data from = pre- +to post-launch code. DRTM service extends the workflow by adding more meta= data +and performing some of the operations itself instead of leaving their +implementation to a user-provided code (Secure Loader or SL). + +Secure Loader image is a binary to which SKINIT instruction passes control= . The +binary must start with a short header defined in the second volume of AMD64 +Architecture Programmer's Manual to have only two required fields. DRTM +integration guide [4]_ adds an extended header which is mostly opaque and = can be +treated as reserved area in the kernel. Together these fields can be prese= nted +as the following structure:: + + struct sl_header { + u16 entry_point; + u16 image_size; + grub_uint8_t reserved[62]; + /* + * Any other fields, if present, are implementation-specif= ic. + */ + } __packed; + +Secure Loader is loaded into Secure Loader Block (SLB) which is a 64 KiB a= rea of +RAM below 4 GiB that starts on a 64 KiB boundary. The smaller a particular= SL +image is, the more space is available for passing additional data which is= to +be placed after the image so it doesn't get measured by SKINIT. + +Passing of the information from bootloader to the kernel is carried out by= the +SLRT which is placed after the end of Secure Loader. A platform-specific e= ntry +of the SLRT is additionally linked as `setup_data` structure allowing the +kernel to discover location of the SLRT by traversing boot parameters look= ing +for the entry. + +Description of the header: + +=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D =3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D +Field Use +=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D =3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D +entry_point Offset from the start of the image +image_size How much of the SLB area is actually occupied by th= e image +reserved Data for DRTM service +=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D =3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D + .. [1] - MLE: Measured Launch Environment is the binary runtime that is measure= d and - then run by the TXT SINIT ACM. The TXT MLE Development Guide describes= the - requirements for the MLE in detail. + DLME: Dynamic Launch Measured Environment (which Intel calls MLE for + Measured Launch Environment) is the binary runtime that is measured and + then run by the DCE. The TXT MLE Development Guide describes the + requirements for the MLE in detail. Because AMD SKINIT doesn't impose = any + specific requirements of that sort, TXT's format of MLE is used on AMD + devices as well for simplicity. =20 .. [2] PMR: Intel VTd has a feature in the IOMMU called Protected Memory Regi= sters. @@ -585,3 +644,7 @@ a resource shortage. =20 .. [3] Secure Launch Specification: https://trenchboot.org/specifications/Sec= ure_Launch/ + +.. [4] + Dynamic Root of Trust Measurement (DRTM) Service Integration Guide: + https://www.amd.com/content/dam/amd/en/documents/epyc-technical-docs/us= er-guides/58453.pdf diff --git a/Documentation/security/launch-integrity/secure_launch_overview= .rst b/Documentation/security/launch-integrity/secure_launch_overview.rst index 492f2b12e297..e9b8082314e1 100644 --- a/Documentation/security/launch-integrity/secure_launch_overview.rst +++ b/Documentation/security/launch-integrity/secure_launch_overview.rst @@ -47,9 +47,8 @@ documentation on these technologies can be readily found = online; see the `Resources`_ section below for references. =20 .. note:: - Currently, only Intel TXT is supported in this first release of the Se= cure - Launch feature. AMD/Hygon SKINIT and Arm support will be added in a - subsequent release. + Currently, only Intel TXT and AMD/Hygon SKINIT are supported by the Se= cure + Launch feature. Arm support will be added later. =20 To enable the kernel to be launched by GETSEC, the Secure Launch stub must be built into the setup section of the compressed kernel to handle the @@ -112,22 +111,26 @@ Pre-launch: *Phase where the environment is prepared = and configured to initiate the secure launch by the boot chain.* =20 - The SLRT is initialized, and dl_stub is placed in memory. - - Load the kernel, initrd and ACM [2]_ into memory. - - Set up the TXT heap and page tables describing the MLE [1]_ per the + - Load the kernel, initrd and DCE [1]_ into memory. + - For TXT, set up the TXT heap and page tables describing the DLME [2]_ p= er the specification. - If non-UEFI platform, dl_stub is called. - If UEFI platform, SLRT registered with UEFI and efi-stub called. - Upon completion, efi-stub will call EBS followed by dl_stub. - The dl_stub will prepare the CPU and the TPM for the launch. - - The secure launch is then initiated with the GETSET[SENTER] instruction. + - The secure launch is then initiated with either GETSEC[SENTER] (Intel) = or + SKINIT (AMD) instruction. =20 -Post-launch: *Phase where control is passed from the ACM to the MLE and th= e secure -kernel begins execution.* +Post-launch: *Phase where control is passed from the DCE to the DLME and t= he +secure kernel begins execution.* =20 - Entry from the dynamic launch jumps to the SL stub. - - SL stub fixes up the world on the BSP. + - For TXT, SL stub fixes up the world on the BSP. - For TXT, SL stub wakes the APs, fixes up their worlds. - For TXT, APs are left in an optimized (MONITOR/MWAIT) wait state. + - For SKINIT, APs are woken up mostly as usual except that the INIT IPIs = aren't + sent before Startup IPIs to avoid compromising security. INIT IPIs were= sent + to APs in pre-launch before issuing SKINIT, thus halting them. - SL stub jumps to startup_32. - SL main does validation of buffers and memory locations. It sets the boot parameter loadflag value SLAUNCH_FLAG to inform the main @@ -137,16 +140,19 @@ kernel begins execution.* - Kernel boot proceeds normally from this point. - During early setup, slaunch_setup() runs to finish validation and setup tasks. - - The SMP bring up code is modified to wake the waiting APs via the monit= or - address. + - For AMD with DRTM service, Trusted Memory Region gets releases after + successful configuration of IOMMU. + - For TXT, the SMP bring up code is modified to wake the waiting APs via = the + monitor address. - APs jump to rmpiggy and start up normally from that point. - SL platform module is registered as a late initcall module. It reads the TPM event log and extends the measurements taken into the TPM PCRs. - SL platform module initializes the securityfs interface to allow - access to the TPM event log and TXT public registers. + access to the TXT public registers on Intel and TPM event log everywher= e. - Kernel boot finishes booting normally. - - SEXIT support to leave SMX mode is present on the kexec path and - the various reboot paths (poweroff, reset, halt). + - On Intel SEXIT support to leave SMX mode is present on the kexec path a= nd + the various reboot paths (poweroff, reset, halt). A similar finalization + (locking of DRTM localities) happens on AMD with DRTM service. =20 PCR Usage =3D=3D=3D=3D=3D=3D=3D=3D=3D @@ -224,17 +230,30 @@ GRUB Secure Launch support: =20 https://github.com/TrenchBoot/grub/tree/grub-sl-fc-38-dlstub =20 +secure-kernel-loader (Secure Loader for AMD SKINIT, a kind of DCE): + +https://github.com/TrenchBoot/secure-kernel-loader/ + FOSDEM 2021: Secure Upgrades with DRTM =20 https://archive.fosdem.org/2021/schedule/event/firmware_suwd/ =20 .. [1] - MLE: Measured Launch Environment is the binary runtime that is measure= d and - then run by the TXT SINIT ACM. The TXT MLE Development Guide describes= the - requirements for the MLE in detail. + DCE: Dynamic Configuration Environment. Either ACM (Intel's Authentica= ted + Code Module) for TXT or SKL (secure-kernel-loader) for AMD SKINIT. + + ACM is a 32-bit binary blob that is run securely by the GETSEC[SENTER] + during a measured launch. It is described in the Intel documentation o= n TXT + and versions for various chipsets are signed and distributed by Intel. + + SKL is an implementation of SL (Secure Loader) which is started secure= ly by + SKINIT instruction in a flat 32-bit protected mode without paging. See= AMD's + System Programming manual for more details on the format and operation. =20 .. [2] - ACM: Intel's Authenticated Code Module. This is the 32b bit binary blo= b that - is run securely by the GETSEC[SENTER] during a measured launch. It is = described - in the Intel documentation on TXT and versions for various chipsets are - signed and distributed by Intel. + DLME: Dynamic Launch Measured Environment (which Intel calls MLE for + Measured Launch Environment) is the binary runtime that is measured and + then run by the DCE. The TXT MLE Development Guide describes the + requirements for the MLE in detail. Because AMD SKINIT doesn't impose = any + specific requirements of that sort, TXT's format of MLE is used on AMD + devices as well for simplicity. --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 12.mo561.mail-out.ovh.net (12.mo561.mail-out.ovh.net [188.165.41.191]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 67C344C80 for ; Thu, 1 May 2025 03:33:40 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=188.165.41.191 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746070428; cv=none; b=kOoVInaH19TgVgoYtjpXAFxc0Bd+w/wA7JyNqa8xOk/8HqYd3Ewzkct/yfYroYD9WiDiQlK6tNHODxXaiFDU68mQGNs6hL17A2w+BM4PoGGVvqkCJyofuc7Za0cAs2iKXPzOPPnK0pDYRSpnzhh3E1Pvj4vDqIHjdE6fEMVfBOo= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746070428; c=relaxed/simple; bh=cgNe+3OAOxlIKumKb00Y9Bg0xhGhpPOcGKx5Zxwtldc=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=caV4vdnqB7z+wDe/ft7QT3wF+S0S8KfmBQ6O8TKeGpdDjO8vMLNU+iT+m5/b2kM7Vnt2DD1AKzbs+45nZjcxTGKI3WwHDozUL9oIxQ9fqXohAJtosLyBwPsvTZ01mDBDUryjm1RHMX7veMxy0ZekpnhV9pktFpKjh6X9crkakg0= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=M4Tuh07R; arc=none smtp.client-ip=188.165.41.191 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="M4Tuh07R" Received: from director11.ghost.mail-out.ovh.net (unknown [10.109.148.49]) by mo561.mail-out.ovh.net (Postfix) with ESMTP id 4ZnshP2byCz1Tvr for ; Wed, 30 Apr 2025 22:45:09 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-rprjd (unknown [10.110.168.167]) by director11.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 056451FE1E; Wed, 30 Apr 2025 22:45:08 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.96]) by ghost-submission-5b5ff79f4f-rprjd with ESMTPSA id ngtvL/SnEmi5GgAAoQYA3w (envelope-from ); Wed, 30 Apr 2025 22:45:08 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-96R0010aa7ac36-938c-4c8f-acd6-c85f48ca5d3f, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com Subject: [RFC PATCH v2 2/9] x86: AMD changes for Secure Launch Resource Table header file Date: Thu, 1 May 2025 01:44:44 +0300 Message-ID: <3106242e092b9e28dfedb75a81ae4a68b0664c11.1746037489.git.sergii.dmytruk@3mdeb.com> X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12102579575522374812 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: 0 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleefucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucenucfjughrpefhvfevufffkffojghfggfgsedtkeertdertddtnecuhfhrohhmpefuvghrghhiihcuffhmhihtrhhukhcuoehsvghrghhiihdrughmhihtrhhukhesfehmuggvsgdrtghomheqnecuggftrfgrthhtvghrnhephfehfeehudeileeikeffgfffgfefuddtveelvedvhfffgfelvdfgtddutdehfeeinecukfhppeduvdejrddtrddtrddupddujeeirdduuddurddukedurddujeekpdefjedrheelrddugedvrdelieenucevlhhushhtvghrufhiiigvpedvnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehiedumgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=Tp9cS7PlRiBXUZqULcyRZnw27hF7l+b4x9U5h5mgUJA=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053109; v=1; b=M4Tuh07R/EEEhryXv0vg5m4qkiCqTzrnKSj3Dhu8VKkMoE0y34IgsdTXfnWXEkJrsaTHsJpL lXjkqs23JL6a3aTJh9rDQpcy3+ctb+rjW3yMMXo/RBwJxhfCDgfcnv/W2hscfmDmNC8zrw6ZWP1 zj4NDOc35B0QaeWzuzEjHEHXLm4ZJDYNzJVs7KCQtlwRvlcKf2C+jpJ5dHbSriuS+ZnbmHUTRZu UkaS7QaRoMAygJK3/oqobOV52cmwSKAImliT1cvLWZZUWwAJNQPAPIo+IFwGyTxsfjMD9OpBjT9 JCFA8Xl4tADuYCo5NO2ZJuinRpGKcr8dPNMCneox0RJMQ== Content-Type: text/plain; charset="utf-8" From: Ross Philipson Introduce the AMD info table that allows the SLRT to be linked in as a setup_data entry. This allows the SLRT to be found and in addition all the DLMR information needed by the SKL (Secure Kernel Loader). Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk --- include/linux/slr_table.h | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/include/linux/slr_table.h b/include/linux/slr_table.h index fea666250033..aecdb62b8a53 100644 --- a/include/linux/slr_table.h +++ b/include/linux/slr_table.h @@ -180,6 +180,21 @@ struct slr_entry_intel_info { struct slr_txt_mtrr_state saved_bsp_mtrrs; } __packed; =20 +/* + * AMD SKINIT Info table + */ +struct slr_entry_amd_info { + struct slr_entry_hdr hdr; + u64 next; + u32 type; + u32 len; + u64 slrt_size; + u64 slrt_base; + u64 boot_params_addr; + u16 psp_version; + u16 reserved[3]; +} __packed; + /* * UEFI config measurement entry */ --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 17.mo582.mail-out.ovh.net (17.mo582.mail-out.ovh.net [46.105.36.150]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 2B8371DC9B0 for ; Wed, 30 Apr 2025 23:03:52 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=46.105.36.150 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746054236; cv=none; b=CJkuW0rlfFSImpbqdZMuN4E6OXPttwhLUUhAc9VCOlOUIgidhp3TqToO4vlQbWLRMHs9P+6h8qJmzCLYuwiPFKQ0Pa3hZCyn1X41U8NzRoqX6YFLgtLrmRpwCMwA9VjConwaLuRB9kLzVuq/OppcFjM/uXcskozMJQfX3WVsPO8= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746054236; c=relaxed/simple; bh=A3qyNpgIhJdTErPTMjoTewRqqr5w/st8rXbErG+JDbw=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=foNuvfqW7oc9JjQM2tDH0TKhwuBTl3UQAYec/isC5uNC21QfzyyolK1Dt6Gcjb7eFS2i3p08ojiE0RGyACkOyDChUuQG6pXiubrz1XnVxpH11+mhCUpRFxWo4ESGeApp2gbXukbwVvMEb5b/K3vcGka72Y1Q1qBGdF8VOYvB7dE= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=J1TK5DX5; arc=none smtp.client-ip=46.105.36.150 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="J1TK5DX5" Received: from director1.ghost.mail-out.ovh.net (unknown [10.109.148.106]) by mo582.mail-out.ovh.net (Postfix) with ESMTP id 4ZnshR51P8z1PG0 for ; Wed, 30 Apr 2025 22:45:11 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-bt6hd (unknown [10.110.188.136]) by director1.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 5CFD11FD61; Wed, 30 Apr 2025 22:45:11 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.108]) by ghost-submission-5b5ff79f4f-bt6hd with ESMTPSA id ejsPCvenEmgevisAyP1w0w (envelope-from ); Wed, 30 Apr 2025 22:45:11 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-108S002c0a7c6fa-a18a-4bd0-a5dd-c1144deb985f, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com Subject: [RFC PATCH v2 3/9] x86: Secure Launch main header file AMD support Date: Thu, 1 May 2025 01:44:45 +0300 Message-ID: X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12103142526215632028 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: 0 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleefucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucenucfjughrpefhvfevufffkffojghfgggtgfesthekredtredtjeenucfhrhhomhepufgvrhhgihhiucffmhihthhruhhkuceoshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmqeenucggtffrrghtthgvrhhnpeegkeffieeitdevkefhudegffevieeggfelgedvgeehffdtteehfeeuleeiudekvdenucfkphepuddvjedrtddrtddruddpudejiedrudduuddrudekuddrudejkedpfeejrdehledrudegvddruddtkeenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehkedvmgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=Z/g7dNV0WLxS81SLsZO/TkyYRGI2634tQDHJNCpmxUQ=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053111; v=1; b=J1TK5DX5XE/LXIqW2zKDsmvlbknl5B+qS0GVjKmmesCUcdSe1h61t3x7b5zEQlUvDKDmxywu TTgDFjaNBiJmJP8gVlDw5b8PZabbhAhMBo3Tguj/cgYabkD2vOnUA/Oo31ifVNqC0h3si+ae8jw 1vaA5t32nAc1ydg0MLLbqLOzINKYchqmrk1S8GWzWhBNnj6HZHxohKPQxL7jfOY3QnAQB9WPdrz yezwbvu7feW027dFDzKZfJNwFfVJXLNKVbZvyvpJ1aCgC8By3dpN51zA4PX/xElTEOc26WBCMTj fPQ0UYU9ofsjtG4NI8SSfSW0Jl2sMANiOkvZ6NBX1Z5MA== From: Ross Philipson Add additional Secure Launch definitions and declarations for AMD/SKINIT support. Use a single implementation of slaunch_is_txt_launch(), slaunch_get_flags() returns to 0 if Secure Launch support isn't enabled. Signed-off-by: Ross Philipson Signed-off-by: Micha=C5=82 =C5=BBygowski Signed-off-by: Sergii Dmytruk --- include/linux/slaunch.h | 81 +++++++++++++++++++++++++++++++++++------ 1 file changed, 70 insertions(+), 11 deletions(-) diff --git a/include/linux/slaunch.h b/include/linux/slaunch.h index ae67314c2aad..ec7e0d736a03 100644 --- a/include/linux/slaunch.h +++ b/include/linux/slaunch.h @@ -14,11 +14,14 @@ */ #define SL_FLAG_ACTIVE 0x00000001 #define SL_FLAG_ARCH_TXT 0x00000002 +#define SL_FLAG_ARCH_SKINIT 0x00000004 +#define SL_FLAG_SKINIT_PSP 0x00000008 =20 /* * Secure Launch CPU Type */ #define SL_CPU_INTEL 1 +#define SL_CPU_AMD 2 =20 #define __SL32_CS 0x0008 #define __SL32_DS 0x0010 @@ -146,6 +149,8 @@ #define SL_ERROR_INVALID_SLRT 0xc0008022 #define SL_ERROR_SLRT_MISSING_ENTRY 0xc0008023 #define SL_ERROR_SLRT_MAP 0xc0008024 +#define SL_ERROR_MISSING_EVENT_LOG 0xc0008025 +#define SL_ERROR_MAP_SETUP_DATA 0xc0008026 =20 /* * Secure Launch Defined Limits @@ -325,9 +330,25 @@ struct smx_rlp_mle_join { u32 rlp_entry_point; /* phys addr */ } __packed; =20 +/* The TCG original Spec ID structure defined for TPM 1.2 */ +#define TCG_SPECID_SIG00 "Spec ID Event00" + +struct tpm_tcg_specid_event_head { + char signature[16]; + u32 platform_class; + u8 spec_ver_minor; + u8 spec_ver_major; + u8 errata; + u8 uintn_size; /* reserved (must be 0) for 1.21 */ + u8 vendor_info_size; + /* vendor_info[]; */ +} __packed; + /* - * TPM event log structures defined in both the TXT specification and - * the TCG documentation. + * TPM event log structures defined by the TXT specification derived + * from the TCG documentation. For TXT this is setup as the conainter + * header. On AMD this header is embedded in to vendor information + * after the TCG spec ID header. */ #define TPM_EVTLOG_SIGNATURE "TXT Event Container" =20 @@ -344,6 +365,25 @@ struct tpm_event_log_header { /* PCREvents[] */ } __packed; =20 +/* TPM Event Log Size Macros */ +#define TCG_PCClientSpecIDEventStruct_SIZE \ + (sizeof(struct tpm_tcg_specid_event_head)) +#define TCG_EfiSpecIdEvent_SIZE(n) \ + ((n) * sizeof(struct tcg_efi_specid_event_algs) \ + + sizeof(struct tcg_efi_specid_event_head) \ + + sizeof(u8) /* vendorInfoSize */) +#define TPM2_HASH_COUNT(base) (*((u32 *)(base) \ + + (offsetof(struct tcg_efi_specid_event_head, num_algs) >> 2))) + +/* AMD Specific Structures and Definitions */ +struct sl_header { + u16 skl_entry_point; + u16 length; + u8 reserved[62]; + u16 skl_info_offset; + u16 bootloader_data_offset; +} __packed; + /* * Functions to extract data from the Intel TXT Heap Memory. The layout * of the heap is as follows: @@ -512,16 +552,14 @@ void slaunch_fixup_jump_vector(void); u32 slaunch_get_flags(void); struct sl_ap_wake_info *slaunch_get_ap_wake_info(void); struct acpi_table_header *slaunch_get_dmar_table(struct acpi_table_header = *dmar); +void slaunch_cpu_setup_skinit(void); +void __noreturn slaunch_skinit_reset(const char *msg, u64 error); void __noreturn slaunch_txt_reset(void __iomem *txt, const char *msg, u64 error); void slaunch_finalize(int do_sexit); - -static inline bool slaunch_is_txt_launch(void) -{ - u32 mask =3D SL_FLAG_ACTIVE | SL_FLAG_ARCH_TXT; - - return (slaunch_get_flags() & mask) =3D=3D mask; -} +bool slaunch_psp_tmr_release(void); +void slaunch_psp_setup(void); +void slaunch_psp_finalize(void); =20 #else =20 @@ -529,6 +567,10 @@ static inline void slaunch_setup_txt(void) { } =20 +static inline void slaunch_cpu_setup_skinit(void) +{ +} + static inline void slaunch_fixup_jump_vector(void) { } @@ -545,14 +587,31 @@ static inline struct acpi_table_header *slaunch_get_d= mar_table(struct acpi_table =20 static inline void slaunch_finalize(int do_sexit) { + (void)do_sexit; } =20 +#endif /* !IS_ENABLED(CONFIG_SECURE_LAUNCH) */ + static inline bool slaunch_is_txt_launch(void) { - return false; + u32 mask =3D SL_FLAG_ACTIVE | SL_FLAG_ARCH_TXT; + + return (slaunch_get_flags() & mask) =3D=3D mask; } =20 -#endif /* !IS_ENABLED(CONFIG_SECURE_LAUNCH) */ +static inline bool slaunch_is_skinit_launch(void) +{ + u32 mask =3D SL_FLAG_ACTIVE | SL_FLAG_ARCH_SKINIT; + + return (slaunch_get_flags() & mask) =3D=3D mask; +} + +static inline bool slaunch_is_skinit_psp(void) +{ + u32 mask =3D SL_FLAG_ACTIVE | SL_FLAG_ARCH_SKINIT | SL_FLAG_SKINIT_PSP; + + return (slaunch_get_flags() & mask) =3D=3D mask; +} =20 #endif /* !__ASSEMBLY */ =20 --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 9.mo550.mail-out.ovh.net (9.mo550.mail-out.ovh.net [178.32.108.172]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 235291BF37 for ; Wed, 30 Apr 2025 22:50:29 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=178.32.108.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746053433; cv=none; b=Gmiu+G5wkYKIT9o1/2Ud2TkoveUgPJjIdoUfpT0QsgW/in043Ojzo9er+zXaTl2v9YXk3UxS/ArPMv3JbIzvkHxXLuwcJDOhU2re0kT9a7+g9wKLQHg+uNiiipVjm6qvuMeFGIIAoZiWtBv4lXtNzfNOt9ktcriPa52toiGWVVk= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746053433; c=relaxed/simple; bh=kPomQ7PXgpw7knpV3SVfubuKhsQUI05+skk6zT7Eq1I=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=KqHHuSqzPpwfFGcoCtCko4DOGL9KBs8PmSuvvV/M7nkmnZkJZdI4y5yJHs2j1P/xg68VcVsnBoQxXv0dqPz2Onzh8PzFCBPlZseZdGkG5u1PP6BqOFfqAMoXKqSq7IrIYlezxuIN4Pp3aK6NyRjc5svfse6wKxSF3VHtHXrsxhU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=NGixRtCX; arc=none smtp.client-ip=178.32.108.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="NGixRtCX" Received: from director4.ghost.mail-out.ovh.net (unknown [10.109.176.170]) by mo550.mail-out.ovh.net (Postfix) with ESMTP id 4ZnshT6jk9z1Xnx for ; Wed, 30 Apr 2025 22:45:13 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-twnx5 (unknown [10.110.164.49]) by director4.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 9A8971FD29; Wed, 30 Apr 2025 22:45:13 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.114]) by ghost-submission-5b5ff79f4f-twnx5 with ESMTPSA id SuivGfmnEmgRWAgA1PhhsQ (envelope-from ); Wed, 30 Apr 2025 22:45:13 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-114S00894c63abd-27f7-477a-bf0c-fa55fba5a45f, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com Subject: [RFC PATCH v2 4/9] x86: Split up Secure Launch setup and finalize functions Date: Thu, 1 May 2025 01:44:46 +0300 Message-ID: X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12103705474822026396 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: 0 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucenucfjughrpefhvfevufffkffojghfggfgsedtkeertdertddtnecuhfhrohhmpefuvghrghhiihcuffhmhihtrhhukhcuoehsvghrghhiihdrughmhihtrhhukhesfehmuggvsgdrtghomheqnecuggftrfgrthhtvghrnhephfehfeehudeileeikeffgfffgfefuddtveelvedvhfffgfelvdfgtddutdehfeeinecukfhppeduvdejrddtrddtrddupddujeeirdduuddurddukedurddujeekpdefjedrheelrddugedvrdduudegnecuvehluhhsthgvrhfuihiivgepudenucfrrghrrghmpehinhgvthepuddvjedrtddrtddruddpmhgrihhlfhhrohhmpehsvghrghhiihdrughmhihtrhhukhesfehmuggvsgdrtghomhdpnhgspghrtghpthhtohepuddprhgtphhtthhopehlihhnuhigqdhkvghrnhgvlhesvhhgvghrrdhkvghrnhgvlhdrohhrghdpoffvtefjohhsthepmhhoheehtdgmpdhmohguvgepshhmthhpohhuth DKIM-Signature: a=rsa-sha256; bh=5VFk4FOVNsAWcUO093+INFp3zTO4CmYlsU9Pb5Y3iAY=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053114; v=1; b=NGixRtCXiVNRihEJULF8W1ZW/fYzDX8yDyGmrA6teCk3Ay5vijC/ujJIEvuiIt77Jvbovyg5 1emvo6H6OUx/EGrumVzKuPIPcKZTXbZF64GGzgswl72MQQ0mDrGCR9ij7vYC91kMCaXiR5r2MOw n/XdkN2Jt67S4UvPhfwyJ3XxJpw3NTLNy2dqsO1RWmTUeWZ///FTqQ8l+xuqU/udfT1oD4aThYV mpsdLtXMW4HPWLiNOriK53mnZvcJt/mEP5aeicp950Rx2d0Z8JOKvouY7B0SfKkyMwx1BWKmNQy zp7kImWAnNhPFybpQ4UIa7rl5+yRadOv952gxYnC6pVUQ== Content-Type: text/plain; charset="utf-8" From: Ross Philipson Split up the setup and findalize functions internally to determine the type of launch and call the appropriate function (TXT or SKINIT version). Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk --- arch/x86/include/asm/svm.h | 2 ++ arch/x86/kernel/setup.c | 2 +- arch/x86/kernel/slaunch.c | 69 +++++++++++++++++++++++++++++++------- include/linux/slaunch.h | 4 +-- 4 files changed, 62 insertions(+), 15 deletions(-) diff --git a/arch/x86/include/asm/svm.h b/arch/x86/include/asm/svm.h index 9b7fa99ae951..da9536c5a137 100644 --- a/arch/x86/include/asm/svm.h +++ b/arch/x86/include/asm/svm.h @@ -584,6 +584,8 @@ static inline void __unused_size_checks(void) =20 #define SVM_CPUID_FUNC 0x8000000a =20 +#define SVM_VM_CR_INIT_REDIRECTION 1 + #define SVM_SELECTOR_S_SHIFT 4 #define SVM_SELECTOR_DPL_SHIFT 5 #define SVM_SELECTOR_P_SHIFT 7 diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c index afb1b238202f..3bcf5a5fbac7 100644 --- a/arch/x86/kernel/setup.c +++ b/arch/x86/kernel/setup.c @@ -999,7 +999,7 @@ void __init setup_arch(char **cmdline_p) early_gart_iommu_check(); #endif =20 - slaunch_setup_txt(); + slaunch_setup(); =20 /* * partially used pages are not usable - thus diff --git a/arch/x86/kernel/slaunch.c b/arch/x86/kernel/slaunch.c index b6ba4c526aa3..d81433a9b699 100644 --- a/arch/x86/kernel/slaunch.c +++ b/arch/x86/kernel/slaunch.c @@ -18,6 +18,7 @@ #include #include #include +#include #include #include #include @@ -437,21 +438,11 @@ void __init slaunch_fixup_jump_vector(void) * Intel TXT specific late stub setup and validation called from within * x86 specific setup_arch(). */ -void __init slaunch_setup_txt(void) +static void __init slaunch_setup_txt(void) { u64 one =3D TXT_REGVALUE_ONE, val; void __iomem *txt; =20 - if (!boot_cpu_has(X86_FEATURE_SMX)) - return; - - /* - * If booted through secure launch entry point, the loadflags - * option will be set. - */ - if (!(boot_params.hdr.loadflags & SLAUNCH_FLAG)) - return; - /* * See if SENTER was done by reading the status register in the * public space. If the public register space cannot be read, TXT may @@ -523,6 +514,42 @@ void __init slaunch_setup_txt(void) pr_info("Intel TXT setup complete\n"); } =20 +/* + * AMD SKINIT specific late stub setup and validation called from within + * x86 specific setup_arch(). + */ +static void __init slaunch_setup_skinit(void) +{ + u64 val; + + /* + * If the platform is performing a Secure Launch via SKINIT + * INIT_REDIRECTION flag will be active. + */ + rdmsrl(MSR_VM_CR, val); + if (!(val & (1 << SVM_VM_CR_INIT_REDIRECTION))) + return; + + /* Set flags on BSP so subsequent code knows it was a SKINIT launch */ + sl_flags |=3D (SL_FLAG_ACTIVE|SL_FLAG_ARCH_SKINIT); + pr_info("AMD SKINIT setup complete\n"); +} + +void __init slaunch_setup(void) +{ + /* + * If booted through secure launch entry point, the loadflags + * option will be set. + */ + if (!(boot_params.hdr.loadflags & SLAUNCH_FLAG)) + return; + + if (boot_cpu_has(X86_FEATURE_SMX)) + slaunch_setup_txt(); + else if (boot_cpu_has(X86_FEATURE_SKINIT)) + slaunch_setup_skinit(); +} + static inline void smx_getsec_sexit(void) { asm volatile ("getsec\n" @@ -533,7 +560,7 @@ static inline void smx_getsec_sexit(void) * Used during kexec and on reboot paths to finalize the TXT state * and do an SEXIT exiting the DRTM and disabling SMX mode. */ -void slaunch_finalize(int do_sexit) +static void slaunch_finalize_txt(int do_sexit) { u64 one =3D TXT_REGVALUE_ONE, val; void __iomem *config; @@ -594,3 +621,21 @@ void slaunch_finalize(int do_sexit) =20 pr_info("TXT SEXIT complete.\n"); } + +/* + * Used during kexec and on reboot paths to finalize the SKINIT. + */ +static void slaunch_finalize_skinit(void) +{ + /* AMD CPUs with PSP-supported DRTM */ + if (!slaunch_is_skinit_psp()) + return; +} + +void slaunch_finalize(int do_sexit) +{ + if (boot_cpu_has(X86_FEATURE_SMX)) + slaunch_finalize_txt(do_sexit); + else if (boot_cpu_has(X86_FEATURE_SKINIT)) + slaunch_finalize_skinit(); +} diff --git a/include/linux/slaunch.h b/include/linux/slaunch.h index ec7e0d736a03..22e253960fdd 100644 --- a/include/linux/slaunch.h +++ b/include/linux/slaunch.h @@ -547,7 +547,7 @@ static inline int tpm2_log_event(struct txt_heap_event_= log_pointer2_1_element *e /* * External functions available in mainline kernel. */ -void slaunch_setup_txt(void); +void slaunch_setup(void); void slaunch_fixup_jump_vector(void); u32 slaunch_get_flags(void); struct sl_ap_wake_info *slaunch_get_ap_wake_info(void); @@ -563,7 +563,7 @@ void slaunch_psp_finalize(void); =20 #else =20 -static inline void slaunch_setup_txt(void) +static inline void slaunch_setup(void) { } =20 --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 2.mo576.mail-out.ovh.net (2.mo576.mail-out.ovh.net [178.33.251.80]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id CC86434545 for ; Wed, 30 Apr 2025 23:21:50 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=178.33.251.80 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746055315; cv=none; b=cStPejN2A8CM+lxs+ibVMNMOKI+wKWMyHq8iXaQ3MszQh5qlLM7aPU/Ogn0KTyGI/I5Na+Z93xqunidEt26OXSsWG34p9UrpaRpcgQrgJkZAKEN7LTperFRabrCAqEzwSKz9sRhb7qYuSzAtiCZufhtp0OLgHmxgA5dUbZqV18g= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746055315; c=relaxed/simple; bh=7CMA7RQv42Zqv1YDnKbPDDgiEuaw242d7v3FQGNIArA=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=SHIPbRbBMdKYOGlhXEBRYaNKzlp/RY60OG1uXRL90kwYtz1yvnM5gK3SYIYgLBeQxyZgPq4F5q23tFOUsZHQ7c+ZFDGcVLwt7kQsVFbrWq7CEg8FIgv04W9kCxUSZVS6q9yuE/r6xmMPFSwpuzqT2KrzbWlhuJWH5tpzsRWSoHo= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=K/Tok666; arc=none smtp.client-ip=178.33.251.80 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="K/Tok666" Received: from director11.ghost.mail-out.ovh.net (unknown [10.109.140.5]) by mo576.mail-out.ovh.net (Postfix) with ESMTP id 4ZnshX30gBz28fv for ; Wed, 30 Apr 2025 22:45:16 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-gdlqt (unknown [10.108.42.247]) by director11.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 005E41FE1E; Wed, 30 Apr 2025 22:45:15 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.99]) by ghost-submission-5b5ff79f4f-gdlqt with ESMTPSA id 5B2dK/unEmgf1gUAvKMIYg (envelope-from ); Wed, 30 Apr 2025 22:45:15 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-99G00380ccad58-b8e3-486b-ab22-202da9e6f1c2, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com Subject: [RFC PATCH v2 5/9] x86: Implement AMD support for Secure Launch Date: Thu, 1 May 2025 01:44:47 +0300 Message-ID: X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12104549898934531228 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: 0 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleefucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucenucfjughrpefhvfevufffkffojghfgggtgfesthekredtredtjeenucfhrhhomhepufgvrhhgihhiucffmhihthhruhhkuceoshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmqeenucggtffrrghtthgvrhhnpeeuudffjedvgfffteegieekteevueetkeefheeileehteetvdefkeffuedtteeiheenucffohhmrghinhepthhruhhsthgvuggtohhmphhuthhinhhgghhrohhuphdrohhrghdpihhnthgvlhdrtghomhdpshhlpghsthhusgdrshgsnecukfhppeduvdejrddtrddtrddupddujeeirdduuddurddukedurddujeekpdefjedrheelrddugedvrdelleenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehjeeimgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=7FdRX2xO8psSzkl6ncytLqbuwudEsRaU/fwzhTME+rI=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053116; v=1; b=K/Tok666ur4LAIS+Ko1MzWZuFdogJwhTXI+iGBcLPeSMObuFnbpKXXznoKHQXvN80cbTI6hM DrerN0Y9uGkohblWOE6Bkzxf7WcaWJ6Vlcs8L46I+yTqD5yTsmCeY4wc+680qHOr9DMW/uyFqEa wHn+6Lmq0ShdO3ma14ou4z1MgSKyi1bcjGYCNVhLSsXAjbX/ttWasZZKQ+R9aT6/od+AP/Mv9aO xTo5354EsjSQPQhvKSfBN0YEOup4kTsxHXiLOK+nZ1zU1e6G3C8IV/3YNBFq8uZmlzZOch0UcBh y+JDHR+tCRTRBlr0Km9MJf1ZGAzLLZpx3muGC4BzqOIpQ== From: Micha=C5=82 =C5=BBygowski AMD SKINIT uses the same entry point as Intel TXT (sl_stub_entry). It follows similar, but simpler path than TXT; there is no TXT heap and APs are started by a standard INIT/SIPI/SIPI sequence. Contrary to the TXT, SKINIT does not use code provided by a CPU vendor. Instead it requires an intermediate loader (SKL), whose task is to set up memory protection and set a proper CPU context before handling control over to the kernel. In order to simplify adding new entries and to minimize the number of differences between AMD and Intel, the event logs have actually two headers, both for TPM 1.2 and 2.0. For TPM 1.2 this is TCG_PCClientSpecIDEventStruct [1] with Intel's own TXT-specific header embedded inside its 'vendorInfo' field. The offset to this field is added to the base address on AMD path, making the code for adding new events the same for both vendors. TPM 2.0 in TXT uses HEAP_EVENT_LOG_POINTER_ELEMENT2_1 structure, which is normally constructed on the TXT stack [2]. For AMD, this structure is put inside TCG_EfiSpecIdEvent [3], also in 'vendorInfo' field. The actual offset to this field depends on the number of hash algorithms supported by the event log. Other changes: - update common code to handle reset on AMD as well - reserve memory region occupied by SKL (called SLB) and event log [1] https://www.trustedcomputinggroup.org/wp-content/uploads/TCG_PCClientIm= plementation_1-21_1_00.pdf [2] http://www.intel.com/content/dam/www/public/us/en/documents/guides/inte= l-txt-software-development-guide.pdf [3] https://trustedcomputinggroup.org/wp-content/uploads/TCG_PCClientSpecPl= at_TPM_2p0_1p04_pub.pdf Signed-off-by: Micha=C5=82 =C5=BBygowski Signed-off-by: Krystian Hebel Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk --- arch/x86/Kconfig | 9 +- arch/x86/boot/compressed/sl_main.c | 271 ++++++++++++++++++++----- arch/x86/boot/compressed/sl_stub.S | 41 +++- arch/x86/include/uapi/asm/setup_data.h | 3 +- arch/x86/kernel/slaunch.c | 99 ++++++++- 5 files changed, 347 insertions(+), 76 deletions(-) diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig index badde1e9742e..d521838c77db 100644 --- a/arch/x86/Kconfig +++ b/arch/x86/Kconfig @@ -2006,11 +2006,12 @@ config SECURE_LAUNCH depends on X86_64 && X86_X2APIC && TCG_TIS && TCG_CRB && CRYPTO_LIB_SHA1 = && CRYPTO_LIB_SHA256 help The Secure Launch feature allows a kernel to be loaded - directly through an Intel TXT measured launch. Intel TXT + directly through a dynamic launch. Intel TXT or AMD SKINIT establishes a Dynamic Root of Trust for Measurement (DRTM) - where the CPU measures the kernel image. This feature then - continues the measurement chain over kernel configuration - information and init images. + where the CPU or a Dynamic Configuration Environment (DCE) + measures the kernel image. This feature then continues the + measurement chain over kernel configuration information and + init images. =20 source "kernel/Kconfig.hz" =20 diff --git a/arch/x86/boot/compressed/sl_main.c b/arch/x86/boot/compressed/= sl_main.c index 5e0fd0d7bd72..f0bb40b608be 100644 --- a/arch/x86/boot/compressed/sl_main.c +++ b/arch/x86/boot/compressed/sl_main.c @@ -13,6 +13,7 @@ #include #include #include +#include #include #include #include @@ -26,6 +27,14 @@ #define SL_TPM_LOG 1 #define SL_TPM2_LOG 2 =20 +#define sl_reset(e) \ + do { \ + if (sl_cpu_type =3D=3D SL_CPU_INTEL) \ + sl_txt_reset(e); \ + else \ + sl_skinit_reset(); \ + } while (0) + static void *evtlog_base; static u32 evtlog_size; static struct txt_heap_event_log_pointer2_1_element *log21_elem; @@ -69,6 +78,14 @@ static void __noreturn sl_txt_reset(u64 error) unreachable(); } =20 +static void __noreturn sl_skinit_reset(void) +{ + /* AMD does not have a reset mechanism or an error register */ + asm volatile ("ud2"); + + unreachable(); +} + static u64 sl_rdmsr(u32 reg) { u64 lo, hi; @@ -78,25 +95,41 @@ static u64 sl_rdmsr(u32 reg) return (hi << 32) | lo; } =20 -static struct slr_table *sl_locate_and_validate_slrt(void) +static struct slr_table *sl_locate_and_validate_slrt(struct boot_params *b= p) { struct txt_os_mle_data *os_mle_data; + struct slr_entry_amd_info *amd_info; + struct setup_data *data; struct slr_table *slrt; void *txt_heap; =20 - txt_heap =3D (void *)sl_txt_read(TXT_CR_HEAP_BASE); - os_mle_data =3D txt_os_mle_data_start(txt_heap); - - if (!os_mle_data->slrt) - sl_txt_reset(SL_ERROR_INVALID_SLRT); + if (sl_cpu_type & SL_CPU_AMD) { + slrt =3D NULL; + data =3D (struct setup_data *)bp->hdr.setup_data; + while (data) { + if (data->type =3D=3D SETUP_SECURE_LAUNCH) { + amd_info =3D + (struct slr_entry_amd_info *)((u8 *)data - + sizeof(struct slr_entry_hdr)); + slrt =3D (struct slr_table *)amd_info->slrt_base; + break; + } + data =3D (struct setup_data *)data->next; + } =20 - slrt =3D (struct slr_table *)os_mle_data->slrt; + if (!slrt || slrt->magic !=3D SLR_TABLE_MAGIC || + slrt->architecture !=3D SLR_AMD_SKINIT) + sl_skinit_reset(); + } else { + txt_heap =3D (void *)sl_txt_read(TXT_CR_HEAP_BASE); + os_mle_data =3D txt_os_mle_data_start(txt_heap); =20 - if (slrt->magic !=3D SLR_TABLE_MAGIC) - sl_txt_reset(SL_ERROR_INVALID_SLRT); + slrt =3D (struct slr_table *)os_mle_data->slrt; =20 - if (slrt->architecture !=3D SLR_INTEL_TXT) - sl_txt_reset(SL_ERROR_INVALID_SLRT); + if (!slrt || slrt->magic !=3D SLR_TABLE_MAGIC || + slrt->architecture !=3D SLR_INTEL_TXT) + sl_txt_reset(SL_ERROR_INVALID_SLRT); + } =20 return slrt; } @@ -177,6 +210,26 @@ static void sl_txt_validate_msrs(struct txt_os_mle_dat= a *os_mle_data) sl_txt_reset(SL_ERROR_MSR_INV_MISC_EN); } =20 +/* + * In order to simplify adding new entries and to minimize the number of + * differences between AMD and Intel, the event logs have actually two hea= ders, + * both for TPM 1.2 and 2.0. + * + * For TPM 1.2 this is TCG_PCClientSpecIDEventStruct [1] with Intel's own + * TXT-specific header embedded inside its 'vendorInfo' field. The offset = to + * this field is added to the base address in AMD path, making the code for + * adding new events the same for both vendors. + * + * TPM 2.0 in TXT uses HEAP_EVENT_LOG_POINTER_ELEMENT2_1 structure, which = is + * normally constructed on the TXT stack [2]. For AMD, this structure is p= ut + * inside TCG_EfiSpecIdEvent [3], also in 'vendorInfo' field. The actual o= ffset + * to this field depends on number of hash algorithms supported by the eve= nt + * log. + * + * [1] https://www.trustedcomputinggroup.org/wp-content/uploads/TCG_PCClie= ntImplementation_1-21_1_00.pdf + * [2] http://www.intel.com/content/dam/www/public/us/en/documents/guides/= intel-txt-software-development-guide.pdf + * [3] https://trustedcomputinggroup.org/wp-content/uploads/TCG_PCClientSp= ecPlat_TPM_2p0_1p04_pub.pdf + */ static void sl_find_drtm_event_log(struct slr_table *slrt) { struct txt_os_sinit_data *os_sinit_data; @@ -185,11 +238,31 @@ static void sl_find_drtm_event_log(struct slr_table *= slrt) =20 log_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_LOG_INFO); if (!log_info) - sl_txt_reset(SL_ERROR_SLRT_MISSING_ENTRY); + sl_reset(SL_ERROR_SLRT_MISSING_ENTRY); =20 evtlog_base =3D (void *)log_info->addr; evtlog_size =3D log_info->size; =20 + if (sl_cpu_type =3D=3D SL_CPU_AMD) { + /* Check if it is TPM 2.0 event log */ + if (!memcmp(evtlog_base + sizeof(struct tcg_pcr_event), + TCG_SPECID_SIG, sizeof(TCG_SPECID_SIG))) { + log21_elem =3D evtlog_base + sizeof(struct tcg_pcr_event) + + TCG_EfiSpecIdEvent_SIZE( + TPM2_HASH_COUNT(evtlog_base + + sizeof(struct tcg_pcr_event))); + tpm_log_ver =3D SL_TPM2_LOG; + } else { + evtlog_base +=3D sizeof(struct tcg_pcr_event) + + TCG_PCClientSpecIDEventStruct_SIZE; + evtlog_size -=3D sizeof(struct tcg_pcr_event) + + TCG_PCClientSpecIDEventStruct_SIZE; + } + + return; + } + + /* Else it is Intel and TXT */ txt_heap =3D (void *)sl_txt_read(TXT_CR_HEAP_BASE); =20 /* @@ -213,7 +286,23 @@ static void sl_find_drtm_event_log(struct slr_table *s= lrt) tpm_log_ver =3D SL_TPM2_LOG; } =20 -static void sl_validate_event_log_buffer(void) +static bool sl_check_buffer_kernel_overlap(void *buffer_base, void *buffer= _end, + void *kernel_base, void *kernel_end, + bool allow_inside) +{ + if (buffer_base >=3D kernel_end && buffer_end > kernel_end) + return false; /* above */ + + if (buffer_end <=3D kernel_base && buffer_base < kernel_base) + return false; /* below */ + + if (allow_inside && buffer_end <=3D kernel_end && buffer_base >=3D kernel= _base) + return false; /* inside */ + + return true; +} + +static void sl_txt_validate_event_log_buffer(void) { struct txt_os_sinit_data *os_sinit_data; void *txt_heap, *txt_end; @@ -235,11 +324,9 @@ static void sl_validate_event_log_buffer(void) * This check is to ensure the event log buffer does not overlap with * the MLE image. */ - if (evtlog_base >=3D mle_end && evtlog_end > mle_end) - goto pmr_check; /* above */ - - if (evtlog_end <=3D mle_base && evtlog_base < mle_base) - goto pmr_check; /* below */ + if (!sl_check_buffer_kernel_overlap(evtlog_base, evtlog_end, + mle_base, mle_end, false)) + goto pmr_check; =20 sl_txt_reset(SL_ERROR_MLE_BUFFER_OVERLAP); =20 @@ -254,6 +341,38 @@ static void sl_validate_event_log_buffer(void) sl_check_pmr_coverage(evtlog_base, evtlog_size, true); } =20 +static void sl_skinit_validate_buffers(struct slr_table *slrt, void *bootp= arams) +{ + void *evtlog_end, *kernel_start, *kernel_end; + struct slr_entry_dl_info *dl_info; + + /* On AMD, all the buffers should be below 4Gb */ + if ((u64)(evtlog_base + evtlog_size) > UINT_MAX) + sl_skinit_reset(); + + evtlog_end =3D evtlog_base + evtlog_size; + + dl_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_DL_INFO); + if (!dl_info) + sl_skinit_reset(); + + kernel_start =3D (void *)dl_info->dlme_base; + kernel_end =3D (void *)(dl_info->dlme_base + dl_info->dlme_size); + + /* + * This check is to ensure the event log buffer and the bootparams do + * overlap with the kernel image. Note on an EFI stub boot, the bootparams + * will be fully inside the kernel image. + */ + if (sl_check_buffer_kernel_overlap(bootparams, bootparams + PAGE_SIZE, + kernel_start, kernel_end, true)) + sl_skinit_reset(); + + if (sl_check_buffer_kernel_overlap(evtlog_base, evtlog_end, + kernel_start, kernel_end, false)) + sl_skinit_reset(); +} + static void sl_find_event_log_algorithms(void) { struct tcg_efi_specid_event_head *efi_head =3D @@ -261,17 +380,17 @@ static void sl_find_event_log_algorithms(void) u32 i; =20 if (efi_head->num_algs =3D=3D 0) - sl_txt_reset(SL_ERROR_TPM_INVALID_ALGS); + sl_reset(SL_ERROR_TPM_INVALID_ALGS); =20 tpm_algs =3D &efi_head->digest_sizes[0]; tpm_num_algs =3D efi_head->num_algs; =20 for (i =3D 0; i < tpm_num_algs; i++) { if (tpm_algs[i].digest_size > TPM_MAX_DIGEST_SIZE) - sl_txt_reset(SL_ERROR_TPM_INVALID_ALGS); + sl_reset(SL_ERROR_TPM_INVALID_ALGS); /* Alg ID 0 is invalid and maps to TPM_ALG_ERROR */ if (tpm_algs[i].alg_id =3D=3D TPM_ALG_ERROR) - sl_txt_reset(SL_ERROR_TPM_INVALID_ALGS); + sl_reset(SL_ERROR_TPM_INVALID_ALGS); } } =20 @@ -301,7 +420,7 @@ static void sl_tpm_log_event(u32 pcr, u32 event_type, total_size =3D sizeof(*pcr_event) + event_size; =20 if (tpm_log_event(evtlog_base, evtlog_size, total_size, pcr_event)) - sl_txt_reset(SL_ERROR_TPM_LOGGING_FAILED); + sl_reset(SL_ERROR_TPM_LOGGING_FAILED); } =20 static void sl_tpm2_log_event(u32 pcr, u32 event_type, @@ -360,7 +479,7 @@ static void sl_tpm2_log_event(u32 pcr, u32 event_type, total_size +=3D sizeof(*event) + event_size; =20 if (tpm2_log_event(log21_elem, evtlog_base, evtlog_size, total_size, &eve= nt_buf[0])) - sl_txt_reset(SL_ERROR_TPM_LOGGING_FAILED); + sl_reset(SL_ERROR_TPM_LOGGING_FAILED); } =20 static void sl_tpm_extend_evtlog(u32 pcr, u32 type, @@ -385,6 +504,13 @@ static struct setup_data *sl_handle_setup_data(struct = setup_data *curr, =20 next =3D (struct setup_data *)(unsigned long)curr->next; =20 + /* + * If this is the Secure Launch setup_data, it is the AMD info in the + * SLR table which is measured separately, skip it. + */ + if (curr->type =3D=3D SETUP_SECURE_LAUNCH) + return next; + /* SETUP_INDIRECT instances have to be handled differently */ if (curr->type =3D=3D SETUP_INDIRECT) { ind =3D (struct setup_indirect *)((u8 *)curr + offsetof(struct setup_dat= a, data)); @@ -427,30 +553,54 @@ static void sl_extend_slrt(struct slr_policy_entry *e= ntry) struct slr_table *slrt =3D (struct slr_table *)entry->entity; struct slr_entry_intel_info *intel_info; struct slr_entry_intel_info intel_tmp; + struct slr_entry_amd_info *amd_info; + struct slr_entry_amd_info amd_tmp; =20 /* * In revision one of the SLRT, the only table that needs to be - * measured is the Intel info table. Everything else is meta-data, - * addresses and sizes. Note the size of what to measure is not set. - * The flag SLR_POLICY_IMPLICIT_SIZE leaves it to the measuring code - * to sort out. + * measured is the platform-specific info table. Everything else is + * meta-data, addresses and sizes. Note the size of what to measure is + * not set. The flag SLR_POLICY_IMPLICIT_SIZE leaves it to the measuring + * code to sort out. */ if (slrt->revision =3D=3D 1) { - intel_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_INTEL_INFO); - if (!intel_info) - sl_txt_reset(SL_ERROR_SLRT_MISSING_ENTRY); + if (sl_cpu_type =3D=3D SL_CPU_INTEL) { + intel_info =3D + slr_next_entry_by_tag(slrt, NULL, + SLR_ENTRY_INTEL_INFO); + if (!intel_info) + sl_txt_reset(SL_ERROR_SLRT_MISSING_ENTRY); =20 - /* - * Make a temp copy and zero out address fields since they should - * not be measured. - */ - intel_tmp =3D *intel_info; - intel_tmp.boot_params_addr =3D 0; - intel_tmp.txt_heap =3D 0; + /* + * Make a temp copy and zero out address fields since they should + * not be measured. + */ + intel_tmp =3D *intel_info; + intel_tmp.boot_params_addr =3D 0; + intel_tmp.txt_heap =3D 0; + + sl_tpm_extend_evtlog(entry->pcr, TXT_EVTYPE_SLAUNCH, + (void *)&intel_tmp, sizeof(*intel_info), + entry->evt_info); + } else if (sl_cpu_type =3D=3D SL_CPU_AMD) { + amd_info =3D slr_next_entry_by_tag(slrt, NULL, + SLR_ENTRY_AMD_INFO); + if (!amd_info) + sl_skinit_reset(); =20 - sl_tpm_extend_evtlog(entry->pcr, TXT_EVTYPE_SLAUNCH, - (void *)&intel_tmp, sizeof(*intel_info), - entry->evt_info); + /* + * Make a temp copy and zero out address fields since + * they should not be measured. + */ + amd_tmp =3D *amd_info; + amd_tmp.next =3D 0; + amd_tmp.boot_params_addr =3D 0; + amd_tmp.slrt_base =3D 0; + + sl_tpm_extend_evtlog(entry->pcr, TXT_EVTYPE_SLAUNCH, + (void *)&amd_tmp, sizeof(amd_tmp), + entry->evt_info); + } } } =20 @@ -480,7 +630,7 @@ static void sl_process_extend_policy(struct slr_table *= slrt) =20 policy =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_ENTRY_POLICY); if (!policy) - sl_txt_reset(SL_ERROR_SLRT_MISSING_ENTRY); + sl_reset(SL_ERROR_SLRT_MISSING_ENTRY); =20 for (i =3D 0; i < policy->nr_entries; i++) { switch (policy->policy_entries[i].entity_type) { @@ -545,20 +695,29 @@ asmlinkage __visible void sl_main(void *bootparams) bp->hdr.loadflags &=3D ~SLAUNCH_FLAG; =20 /* - * Currently only Intel TXT is supported for Secure Launch. Testing + * Intel TXT and AMD SKINIT are supported for Secure Launch. Testing * this value also indicates that the kernel was booted successfully - * through the Secure Launch entry point and is in SMX mode. + * through the Secure Launch entry point and is in SMX or SKINIT mode. */ - if (!(sl_cpu_type & SL_CPU_INTEL)) + if (!(sl_cpu_type & (SL_CPU_INTEL | SL_CPU_AMD))) return; =20 - slrt =3D sl_locate_and_validate_slrt(); + slrt =3D sl_locate_and_validate_slrt(bp); =20 /* Locate the TPM event log. */ sl_find_drtm_event_log(slrt); =20 - /* Validate the location of the event log buffer before using it */ - sl_validate_event_log_buffer(); + /* + * On a TXT launch, validate the logging buffer for overlaps with the + * MLE and proper PMR coverage before using it. On an SKINIT launch, + * the boot params have to be used here to find the base and extent of + * the launched kernel. These values can then be used to make sure the + * boot params and logging buffer do not overlap the kernel. + */ + if (sl_cpu_type & SL_CPU_INTEL) + sl_txt_validate_event_log_buffer(); + else + sl_skinit_validate_buffers(slrt, bootparams); =20 /* * Find the TPM hash algorithms used by the ACM and recorded in the @@ -585,13 +744,15 @@ asmlinkage __visible void sl_main(void *bootparams) =20 sl_tpm_extend_evtlog(17, TXT_EVTYPE_SLAUNCH_END, NULL, 0, ""); =20 - /* No PMR check is needed, the TXT heap is covered by the DPR */ - txt_heap =3D (void *)sl_txt_read(TXT_CR_HEAP_BASE); - os_mle_data =3D txt_os_mle_data_start(txt_heap); + if (sl_cpu_type & SL_CPU_INTEL) { + /* No PMR check is needed, the TXT heap is covered by the DPR */ + txt_heap =3D (void *)sl_txt_read(TXT_CR_HEAP_BASE); + os_mle_data =3D txt_os_mle_data_start(txt_heap); =20 - /* - * Now that the OS-MLE data is measured, ensure the MTRR and - * misc enable MSRs are what we expect. - */ - sl_txt_validate_msrs(os_mle_data); + /* + * Now that the OS-MLE data is measured, ensure the MTRR and + * misc enable MSRs are what we expect. + */ + sl_txt_validate_msrs(os_mle_data); + } } diff --git a/arch/x86/boot/compressed/sl_stub.S b/arch/x86/boot/compressed/= sl_stub.S index 6c0f0b2a062d..7a6492bf04e4 100644 --- a/arch/x86/boot/compressed/sl_stub.S +++ b/arch/x86/boot/compressed/sl_stub.S @@ -23,6 +23,9 @@ /* CPUID: leaf 1, ECX, SMX feature bit */ #define X86_FEATURE_BIT_SMX (1 << 6) =20 +/* CPUID: leaf 0x80000001, ECX, SKINIT feature bit */ +#define X86_FEATURE_BIT_SKINIT (1 << 12) + #define IDT_VECTOR_LO_BITS 0 #define IDT_VECTOR_HI_BITS 6 =20 @@ -71,7 +74,11 @@ SYM_FUNC_START(sl_stub_entry) * On entry, %ebx has the entry abs offset to sl_stub_entry. The rva() * macro is used to generate relative references using %ebx as a base, as * to avoid absolute relocations, which would require fixups at runtime. - * Only %cs and %ds segments are known good. + * Only %cs and %ds segments are known good. On Intel, the ACM guarantees + * this while on AMD the SKL (Secure Kernel Loader) likewise does. + * + * In addition, on Intel %ecx holds the MLE page directory pointer + * table and on AMD %edx holds the physical base address of the SKL. */ =20 /* Load GDT, set segment regs and lret to __SL32_CS */ @@ -98,6 +105,12 @@ SYM_FUNC_START(sl_stub_entry) lret =20 .Lsl_cs: + /* + * For AMD, save SKL base before the CPUID instruction overwrites it. + * Performs cast from u32 to 64b void* for simpler use later. + */ + movl %edx, rva(sl_skl_base)(%ebx) + /* Save our base pointer reg and page table for MLE */ pushl %ebx pushl %ecx @@ -106,7 +119,7 @@ SYM_FUNC_START(sl_stub_entry) movl $1, %eax cpuid testl $(X86_FEATURE_BIT_SMX), %ecx - jz .Ldo_unknown_cpu + jz .Ldo_amd /* maybe AMD/SKINIT? */ =20 popl %ecx popl %ebx @@ -189,9 +202,21 @@ SYM_FUNC_START(sl_stub_entry) =20 jmp .Lcpu_setup_done =20 -.Ldo_unknown_cpu: - /* Non-Intel CPUs are not yet supported */ - ud2 +.Ldo_amd: + /* See if SKINIT feature is supported. */ + movl $0x80000001, %eax + cpuid + testl $(X86_FEATURE_BIT_SKINIT), %ecx + jz .Ldo_unknown_cpu + + popl %ecx + /* Base pointer reg saved in Intel check */ + popl %ebx + + /* Know it is AMD */ + movl $(SL_CPU_AMD), rva(sl_cpu_type)(%ebx) + + /* On AMD %esi is set up by the SKL, just go on */ =20 .Lcpu_setup_done: /* @@ -201,6 +226,10 @@ SYM_FUNC_START(sl_stub_entry) =20 /* Done, jump to normal 32b pm entry */ jmp startup_32 + +.Ldo_unknown_cpu: + /* Neither Intel nor AMD */ + ud2 SYM_FUNC_END(sl_stub_entry) =20 SYM_FUNC_START(sl_find_mle_base) @@ -722,6 +751,8 @@ SYM_DATA(sl_cpu_type, .long 0x00000000) =20 SYM_DATA(sl_mle_start, .long 0x00000000) =20 +SYM_DATA(sl_skl_base, .quad 0x0000000000000000) + SYM_DATA_LOCAL(sl_txt_spin_lock, .long 0x00000000) =20 SYM_DATA_LOCAL(sl_txt_stack_index, .long 0x00000000) diff --git a/arch/x86/include/uapi/asm/setup_data.h b/arch/x86/include/uapi= /asm/setup_data.h index 50c45ead4e7c..6f376c050c76 100644 --- a/arch/x86/include/uapi/asm/setup_data.h +++ b/arch/x86/include/uapi/asm/setup_data.h @@ -13,7 +13,8 @@ #define SETUP_CC_BLOB 7 #define SETUP_IMA 8 #define SETUP_RNG_SEED 9 -#define SETUP_ENUM_MAX SETUP_RNG_SEED +#define SETUP_SECURE_LAUNCH 10 +#define SETUP_ENUM_MAX SETUP_SECURE_LAUNCH =20 #define SETUP_INDIRECT (1<<31) #define SETUP_TYPE_MAX (SETUP_ENUM_MAX | SETUP_INDIRECT) diff --git a/arch/x86/kernel/slaunch.c b/arch/x86/kernel/slaunch.c index d81433a9b699..3a031043d2f1 100644 --- a/arch/x86/kernel/slaunch.c +++ b/arch/x86/kernel/slaunch.c @@ -93,6 +93,20 @@ void __noreturn slaunch_txt_reset(void __iomem *txt, unreachable(); } =20 +/* + * SKINIT has no sticky register to set an error code or a DRTM reset + * facility. The best that can be done is to trace an error and trigger + * a system reset using the undefined instruction. + */ +void __noreturn slaunch_skinit_reset(const char *msg, u64 error) +{ + pr_err("%s - error: 0x%llx", msg, error); + + asm volatile ("ud2"); + + unreachable(); +} + /* * The TXT heap is too big to map all at once with early_ioremap * so it is done a table at a time. @@ -217,7 +231,7 @@ static void __init slaunch_verify_pmrs(void __iomem *tx= t) slaunch_txt_reset(txt, errmsg, err); } =20 -static void __init slaunch_txt_reserve_range(u64 base, u64 size) +static void __init slaunch_reserve_range(u64 base, u64 size) { int type; =20 @@ -255,15 +269,15 @@ static void __init slaunch_txt_reserve(void __iomem *= txt) =20 base =3D TXT_PRIV_CONFIG_REGS_BASE; size =3D TXT_PUB_CONFIG_REGS_BASE - TXT_PRIV_CONFIG_REGS_BASE; - slaunch_txt_reserve_range(base, size); + slaunch_reserve_range(base, size); =20 memcpy_fromio(&heap_base, txt + TXT_CR_HEAP_BASE, sizeof(heap_base)); memcpy_fromio(&heap_size, txt + TXT_CR_HEAP_SIZE, sizeof(heap_size)); - slaunch_txt_reserve_range(heap_base, heap_size); + slaunch_reserve_range(heap_base, heap_size); =20 memcpy_fromio(&base, txt + TXT_CR_SINIT_BASE, sizeof(base)); memcpy_fromio(&size, txt + TXT_CR_SINIT_SIZE, sizeof(size)); - slaunch_txt_reserve_range(base, size); + slaunch_reserve_range(base, size); =20 field_offset =3D offsetof(struct txt_sinit_mle_data, sinit_vtd_dmar_table_size); @@ -288,14 +302,14 @@ static void __init slaunch_txt_reserve(void __iomem *= txt) for (i =3D 0; i < mdrnum; i++, mdr++) { /* Spec says some entries can have length 0, ignore them */ if (mdr->type > 0 && mdr->length > 0) - slaunch_txt_reserve_range(mdr->address, mdr->length); + slaunch_reserve_range(mdr->address, mdr->length); } =20 txt_early_put_heap_table(mdrs, mdroffset + mdrslen - 8); =20 nomdr: - slaunch_txt_reserve_range(ap_wake_info.ap_wake_block, - ap_wake_info.ap_wake_block_size); + slaunch_reserve_range(ap_wake_info.ap_wake_block, + ap_wake_info.ap_wake_block_size); =20 /* * Earlier checks ensured that the event log was properly situated @@ -304,16 +318,16 @@ static void __init slaunch_txt_reserve(void __iomem *= txt) * already reserved. */ if (evtlog_addr < heap_base || evtlog_addr > (heap_base + heap_size)) - slaunch_txt_reserve_range(evtlog_addr, evtlog_size); + slaunch_reserve_range(evtlog_addr, evtlog_size); =20 for (i =3D 0; i < e820_table->nr_entries; i++) { base =3D e820_table->entries[i].addr; size =3D e820_table->entries[i].size; if (base >=3D vtd_pmr_lo_size && base < 0x100000000ULL) - slaunch_txt_reserve_range(base, size); + slaunch_reserve_range(base, size); else if (base < vtd_pmr_lo_size && base + size > vtd_pmr_lo_size) - slaunch_txt_reserve_range(vtd_pmr_lo_size, - base + size - vtd_pmr_lo_size); + slaunch_reserve_range(vtd_pmr_lo_size, + base + size - vtd_pmr_lo_size); } } =20 @@ -514,6 +528,67 @@ static void __init slaunch_setup_txt(void) pr_info("Intel TXT setup complete\n"); } =20 +static void slaunch_skinit_prepare(void) +{ + struct slr_entry_amd_info amd_info_temp; + struct slr_entry_amd_info *amd_info; + struct slr_entry_log_info *log_info; + struct setup_data *data; + struct slr_table *slrt; + u64 pa_data; + + pa_data =3D (u64)boot_params.hdr.setup_data; + amd_info =3D NULL; + + while (pa_data) { + data =3D (struct setup_data *)early_memremap(pa_data, sizeof(*data)); + if (!data) + slaunch_skinit_reset("Error failed to early_memremap setup data\n", + SL_ERROR_MAP_SETUP_DATA); + + if (data->type =3D=3D SETUP_SECURE_LAUNCH) { + early_memunmap(data, sizeof(*data)); + amd_info =3D (struct slr_entry_amd_info *) + early_memremap(pa_data - sizeof(struct slr_entry_hdr), + sizeof(*amd_info)); + if (!amd_info) + slaunch_skinit_reset("Error failed to early_memremap AMD info\n", + SL_ERROR_MAP_SETUP_DATA); + break; + } + + pa_data =3D data->next; + early_memunmap(data, sizeof(*data)); + } + + if (!amd_info) + slaunch_skinit_reset("Error failed to find AMD info\n", + SL_ERROR_MISSING_EVENT_LOG); + + amd_info_temp =3D *amd_info; + early_memunmap(amd_info, sizeof(*amd_info)); + + slaunch_reserve_range(amd_info_temp.slrt_base, amd_info_temp.slrt_size); + + /* Get the SLRT and remap it */ + slrt =3D early_memremap(amd_info_temp.slrt_base, amd_info_temp.slrt_size); + if (!slrt) + slaunch_skinit_reset("Error failed to early_memremap SLR Table\n", + SL_ERROR_SLRT_MAP); + + log_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_LOG_INFO); + if (!log_info) + slaunch_skinit_reset("Error failed to find event log info SLR Table\n", + SL_ERROR_SLRT_MISSING_ENTRY); + + slaunch_reserve_range(log_info->addr, log_info->size); + + early_memunmap(slrt, amd_info_temp.slrt_size); + + if (amd_info_temp.psp_version =3D=3D 2 || amd_info_temp.psp_version =3D= =3D 3) + sl_flags |=3D SL_FLAG_SKINIT_PSP; +} + /* * AMD SKINIT specific late stub setup and validation called from within * x86 specific setup_arch(). @@ -530,6 +605,8 @@ static void __init slaunch_setup_skinit(void) if (!(val & (1 << SVM_VM_CR_INIT_REDIRECTION))) return; =20 + slaunch_skinit_prepare(); + /* Set flags on BSP so subsequent code knows it was a SKINIT launch */ sl_flags |=3D (SL_FLAG_ACTIVE|SL_FLAG_ARCH_SKINIT); pr_info("AMD SKINIT setup complete\n"); --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 7.mo584.mail-out.ovh.net (7.mo584.mail-out.ovh.net [178.33.253.54]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E42821BF37 for ; Wed, 30 Apr 2025 22:55:05 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=178.33.253.54 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746053708; cv=none; b=fJelbT0SdNcdb1aCALSJKzY/DFaBJw8B7pRTffQrcPinF0yP9LMtZfcIjbPQpllrw7ZJh66Hr8rGR6b66a0+kMX9EYCsW9GQ8COPnOAZgBC+a5fi9IQ2HSBG+DQDq30/5Oy8m5ieJdQHtE25M1Wxoq238dSnB6W+a6h41eyxAT8= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746053708; c=relaxed/simple; bh=hAX5/2RgCiZ7dm8HuqF2Gk36vMTUzfOwRjmXOB7iipI=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=OALcgvv1XPG7rf45YIMSc5+v6aaC9IkJpS4oSfsoyNiuNHxePMtJeBvfnZdhPS9X0OjXdAc0BjkjYI3IseU6OOVZTB/uUnG4jOo0XdkP0X4yFfZBRR24PjFOBITL5dg3hvhI9vWoHixFtlMdlKErQLBwtSNjUgsVoN/AhZoGzYc= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=TBVfq+Oh; arc=none smtp.client-ip=178.33.253.54 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="TBVfq+Oh" Received: from director7.ghost.mail-out.ovh.net (unknown [10.109.140.5]) by mo584.mail-out.ovh.net (Postfix) with ESMTP id 4Znshb2DQ7z1GPD for ; Wed, 30 Apr 2025 22:45:19 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-bggcb (unknown [10.111.182.153]) by director7.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 762311FD63; Wed, 30 Apr 2025 22:45:18 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.111]) by ghost-submission-5b5ff79f4f-bggcb with ESMTPSA id rIBXDf6nEmij+wgAhAnCLA (envelope-from ); Wed, 30 Apr 2025 22:45:18 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-111S0057806b8b7-35c0-4670-b495-38674cfdb939, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com, Thomas Gleixner , Ingo Molnar , Borislav Petkov , Dave Hansen , x86@kernel.org, "H. Peter Anvin" Subject: [RFC PATCH v2 6/9] x86: Prepare CPUs for post SKINIT launch Date: Thu, 1 May 2025 01:44:48 +0300 Message-ID: X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12105394324229108987 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmnecujfgurhephffvvefufffkofgjfhgggfestdekredtredttdenucfhrhhomhepufgvrhhgihhiucffmhihthhruhhkuceoshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmqeenucggtffrrghtthgvrhhnpefhheefheduieelieekfffgfffgfedutdevleevvdfhfffgledvgfdtuddtheefieenucfkphepuddvjedrtddrtddruddpudejiedrudduuddrudekuddrudejkedpfeejrdehledrudegvddrudduudenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehkeegmgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=O00A8RdNRWNaW2vNZPkGrsXiTUMw9V7ndOmhojSb+LI=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053119; v=1; b=TBVfq+Ohq0rxNWJ5bjI9PDDnSjnSARFA4+vJVSlrIM+DKe+9y+77koDHrfgT0rFXNia14Ue+ U/xjB8huUlEl70HI29Jnaph2gMqFR/Jn9OBep3yhybSBm0/VTDqNZv9GF73weSTX8NPpDqSQzi3 VjHv3OmCtKJB8ohSXhwOSD9iG1vmaI1v5WCz5BmN/DJrmXS98yTKq0hCMGRuvj09kqtdgZIZbz4 tR+seUCeOvfm/O0LoQ03FMHtMY0Vgp2aFbiJRZ6h6CFNWqm2ncYRTgEpRnkeJm9OhVHj4taSquX APzYkQPDJvXJZ7Beo/5nHGzu/7wxOvUV5GCCm1H5em+cg== Content-Type: text/plain; charset="utf-8" From: Ross Philipson The SKINIT instruction disables the GIF and it must be re-enabled on the BSP and APs as they are started. Since enabling GIF also re-enables NMIs, it should be done after a valid IDT is loaded for each CPU. SKINIT also already performed #INIT on the APs and it should be bypassed before issuing the startup IPIs. Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk --- arch/x86/kernel/slaunch.c | 23 +++++++++++++++++++++++ arch/x86/kernel/smpboot.c | 15 ++++++++++++++- arch/x86/kernel/traps.c | 4 ++++ 3 files changed, 41 insertions(+), 1 deletion(-) diff --git a/arch/x86/kernel/slaunch.c b/arch/x86/kernel/slaunch.c index 3a031043d2f1..a1c8be7de8d3 100644 --- a/arch/x86/kernel/slaunch.c +++ b/arch/x86/kernel/slaunch.c @@ -17,6 +17,7 @@ #include #include #include +#include #include #include #include @@ -716,3 +717,25 @@ void slaunch_finalize(int do_sexit) else if (boot_cpu_has(X86_FEATURE_SKINIT)) slaunch_finalize_skinit(); } + +/* + * AMD specific SKINIT CPU setup and initialization. + */ +void slaunch_cpu_setup_skinit(void) +{ + u64 val; + + if (!slaunch_is_skinit_launch()) + return; + + /* + * We don't yet handle #SX. Disable INIT_REDIRECTION first, before + * enabling GIF, so a pending INIT resets us, rather than causing a + * panic due to an unknown exception. + */ + rdmsrl(MSR_VM_CR, val); + wrmsrl(MSR_VM_CR, val & ~(1 << SVM_VM_CR_INIT_REDIRECTION)); + + /* Enable Global Interrupts flag */ + asm volatile ("stgi" ::: "memory"); +} diff --git a/arch/x86/kernel/smpboot.c b/arch/x86/kernel/smpboot.c index 219523884fdc..322fa4f8c5df 100644 --- a/arch/x86/kernel/smpboot.c +++ b/arch/x86/kernel/smpboot.c @@ -251,6 +251,12 @@ static void notrace __noendbr start_secondary(void *un= used) =20 cpu_init_exception_handling(false); =20 + /* + * If this is an AMD SKINIT secure launch, some extra work is done + * to prepare to start the secondary CPUs. + */ + slaunch_cpu_setup_skinit(); + /* * Load the microcode before reaching the AP alive synchronization * point below so it is not part of the full per CPU serialized @@ -703,7 +709,14 @@ static int wakeup_secondary_cpu_via_init(u32 phys_apic= id, unsigned long start_ei =20 preempt_disable(); maxlvt =3D lapic_get_maxlvt(); - send_init_sequence(phys_apicid); + + /* + * If this is an SKINIT secure launch, #INIT is already done on the APs + * by issuing the SKINIT instruction. For security reasons #INIT + * should not be done again. + */ + if (!slaunch_is_skinit_launch()) + send_init_sequence(phys_apicid); =20 mb(); =20 diff --git a/arch/x86/kernel/traps.c b/arch/x86/kernel/traps.c index 9f88b8a78e50..0a4d218a426b 100644 --- a/arch/x86/kernel/traps.c +++ b/arch/x86/kernel/traps.c @@ -43,6 +43,7 @@ #include #include #include +#include =20 #include #include @@ -1564,5 +1565,8 @@ void __init trap_init(void) if (!cpu_feature_enabled(X86_FEATURE_FRED)) idt_setup_traps(); =20 + /* If SKINIT was done on the BSP, this is the spot to enable GIF */ + slaunch_cpu_setup_skinit(); + cpu_init(); } --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 2.mo550.mail-out.ovh.net (2.mo550.mail-out.ovh.net [178.32.119.250]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 27C151BF37 for ; Wed, 30 Apr 2025 22:50:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=178.32.119.250 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746053441; cv=none; b=muataBeu9QmlwYP86L45VMMBw08uH7masgQxC3EivOcZdRnxiG53c312HYLP1MyfibKsj6F09Qh66lW4wmlXA9+Uy8v4LGdvB7w5daO7rBSh8AqlVajY/aJD0BWfD1o/FRo3sVFqtGde7rUVYQlzM42qVhjD8FLBZ7XwVrzXMcI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746053441; c=relaxed/simple; bh=DJOkI8RRTkcQYiwRlk6gpscGvGHJ0hzePQk2+QLs4Qw=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=U+cQ51r0X6oo3dWRnvgH4j38BHLuBD9atCTZoeVNg5Sfcqy98A+ex+RwqNStql9fQBkKMUwPKS0wH4lFXIAqQtO/WdFvv8Hg00xTc536kyGnIbj+4JXRW3QRLTsDp3mEhdnJvik5k29Q0TW2wFle6nn/06tRNa0iiQekL/9GFkk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=bmWpKgDX; arc=none smtp.client-ip=178.32.119.250 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="bmWpKgDX" Received: from director4.ghost.mail-out.ovh.net (unknown [10.109.176.170]) by mo550.mail-out.ovh.net (Postfix) with ESMTP id 4Znshd3trMz1XpY for ; Wed, 30 Apr 2025 22:45:21 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-qblm5 (unknown [10.110.188.135]) by director4.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 402571FDEE; Wed, 30 Apr 2025 22:45:21 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.103]) by ghost-submission-5b5ff79f4f-qblm5 with ESMTPSA id IwamBQGoEmhmuQIAmzuhMg (envelope-from ); Wed, 30 Apr 2025 22:45:21 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-103G00578138a33-c66c-4bcf-8dca-08c187643215, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com Subject: [RFC PATCH v2 7/9] x86/slmodule: Support AMD SKINIT Date: Thu, 1 May 2025 01:44:49 +0300 Message-ID: <7a39e40036b795339244fac870bead7983f06aec.1746037489.git.sergii.dmytruk@3mdeb.com> X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12105957275724133532 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: 0 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucenucfjughrpefhvfevufffkffojghfggfgsedtkeertdertddtnecuhfhrohhmpefuvghrghhiihcuffhmhihtrhhukhcuoehsvghrghhiihdrughmhihtrhhukhesfehmuggvsgdrtghomheqnecuggftrfgrthhtvghrnhephfehfeehudeileeikeffgfffgfefuddtveelvedvhfffgfelvdfgtddutdehfeeinecukfhppeduvdejrddtrddtrddupddujeeirdduuddurddukedurddujeekpdefjedrheelrddugedvrddutdefnecuvehluhhsthgvrhfuihiivgepfeenucfrrghrrghmpehinhgvthepuddvjedrtddrtddruddpmhgrihhlfhhrohhmpehsvghrghhiihdrughmhihtrhhukhesfehmuggvsgdrtghomhdpnhgspghrtghpthhtohepuddprhgtphhtthhopehlihhnuhigqdhkvghrnhgvlhesvhhgvghrrdhkvghrnhgvlhdrohhrghdpoffvtefjohhsthepmhhoheehtdgmpdhmohguvgepshhmthhpohhuth DKIM-Signature: a=rsa-sha256; bh=+FaceXCqu/ICnaOIGecXj8d3JMkfkxWToutOnQ3DjqU=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053121; v=1; b=bmWpKgDXEybw6vS4cDcRwuOlciKyjxKn2yUjKSQT0/J8M0Hxx13rz9mugrBd1ruMHKF1Au70 abUKB8uUq7d7iegeE6tGDArL54xhisd8H5OtlMF24cwpFuwVWgAQ/ZndqG6qAI1iznLS55RecIY 12ezxAhtrFuy+Ff4x+wn2oNtL5rXCq66vQSwlFsXC5xnzkLfIKG+FEQ8kHZrWGf800UPxDGtTHx ze5Jh92geUf0dJIxS/7/drHx1PlpB4krTrdv++c8wqgV7QK8JXFN/GBWXa/mbVW2akyuR6Grfm8 IMs7qc405DMyNPQ/UC53B6pp2SQERMaJ8L/M4wZRhQgwg== Content-Type: text/plain; charset="utf-8" From: Ross Philipson Some of the changes are related to generalization: common macro for resetting the platform. The rest are: - SKINIT-specific way of getting to SLRT - handling of TPM log which has TXT-specific header embedded as vendor data of a TCG-compliant one Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk --- arch/x86/kernel/slmodule.c | 161 ++++++++++++++++++++++++++++++------- 1 file changed, 134 insertions(+), 27 deletions(-) diff --git a/arch/x86/kernel/slmodule.c b/arch/x86/kernel/slmodule.c index 64010bac038c..4d29c1628a90 100644 --- a/arch/x86/kernel/slmodule.c +++ b/arch/x86/kernel/slmodule.c @@ -18,12 +18,21 @@ #include #include #include +#include #include #include #include #include #include =20 +#define slaunch_reset(t, m, e) \ + do { \ + if (t) \ + slaunch_txt_reset((t), (m), (e)); \ + else \ + slaunch_skinit_reset((m), (e)); \ + } while (0) + /* * The macro DECLARE_TXT_PUB_READ_U is used to read values from the TXT * public registers as unsigned values. @@ -83,6 +92,7 @@ struct memfile { =20 static struct memfile sl_evtlog =3D {"eventlog", NULL, 0}; static void *txt_heap; +static void *skinit_evtlog; static struct txt_heap_event_log_pointer2_1_element *evtlog21; static DEFINE_MUTEX(sl_evt_log_mutex); static struct tcg_efi_specid_event_head *efi_head; @@ -239,12 +249,19 @@ static void slaunch_teardown_securityfs(void) memunmap(txt_heap); txt_heap =3D NULL; } + } else if (slaunch_get_flags() & SL_FLAG_ARCH_SKINIT) { + if (skinit_evtlog) { + memunmap(skinit_evtlog); + skinit_evtlog =3D NULL; + } + sl_evtlog.addr =3D NULL; + sl_evtlog.size =3D 0; } =20 securityfs_remove(slaunch_dir); } =20 -static void slaunch_intel_evtlog(void __iomem *txt) +static void slaunch_txt_evtlog(void __iomem *txt) { struct slr_entry_log_info *log_info; struct txt_os_mle_data *params; @@ -312,6 +329,88 @@ static void slaunch_intel_evtlog(void __iomem *txt) efi_head =3D (struct tcg_efi_specid_event_head *)(sl_evtlog.addr + sizeof= (struct tcg_pcr_event)); } =20 +static void slaunch_skinit_evtlog(void) +{ + struct slr_entry_amd_info amd_info_temp; + struct slr_entry_amd_info *amd_info; + struct slr_entry_log_info *log_info; + struct setup_data *data; + struct slr_table *slrt; + u64 pa_data; + + pa_data =3D (u64)boot_params.hdr.setup_data; + amd_info =3D NULL; + + while (pa_data) { + data =3D (struct setup_data *)memremap(pa_data, sizeof(*data), MEMREMAP_= WB); + if (!data) + slaunch_skinit_reset("Error failed to memremap setup data\n", + SL_ERROR_MAP_SETUP_DATA); + + if (data->type =3D=3D SETUP_SECURE_LAUNCH) { + memunmap(data); + amd_info =3D (struct slr_entry_amd_info *) + memremap(pa_data - sizeof(struct slr_entry_hdr), + sizeof(*amd_info), MEMREMAP_WB); + if (!amd_info) + slaunch_skinit_reset("Error failed to memremap AMD info\n", + SL_ERROR_MAP_SETUP_DATA); + break; + } + + pa_data =3D data->next; + memunmap(data); + } + + if (!amd_info) + slaunch_skinit_reset("Error failed to find AMD info\n", SL_ERROR_MISSING= _EVENT_LOG); + + amd_info_temp =3D *amd_info; + memunmap(amd_info); + + /* Get the SLRT and remap it */ + slrt =3D memremap(amd_info_temp.slrt_base, amd_info_temp.slrt_size, MEMRE= MAP_WB); + if (!slrt) + slaunch_skinit_reset("Error failed to memremap SLR Table\n", SL_ERROR_SL= RT_MAP); + + log_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_LOG_INFO); + if (!log_info) + slaunch_skinit_reset("Error failed to find event log info SLR Table\n", + SL_ERROR_SLRT_MISSING_ENTRY); + + /* Finally map the actual event log and find the proper offsets */ + skinit_evtlog =3D memremap(log_info->addr, log_info->size, MEMREMAP_WB); + if (!skinit_evtlog) + slaunch_skinit_reset("Error failed to memremap TPM event log\n", + SL_ERROR_EVENTLOG_MAP); + + sl_evtlog.size =3D log_info->size; + sl_evtlog.addr =3D skinit_evtlog; + + memunmap(slrt); + + /* + * See the comment for the following function concerning the + * logic used here: + * arch/x86/boot/compressed/sl_main.c:sl_find_event_log() + */ + if (!memcmp(skinit_evtlog + sizeof(struct tcg_pcr_event), + TCG_SPECID_SIG, sizeof(TCG_SPECID_SIG))) { + evtlog21 =3D skinit_evtlog + sizeof(struct tcg_pcr_event) + + TCG_EfiSpecIdEvent_SIZE( + TPM2_HASH_COUNT(skinit_evtlog + + sizeof(struct tcg_pcr_event))); + } else { + sl_evtlog.addr +=3D sizeof(struct tcg_pcr_event) + + TCG_PCClientSpecIDEventStruct_SIZE; + sl_evtlog.size -=3D sizeof(struct tcg_pcr_event) + + TCG_PCClientSpecIDEventStruct_SIZE; + } + + /* Save pointer to the EFI SpecID log header */ + efi_head =3D (struct tcg_efi_specid_event_head *)(skinit_evtlog + sizeof(= struct tcg_pcr_event)); +} + static void slaunch_tpm2_extend_event(struct tpm_chip *tpm, void __iomem *= txt, struct tcg_pcr_event2_head *event) { @@ -331,8 +430,7 @@ static void slaunch_tpm2_extend_event(struct tpm_chip *= tpm, void __iomem *txt, =20 digests =3D kzalloc(efi_head->num_algs * sizeof(*digests), GFP_KERNEL); if (!digests) - slaunch_txt_reset(txt, "Failed to allocate array of digests\n", - SL_ERROR_GENERIC); + slaunch_reset(txt, "Failed to allocate array of digests\n", SL_ERROR_GEN= ERIC); =20 for (i =3D 0; i < event->count; i++) { dptr =3D (u8 *)alg_id_field + sizeof(u16); @@ -349,8 +447,7 @@ static void slaunch_tpm2_extend_event(struct tpm_chip *= tpm, void __iomem *txt, ret =3D tpm_pcr_extend(tpm, event->pcr_idx, digests); if (ret) { pr_err("Error extending TPM20 PCR, result: %d\n", ret); - slaunch_txt_reset(txt, "Failed to extend TPM20 PCR\n", - SL_ERROR_TPM_EXTEND); + slaunch_reset(txt, "Failed to extend TPM20 PCR\n", SL_ERROR_TPM_EXTEND); } =20 kfree(digests); @@ -372,8 +469,8 @@ static void slaunch_tpm2_extend(struct tpm_chip *tpm, v= oid __iomem *txt) while ((void *)event < sl_evtlog.addr + evtlog21->next_record_offset) { size =3D __calc_tpm2_event_size(event, event_header, false); if (!size) - slaunch_txt_reset(txt, "TPM20 invalid event in event log\n", - SL_ERROR_TPM_INVALID_EVENT); + slaunch_reset(txt, "TPM20 invalid event in event log\n", + SL_ERROR_TPM_INVALID_EVENT); =20 /* * Marker events indicate where the Secure Launch early stub @@ -400,8 +497,8 @@ static void slaunch_tpm2_extend(struct tpm_chip *tpm, v= oid __iomem *txt) } =20 if (!start || !end) - slaunch_txt_reset(txt, "Missing start or end events for extending TPM20 = PCRs\n", - SL_ERROR_TPM_EXTEND); + slaunch_reset(txt, "Missing start or end events for extending TPM20 PCRs= \n", + SL_ERROR_TPM_EXTEND); } =20 static void slaunch_tpm_extend(struct tpm_chip *tpm, void __iomem *txt) @@ -442,8 +539,8 @@ static void slaunch_tpm_extend(struct tpm_chip *tpm, vo= id __iomem *txt) ret =3D tpm_pcr_extend(tpm, event->pcr_idx, &digest); if (ret) { pr_err("Error extending TPM12 PCR, result: %d\n", ret); - slaunch_txt_reset(txt, "Failed to extend TPM12 PCR\n", - SL_ERROR_TPM_EXTEND); + slaunch_reset(txt, "Failed to extend TPM12 PCR\n", + SL_ERROR_TPM_EXTEND); } } =20 @@ -452,8 +549,8 @@ static void slaunch_tpm_extend(struct tpm_chip *tpm, vo= id __iomem *txt) } =20 if (!start || !end) - slaunch_txt_reset(txt, "Missing start or end events for extending TPM12 = PCRs\n", - SL_ERROR_TPM_EXTEND); + slaunch_reset(txt, "Missing start or end events for extending TPM12 PCRs= \n", + SL_ERROR_TPM_EXTEND); } =20 static void slaunch_pcr_extend(void __iomem *txt) @@ -463,13 +560,11 @@ static void slaunch_pcr_extend(void __iomem *txt) =20 tpm =3D tpm_default_chip(); if (!tpm) - slaunch_txt_reset(txt, "Could not get default TPM chip\n", - SL_ERROR_TPM_INIT); + slaunch_reset(txt, "Could not get default TPM chip\n", SL_ERROR_TPM_INIT= ); =20 rc =3D tpm_chip_set_locality(tpm, 2); if (rc) - slaunch_txt_reset(txt, "Could not set TPM chip locality 2\n", - SL_ERROR_TPM_INIT); + slaunch_reset(txt, "Could not set TPM chip locality 2\n", SL_ERROR_TPM_I= NIT); =20 if (evtlog21) slaunch_tpm2_extend(tpm, txt); @@ -482,19 +577,31 @@ static int __init slaunch_module_init(void) void __iomem *txt; =20 /* Check to see if Secure Launch happened */ - if ((slaunch_get_flags() & (SL_FLAG_ACTIVE|SL_FLAG_ARCH_TXT)) !=3D - (SL_FLAG_ACTIVE | SL_FLAG_ARCH_TXT)) + if (!(slaunch_get_flags() & SL_FLAG_ACTIVE)) return 0; =20 - txt =3D ioremap(TXT_PRIV_CONFIG_REGS_BASE, TXT_NR_CONFIG_PAGES * - PAGE_SIZE); - if (!txt) - panic("Error ioremap of TXT priv registers\n"); + if (slaunch_get_flags() & SL_FLAG_ARCH_TXT) { + txt =3D ioremap(TXT_PRIV_CONFIG_REGS_BASE, TXT_NR_CONFIG_PAGES * + PAGE_SIZE); + if (!txt) + panic("Error ioremap of TXT priv registers\n"); + + slaunch_txt_evtlog(txt); + + slaunch_pcr_extend(txt); + + iounmap(txt); + + pr_info("TXT Secure Launch module setup\n"); + } else if (slaunch_get_flags() & SL_FLAG_ARCH_SKINIT) { + slaunch_skinit_evtlog(); + + slaunch_pcr_extend(NULL); + + pr_info("SKINIT Secure Launch module setup\n"); + } else + panic("Secure Launch unknown architecture\n"); =20 - /* Only Intel TXT is supported at this point */ - slaunch_intel_evtlog(txt); - slaunch_pcr_extend(txt); - iounmap(txt); =20 return slaunch_expose_securityfs(); } --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 10.mo581.mail-out.ovh.net (10.mo581.mail-out.ovh.net [178.33.250.56]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 60561211C for ; Thu, 1 May 2025 01:11:42 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=178.33.250.56 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746061909; cv=none; b=HDR1DcwyZ8uB638Q+5RJs4F6ryA6mOwifSZsFESAJ90iw5T7pXpTfIwbHLULrCuMmjONVChFW3HIMxCN+9VWBzhgXqex6/neQMCP7sAzsU9KnUhlkMUDKdozU9l03D5yBPKWZyzrpe5oE5/q4Eyuk1Ype4bi34F5NU9BCT7xxyE= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746061909; c=relaxed/simple; bh=KVl87mxGkMT3rFt2okoJ89BYbEAONsppjlmmv96ipo0=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=MCjrK8r0gZs6/Gc8e2qtNvAU9y/JwV0ElxMAUr/pVmtJN1kobcx+QklMk0kkNzOFRs7eCkDzktu32YO6WgZTBx6adzfSNsC4EniOmi+lqaeRsqzZgRUJQKpQXsnG3VPMN/3KoVzjeikiv4NMbZ1+TvIdBwDY1lr083jGqDDA6jA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=Vf9Yo0s1; arc=none smtp.client-ip=178.33.250.56 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="Vf9Yo0s1" Received: from director11.ghost.mail-out.ovh.net (unknown [10.108.17.147]) by mo581.mail-out.ovh.net (Postfix) with ESMTP id 4Znshh0Xw6z1MGP for ; Wed, 30 Apr 2025 22:45:24 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-bggcb (unknown [10.111.182.166]) by director11.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 9C97E1FE1E; Wed, 30 Apr 2025 22:45:23 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.110]) by ghost-submission-5b5ff79f4f-bggcb with ESMTPSA id yhGnFgOoEmix+wgAhAnCLA (envelope-from ); Wed, 30 Apr 2025 22:45:23 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-110S004d3d77194-a22f-47ee-abc9-6b3f4bb4fce5, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com, Ard Biesheuvel Subject: [RFC PATCH v2 8/9] x86: AMD changes for EFI stub DRTM launch support Date: Thu, 1 May 2025 01:44:50 +0300 Message-ID: <5c4d5adaa40fc5d5d1bcfef813713040e4df13a4.1746037489.git.sergii.dmytruk@3mdeb.com> X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12106801701031425260 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleefucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmnecujfgurhephffvvefufffkofgjfhgggfestdekredtredttdenucfhrhhomhepufgvrhhgihhiucffmhihthhruhhkuceoshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmqeenucggtffrrghtthgvrhhnpefhheefheduieelieekfffgfffgfedutdevleevvdfhfffgledvgfdtuddtheefieenucfkphepuddvjedrtddrtddruddpudejiedrudduuddrudekuddrudejkedpfeejrdehledrudegvddruddutdenucevlhhushhtvghrufhiiigvpedunecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehkedumgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=AxO8+pqA5ngI1PtQlcwGIyLcYBmP10KryNrbaqciCQI=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053124; v=1; b=Vf9Yo0s1C2KgoG9AQQiXV+B9NTnATlsGzRTi6WZWPrqeZoMcGQD0Fu2Xlq+d5W/RmV90Llkf jtzaUah7zMT9LJQSU2/RqQY977e2hoBILMcpGOZD3Ey4Q+znbwSbUSspfx2Qanni7gzdTkFkfCg 3RgR7Vo/2wBdVLl22m8DLQI3wILOQxY99Sc+/6NfAR/EfHE7FeoSiJODKzN9jz9WgBCo4eEuCE5 dAu2Xf8FkjVBddfWGqA/DfM9ohy66REskpY6Q7QLI0Y3ngpeI2GktcQudQWnYLKv39tLpcuDFQ6 5U9KqaxSKj12G6LvoC7K7dlqB5RvN3ykry4in9qFfbRqw== Content-Type: text/plain; charset="utf-8" From: Ross Philipson * Only do the TXT setup steps if this is a TXT launch not an SKINIT one. * Initialize boot params address for SKINIT. Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk Acked-by: Ard Biesheuvel --- drivers/firmware/efi/libstub/x86-stub.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/drivers/firmware/efi/libstub/x86-stub.c b/drivers/firmware/efi= /libstub/x86-stub.c index bfa36466a79c..0453be1ba58d 100644 --- a/drivers/firmware/efi/libstub/x86-stub.c +++ b/drivers/firmware/efi/libstub/x86-stub.c @@ -798,15 +798,21 @@ static bool efi_secure_launch_update_boot_params(stru= ct slr_table *slrt, struct boot_params *boot_params) { struct slr_entry_intel_info *txt_info; + struct slr_entry_amd_info *skinit_info; struct slr_entry_policy *policy; bool updated =3D false; int i; =20 txt_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_INTEL_INFO); - if (!txt_info) - return false; + if (txt_info) + txt_info->boot_params_addr =3D (u64)boot_params; + + skinit_info =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_AMD_INFO); + if (skinit_info) + skinit_info->boot_params_addr =3D (u64)boot_params; =20 - txt_info->boot_params_addr =3D (u64)boot_params; + if (!txt_info && !skinit_info) + return false; =20 policy =3D slr_next_entry_by_tag(slrt, NULL, SLR_ENTRY_ENTRY_POLICY); if (!policy) --=20 2.49.0 From nobody Wed Dec 17 12:34:25 2025 Received: from 18.mo584.mail-out.ovh.net (18.mo584.mail-out.ovh.net [188.165.54.143]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 3A6A8228CB0 for ; Wed, 30 Apr 2025 23:25:02 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=188.165.54.143 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746055506; cv=none; b=ORMraF91q7xq0zXItOJnUYFIPmo1xGsna6OblBXiZlGkWHkLA2GgrIVpNztBBc6flvkSnJP4flA+mdfKMTNDB2xt954TszsB1yFLWXnJvk6KuqQofDr8N0j+TuLbVuzK1bhNw4vtLZNpl10MKrklAwuu+Ml6+M4qX68QGS74fVI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1746055506; c=relaxed/simple; bh=XBIr74i6KxD+PEkL21pkDZrgl6KSA5thni9WDJWykmo=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=nnu7C/Wdq4/IeTsvspk0lYwNrYoPjCX3lW3PseqLf54p2nYipeTgGNuAPlJhdx1VoOm8A7fc2wWoRpillsB2VSyd6RzqTYaYIteAdBPm2Yiof8F5EXqDvq2HAMeS33lSHb/cy6BgPZHBZwJQmRYDCE5ZKAiQGGSqhLK+asB5DAw= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com; spf=pass smtp.mailfrom=3mdeb.com; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b=YLW/tGPj; arc=none smtp.client-ip=188.165.54.143 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=3mdeb.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=3mdeb.com header.i=@3mdeb.com header.b="YLW/tGPj" Received: from director2.ghost.mail-out.ovh.net (unknown [10.108.2.54]) by mo584.mail-out.ovh.net (Postfix) with ESMTP id 4Znshk417Hz1PgY for ; Wed, 30 Apr 2025 22:45:26 +0000 (UTC) Received: from ghost-submission-5b5ff79f4f-46gmz (unknown [10.110.168.229]) by director2.ghost.mail-out.ovh.net (Postfix) with ESMTPS id 0570E1FE6A; Wed, 30 Apr 2025 22:45:25 +0000 (UTC) Received: from 3mdeb.com ([37.59.142.114]) by ghost-submission-5b5ff79f4f-46gmz with ESMTPSA id QyoaMgWoEmiwIwoAqBLyHQ (envelope-from ); Wed, 30 Apr 2025 22:45:25 +0000 Authentication-Results: garm.ovh; auth=pass (GARM-114S00855921a9f-45f1-4aa2-87e3-3952a813bd90, 7FFE21389DDF989CCD6FB7268846A7FDE11993D7) smtp.auth=sergii.dmytruk@3mdeb.com X-OVh-ClientIp: 176.111.181.178 From: Sergii Dmytruk To: linux-kernel@vger.kernel.org Cc: trenchboot-devel@googlegroups.com, Joerg Roedel , Suravee Suthikulpanit Subject: [RFC PATCH v2 9/9] psp: Perform kernel portion of DRTM procedures Date: Thu, 1 May 2025 01:44:51 +0300 Message-ID: X-Mailer: git-send-email 2.49.0 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 12107364648499197046 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeefvddrtddtgddvieejleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmnecujfgurhephffvvefufffkofgjfhgggfestdekredtredttdenucfhrhhomhepufgvrhhgihhiucffmhihthhruhhkuceoshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmqeenucggtffrrghtthgvrhhnpefhheefheduieelieekfffgfffgfedutdevleevvdfhfffgledvgfdtuddtheefieenucfkphepuddvjedrtddrtddruddpudejiedrudduuddrudekuddrudejkedpfeejrdehledrudegvddruddugeenucevlhhushhtvghrufhiiigvpedvnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepshgvrhhgihhirdgumhihthhruhhkseefmhguvggsrdgtohhmpdhnsggprhgtphhtthhopedupdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdfovfetjfhoshhtpehmohehkeegmgdpmhhouggvpehsmhhtphhouhht DKIM-Signature: a=rsa-sha256; bh=uzuyqTU59cRs6tTD9qQgPqXvYJjj3k7Dr5X7pAMqm9w=; c=relaxed/relaxed; d=3mdeb.com; h=From; s=ovhmo3617313-selector1; t=1746053126; v=1; b=YLW/tGPjmoIUHAyMr1X0nW4Xq6iRnhYm1T66V3Atj36YhQTGj/Uy1h1bof8X0mEKBlPhs/RE DcP7G69J5euzQ3YQdoFZjVTlYjN58nOiOQKIPeQuc7qs0ar+FhUtybFq29/AUBXfUHXcEGuexYT mpMALYTFDxWaf6DfSXmnjq+HuCKX6u0EKw7jypDhxte1BSin98wmQTxEp04bpTfbIDwGfoz/pwR CTQdl9rIIUkVijawftTpB2+N5rcfOoc74Ad0Rka2TrAAW8u95pz3FbjuxKrzs2f5pNrOEgCc2oB n4Hj6Nl+9VGP8TLMV6TOmGryooDeAnradV5lr56/CtftQ== Content-Type: text/plain; charset="utf-8" From: Jagannathan Raman GRUB and AMD-SL would have executed the SKINIT instruction and performed DRTM setup procedures. As part of DRTM, GRUB sets up TMRs to cover the whole of the system's physical memory regions. The Kernel should release these TMRs to facilitate communication between devices and drivers. TMRs are released after the Kernel sets up IOMMU. Releasing TMRs concludes DRTM. The Kernel should also execute DRTM_CMD_TPM_LOCALITY_ACCESS to lock TPM locality two before removing TMRs. But this prevents the Kernel's TPM driver (which loads subsequently) from extending PCRs. As such, we are skipping the TPM locality access command. Signed-off-by: Jagannathan Raman Signed-off-by: Ross Philipson Signed-off-by: Sergii Dmytruk --- arch/x86/kernel/Makefile | 1 + arch/x86/kernel/sl-psp.c | 239 ++++++++++++++++++++++++++++++++++++++ arch/x86/kernel/slaunch.c | 4 +- drivers/iommu/amd/init.c | 12 ++ 4 files changed, 255 insertions(+), 1 deletion(-) create mode 100644 arch/x86/kernel/sl-psp.c diff --git a/arch/x86/kernel/Makefile b/arch/x86/kernel/Makefile index bed87b1c49a2..8ccad4f5c129 100644 --- a/arch/x86/kernel/Makefile +++ b/arch/x86/kernel/Makefile @@ -84,6 +84,7 @@ obj-y +=3D step.o obj-$(CONFIG_INTEL_TXT) +=3D tboot.o obj-$(CONFIG_SECURE_LAUNCH) +=3D slaunch.o obj-$(CONFIG_SECURE_LAUNCH) +=3D slmodule.o +obj-$(CONFIG_SECURE_LAUNCH) +=3D sl-psp.o obj-$(CONFIG_ISA_DMA_API) +=3D i8237.o obj-y +=3D stacktrace.o obj-y +=3D cpu/ diff --git a/arch/x86/kernel/sl-psp.c b/arch/x86/kernel/sl-psp.c new file mode 100644 index 000000000000..69d24f275042 --- /dev/null +++ b/arch/x86/kernel/sl-psp.c @@ -0,0 +1,239 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Secure Launch early setup. + * + * Copyright (c) 2024, Oracle and/or its affiliates. + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#define DRTM_MBOX_READY_MASK 0x80000000 +#define DRTM_MBOX_TMR_INDEX_ID_MASK 0x0F000000 +#define DRTM_MBOX_CMD_MASK 0x00FF0000 +#define DRTM_MBOX_STATUS_MASK 0x0000FFFF + +#define DRTM_MBOX_CMD_SHIFT 16 + +#define DRTM_NO_ERROR 0x00000000 +#define DRTM_NOT_SUPPORTED 0x00000001 +#define DRTM_LAUNCH_ERROR 0x00000002 +#define DRTM_TMR_SETUP_FAILED_ERROR 0x00000003 +#define DRTM_TMR_DESTROY_FAILED_ERROR 0x00000004 +#define DRTM_GET_TCG_LOGS_FAILED_ERROR 0x00000007 +#define DRTM_OUT_OF_RESOURCES_ERROR 0x00000008 +#define DRTM_GENERIC_ERROR 0x00000009 +#define DRTM_INVALID_SERVICE_ID_ERROR 0x0000000A +#define DRTM_MEMORY_UNALIGNED_ERROR 0x0000000B +#define DRTM_MINIMUM_SIZE_ERROR 0x0000000C +#define DRTM_GET_TMR_DESCRIPTOR_FAILED 0x0000000D +#define DRTM_EXTEND_OSSL_DIGEST_FAILED 0x0000000E +#define DRTM_SETUP_NOT_ALLOWED 0x0000000F +#define DRTM_GET_IVRS_TABLE_FAILED 0x00000010 + +#define DRTM_CMD_GET_CAPABILITY 0x1 +#define DRTM_CMD_TMR_SETUP 0x2 +#define DRTM_CMD_TMR_RELEASE 0x3 +#define DRTM_CMD_LAUNCH 0x4 +#define DRTM_CMD_GET_TCG_LOGS 0x7 +#define DRTM_CMD_TPM_LOCALITY_ACCESS 0x8 +#define DRTM_CMD_GET_TMR_DESCRIPTORS 0x9 +#define DRTM_CMD_ALLOCATE_SHARED_MEMORY 0xA +#define DRTM_CMD_EXTEND_OSSL_DIGEST 0xB +#define DRTM_CMD_GET_IVRS_TABLE_INFO 0xC + +#define DRTM_TMR_INDEX_0 0 +#define DRTM_TMR_INDEX_1 1 +#define DRTM_TMR_INDEX_2 2 +#define DRTM_TMR_INDEX_3 3 +#define DRTM_TMR_INDEX_4 4 +#define DRTM_TMR_INDEX_5 5 +#define DRTM_TMR_INDEX_6 6 +#define DRTM_TMR_INDEX_7 7 + +#define DRTM_CMD_READY 0 +#define DRTM_RESPONSE_READY 1 + +static bool slaunch_psp_early_setup_done; + +static u32 __iomem *c2pmsg_72; + +static void slaunch_smn_register_read(u32 address, u32 *value) +{ + u32 val; + + val =3D address; + pci_direct_conf1.write(0, 0, 0, 0xB8, 4, val); + pci_direct_conf1.read(0, 0, 0, 0xBC, 4, &val); + + *value =3D val; +} + +#define IOHC0NBCFG_SMNBASE 0x13B00000 +#define PSP_BASE_ADDR_LO_SMN_ADDRESS (IOHC0NBCFG_SMNBASE + 0x102E0) + +static u32 slaunch_get_psp_bar_addr(void) +{ + u32 pspbaselo =3D 0; + + slaunch_smn_register_read(PSP_BASE_ADDR_LO_SMN_ADDRESS, &pspbaselo); + + /* Mask out the lower bits */ + pspbaselo &=3D 0xFFF00000; + + return pspbaselo; +} + +static void slaunch_clear_c2pmsg_regs(void) +{ + if (c2pmsg_72) + iounmap(c2pmsg_72); + + c2pmsg_72 =3D NULL; +} + +static bool slaunch_setup_c2pmsg_regs(void) +{ + phys_addr_t bar2; + + bar2 =3D (phys_addr_t)slaunch_get_psp_bar_addr(); + if (!bar2) + return false; + + c2pmsg_72 =3D ioremap(bar2 + 0x10a20, 4); + if (!c2pmsg_72) { + slaunch_clear_c2pmsg_regs(); + return false; + } + + return true; +} + +static const char *const slaunch_status_strings[] =3D { + "DRTM_NO_ERROR", + "DRTM_NOT_SUPPORTED", + "DRTM_LAUNCH_ERROR", + "DRTM_TMR_SETUP_FAILED_ERROR", + "DRTM_TMR_DESTROY_FAILED_ERROR", + "UNDEFINED", + "UNDEFINED", + "DRTM_GET_TCG_LOGS_FAILED_ERROR", + "DRTM_OUT_OF_RESOURCES_ERROR", + "DRTM_GENERIC_ERROR", + "DRTM_INVALID_SERVICE_ID_ERROR", + "DRTM_MEMORY_UNALIGNED_ERROR", + "DRTM_MINIMUM_SIZE_ERROR", + "DRTM_GET_TMR_DESCRIPTOR_FAILED", + "DRTM_EXTEND_OSSL_DIGEST_FAILED", + "DRTM_SETUP_NOT_ALLOWED", + "DRTM_GET_IVRS_TABLE_FAILED" +}; + +static const char *slaunch_status_string(u32 status) +{ + if (status > DRTM_GET_IVRS_TABLE_FAILED) + return "UNDEFINED"; + + return slaunch_status_strings[status]; +} + +static bool slaunch_wait_for_psp_ready(u32 *status) +{ + u32 reg_val =3D 0; + int retry =3D 5; + + if (readl(c2pmsg_72) =3D=3D 0xFFFFFFFF) + return false; + + while (--retry) { + reg_val =3D readl(c2pmsg_72); + if (reg_val & DRTM_MBOX_READY_MASK) + break; + + /* TODO: select wait time appropriately */ + mdelay(100); + } + + if (!retry) + return false; + + if (status) + *status =3D reg_val & 0xffff; + + return true; +} + +static bool slaunch_tpm_locality_access(void) +{ + u32 status; + + writel(DRTM_CMD_TPM_LOCALITY_ACCESS << DRTM_MBOX_CMD_SHIFT, c2pmsg_72); + + if (!slaunch_wait_for_psp_ready(&status)) { + pr_err("Failed to execute DRTM_CMD_TPM_LOCALITY_ACCESS\n"); + return false; + } + + if (status !=3D DRTM_NO_ERROR) { + pr_err("DRTM_CMD_TPM_LOCALITY_ACCESS failed - %s", + slaunch_status_string(status)); + return false; + } + + return true; +} + +bool slaunch_psp_tmr_release(void) +{ + u32 status; + + if (!slaunch_psp_early_setup_done) + return false; + + writel(DRTM_CMD_TMR_RELEASE << DRTM_MBOX_CMD_SHIFT, c2pmsg_72); + + if (!slaunch_wait_for_psp_ready(&status)) { + pr_err("Failed to execute DRTM_CMD_TMR_RELEASE_ACCESS\n"); + return false; + } + + if (status !=3D DRTM_NO_ERROR) { + pr_err("DRTM_CMD_TMR_RELEASE failed - %s", + slaunch_status_string(status)); + return false; + } + + return true; +} + +void slaunch_psp_setup(void) +{ + if (slaunch_psp_early_setup_done) + return; + + if (!slaunch_setup_c2pmsg_regs()) + return; + + if (!slaunch_wait_for_psp_ready(NULL)) { + pr_err("PSP not ready to take commands\n"); + return; + } + + slaunch_psp_early_setup_done =3D true; +} + +void slaunch_psp_finalize(void) +{ + if (!slaunch_tpm_locality_access()) { + pr_err("PSP failed to lock TPM DRTM localities\n"); + return; + } + + slaunch_clear_c2pmsg_regs(); +} diff --git a/arch/x86/kernel/slaunch.c b/arch/x86/kernel/slaunch.c index a1c8be7de8d3..0a806df74586 100644 --- a/arch/x86/kernel/slaunch.c +++ b/arch/x86/kernel/slaunch.c @@ -701,13 +701,15 @@ static void slaunch_finalize_txt(int do_sexit) } =20 /* - * Used during kexec and on reboot paths to finalize the SKINIT. + * Used during kexec and on reboot paths to finalize the SKINIT PSP state. */ static void slaunch_finalize_skinit(void) { /* AMD CPUs with PSP-supported DRTM */ if (!slaunch_is_skinit_psp()) return; + + slaunch_psp_finalize(); } =20 void slaunch_finalize(int do_sexit) diff --git a/drivers/iommu/amd/init.c b/drivers/iommu/amd/init.c index dd9e26b7b718..c7c60183a27f 100644 --- a/drivers/iommu/amd/init.c +++ b/drivers/iommu/amd/init.c @@ -21,6 +21,7 @@ #include #include #include +#include #include #include #include @@ -3357,6 +3358,17 @@ int __init amd_iommu_enable(void) if (ret) return ret; =20 +#if IS_ENABLED(CONFIG_SECURE_LAUNCH) + if (slaunch_is_skinit_psp()) { + /* Initialize PSP access to SKINIT DRTM functions */ + slaunch_psp_setup(); + + /* Release the Trusted Memory Region since IOMMU is configured */ + if (!slaunch_psp_tmr_release()) + return -ENODEV; + } +#endif + irq_remapping_enabled =3D 1; return amd_iommu_xt_mode; } --=20 2.49.0