From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received-SPF: Pass (sender SPF authorized) identity=mailfrom; client-ip=2607:f8b0:4864:20::d43; helo=mail-io1-xd43.google.com; envelope-from=ard.biesheuvel@linaro.org; receiver=edk2-devel@lists.01.org Received: from mail-io1-xd43.google.com (mail-io1-xd43.google.com [IPv6:2607:f8b0:4864:20::d43]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by ml01.01.org (Postfix) with ESMTPS id A2AE321195BEE for ; Tue, 11 Dec 2018 00:26:29 -0800 (PST) Received: by mail-io1-xd43.google.com with SMTP id r200so11073961iod.11 for ; Tue, 11 Dec 2018 00:26:29 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=mime-version:references:in-reply-to:from:date:message-id:subject:to :cc; bh=0cXrqYcKGdMl6ayGfKJBgK0v9zyuFru8GTIzvkFVs9M=; b=HxIeKYie34SV8ULwW0pFJNeONshPDPupHH3TYDosbsZV6031v6pJNO7iYCpHua4pBI B1HV8i09AMozHKb+RCfIqafiepc9NKefMzePQYpRfw+Nyu3A2RLTowstnV/XfglIoN3V m/8zNGC4ya+t/7dpChido4vsPnDgG/0AScl3A= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:references:in-reply-to:from:date :message-id:subject:to:cc; bh=0cXrqYcKGdMl6ayGfKJBgK0v9zyuFru8GTIzvkFVs9M=; b=R+LelS8p+I+LyuAOv3sdr1h11+jtXFjjlrpHTw3m/0Z4AEMJwZurNS3344EnmMhYaL ChZDpJ6JXXHhiKrx+lzdrzpy1u9/WHkhGFfKH6bY3aFrnF2WDx382vnFuVKoLMRLXZPw q0rQvygR9aosW18K6On8GytQnmcSOjdfKUokec/wUovgnRElNLs08Hq9D5cDVB/UxQMu +JKwScX1yTKcjbR9O1CPvLmS6082uuplBVhzJsKqwe1vUSZ3PxJxTmDN+Ifj88t6eiY0 6Qz62KLti7TFzMnyxfe4qGybahxagAAxEVRsF4a+CNiEUnmJnWV4hJ1l+OE24wTGtRGe TFvw== X-Gm-Message-State: AA+aEWazTq606OE7wvbCWB2uggZKe3oJfJZCmn5cxPici+AUrCxJxwTX dGK4Y2ItqKW9pDNEx93jBW7hsD4xGpQf02hhX/TG4g== X-Google-Smtp-Source: AFSGD/UHBHKEwl42hUJ0da00tHP4B6xCT+iQ5lgD5nEc4jkOLdbrSvLiQwAaSJ3IRnpXQHppThbMzGh2ls4CI8obaU4= X-Received: by 2002:a5d:8415:: with SMTP id i21mr12426154ion.173.1544516788478; Tue, 11 Dec 2018 00:26:28 -0800 (PST) MIME-Version: 1.0 References: <1544514341-3176-1-git-send-email-sumit.garg@linaro.org> In-Reply-To: <1544514341-3176-1-git-send-email-sumit.garg@linaro.org> From: Ard Biesheuvel Date: Tue, 11 Dec 2018 09:26:16 +0100 Message-ID: To: Sumit Garg Cc: "edk2-devel@lists.01.org" , Daniel Thompson , Leif Lindholm Subject: Re: [PATCH edk2-platforms v1 1/1] Silicon/SynQuacer: add OP-TEE based RNG driver X-BeenThere: edk2-devel@lists.01.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: EDK II Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 11 Dec 2018 08:26:29 -0000 Content-Type: text/plain; charset="UTF-8" On Tue, 11 Dec 2018 at 08:46, Sumit Garg wrote: > > This driver uses OpteeLib to interface with OP-TEE based RNG service > (pseudo trusted application) to implement EFI_RNG_PROTOCOL that is used > to seed kernel entropy pool. > > Cc: Ard Biesheuvel > Cc: Leif Lindholm > Contributed-under: TianoCore Contribution Agreement 1.1 > Signed-off-by: Sumit Garg Excellent! Happy to see this code going upstream. This code looks fine to me, but I'd like to test it with an updated OP-TEE build first before I merge it. > --- > > Depends on "ArmPkg/OpteeLib: Add OPTEE_SUCCESS return code" patch. > > For detailed implementation of OP-TEE based RNG service (pseudo > trusted application), please refer to OP-TEE PR here [1]. > > [1] https://github.com/OP-TEE/optee_os/pull/2564 > > Silicon/Socionext/SynQuacer/SynQuacer.dec | 2 + > Platform/Socionext/DeveloperBox/DeveloperBox.dsc | 1 + > Platform/Socionext/DeveloperBox/DeveloperBox.fdf | 1 + > Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.inf | 55 ++++ > Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRng.c | 270 ++++++++++++++++++++ > Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.uni | 19 ++ > Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxeExtra.uni | 18 ++ > 7 files changed, 366 insertions(+) > > diff --git a/Silicon/Socionext/SynQuacer/SynQuacer.dec b/Silicon/Socionext/SynQuacer/SynQuacer.dec > index ccaf80def06b..e58a373ecb3d 100644 > --- a/Silicon/Socionext/SynQuacer/SynQuacer.dec > +++ b/Silicon/Socionext/SynQuacer/SynQuacer.dec > @@ -29,6 +29,8 @@ [Guids] > > gSynQuacerPlatformFormSetGuid = { 0xe9cd576a, 0xaf9a, 0x4d41, { 0xbf, 0x1a, 0x29, 0xe1, 0xbc, 0x99, 0x99, 0x54 } } > > + gOpteeRngTaGuid = { 0xab7a617c, 0xb8e7, 0x4d8f, { 0x83, 0x01, 0xd0, 0x9b, 0x61, 0x03, 0x6b, 0x64 } } > + > [Ppis] > gSynQuacerDramInfoPpiGuid = { 0x3e1d7356, 0xdda4, 0x4b1a, { 0x93, 0x46, 0xbf, 0x89, 0x1c, 0x86, 0x46, 0xcc } } > > diff --git a/Platform/Socionext/DeveloperBox/DeveloperBox.dsc b/Platform/Socionext/DeveloperBox/DeveloperBox.dsc > index 997ea344330d..b18286a0b228 100644 > --- a/Platform/Socionext/DeveloperBox/DeveloperBox.dsc > +++ b/Platform/Socionext/DeveloperBox/DeveloperBox.dsc > @@ -628,6 +628,7 @@ [Components.common] > # > # RNG > # > + Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.inf > Silicon/Openmoko/ChaosKeyDxe/ChaosKeyDxe.inf > > # > diff --git a/Platform/Socionext/DeveloperBox/DeveloperBox.fdf b/Platform/Socionext/DeveloperBox/DeveloperBox.fdf > index 3a92e0fe63ef..4a234a36525e 100644 > --- a/Platform/Socionext/DeveloperBox/DeveloperBox.fdf > +++ b/Platform/Socionext/DeveloperBox/DeveloperBox.fdf > @@ -189,6 +189,7 @@ [FV.FvMain] > # > # RNG > # > + INF Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.inf > INF Silicon/Openmoko/ChaosKeyDxe/ChaosKeyDxe.inf > > # > diff --git a/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.inf b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.inf > new file mode 100644 > index 000000000000..6fef1b380270 > --- /dev/null > +++ b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.inf > @@ -0,0 +1,55 @@ > +## @file > +# Device driver for the OP-TEE based random number generator. > +# > +# Copyright (c) 2018, Linaro Ltd. All rights reserved.
> +# > +# This program and the accompanying materials > +# are licensed and made available under the terms and conditions of the BSD > +# License which accompanies this distribution. The full text of the license may > +# be found at http://opensource.org/licenses/bsd-license.php. > +# > +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > +# > +## > + > +[Defines] > + INF_VERSION = 0x0001001A > + BASE_NAME = OpteeRngDxe > + MODULE_UNI_FILE = OpteeRngDxe.uni > + FILE_GUID = 93A599F2-6D82-4FCC-9970-49BB013D695A > + MODULE_TYPE = DXE_DRIVER > + VERSION_STRING = 1.0 > + ENTRY_POINT = OpteeRngEntry > + > +# > +# VALID_ARCHITECTURES = AARCH64 ARM > +# > + > +[Sources] > + OpteeRng.c > + > +[Packages] > + ArmPkg/ArmPkg.dec > + MdePkg/MdePkg.dec > + Silicon/Socionext/SynQuacer/SynQuacer.dec > + > +[LibraryClasses] > + OpteeLib > + TimerLib > + UefiBootServicesTableLib > + UefiDriverEntryPoint > + UefiLib > + > +[Protocols] > + gEfiRngProtocolGuid # PROTOCOL BY_START > + > +[Guids] > + gEfiRngAlgorithmRaw > + gOpteeRngTaGuid > + > +[Depex] > + TRUE > + > +[UserExtensions.TianoCore."ExtraFiles"] > + OpteeRngDxeExtra.uni > diff --git a/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRng.c b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRng.c > new file mode 100644 > index 000000000000..089fad8b5ce5 > --- /dev/null > +++ b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRng.c > @@ -0,0 +1,270 @@ > +/** @file > + Device driver for the OpteeRng hardware random number generator. > + > + Copyright (c) 2018, Linaro Ltd. All rights reserved.
> + > + This program and the accompanying materials > + are licensed and made available under the terms and conditions of the BSD > + License which accompanies this distribution. The full text of the license may > + be found at http://opensource.org/licenses/bsd-license.php. > + > + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > + > +**/ > + > +#include > +#include > +#include > +#include > +#include > +#include > +#include > + > +#define PTA_COMMAND_GET_ENTROPY 0x0 > +#define OPTEE_RNG_POOL_SIZE (4 * 1024) > + > +/** > + Returns information about the random number generation implementation. > + > + @param[in] This A pointer to the EFI_RNG_PROTOCOL instance. > + @param[in,out] AlgorithmListSize On input, the size in bytes of AlgorithmList > + On output with a return code of EFI_SUCCESS, > + the size in bytes of the data returned in > + AlgorithmList. On output with a return > + code of EFI_BUFFER_TOO_SMALL, the size of > + AlgorithmList required to obtain the list. > + @param[out] AlgorithmList A caller-allocated memory buffer filled by > + the driver with one EFI_RNG_ALGORITHM > + element for each supported RNG algorithm. > + The list must not change across multiple > + calls to the same driver. The first > + algorithm in the list is the default > + algorithm for the driver. > + > + @retval EFI_SUCCESS The RNG algorithm list was returned > + successfully. > + @retval EFI_UNSUPPORTED The services is not supported by this driver > + @retval EFI_DEVICE_ERROR The list of algorithms could not be > + retrieved due to a hardware or firmware > + error. > + @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect. > + @retval EFI_BUFFER_TOO_SMALL The buffer RNGAlgorithmList is too small to > + hold the result. > + > +**/ > +STATIC > +EFI_STATUS > +EFIAPI > +GetInfo ( > + IN EFI_RNG_PROTOCOL *This, > + IN OUT UINTN *AlgorithmListSize, > + OUT EFI_RNG_ALGORITHM *AlgorithmList > +) > +{ > + UINTN Size; > + > + // > + // We only implement the raw algorithm > + // > + Size = sizeof gEfiRngAlgorithmRaw; > + > + if (*AlgorithmListSize < Size) { > + *AlgorithmListSize = Size; > + return EFI_BUFFER_TOO_SMALL; > + } > + > + gBS->CopyMem (AlgorithmList, &gEfiRngAlgorithmRaw, Size); > + *AlgorithmListSize = Size; > + > + return EFI_SUCCESS; > +} > + > + > +/** > + Produces and returns an RNG value using either the default or specified RNG > + algorithm. > + > + @param[in] This A pointer to the EFI_RNG_PROTOCOL instance. > + @param[in] Algorithm A pointer to the EFI_RNG_ALGORITHM that > + identifies the RNG algorithm to use. May be > + NULL in which case the function will use its > + default RNG algorithm. > + @param[in] ValueLength The length in bytes of the memory buffer > + pointed to by RNGValue. The driver shall > + return exactly this numbers of bytes. > + @param[out] Value A caller-allocated memory buffer filled by the > + driver with the resulting RNG value. > + > + @retval EFI_SUCCESS The RNG value was returned successfully. > + @retval EFI_UNSUPPORTED The algorithm specified by RNGAlgorithm is not > + supported by this driver. > + @retval EFI_DEVICE_ERROR An RNG value could not be retrieved due to a > + hardware or firmware error. > + @retval EFI_NOT_READY There is not enough random data available to > + satisfy the length requested by > + RNGValueLength. > + @retval EFI_INVALID_PARAMETER RNGValue is NULL and RNGValueLength is > + non-zero. > + > +**/ > +STATIC > +EFI_STATUS > +EFIAPI > +GetRNG ( > + IN EFI_RNG_PROTOCOL *This, > + IN EFI_RNG_ALGORITHM *Algorithm OPTIONAL, > + IN UINTN ValueLength, > + OUT UINT8 *Value > +) > +{ > + EFI_STATUS Status; > + OPTEE_OPEN_SESSION_ARG OpenSessionArg; > + OPTEE_INVOKE_FUNCTION_ARG InvokeFunctionArg; > + UINT8 *OutPointer; > + UINTN OutSize; > + UINTN WaitMiliSeconds; > + > + if ((Value == NULL) && (ValueLength != 0)) { > + return EFI_INVALID_PARAMETER; > + } > + > + if (ValueLength > OPTEE_RNG_POOL_SIZE) { > + return EFI_UNSUPPORTED; > + } > + > + if (Algorithm != NULL && !CompareGuid (Algorithm, &gEfiRngAlgorithmRaw)) { > + return EFI_UNSUPPORTED; > + } > + > + ZeroMem (&OpenSessionArg, sizeof (OPTEE_OPEN_SESSION_ARG)); > + CopyMem (&OpenSessionArg.Uuid, &gOpteeRngTaGuid, sizeof (EFI_GUID)); > + > + Status = OpteeOpenSession (&OpenSessionArg); > + if ((Status != EFI_SUCCESS) || (OpenSessionArg.Return != OPTEE_SUCCESS)) { > + DEBUG ((DEBUG_ERROR, "OP-TEE Open Session failed with return: %08x and" > + "return origin: %d\n", OpenSessionArg.Return, > + OpenSessionArg.ReturnOrigin)); > + return EFI_DEVICE_ERROR; > + } > + > + OutPointer = Value; > + > + while (ValueLength > 0) { > + ZeroMem (&InvokeFunctionArg, sizeof (OPTEE_INVOKE_FUNCTION_ARG)); > + > + InvokeFunctionArg.Function = PTA_COMMAND_GET_ENTROPY; > + InvokeFunctionArg.Session = OpenSessionArg.Session; > + > + InvokeFunctionArg.Params[0].Attribute = > + OPTEE_MESSAGE_ATTRIBUTE_TYPE_MEMORY_INOUT; > + InvokeFunctionArg.Params[0].Union.Memory.BufferAddress = > + (UINT64) OutPointer; > + InvokeFunctionArg.Params[0].Union.Memory.Size = ValueLength; > + > + Status = OpteeInvokeFunction (&InvokeFunctionArg); > + if ((Status != EFI_SUCCESS) || > + (InvokeFunctionArg.Return != OPTEE_SUCCESS)) { > + DEBUG ((DEBUG_ERROR, "OP-TEE Invoke Function failed with return: %x and" > + "return origin: %d\n", InvokeFunctionArg.Return, > + InvokeFunctionArg.ReturnOrigin)); > + > + OpteeCloseSession (OpenSessionArg.Session); > + > + return EFI_DEVICE_ERROR; > + } > + > + OutSize = MIN (InvokeFunctionArg.Params[0].Union.Memory.Size, ValueLength); > + > + OutPointer += OutSize; > + ValueLength -= OutSize; > + > + // > + // OP-TEE RNG Trusted application takes approximately 256ms for every 32 > + // bytes of full entropy output. > + // > + if (ValueLength > 0) { > + WaitMiliSeconds = ((ValueLength + 32) * 256) / 32; > + MicroSecondDelay (WaitMiliSeconds * 1000); > + } > + } > + > + OpteeCloseSession (OpenSessionArg.Session); > + > + return EFI_SUCCESS; > +} > + > +// > +// OP-TEE based Random Number Generator (RNG) protocol > +// > +EFI_RNG_PROTOCOL mOpteeRng = { > + GetInfo, > + GetRNG > +}; > + > +/** > + The user Entry Point for the OP-TEE Random Number Generator (RNG) driver. > + > + @param[in] ImageHandle The firmware allocated handle for the EFI image. > + @param[in] SystemTable A pointer to the EFI System Table. > + > + @retval EFI_SUCCESS The entry point is executed successfully. > + @retval EFI_NOT_FOUND Not able to find OP-TEE based RNG. > + @retval Other Some error occurs when executing this entry point. > + > +**/ > +EFI_STATUS > +EFIAPI > +OpteeRngEntry ( > + IN EFI_HANDLE ImageHandle, > + IN EFI_SYSTEM_TABLE *SystemTable > + ) > +{ > + EFI_STATUS Status; > + EFI_HANDLE Handle; > + OPTEE_OPEN_SESSION_ARG OpenSessionArg; > + > + if (!IsOpteePresent()) { > + return EFI_NOT_FOUND; > + } > + > + // > + // Initialize OP-TEE > + // > + Status = OpteeInit (); > + if (Status != EFI_SUCCESS) { > + return EFI_NOT_FOUND; > + } > + > + ZeroMem (&OpenSessionArg, sizeof (OPTEE_OPEN_SESSION_ARG)); > + CopyMem (&OpenSessionArg.Uuid, &gOpteeRngTaGuid, sizeof (EFI_GUID)); > + > + // > + // Try to open session with RNG Trusted Application to check if its present > + // > + Status = OpteeOpenSession (&OpenSessionArg); > + if ((Status != EFI_SUCCESS) || (OpenSessionArg.Return != OPTEE_SUCCESS)) { > + return EFI_NOT_FOUND; > + } else { > + OpteeCloseSession (OpenSessionArg.Session); > + } > + > + // > + // Install UEFI RNG (Random Number Generator) Protocol > + // > + Handle = NULL; > + Status = gBS->InstallProtocolInterface (&Handle, > + &gEfiRngProtocolGuid, > + EFI_NATIVE_INTERFACE, > + &mOpteeRng); > + if (EFI_ERROR (Status)) { > + DEBUG ((DEBUG_ERROR, > + "Failed to install OP-TEE RNG protocol interface (Status == %r)\n", > + Status)); > + return Status; > + } > + > + DEBUG ((DEBUG_INIT | DEBUG_INFO, "*** Installed OpteeRng driver! ***\n")); > + > + return EFI_SUCCESS; > +} > diff --git a/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.uni b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.uni > new file mode 100644 > index 000000000000..320561f39d8c > --- /dev/null > +++ b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxe.uni > @@ -0,0 +1,19 @@ > +// /** @file > +// Installs OP-TEE based UEFI Random Number Generator protocol. > +// > +// Copyright (c) 2018, Linaro, Ltd. All rights reserved.
> +// > +// This program and the accompanying materials > +// are licensed and made available under the terms and conditions of the BSD License > +// which accompanies this distribution. The full text of the license may be found at > +// http://opensource.org/licenses/bsd-license.php > +// THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > +// WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > +// > +// **/ > + > + > +#string STR_MODULE_ABSTRACT #language en-US "Installs OP-TEE based UEFI Random Number Generator protocol" > + > +#string STR_MODULE_DESCRIPTION #language en-US "This driver installs UEFI Random Number Generator protocol based on OP-TEE library to interface with RNG service running in OP-TEE environment." > + > diff --git a/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxeExtra.uni b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxeExtra.uni > new file mode 100644 > index 000000000000..eadd103de688 > --- /dev/null > +++ b/Silicon/Socionext/SynQuacer/Drivers/OpteeRngDxe/OpteeRngDxeExtra.uni > @@ -0,0 +1,18 @@ > +// /** @file > +// OpteeRngDxe Localized Strings and Content > +// > +// Copyright (c) 2018, Linaro, Ltd. All rights reserved.
> +// > +// This program and the accompanying materials > +// are licensed and made available under the terms and conditions of the BSD License > +// which accompanies this distribution. The full text of the license may be found at > +// http://opensource.org/licenses/bsd-license.php > +// THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > +// WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > +// > +// **/ > + > +#string STR_PROPERTIES_MODULE_NAME > +#language en-US > +"OP-TEE RNG DXE Driver" > + > -- > 2.7.4 >