From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: mx.groups.io; dkim=pass header.i=@amdcloud.onmicrosoft.com header.s=selector2-amdcloud-onmicrosoft-com header.b=QCFipxY6; spf=none, err=SPF record not found (domain: amd.com, ip: 40.107.72.81, mailfrom: thomas.lendacky@amd.com) Received: from NAM05-CO1-obe.outbound.protection.outlook.com (NAM05-CO1-obe.outbound.protection.outlook.com [40.107.72.81]) by groups.io with SMTP; Mon, 19 Aug 2019 14:36:25 -0700 ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=gXwtdNUUmCOyor/9CIMXBJnIrrNWAe4qOBXRB1YoCcwepyJD3mdjR43vkWC6li4rupScAlbhAT/Fm1WloSTaxxOOjMFxZYpOoT77gn/Vuxvb4+VaPR8KXGih7WI490/EInY4wnCt99jVq+YhojkjW9IbW2+gbbFymTk+9vir5yIkhlmG7OfAK8CnEHwto+px/M8uiyH45nemVnktDwQkFI07iTtTFl+hbC/ljUVGpUPBHV3XYmJsT6xE0Zn7s0cAj1IIzGEIFSAvdSWU2tIFExoYCIvLqDLtH547fYcZ42ZJMQLYQKUJl/UbkG36APCn6RzZ8dWus+5NoC0H5yXalA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=H9RgIrvs1LXqQUuUfHUSPDifcwIRRHnH8jMzJlFKxok=; b=ZuzI6HwHUUtknCIuN5u29QklW9J1TRAzSoytKy2de8P2y+iiQBD3/dANWnxhfYnPPk1vdlSIJDQmFqqpf1Gj2stkkvJPeN5ISzTmQe/0cSmlZDibleDYLFLptXKErWpSGLOoNBpggcGmUePaemm6JQZfIMJqO2smZuLo9r8wkyPG7ROPH+8X1CDx8m98g1Ofq2yU2FDGf5jnSlIuZq1Y97AU7mI1CoRP4CAeogV41UV881RXTQ50Q6ATFsbiW+TyquP93xjLKNI3uP02o2p8VgxG5ZKZy3lKarGhyhF+jPxz8LGqFLboIU/YSVJQuNUxwllKrZP/iocBqOMpdyXARA== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=amd.com; dmarc=pass action=none header.from=amd.com; dkim=pass header.d=amd.com; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=amdcloud.onmicrosoft.com; s=selector2-amdcloud-onmicrosoft-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=H9RgIrvs1LXqQUuUfHUSPDifcwIRRHnH8jMzJlFKxok=; b=QCFipxY6WB4TQ4SUDJyn/gmgKsrdTzabxWQVMaJMPMqHqf8pJm/ONuLApd740YC8vxJGkkvfVbq6sJKe1FF+S1IT3y35GRgNWCajIp1/s+kEzx254n18TkG5QrHuibEy4OPUqMFvdZ9ruJDn6BiOMBCFQsjGiC7P3c9boljnwEc= Received: from BYAPR12MB3158.namprd12.prod.outlook.com (20.179.92.19) by BYAPR12MB3112.namprd12.prod.outlook.com (20.178.54.205) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.2157.20; Mon, 19 Aug 2019 21:36:24 +0000 Received: from BYAPR12MB3158.namprd12.prod.outlook.com ([fe80::39b9:76bd:a491:1f27]) by BYAPR12MB3158.namprd12.prod.outlook.com ([fe80::39b9:76bd:a491:1f27%6]) with mapi id 15.20.2157.022; Mon, 19 Aug 2019 21:36:24 +0000 From: "Lendacky, Thomas" To: "devel@edk2.groups.io" CC: Jordan Justen , Laszlo Ersek , Ard Biesheuvel , Michael D Kinney , Liming Gao , Eric Dong , Ray Ni , "Singh, Brijesh" Subject: [RFC PATCH 28/28] UefiCpuPkg/MpInitLib: Introduce an MP finalization routine to support SEV-ES Thread-Topic: [RFC PATCH 28/28] UefiCpuPkg/MpInitLib: Introduce an MP finalization routine to support SEV-ES Thread-Index: AQHVVtYm0yi6mrqLkUyI6eU7AImGuQ== Date: Mon, 19 Aug 2019 21:36:23 +0000 Message-ID: References: In-Reply-To: Accept-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: x-mailer: git-send-email 2.17.1 x-clientproxiedby: SN2PR01CA0031.prod.exchangelabs.com (2603:10b6:804:2::41) To BYAPR12MB3158.namprd12.prod.outlook.com (2603:10b6:a03:132::19) authentication-results: spf=none (sender IP is ) smtp.mailfrom=Thomas.Lendacky@amd.com; x-ms-exchange-messagesentrepresentingtype: 1 x-originating-ip: [165.204.77.1] x-ms-publictraffictype: Email x-ms-office365-filtering-correlation-id: 162a4134-dbe6-4792-35ad-08d724ed4866 x-ms-office365-filtering-ht: Tenant x-microsoft-antispam: BCL:0;PCL:0;RULEID:(2390118)(7020095)(4652040)(8989299)(5600148)(711020)(4605104)(1401327)(4618075)(4534185)(4627221)(201703031133081)(201702281549075)(8990200)(2017052603328)(7193020);SRVR:BYAPR12MB3112; x-ms-traffictypediagnostic: BYAPR12MB3112: x-ms-exchange-transport-forked: True x-microsoft-antispam-prvs: x-ms-oob-tlc-oobclassifiers: OLM:2803; x-forefront-prvs: 0134AD334F x-forefront-antispam-report: SFV:NSPM;SFS:(10009020)(6029001)(4636009)(39860400002)(346002)(376002)(366004)(396003)(136003)(189003)(199004)(66556008)(66476007)(5660300002)(52116002)(76176011)(186003)(86362001)(305945005)(30864003)(7736002)(6116002)(66446008)(6916009)(5640700003)(36756003)(6436002)(6486002)(102836004)(6506007)(386003)(26005)(2351001)(476003)(2501003)(2616005)(486006)(11346002)(66066001)(118296001)(25786009)(446003)(54906003)(2906002)(19627235002)(4326008)(6512007)(99286004)(71200400001)(8936002)(50226002)(71190400001)(316002)(14444005)(53946003)(8676002)(478600001)(256004)(53936002)(3846002)(81166006)(1730700003)(81156014)(66946007)(64756008)(14454004);DIR:OUT;SFP:1101;SCL:1;SRVR:BYAPR12MB3112;H:BYAPR12MB3158.namprd12.prod.outlook.com;FPR:;SPF:None;LANG:en;PTR:InfoNoRecords;MX:1;A:1; received-spf: None (protection.outlook.com: amd.com does not designate permitted sender hosts) x-ms-exchange-senderadcheck: 1 x-microsoft-antispam-message-info: t5gRsbVqWjHl2l6f4TVBdwdgEYVG+4SH/aeitkicMFi/NE1mtSmD3U+EdGNtIefRdRB49180Mwi7FTVsCS8C0DHjpqi4NXIVJd10EdjolOBJqpMO+isOSnKeS6FGZcYLy2SsQ0hnxjlFDOG5cEaCDasndotWG1stmEK38nbNMLBDLEDxRKH4xPJrWxR96P4Q74KVFevz6/FAFIBE7hXmWlguC0TovXal8c0ME6KkW+nBRmXZ5NT01PniDsBrDTsnUnrhPZ3VI1gJG2bk0fiLZ0icLn7TmFsj8ARV6g3aghoxwXW6eHm2mpJGkrB25oWI8harYkWe7IQcVcG+9B5QjH932nKvE8jUQC4XXdRfaAmOzRC+OHCrXLPNoQMdHASLXs0WHRZf0bBYJUypWrtWUp/OmvzPJEZBCYa+p8yKHbs= MIME-Version: 1.0 X-OriginatorOrg: amd.com X-MS-Exchange-CrossTenant-Network-Message-Id: 162a4134-dbe6-4792-35ad-08d724ed4866 X-MS-Exchange-CrossTenant-originalarrivaltime: 19 Aug 2019 21:36:23.9180 (UTC) X-MS-Exchange-CrossTenant-fromentityheader: Hosted X-MS-Exchange-CrossTenant-id: 3dd8961f-e488-4e60-8e11-a82d994e183d X-MS-Exchange-CrossTenant-mailboxtype: HOSTED X-MS-Exchange-CrossTenant-userprincipalname: CCX0dtbP2fu4FPm9mMOXTfFQUXPY8RNRUSaQSfFPjdNpoJOB5cEs7j7jd/jvl8WriMscwqzGdaMwObXrnQojcQ== X-MS-Exchange-Transport-CrossTenantHeadersStamped: BYAPR12MB3112 Content-Language: en-US Content-Type: text/plain; charset="us-ascii" Content-ID: <2816290B81C19F439489A5B7931512E3@namprd12.prod.outlook.com> Content-Transfer-Encoding: quoted-printable From: Tom Lendacky Introduce a finalization routine to the MP library. This routine is used at the end of UEFI before transferring control to the OS and allows for SEV-ES related AP state and information to be communicated to the OS. The APs will be parked using VMGEXIT AP Reset Hold and the GHCB will be modified to communicate a reserved page of memory that will be used by the OS to direct the "initial" AP boot in the OS. Signed-off-by: Tom Lendacky --- MdePkg/Include/Protocol/Cpu.h | 6 + UefiCpuPkg/CpuDxe/CpuDxe.h | 14 ++ UefiCpuPkg/Include/Library/MpInitLib.h | 17 +++ UefiCpuPkg/Library/MpInitLib/MpLib.h | 18 ++- MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c | 5 + OvmfPkg/PlatformPei/AmdSev.c | 2 +- UefiCpuPkg/CpuDxe/CpuDxe.c | 10 ++ UefiCpuPkg/Library/MpInitLib/DxeMpLib.c | 57 +++++++- UefiCpuPkg/Library/MpInitLib/MpLib.c | 25 ++++ UefiCpuPkg/Library/MpInitLib/X64/MpFuncs.nasm | 130 ++++++++++++++++-- 10 files changed, 265 insertions(+), 19 deletions(-) diff --git a/MdePkg/Include/Protocol/Cpu.h b/MdePkg/Include/Protocol/Cpu.h index e392f4cd9a13..79a701bc0d93 100644 --- a/MdePkg/Include/Protocol/Cpu.h +++ b/MdePkg/Include/Protocol/Cpu.h @@ -257,6 +257,11 @@ EFI_STATUS IN UINT64 Attributes ); =20 +typedef +EFI_STATUS +(EFIAPI *EFI_CPU_FINALIZE)( + IN EFI_CPU_ARCH_PROTOCOL *This + ); =20 /// /// The EFI_CPU_ARCH_PROTOCOL is used to abstract processor-specific funct= ions from the DXE @@ -273,6 +278,7 @@ struct _EFI_CPU_ARCH_PROTOCOL { EFI_CPU_REGISTER_INTERRUPT_HANDLER RegisterInterruptHandler; EFI_CPU_GET_TIMER_VALUE GetTimerValue; EFI_CPU_SET_MEMORY_ATTRIBUTES SetMemoryAttributes; + EFI_CPU_FINALIZE Finalize; /// /// The number of timers that are available in a processor. The value in= this /// field is a constant that must not be modified after the CPU Architec= tural diff --git a/UefiCpuPkg/CpuDxe/CpuDxe.h b/UefiCpuPkg/CpuDxe/CpuDxe.h index b029be430b4c..c5b9ada72ac9 100644 --- a/UefiCpuPkg/CpuDxe/CpuDxe.h +++ b/UefiCpuPkg/CpuDxe/CpuDxe.h @@ -232,6 +232,20 @@ CpuSetMemoryAttributes ( IN UINT64 Attributes ); =20 +/** + Set ... + + @param This Protocol instance structure + + @retval EFI_SUCCESS If ... + +**/ +EFI_STATUS +EFIAPI +CpuFinalize ( + IN EFI_CPU_ARCH_PROTOCOL *This + ); + /** Initialize Global Descriptor Table. =20 diff --git a/UefiCpuPkg/Include/Library/MpInitLib.h b/UefiCpuPkg/Include/Li= brary/MpInitLib.h index fa8252937313..2095fb758664 100644 --- a/UefiCpuPkg/Include/Library/MpInitLib.h +++ b/UefiCpuPkg/Include/Library/MpInitLib.h @@ -344,4 +344,21 @@ MpInitLibWhoAmI ( OUT UINTN *ProcessorNumber ); =20 +/** + MP Exit ... + + This service ... + + This service must be invoked before ... + + @retval EFI_SUCCESS MP initialization succeeds. + @retval Others MP initialization fails. + +**/ +EFI_STATUS +EFIAPI +MpLibFinalize ( + VOID + ); + #endif diff --git a/UefiCpuPkg/Library/MpInitLib/MpLib.h b/UefiCpuPkg/Library/MpIn= itLib/MpLib.h index f2ba1a508715..a2ba6de0278f 100644 --- a/UefiCpuPkg/Library/MpInitLib/MpLib.h +++ b/UefiCpuPkg/Library/MpInitLib/MpLib.h @@ -273,7 +273,8 @@ struct _CPU_MP_DATA { UINT64 GhcbBase; }; =20 -#define AP_RESET_STACK_SIZE 64 +#define AP_SAFE_STACK_SIZE 128 +#define AP_RESET_STACK_SIZE AP_SAFE_STACK_SIZE =20 typedef union { struct { @@ -327,8 +328,11 @@ VOID IN BOOLEAN MwaitSupport, IN UINTN ApTargetCState, IN UINTN PmCodeSegment, + IN UINTN Pm16CodeSegment, IN UINTN TopOfApStack, - IN UINTN NumberToFinish + IN UINTN NumberToFinish, + IN UINTN SevEsAPJumpTable, + IN UINTN WakeupBuffer ); =20 /** @@ -645,5 +649,15 @@ EnableDebugAgent ( VOID ); =20 +/** + MP finalize ... + + @param[in] CpuMpData The pointer to CPU MP Data structure will be saved= . +**/ +EFI_STATUS +MpFinalize ( + IN CPU_MP_DATA *CpuMpData + ); + #endif =20 diff --git a/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c b/MdeModulePkg/Core/Dx= e/DxeMain/DxeMain.c index 514d1aa75ada..13c962247243 100644 --- a/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c +++ b/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c @@ -785,6 +785,11 @@ CoreExitBootServices ( // gCpu->DisableInterrupt (gCpu); =20 + // + // Finalize CPU + // + gCpu->Finalize (gCpu); + // // Clear the non-runtime values of the EFI System Table // diff --git a/OvmfPkg/PlatformPei/AmdSev.c b/OvmfPkg/PlatformPei/AmdSev.c index fc396a6f229d..f0a18f026460 100644 --- a/OvmfPkg/PlatformPei/AmdSev.c +++ b/OvmfPkg/PlatformPei/AmdSev.c @@ -65,7 +65,7 @@ AmdSevEsInitialize ( BuildMemoryAllocationHob ( GhcbBasePa, EFI_PAGES_TO_SIZE (GhcbPageCount), - EfiBootServicesData + EfiReservedMemoryType ); =20 SetMem (GhcbBase, GhcbPageCount * SIZE_4KB, 0); diff --git a/UefiCpuPkg/CpuDxe/CpuDxe.c b/UefiCpuPkg/CpuDxe/CpuDxe.c index 7d7270e10b4a..7003f74e7d87 100644 --- a/UefiCpuPkg/CpuDxe/CpuDxe.c +++ b/UefiCpuPkg/CpuDxe/CpuDxe.c @@ -92,6 +92,7 @@ EFI_CPU_ARCH_PROTOCOL gCpu =3D { CpuRegisterInterruptHandler, CpuGetTimerValue, CpuSetMemoryAttributes, + CpuFinalize, 1, // NumberOfTimers 4 // DmaBufferAlignment }; @@ -499,6 +500,15 @@ CpuSetMemoryAttributes ( return AssignMemoryPageAttributes (NULL, BaseAddress, Length, MemoryAttr= ibutes, NULL); } =20 +EFI_STATUS +EFIAPI +CpuFinalize ( + IN EFI_CPU_ARCH_PROTOCOL *This + ) +{ + return MpLibFinalize (); +} + /** Initializes the valid bits mask and valid address mask for MTRRs. =20 diff --git a/UefiCpuPkg/Library/MpInitLib/DxeMpLib.c b/UefiCpuPkg/Library/M= pInitLib/DxeMpLib.c index 127f64eb87e1..6e1bdbeed259 100644 --- a/UefiCpuPkg/Library/MpInitLib/DxeMpLib.c +++ b/UefiCpuPkg/Library/MpInitLib/DxeMpLib.c @@ -18,7 +18,6 @@ #include =20 #define AP_CHECK_INTERVAL (EFI_TIMER_PERIOD_MILLISECONDS (100)) -#define AP_SAFE_STACK_SIZE 128 =20 CPU_MP_DATA *mCpuMpData =3D NULL; EFI_EVENT mCheckAllApsEvent =3D NULL; @@ -98,7 +97,7 @@ GetWakeupBuffer ( StartAddress =3D 0x88000; Status =3D gBS->AllocatePages ( AllocateMaxAddress, - EfiBootServicesData, + EfiReservedMemoryType, EFI_SIZE_TO_PAGES (WakeupBufferSize), &StartAddress ); @@ -328,17 +327,26 @@ RelocateApLoop ( BOOLEAN MwaitSupport; ASM_RELOCATE_AP_LOOP AsmRelocateApLoopFunc; UINTN ProcessorNumber; + UINTN StackStart; =20 MpInitLibWhoAmI (&ProcessorNumber); CpuMpData =3D GetCpuMpData (); MwaitSupport =3D IsMwaitSupport (); + if (CpuMpData->SevEsActive) { + StackStart =3D CpuMpData->SevEsAPResetStackStart; + } else { + StackStart =3D mReservedTopOfApStack; + } AsmRelocateApLoopFunc =3D (ASM_RELOCATE_AP_LOOP) (UINTN) mReservedApLoop= Func; AsmRelocateApLoopFunc ( MwaitSupport, CpuMpData->ApTargetCState, CpuMpData->PmCodeSegment, - mReservedTopOfApStack - ProcessorNumber * AP_SAFE_STACK_SIZE, - (UINTN) &mNumberToFinish + CpuMpData->Pm16CodeSegment, + StackStart - ProcessorNumber * AP_SAFE_STACK_SIZE, + (UINTN) &mNumberToFinish, + CpuMpData->SevEsAPBuffer, + CpuMpData->WakeupBuffer ); // // It should never reach here @@ -880,3 +888,44 @@ MpInitLibEnableDisableAP ( =20 return Status; } + +/** + MP finalize ... + + @param[in] CpuMpData The pointer to CPU MP Data structure will be saved= . +**/ +EFI_STATUS +MpFinalize ( + IN CPU_MP_DATA *CpuMpData + ) +{ + if (CpuMpData->SevEsActive) { + // + // Perform SEV-ES specific finalization + // + if (CpuMpData->WakeupBuffer =3D=3D (UINTN) -1) { + // + // No APs parked in UEFI, clear the GHCB + // + AsmWriteMsr64 (MSR_SEV_ES_GHCB, 0); + } else { + // + // Re-use reserved memory area below 1MB from WakeupBuffer + // + CopyMem ( + (VOID *) CpuMpData->WakeupBuffer, + (VOID *) CpuMpData->AddressMap.RendezvousFunnelAddress + + CpuMpData->AddressMap.SwitchToRealPM16ModeOffset, + CpuMpData->AddressMap.SwitchToRealPM16ModeSize + ); + + // + // Point the GHCB at the AP jump table to communicate the address to + // the booting system. + // + AsmWriteMsr64 (MSR_SEV_ES_GHCB, (CpuMpData->SevEsAPBuffer) | 0x03); + } + } + + return EFI_SUCCESS; +} diff --git a/UefiCpuPkg/Library/MpInitLib/MpLib.c b/UefiCpuPkg/Library/MpIn= itLib/MpLib.c index 0939019d7b8c..bc800a69527e 100644 --- a/UefiCpuPkg/Library/MpInitLib/MpLib.c +++ b/UefiCpuPkg/Library/MpInitLib/MpLib.c @@ -1707,6 +1707,31 @@ CheckAllAPs ( return EFI_NOT_READY; } =20 +/** + MP Exit ... + + This service ... + + This service must be invoked before ... + + @retval EFI_SUCCESS MP initialization succeeds. + @retval Others MP initialization fails. + +**/ +EFI_STATUS +EFIAPI +MpLibFinalize ( + VOID + ) +{ + CPU_MP_DATA *CpuMpData; + + CpuMpData =3D GetCpuMpData (); + MpFinalize (CpuMpData); + + return EFI_SUCCESS; +} + /** MP Initialize Library initialization. =20 diff --git a/UefiCpuPkg/Library/MpInitLib/X64/MpFuncs.nasm b/UefiCpuPkg/Lib= rary/MpInitLib/X64/MpFuncs.nasm index 286fa297791c..8936963913c4 100644 --- a/UefiCpuPkg/Library/MpInitLib/X64/MpFuncs.nasm +++ b/UefiCpuPkg/Library/MpInitLib/X64/MpFuncs.nasm @@ -446,7 +446,7 @@ CompatMode: =20 BITS 16 ; - ; At entry to this label + ; At entry to this label (used also by AsmRelocateApLoop): ; - RDX will have its reset value ; - On the top of the stack ; - Alignment data (two bytes) to be discarded @@ -475,32 +475,93 @@ PM16Mode: SwitchToRealProcEnd: =20 ;-------------------------------------------------------------------------= ------------ -; AsmRelocateApLoop (MwaitSupport, ApTargetCState, PmCodeSegment, TopOfAp= Stack, CountTofinish); +; AsmRelocateApLoop (MwaitSupport, ApTargetCState, PmCodeSegment, Pm16Cod= eSegment, TopOfApStack, CountTofinish, SevEsAPJumpTable, WakeupBuffer); ;-------------------------------------------------------------------------= ------------ global ASM_PFX(AsmRelocateApLoop) ASM_PFX(AsmRelocateApLoop): AsmRelocateApLoopStart: BITS 64 + cmp qword [rsp + 56], 0 + je NoSevEs + + ; + ; Perform some SEV-ES related setup before leaving 64-bit mode + ; + push rcx + push rdx + + ; + ; Get the RDX reset value using CPUID + ; + mov rax, 1 + cpuid + mov rsi, rax ; Save off the reset value for RDX + + ; + ; Prepare the GHCB for the AP_HLT_LOOP VMGEXIT call + ; - No NAE events can be generated once this is set otherwise + ; the AP_HLT_LOOP SW_EXITCODE will be overwritten. + ; + mov rcx, 0xc0010130 + rdmsr ; Retrieve current GHCB address + shl rdx, 32 + or rdx, rax + + mov rdi, rdx + xor rax, rax + mov rcx, 0x800 + shr rcx, 3 + rep stosq ; Clear the GHCB + + mov rax, 0x80000004 ; VMGEXIT AP_HLT_LOOP + mov [rdx + 0x390], rax + + pop rdx + pop rcx + +NoSevEs: cli ; Disable interrupt before switching to 3= 2-bit mode - mov rax, [rsp + 40] ; CountTofinish + mov rax, [rsp + 48] ; CountTofinish lock dec dword [rax] ; (*CountTofinish)-- - mov rsp, r9 - push rcx - push rdx =20 - lea rsi, [PmEntry] ; rsi <- The start address of transition = code + mov rax, [rsp + 56] ; SevEsAPJumpTable + mov rbx, [rsp + 64] ; WakeupBuffer + mov rsp, [rsp + 40] ; TopOfApStack + + push rax ; Save SevEsAPJumpTable + push rbx ; Save WakeupBuffer + push r9 ; Save Pm16CodeSegment + push rcx ; Save MwaitSupport + push rdx ; Save ApTargetCState + + lea rax, [PmEntry] ; rax <- The start address of transition = code =20 push r8 - push rsi - DB 0x48 - retf + push rax + + ; + ; Clear R8 - R15, for reset, before going into 32-bit mode + ; + xor r8, r8 + xor r9, r9 + xor r10, r10 + xor r11, r11 + xor r12, r12 + xor r13, r13 + xor r14, r14 + xor r15, r15 + + ; + ; Far return into 32-bit mode + ; +o64 retf + BITS 32 PmEntry: mov eax, cr0 btr eax, 31 ; Clear CR0.PG mov cr0, eax ; Disable paging and caches =20 - mov ebx, edx ; Save EntryPoint to rbx, for rdmsr will = overwrite rdx mov ecx, 0xc0000080 rdmsr and ah, ~ 1 ; Clear LME @@ -513,6 +574,8 @@ PmEntry: add esp, 4 pop ecx, add esp, 4 + +MwaitCheck: cmp cl, 1 ; Check mwait-monitor support jnz HltLoop mov ebx, edx ; Save C-State to ebx @@ -526,10 +589,53 @@ MwaitLoop: shl eax, 4 mwait jmp MwaitLoop + HltLoop: + pop edx ; PM16CodeSegment + add esp, 4 + pop ebx ; WakeupBuffer + add esp, 4 + pop eax ; SevEsAPJumpTable + add esp, 4 + cmp eax, 0 ; Check for SEV-ES + je DoHlt + + cli + ; + ; SEV-ES is active, use VMGEXIT (GHCB information already + ; set by caller) + ; + ; VMGEXIT is rep vmmcall + ; + db 0xf3 + db 0x0f + db 0x01 + db 0xd9 + + ; + ; Back from VMGEXIT AP_HLT_LOOP + ; Push the FLAGS/CS/IP values to use + ; + push word 0x0002 ; EFLAGS + xor ecx, ecx + mov cx, [eax + 2] ; CS + push cx + mov cx, [eax] ; IP + push cx + push word 0x0000 ; For alignment, will be discarded + + push edx + push ebx + + mov edx, esi ; Restore RDX reset value + + retf + +DoHlt: cli hlt - jmp HltLoop + jmp DoHlt + BITS 64 AsmRelocateApLoopEnd: =20 --=20 2.17.1