From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from DM1PR04CU001.outbound.protection.outlook.com (mail-centralusazon11010030.outbound.protection.outlook.com [52.101.61.30]) (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 820394519AB for ; Fri, 31 Jul 2026 17:39:46 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.61.30 ARC-Seal:i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1785519590; cv=fail; b=APGNkvdeqxJxY32fN8V9iZpJckNybcKQF5xP68eivd71OH+oPo5/rasIbJtrNTs+5EwsL5t5LYfrha5Hns7zQlwR4j795tuwVx4pTZFeTXQOpkU9lYBrvAyNUoC+mBVmhQkxyFHjzHLR2RSJaBrl9aAFU47+dUFwp2N0SfDVGZQ= ARC-Message-Signature:i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1785519590; c=relaxed/simple; bh=D81aPoF+FThW9RiwfaZXafbENmrRSanlcNOONO0+RXE=; h=Message-ID:Date:Subject:To:Cc:References:From:In-Reply-To: Content-Type:MIME-Version; b=n2RcPKbE1CwS6av+/Kvx9XKr5ndxbQ0e1SNvAgaovreBl040KtAq7XMw1oT6Ozcmg4jsAI8jDOsN/0bCIoHphynwPYgICtQhEnZG9hpR01lXc9ueO1NQ0o7TozCaRArwGXmjFzxl1vfXCjwvJg8CMLHcU+JaZho7R46Obt6LFnA= ARC-Authentication-Results:i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=amd.com; spf=fail smtp.mailfrom=amd.com; dkim=pass (1024-bit key) header.d=amd.com header.i=@amd.com header.b=BQefXPsH; arc=fail smtp.client-ip=52.101.61.30 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=amd.com Authentication-Results: smtp.subspace.kernel.org; spf=fail smtp.mailfrom=amd.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=amd.com header.i=@amd.com header.b="BQefXPsH" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=secbLpnszzHQ61Z+7NLO/bqpMRk2yN2sxApV8kKsZkDZPMGz27eewjDRs8Pn4GHxOjUWRUGgnN7phz2faAynYhIKB39uXfj9gMMvxHGexlTW5NvOU8fx0oxpwa+EKZetAMgf+g4qlCMsOojMeQZV170mgfwjqnGtKbiqb3AvRjxPivGq2/pSNaYVMZgsU78edo36AmEeAS81qQux4/1Mkn9id9M0ca0w6DGiEEh3jo2+uCXH7Qi8Q9eL9Cx26ruCV8tdTE+CBSevtG9LuWR45JbZ7+sXIW8F5BG8AISgi7YR2xE6Q+puZlXirN7xfweaRtzMoqMf6GLxePsPKEBYgQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector10001; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=TeXdpaE4wIY7v3/WSwFxnSp56JPC5sMW8a6ijQ5PDm8=; b=uDXK3KAwPEgeJFm9FTdPN0B4lphDhX7FA/fmbNg5+vWG3YD/xGQM8g/FunGWz7jD+eXsbPxWM/HnQ544KTY6ncJ5FCnP7kjGX1eNEdPTlWGsuQu4nxvCuBjKFGzobZgz6lwWKVoEJ5QB9uINz+7lzyQGn8ZN6O2fcxaTfAj1YVho2uwZZuT+UnXb9ijxTj7xre5SUMfGCTlA8Ft4QBapEQsgVT7MRnNYAozQ6PRo4Av/0l7PXEtbg0V/sV94GaPtQgntfrXWFw9gJl1VXlXFYpWT1+eo2xKXvf2yEmz6NeQc8Q7a2ygrawbm3+tUgG/54V4z7R1xZ3h1LlPaQzqRYQ== 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=amd.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=TeXdpaE4wIY7v3/WSwFxnSp56JPC5sMW8a6ijQ5PDm8=; b=BQefXPsH2zoBKvGESbBVjnEqzpXJhNUUdoMXddYW3tYUorQB9mP7/ta/5WpfZjXGVwF0HFSJgjtbPZWXoL8fBtXQfnELPN+TBNvF/TsRpFmigXGTZQd8LHw1eIiajE/kCpsEWCfyMtdloW1Eo5BADZaYleaRrLfn6OibsWClNV0= Authentication-Results: dkim=none (message not signed) header.d=none;dmarc=none action=none header.from=amd.com; Received: from SN7PR12MB8131.namprd12.prod.outlook.com (2603:10b6:806:32d::12) by SA3PR12MB8437.namprd12.prod.outlook.com (2603:10b6:806:2f5::10) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.245.13; Fri, 31 Jul 2026 17:39:41 +0000 Received: from SN7PR12MB8131.namprd12.prod.outlook.com ([fe80::c2dd:62c5:67fe:aa46]) by SN7PR12MB8131.namprd12.prod.outlook.com ([fe80::c2dd:62c5:67fe:aa46%4]) with mapi id 15.21.0270.012; Fri, 31 Jul 2026 17:39:40 +0000 Message-ID: <0514ffca-89a3-42e9-bc30-50c317aa7bd9@amd.com> Date: Fri, 31 Jul 2026 12:39:37 -0500 User-Agent: Mozilla Thunderbird Subject: Re: [PATCH 2/7] x86/apic: Add an SVSM APIC driver To: Melody Wang , x86@kernel.org Cc: LKML References: <7c4f962cb0c993f0cb136a9abcbd4f3e4759282c.1785375271.git.huibo.wang@amd.com> Content-Language: en-US From: Tom Lendacky Autocrypt: addr=thomas.lendacky@amd.com; keydata= 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 WiyqywZI5g== In-Reply-To: <7c4f962cb0c993f0cb136a9abcbd4f3e4759282c.1785375271.git.huibo.wang@amd.com> Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-ClientProxiedBy: YT4P288CA0008.CANP288.PROD.OUTLOOK.COM (2603:10b6:b01:d4::13) To SN7PR12MB8131.namprd12.prod.outlook.com (2603:10b6:806:32d::12) Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: SN7PR12MB8131:EE_|SA3PR12MB8437:EE_ X-MS-Office365-Filtering-Correlation-Id: 09248295-35e7-4560-b22b-08deef2ab2f5 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|23010399003|376014|1800799024|366016|5023799004|11063799006|4143699003|10067099003|56012099006|6133799003|22082099003|18002099003|3023799007; X-Microsoft-Antispam-Message-Info: Kh5F8418lfsGj/WnAG32NetN/5cMCorgBpPU4cpv6KQMmdtmH8rv1ZkuWzmv2SrxmJarJeACrJCdj90VkC5flvztcipYwGaMh5IyrVIq8G+AjKq0+v7raVUVF2smj6I45fYFCLEzVJst7fLe3J8+FETQ+HdhtnrrrvR7OMfPTMGV9uvE+NPRXoX1V6YZcjiHrN7fLdLlptfJeHRbX51FFpgS8FK9LRHqTvU6VdBZ8I+dDPnWGLa/sEvAxYZa/LYM0L97SK2TG80k/nZ0Rl+vwrgcZuR8JNEQjo3jGOWFurUNgeeBkSdIdtQpopAjzScolXj9gwp1FK0i7P4Oe+48+BAfmCiM1GSVij9zJJoVWwXLyW/2SBg6rWNJlYIEZ2KPzlvCMxBHq58fIG6Ifh7y1FkT7sAPG/s1/36ysMjzLtJwTsO5Tu0d71DPLFZAydupYwjyguYfOxKaYEbDhaFTYEUf7xw3AkUueMxA3VeJyaRMmDj/eamIUpnow8OMA9lppf7R3Q1ym6bWfB3SZlAo9thlCvBJKudKb2MvioiOEDwQH5SBWQKumOubjrj1L5tbg2rctBOV8wKeX4+y8DBJXgCp4kAlwPP2gZAwZ5g7BwYGwwAeW8NiaaXPQom2ZHjptprWl67BZBARynvm/fZJrQMhwKMucbkNHAlS8MZuiKQ= X-Forefront-Antispam-Report: CIP:255.255.255.255;CTRY:;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:SN7PR12MB8131.namprd12.prod.outlook.com;PTR:;CAT:NONE;SFS:(13230040)(23010399003)(376014)(1800799024)(366016)(5023799004)(11063799006)(4143699003)(10067099003)(56012099006)(6133799003)(22082099003)(18002099003)(3023799007);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: =?utf-8?B?M3lYMURnVnZGSDdBZjdUSlZHaFZhSjlMYXdUWm52c0lrcTR4WHNTZjJvZnFZ?= =?utf-8?B?SnYvSUhEc3pZM2tTaUU0UFBUK09GdHQ4eENLT0pzNjVJcHE3WWJvRzNDblpG?= =?utf-8?B?cmcvTjFJRFRuVnlKVDhHOTI3NnEzbGh6KzBjdm9nelFJN0liVXRDaml6ZFgv?= =?utf-8?B?dCtVNkZxRStnNnZGQ2NRYWExSjFUSjZ1NmxqVUoxVG42Qm1vYVVvdkVTUWtN?= =?utf-8?B?NUNtV0JZL0htdW9QbmNpSXpsbTRCd1lCNVh5aVNzVlhDQ0tURWpSNVBzZWVn?= =?utf-8?B?VENRNWd5Vlcvb250S1lRVERYNEtVVS8rcmRJTWdMeHJjbk5reWVzL1N0WElj?= =?utf-8?B?N1h3YzZ0amovRUU3emk2R0RJOEN4TjlZVjA5Q3FHbUtSancvMkxleDU3NnNt?= =?utf-8?B?OHNSNGVJS3VMb2U4TUNrcTNpaWtoNEc4aUJoN0x4WHUzU05pQTNMRldJLzR1?= =?utf-8?B?TmtqMmdONWdYY2dhWlpKK2huMUpSVDVMY0QzenR4cm5lNUZYUW43NWV1eHBE?= =?utf-8?B?TUNzNkJSbE9IMGJ1cFI3VXNWVDd6ZUl6OWRuU3FONHBBdFJveWpUVWR5RWRF?= =?utf-8?B?QTU0a1JoRVBTMG1PY2N4T3VJTkRKcHRodUk0ei9Kc3dnOTRXRGtWWW1CNGN5?= =?utf-8?B?WmMvYWhNbU9EN3hRZVNXZ1dQUmR6a2pBL1NMMjVnZ2tIdElvZElHRlJpWVhk?= =?utf-8?B?Y0NMY2NPRmNJVTVNS2RESUwyUUNuTXRVVTdxTlNDZ1p0eHlmRXlIUXkrTk5G?= =?utf-8?B?aDhISE5jbUFJdi84Y21XM29lcTNzdCtGNHkwOVNIcFpxQ1dJbkJQd0pLdGJh?= =?utf-8?B?REFHN0ZWTDMybjJUay9Ud1JXcEo5TmwyVVo3dDM0ajlXNXhNenQwMGhuZnpU?= =?utf-8?B?K0pKSUxjYk43d3Rxa0tocEhpWk5RWG1RQzFFeHFSTEpXZnd6K1k4bU9Nemds?= =?utf-8?B?S2FYTE9nYnlyMG1wckxmbkhYK3FucU1CU2o5cUFHMkxHaTVhc0Iyc1lvNDh0?= =?utf-8?B?UEtQREhLQmNYMUxIN2o4QXpSOGF6SXVvY1NySGhLQVRqNGRVSVoxY3NFMTZw?= =?utf-8?B?bjVTMXZFYkNiazh6akxTUlhqUjRuUUNSekNyNTE1Z2VCUk5tMi9GYkhVV1ov?= =?utf-8?B?ZkRlRlk3VEFEQWVMUHdQaHd4SFNyWHVXREZOY1FDaC9ueWIwY0hudjdSRis3?= =?utf-8?B?RTBaYWpLOVNsMzRTaFNPbVRoS3BiV3F6aFFQU3JpS2d5ZWZNRXZkWnFQcHRJ?= =?utf-8?B?OHNKdnFJVnBqK3ZNVWxETkZHN0s3VStnQ3h4Y1djd2VKeUpJbjdXYWNLNThG?= =?utf-8?B?Y2dVMDI3dS96d0ZFT3VMMVkrNDNEUWZqbjJZNXJsZzJXVVRBTVQxRzFTWCt6?= =?utf-8?B?d3YwTWRERkNDM2ZKSmpBRGdTV2dia21uR2s3SWFtYTR4WXMrclRROWRlS2xZ?= =?utf-8?B?ODc3Vnpxek1xSUxkclNsdk1tb2xkSFR1RGczZjAreEVxdWdCVVN1d05aeEFy?= =?utf-8?B?TWRXbjBOZFVleUJjN1ZUbmdFcjFWMGdZUEp0MnNjKzJCUFByc0RGQmkyS3ZO?= =?utf-8?B?ZlFObHoyWXJXL2kyNzV5Q09VV2VhWjZOeEtIWlE0aGFJRlR6VjNIbC9QbkRy?= =?utf-8?B?NUF2Rlo1VlFzTGlDYVpyTi9objJDRWs0TUpCemdKNUM0WW14NVkyTzB4SjNQ?= =?utf-8?B?TWFlS2xtak04K0dTellMejRDVzZpOS8rTVlNZmo0MTF2MDZ6amx6TXNCREk4?= =?utf-8?B?ZW4zNUtZeG95WDFhSUwyeC92dXNVWHBBNnNvRkZlbTdveCswWUdBZGF6UzRs?= =?utf-8?B?UDIrbXNTNTdhdWVUNmhwSVBZVkZIREF2eDZ6T3lZTU54Tmx0RUgwY1Q0cnJW?= =?utf-8?B?bndFaEJ5NWU1RUt0K2V1WVlWbktQcUt2VWQrWEM1SlMrMXgwa081K3p6Kzdl?= =?utf-8?B?M3B6cDQ5S0NNWm83T2JZZVV5YTNHaU9VeFFxOEU3bjhhZk8rdEgwcWpJQkdk?= =?utf-8?B?dVJLOEdCNklEU1FSY2FtYndpK1g1T01DcHQzR2VuMnNGcmJoOWlBVFFVaVBu?= =?utf-8?B?NlRqN1BEVTRiMUF2NHNIUk8zSHUxWDd3VFNEOEJMajMrdENCa3JVUFNUd1Zr?= =?utf-8?B?U2xESFFFVWducGRPZm5Sci9BZmt5R3BESGdUdlFZM0xEb1ZPQzVZR3RNK3pQ?= =?utf-8?B?TzRMOVBiblEyL1JGMk9DSG1vaUJTSk9IMEEvZm1memIzelVzSXhPWWhSeCt4?= =?utf-8?B?cnBsSGFuQW43dXFNVTkyUnZvNDNmUzh2dDhEZEdXTEo0elNkTGdwQ0t2MU9U?= =?utf-8?Q?uY7roYwDYwIHLKncvE?= X-OriginatorOrg: amd.com X-MS-Exchange-CrossTenant-Network-Message-Id: 09248295-35e7-4560-b22b-08deef2ab2f5 X-MS-Exchange-CrossTenant-AuthSource: SN7PR12MB8131.namprd12.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-OriginalArrivalTime: 31 Jul 2026 17:39:40.4294 (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: BMkzWhjWC5MRC3Xv790ddBXxLlRdqgEYY/n/tFJhx6FLudQFAUl8pKgIRoE3CbEJgaC2GlS9RqY8Hp7XVcZoZA== X-MS-Exchange-Transport-CrossTenantHeadersStamped: SA3PR12MB8437 On 7/29/26 20:48, Melody Wang wrote: > The SVSM specification mandates the use of a SVSM APIC protocol instead > of any other APICs when an Alternate Injection guest talks to the SVSM. I would reword this to be more informative and describe why the SVSM APIC protocol is needed (similar to what the APM states). Something like... Alternate Injection replaces hypervisor-based interrupt queuing and event injection, requiring guest-controlled queuing and injection. In order to perform this guest-controlled queuing and injection, an SVSM is used to update the guest VMSA to perform the required actions. The guest uses the SVSM APIC protocol to communicate with the SVSM to perform selected APIC related operations instead of using standard APIC MSR access. Reword as needed to better explain it. > > Add such a SVSM APIC driver (which implements a subset of an X2APIC), > for the APIC emulation supported by the SVSM. > > Signed-off-by: Melody Wang > --- > arch/x86/coco/sev/svsm.c | 6 + > arch/x86/include/asm/sev.h | 9 ++ > arch/x86/kernel/apic/Makefile | 1 + > arch/x86/kernel/apic/svsm_apic.c | 252 +++++++++++++++++++++++++++++++ > 4 files changed, 268 insertions(+) > create mode 100644 arch/x86/kernel/apic/svsm_apic.c > > diff --git a/arch/x86/coco/sev/svsm.c b/arch/x86/coco/sev/svsm.c > index 916d62cd17dc..e2d3bc3c26eb 100644 > --- a/arch/x86/coco/sev/svsm.c > +++ b/arch/x86/coco/sev/svsm.c > @@ -354,3 +354,9 @@ bool snp_svsm_vtpm_probe(void) > /* Check platform commands contains TPM_SEND_COMMAND - platform command 8 */ > return call.rcx_out & BIT_ULL(8); > } > + > +int svsm_do_call(struct svsm_call *call) > +{ > + call->caa = svsm_get_caa(); > + return svsm_perform_call_protocol(call); > +} This helper is unneeded, all it does is set the calling area and then issue svsm_perform_call_protocol(). You're already setting other call values where you use this helper, so just add setting the calling area to those and directly issue svsm_perform_call_protocol(). > diff --git a/arch/x86/include/asm/sev.h b/arch/x86/include/asm/sev.h > index 594cfa19cbd4..f958f78e1db8 100644 > --- a/arch/x86/include/asm/sev.h > +++ b/arch/x86/include/asm/sev.h > @@ -435,6 +435,13 @@ struct svsm_call { > #define SVSM_VTPM_QUERY 0 > #define SVSM_VTPM_CMD 1 > > +#define SVSM_APIC_CALL(x) ((3ULL << 32) | (x)) > +#define SVSM_APIC_QUERY_FEATURES 0 > +#define SVSM_APIC_CONFIG_EMULATION 1 > +#define SVSM_APIC_READ_REGISTER 2 > +#define SVSM_APIC_WRITE_REGISTER 3 > +#define SVSM_APIC_CONFIG_VECTOR 4 > + > #ifdef CONFIG_AMD_MEM_ENCRYPT > > extern u8 snp_vmpl; > @@ -519,6 +526,7 @@ u64 sev_get_status(void); > void sev_show_status(void); > int prepare_pte_enc(struct pte_enc_desc *d); > void set_pte_enc_mask(pte_t *kpte, unsigned long pfn, pgprot_t new_prot); > +int svsm_do_call(struct svsm_call *call); > void snp_kexec_finish(void); > void snp_kexec_begin(void); > > @@ -611,6 +619,7 @@ static inline int rmpadjust(unsigned long vaddr, bool rmp_psize, unsigned long a > static inline void setup_ghcb(void) { } > static inline void __init > early_snp_set_memory_private(unsigned long vaddr, unsigned long paddr, unsigned long npages) { } > +static inline int svsm_do_call(struct svsm_call *call) { return 0; } > static inline void __init > early_snp_set_memory_shared(unsigned long vaddr, unsigned long paddr, unsigned long npages) { } > static inline void snp_set_memory_shared(unsigned long vaddr, unsigned long npages) { } > diff --git a/arch/x86/kernel/apic/Makefile b/arch/x86/kernel/apic/Makefile > index 581db89477f9..d23b1c4c0e14 100644 > --- a/arch/x86/kernel/apic/Makefile > +++ b/arch/x86/kernel/apic/Makefile > @@ -17,6 +17,7 @@ obj-$(CONFIG_SMP) += ipi.o > ifeq ($(CONFIG_X86_64),y) > # APIC probe will depend on the listing order here > obj-$(CONFIG_X86_NUMACHIP) += apic_numachip.o > +obj-$(CONFIG_AMD_ALTERNATE_INJ) += svsm_apic.o > obj-$(CONFIG_X86_UV) += x2apic_uv_x.o > obj-$(CONFIG_AMD_SECURE_AVIC) += x2apic_savic.o > obj-$(CONFIG_X86_X2APIC) += x2apic_phys.o > diff --git a/arch/x86/kernel/apic/svsm_apic.c b/arch/x86/kernel/apic/svsm_apic.c > new file mode 100644 > index 000000000000..7040a1ca8b55 > --- /dev/null > +++ b/arch/x86/kernel/apic/svsm_apic.c Should this be name x2apic-svsm.c, similar to x2apic-savic.c? > @@ -0,0 +1,252 @@ > +// SPDX-License-Identifier: GPL-2.0-only > +/* > + * AMD Alternate Injection Support (SEV-SNP Guests) > + * > + * Copyright (C) 2026 Advanced Micro Devices, Inc. > + * > + * Author: Melody Wang > + */ > + > +#include > +#include > + > +#include > +#include > + > +#include "local.h" > + > +extern u8 snp_vmpl; This is already in the asm/sev.h file. > + > +static int svsm_apic_probe(void) > +{ > + if (!cc_platform_has(CC_ATTR_SNP_ALTERNATE_INJECTION) || !snp_vmpl) Do you need both checks? Shouldn't the attribute only be set if the feature is set and the VMPL level is greater than 0? > + return 0; > + > + /* Alternate Injection and Secure AVIC are mutually exclusive */ > + if (cc_platform_has(CC_ATTR_SNP_SECURE_AVIC)) > + return 0; What happens in this situation? Will Secure AVIC still work if Alternate Injection is enabled? > + > + if (!x2apic_mode) { > + pr_err("Alternate Injection in non x2APIC mode impossible. Terminating.\n"); > + sev_es_terminate(SEV_TERM_SET_GEN, GHCB_SNP_UNSUPPORTED); > + } > + > + pr_info("Alternate Injection SVSM APIC enabled\n"); > + Should the probe routine query the SVSM for the APIC protocol? > + return 1; > +} > + > +static int svsm_acpi_madt_oem_check(char *oem_id, char *oem_table_id) > +{ > + return x2apic_enabled() && cc_platform_has(CC_ATTR_SNP_ALTERNATE_INJECTION) && snp_vmpl; > +} > + > +static void svsm_apic_msr_write(u32 reg, u32 v) > +{ > + u32 msr = APIC_BASE_MSR + (reg >> 4); > + struct svsm_call call = {}; > + int ret; > + > + switch (reg) { > + case APIC_ID: > + case APIC_TASKPRI: > + case APIC_PROCPRI: > + case APIC_EOI: > + case APIC_ISR ... APIC_ISR + 0x70: > + case APIC_TMR ... APIC_TMR + 0x70: > + case APIC_IRR ... APIC_IRR + 0x70: > + case APIC_ICR: > + case APIC_SELF_IPI: > + call.rax = SVSM_APIC_CALL(SVSM_APIC_WRITE_REGISTER); > + call.rcx = msr; > + call.rdx = v; > + > + ret = svsm_do_call(&call); > + if (ret) { > + pr_err("SVSM_APIC_WRITE_REGISTER: 0x%x, error: %d\n", reg, ret); > + sev_es_terminate(SEV_TERM_SET_GEN, GHCB_SNP_UNSUPPORTED); Can this be a new SEV_TERM_SET_LINUX value? > + } > + break; > + default: > + pr_err("SVSM_APIC_WRITE_REGISTER 0x%x not supported\n", reg); > + break; > + } > +} > + > +static u32 svsm_apic_msr_read(u32 reg) > +{ > + u32 msr = APIC_BASE_MSR + (reg >> 4); > + struct svsm_call call = {}; > + int ret; > + > + switch (reg) { > + case APIC_ID: > + case APIC_TASKPRI: > + case APIC_PROCPRI: > + case APIC_EOI: > + case APIC_ISR ... APIC_ISR + 0x70: > + case APIC_TMR ... APIC_TMR + 0x70: > + case APIC_IRR ... APIC_IRR + 0x70: > + case APIC_ICR: > + case APIC_SELF_IPI: > + call.rax = SVSM_APIC_CALL(SVSM_APIC_READ_REGISTER); > + call.rcx = msr; > + > + ret = svsm_do_call(&call); > + if (ret) { > + pr_err("SVSM_APIC_READ_REGISTER: 0x%x, error: %d\n", reg, ret); > + sev_es_terminate(SEV_TERM_SET_GEN, GHCB_SNP_UNSUPPORTED); > + } > + break; > + default: > + pr_err("SVSM_APIC_READ_REGISTER: 0x%x not supported\n", reg); > + return 0; > + } > + > + return call.rdx_out; > +} The read and write are very similar. Can you have a common function that takes a reg paramter, value parameter (that is input and output), and a mode parameter (read/write) and then have small read and write functions? > + > +static inline void svsm_apic_msr_eoi(void) > +{ > + svsm_apic_msr_write(APIC_EOI, APIC_EOI_ACK); > +} > + > +static inline u64 svsm_apic_icr_read(void) > +{ > + u32 reg; > + struct svsm_call call = {}; Move this up above the reg declaration. > + int ret; > + > + reg = APIC_ICR; > + > + call.rax = SVSM_APIC_CALL(SVSM_APIC_READ_REGISTER); > + call.rcx = APIC_BASE_MSR + (reg >> 4); > + > + ret = svsm_do_call(&call); > + if (ret) { > + pr_err("svsm_apic_icr_read error: %d\n", ret); > + sev_es_terminate(SEV_TERM_SET_GEN, GHCB_SNP_UNSUPPORTED); > + } > + > + return call.rdx_out; > +} > + > +static void svsm_apic_icr_write(u32 low, u32 id) > +{ > + u64 icr_data; > + u32 reg; > + struct svsm_call call = {}; Move this to the top. > + int ret; > + > + reg = APIC_ICR; > + icr_data = ((u64)id) << 32 | low; > + > + call.rax = SVSM_APIC_CALL(SVSM_APIC_WRITE_REGISTER); > + call.rcx = APIC_BASE_MSR + (reg >> 4); > + call.rdx = icr_data; > + > + ret = svsm_do_call(&call); > + if (ret) { > + pr_err("svsm_apic_icr_write error: %d\n", ret); > + sev_es_terminate(SEV_TERM_SET_GEN, GHCB_SNP_UNSUPPORTED); > + } > +} > + > +static void __svsm_apic_send_IPI_dest(unsigned int apicid, int vector, unsigned int dest) > +{ > + svsm_apic_icr_write(__prepare_ICR(0, vector, dest), apicid); > +} I don't think this routine is needed, just do the svsm_apic_icr_write() in the svsm_apic_send_IPI() below and then ... > + > +static void svsm_apic_send_IPI(int cpu, int vector) > +{ > + u32 dest = per_cpu(x86_cpu_to_apicid, cpu); > + > + __svsm_apic_send_IPI_dest(dest, vector, APIC_DEST_PHYSICAL); > +} > + > +static void __svsm_apic_send_IPI_mask(const struct cpumask *mask, int vector, int apic_dest) > +{ > + unsigned long query_cpu; > + unsigned long this_cpu; > + > + guard(irqsave)(); > + > + this_cpu = smp_processor_id(); > + for_each_cpu(query_cpu, mask) { > + if (apic_dest == APIC_DEST_ALLBUT && this_cpu == query_cpu) > + continue; > + > + __svsm_apic_send_IPI_dest(per_cpu(x86_cpu_to_apicid, query_cpu), > + vector, APIC_DEST_PHYSICAL); ... this can just invoke svsm_apic_send_IPI(), right? Thanks, Tom > + } > +} > + > +static void svsm_apic_send_IPI_mask(const struct cpumask *mask, int vector) > +{ > + __svsm_apic_send_IPI_mask(mask, vector, APIC_DEST_ALLINC); > +} > + > +static void svsm_apic_send_IPI_mask_allbutself(const struct cpumask *mask, int vector) > +{ > + __svsm_apic_send_IPI_mask(mask, vector, APIC_DEST_ALLBUT); > +} > + > +static void __svsm_apic_send_IPI_shorthand(int vector, u32 which) > +{ > + svsm_apic_icr_write(__prepare_ICR(which, vector, 0), 0); > +} > + > +static void svsm_apic_send_IPI_allbutself(int vector) > +{ > + __svsm_apic_send_IPI_shorthand(vector, APIC_DEST_ALLBUT); > +} > + > +static void svsm_apic_send_IPI_all(int vector) > +{ > + __svsm_apic_send_IPI_shorthand(vector, APIC_DEST_ALLINC); > +} > + > +static void svsm_apic_send_IPI_self(int vector) > +{ > + __svsm_apic_send_IPI_shorthand(vector, APIC_DEST_SELF); > +} > + > +static u32 svsm_apic_get_apic_id(u32 id) > +{ > + return id; > +} > + > +static struct apic svsm_apic __ro_after_init = { > + > + .name = "svsm apic", > + .probe = svsm_apic_probe, > + .acpi_madt_oem_check = svsm_acpi_madt_oem_check, > + > + .dest_mode_logical = false, > + > + .disable_esr = 0, > + > + .cpu_present_to_apicid = default_cpu_present_to_apicid, > + > + .max_apic_id = UINT_MAX, > + .x2apic_set_max_apicid = true, > + .get_apic_id = svsm_apic_get_apic_id, > + > + .calc_dest_apicid = apic_default_calc_apicid, > + > + .send_IPI = svsm_apic_send_IPI, > + .send_IPI_mask = svsm_apic_send_IPI_mask, > + .send_IPI_mask_allbutself = svsm_apic_send_IPI_mask_allbutself, > + .send_IPI_allbutself = svsm_apic_send_IPI_allbutself, > + .send_IPI_all = svsm_apic_send_IPI_all, > + .send_IPI_self = svsm_apic_send_IPI_self, > + .nmi_to_offline_cpu = true, > + > + .read = svsm_apic_msr_read, > + .write = svsm_apic_msr_write, > + .eoi = svsm_apic_msr_eoi, > + .icr_read = svsm_apic_icr_read, > + .icr_write = svsm_apic_icr_write, > + > +}; > +apic_driver(svsm_apic);