From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (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 A02633F6C26; Wed, 8 Jul 2026 07:16:02 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783494962; cv=none; b=Fhl1l4VxpWF3jZLKND8c+bmcVtXCz6cw8jngSPCfs8bL1wsVvgGE0CG8cfmvnt8cwyzpmNKCUA8Na9U3KqL0n1rNO9UVpEQTdf7BJw5vB6zBOYos3YJLBjdZ84ClsdWeqXGtc4oBJSDWbXUS/yg7q8oClHnZFI3PXci7mr6cf6o= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783494962; c=relaxed/simple; bh=Inmjc7fy2KHCPtWNbqaEGcDOCoTWrKNk24udNuAiX/Q=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=k8bFLlgiu+hYNhru631npiD0NsybvBd0t0VUz4L/+iDrpct0gY7HjkRlH2fEQKSqUDZmORtvq7Z/yzngyibd+TEg1nutAZYFhBw3KkBDMZuSDwdlJ9mIu+NE3WCzEeJJI0RmTKs6dUSCzMFZPZi1AYlAAWkXIN7/CxprbrTFSPQ= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=cUXRdBJD; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="cUXRdBJD" Received: by smtp.kernel.org (Postfix) with ESMTPS id D83AAC2BD00; Wed, 8 Jul 2026 07:16:00 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1783494960; bh=Inmjc7fy2KHCPtWNbqaEGcDOCoTWrKNk24udNuAiX/Q=; h=From:Date:Subject:References:In-Reply-To:To:Cc:From; b=cUXRdBJDI0E/Xw2KvOlJn6fUGNMuJCUeq+AGhCs64w5A2fjSeelXSGeh9vK4qbS8Y 5bMuFOFH9IcXkDYjTWvMOvFPUaVSpMQfAFtKTl4dittqQO3tQeCZLWcB2PENb90bpe P6t3+me4dtrkb6DkEZCcZY889nqoYBDOpgwIEdX3heC2jvava5SWZh24siX+kRO2rI 22Pv24C18XVq+5ifp7zKeZ5n7NQJn3cO10ibAUpEDOk0T6oht7wzlhKiy9MB1faFU8 kE27B0BYcFmAiDUjIiMGVJMSvjgwzxFl9RL2iTukV4g4C9c7DB3rNN6TeEqdsglFe7 n6z95XxnP5b6Q== Received: from aws-us-west-2-korg-lkml-1.web.codeaurora.org (localhost.localdomain [127.0.0.1]) by smtp.lore.kernel.org (Postfix) with ESMTP id C6F06C43458; Wed, 8 Jul 2026 07:16:00 +0000 (UTC) From: Sven Peter Date: Wed, 08 Jul 2026 09:15:41 +0200 Subject: [PATCH RFC 5/6] firmware/psci: Add EFI runtime conduit Precedence: bulk X-Mailing-List: devicetree@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: 7bit Message-Id: <20260708-efi-psci-v1-5-9efb3abf0e4c@kernel.org> References: <20260708-efi-psci-v1-0-9efb3abf0e4c@kernel.org> In-Reply-To: <20260708-efi-psci-v1-0-9efb3abf0e4c@kernel.org> To: Mark Rutland , Lorenzo Pieralisi , Rob Herring , Krzysztof Kozlowski , Conor Dooley , Ard Biesheuvel , Ilias Apalodimas , Catalin Marinas , Will Deacon , Sudeep Holla , Janne Grunau , Neal Gompa Cc: linux-arm-kernel@lists.infradead.org, devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, linux-efi@vger.kernel.org, asahi@lists.linux.dev, Sven Peter X-Mailer: b4 0.14.3 X-Developer-Signature: v=1; a=openpgp-sha256; l=4276; i=sven@kernel.org; h=from:subject:message-id; bh=Inmjc7fy2KHCPtWNbqaEGcDOCoTWrKNk24udNuAiX/Q=; b=owGbwMvMwCXmIlirolUq95LxtFoSQ5bvT23luh6jNRmec1i/zfwgLh37Z3XochFpTrvb7ybPi f/qH7Ggo5SFQYyLQVZMkWX7fnvTJw/fCC7ddOk9zBxWJpAhDFycAjARbx+G/5UnObc9rFeO2jJR LuD0u3VzzCY1Of3eHFblG+C9UbP0wk1Ghna5/cuSDr+zmtEQMcVq4jaHp98DlQXLDh5mrt+22+Y TLzsA X-Developer-Key: i=sven@kernel.org; a=openpgp; fpr=A1E3E34A2B3C820DBC4955E5993B08092F131F93 X-Endpoint-Received: by B4 Relay for sven@kernel.org/default with auth_id=407 Apple Silicon machines run the kernel at the highest available exception level, leaving no higher level to trap into for PSCI firmware calls. The firmware implementing PSCI therefore shares that level with the kernel and is exposed as an EFI runtime service instead of being reached through an SMC or HVC trap. Add a new "efi" conduit that routes PSCI calls to the handler extracted from the custom EFI configuration table. PSCI_VERSION, MIGRATE_INFO_TYPE and PSCI_FEATURES are queried during early CPU bring-up before EFI runtime services are available and have to be answered directly from the firmware-provided table. Signed-off-by: Sven Peter --- drivers/firmware/psci/psci.c | 64 ++++++++++++++++++++++++++++++++++++++++++++ include/linux/arm-smccc.h | 1 + 2 files changed, 65 insertions(+) diff --git a/drivers/firmware/psci/psci.c b/drivers/firmware/psci/psci.c index e73bae6cb23a..af022bf2cb9f 100644 --- a/drivers/firmware/psci/psci.c +++ b/drivers/firmware/psci/psci.c @@ -10,6 +10,7 @@ #include #include #include +#include #include #include #include @@ -24,6 +25,7 @@ #include #include +#include #include #include #include @@ -131,6 +133,63 @@ __invoke_psci_fn_smc(unsigned long function_id, return res.a0; } +#if IS_ENABLED(CONFIG_EFI) && IS_ENABLED(CONFIG_ARM64) +static bool efi_psci_fn_valid(unsigned long function_id) +{ + if (function_id >= PSCI_0_2_FN_BASE && + function_id <= PSCI_0_2_FN(EFI_PSCI_MAX_FN)) + return true; + + if (function_id >= PSCI_0_2_FN64_BASE && + function_id <= PSCI_0_2_FN64(EFI_PSCI_MAX_FN)) + return true; + + return false; +} + +static unsigned long __invoke_psci_fn_efi(unsigned long function_id, + unsigned long arg0, + unsigned long arg1, + unsigned long arg2) +{ + u32 fn; + + /* These are called before EFI runtime services are available */ + switch (function_id) { + case PSCI_0_2_FN_PSCI_VERSION: + return efi_psci.version; + case PSCI_0_2_FN_MIGRATE_INFO_TYPE: + return PSCI_0_2_TOS_MP; + case PSCI_1_0_FN_PSCI_FEATURES: + if (!efi_psci_fn_valid(arg0)) + return PSCI_RET_NOT_SUPPORTED; + fn = arg0 & 0xff; + if (fn >= efi_psci.num_features || fn >= EFI_PSCI_MAX_FN) + return PSCI_RET_NOT_SUPPORTED; + return efi_psci.features[fn]; + } + + if (!efi_psci_fn_valid(function_id)) + return PSCI_RET_NOT_SUPPORTED; + + if (WARN_ON_ONCE(!efi_psci.psci_handler)) + return PSCI_RET_NOT_SUPPORTED; + if (WARN_ON_ONCE(!efi_enabled(EFI_RUNTIME_SERVICES))) + return PSCI_RET_NOT_SUPPORTED; + + return arm64_efi_psci_call(function_id, arg0, arg1, arg2); +} +#else +static unsigned long __invoke_psci_fn_efi(unsigned long function_id, + unsigned long arg0, + unsigned long arg1, + unsigned long arg2) +{ + WARN(1, "EFI PSCI conduit invoked but kernel has not EFI support"); + return PSCI_RET_NOT_SUPPORTED; +} +#endif + static __always_inline int psci_to_linux_errno(int errno) { switch (errno) { @@ -277,6 +336,9 @@ static void set_conduit(enum arm_smccc_conduit conduit) case SMCCC_CONDUIT_SMC: invoke_psci_fn = __invoke_psci_fn_smc; break; + case SMCCC_CONDUIT_EFI: + invoke_psci_fn = __invoke_psci_fn_efi; + break; default: WARN(1, "Unexpected PSCI conduit %d\n", conduit); } @@ -299,6 +361,8 @@ static int get_set_conduit_method(const struct device_node *np) set_conduit(SMCCC_CONDUIT_HVC); } else if (!strcmp("smc", method)) { set_conduit(SMCCC_CONDUIT_SMC); + } else if (!strcmp("efi", method)) { + set_conduit(SMCCC_CONDUIT_EFI); } else { pr_warn("invalid \"method\" property: %s\n", method); return -EINVAL; diff --git a/include/linux/arm-smccc.h b/include/linux/arm-smccc.h index 4de81848fe2e..7328e1e222ca 100644 --- a/include/linux/arm-smccc.h +++ b/include/linux/arm-smccc.h @@ -322,6 +322,7 @@ enum arm_smccc_conduit { SMCCC_CONDUIT_NONE, SMCCC_CONDUIT_SMC, SMCCC_CONDUIT_HVC, + SMCCC_CONDUIT_EFI, }; /** -- 2.55.0