Date: Wed, 15 Nov 2023 18:27:57 +0000 From: Jessica Clarke <jrtc27@freebsd.org> To: Andrew Turner <andrew@FreeBSD.org> Cc: "src-committers@freebsd.org" <src-committers@FreeBSD.org>, "dev-commits-src-all@freebsd.org" <dev-commits-src-all@FreeBSD.org>, "dev-commits-src-main@freebsd.org" <dev-commits-src-main@FreeBSD.org> Subject: Re: git: 9eecef052155 - main - Add an Armv8 rndr random number provider Message-ID: <E302C81B-CAA0-4122-8754-FE9F055C3FBB@freebsd.org> In-Reply-To: <202311151812.3AFICLIs077567@gitrepo.freebsd.org> References: <202311151812.3AFICLIs077567@gitrepo.freebsd.org>
next in thread | previous in thread | raw e-mail | index | archive | help
On 15 Nov 2023, at 18:12, Andrew Turner <andrew@FreeBSD.org> wrote: >=20 > The branch main has been updated by andrew: >=20 > URL: = https://cgit.FreeBSD.org/src/commit/?id=3D9eecef052155646fbc5f8f533b952b37= 2572d06a >=20 > commit 9eecef052155646fbc5f8f533b952b372572d06a > Author: Andrew Turner <andrew@FreeBSD.org> > AuthorDate: 2023-11-15 17:42:02 +0000 > Commit: Andrew Turner <andrew@FreeBSD.org> > CommitDate: 2023-11-15 18:05:08 +0000 >=20 > Add an Armv8 rndr random number provider >=20 > Armv8.5 adds an optional random number generator. This is = implemented > as two special registers one to read a random number, the other to > re-seed the entropy pool before reading a random number. Both = registers > will set the condition flags to tell the caller they can't produce = a > random number in a reasonable amount of time. >=20 > Without a signal to reseed the entropy pool use the latter register > to provide random numbers to the kernel pool. If at a later time we > had a way to tell the provider if it needs to reseed or not we = could > use the former. >=20 > On an Amazon AWS Graviton3 VM this never failed, however this may = not > be the case on low end CPUs so retry reading the random number 10 = times > before returning an error. >=20 > Reviewed by: imp, delphij (csprng) > Sponsored by: The FreeBSD Foundation > Sponsored by: Arm Ltd > Differential Revision: https://reviews.freebsd.org/D35411 > --- > sys/arm64/conf/std.dev | 1 + > sys/conf/files.arm64 | 2 + > sys/dev/random/armv8rng.c | 135 = +++++++++++++++++++++++++++++++++++++++ > sys/dev/random/random_harvestq.c | 1 + > sys/modules/Makefile | 2 + > sys/modules/armv8_rng/Makefile | 11 ++++ > sys/sys/random.h | 1 + > 7 files changed, 153 insertions(+) >=20 > diff --git a/sys/arm64/conf/std.dev b/sys/arm64/conf/std.dev > index 74d2407e0aec..0ebf2e775b11 100644 > --- a/sys/arm64/conf/std.dev > +++ b/sys/arm64/conf/std.dev > @@ -53,6 +53,7 @@ device vt_simplefb >=20 > # Pseudo devices. > device crypto # core crypto support > +device armv8_rng # Armv8.5 rndr RNG > device loop # Network loopback > device ether # Ethernet support > device vlan # 802.1Q VLAN support > diff --git a/sys/conf/files.arm64 b/sys/conf/files.arm64 > index 38b9e40463eb..9ccead6a98e1 100644 > --- a/sys/conf/files.arm64 > +++ b/sys/conf/files.arm64 > @@ -379,6 +379,8 @@ dev/psci/psci.c standard > dev/psci/smccc_arm64.S standard > dev/psci/smccc.c standard >=20 > +dev/random/armv8rng.c optional armv8_rng !random_loadable > + > dev/safexcel/safexcel.c optional safexcel fdt >=20 > dev/sdhci/sdhci_xenon.c optional sdhci_xenon sdhci > diff --git a/sys/dev/random/armv8rng.c b/sys/dev/random/armv8rng.c > new file mode 100644 > index 000000000000..3cca42a5bbf3 > --- /dev/null > +++ b/sys/dev/random/armv8rng.c > @@ -0,0 +1,135 @@ > +/*- > + * Copyright (c) 2022 The FreeBSD Foundation > + * > + * This software was developed by Andrew Turner under sponsorship = from > + * the FreeBSD Foundation. > + * > + * Redistribution and use in source and binary forms, with or without > + * modification, are permitted provided that the following conditions > + * are met: > + * 1. Redistributions of source code must retain the above copyright > + * notice, this list of conditions and the following disclaimer. > + * 2. Redistributions in binary form must reproduce the above = copyright > + * notice, this list of conditions and the following disclaimer in = the > + * documentation and/or other materials provided with the = distribution. > + * > + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' = AND > + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, = THE > + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR = PURPOSE > + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE = LIABLE > + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR = CONSEQUENTIAL > + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE = GOODS > + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS = INTERRUPTION) > + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN = CONTRACT, STRICT > + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN = ANY WAY > + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE = POSSIBILITY OF > + * SUCH DAMAGE. > + */ > + > +#include <sys/cdefs.h> > + > +#include <sys/param.h> > +#include <sys/systm.h> > +#include <sys/conf.h> > +#include <sys/kernel.h> > +#include <sys/lock.h> > +#include <sys/malloc.h> > +#include <sys/module.h> > +#include <sys/random.h> > + > +#include <machine/armreg.h> > + > +#include <dev/random/randomdev.h> > + > +static u_int random_rndr_read(void *, u_int); > + > +static bool has_rndr; > +static struct random_source random_armv8_rndr =3D { > + .rs_ident =3D "Armv8 rndr RNG", > + .rs_source =3D RANDOM_PURE_ARMV8, > + .rs_read =3D random_rndr_read, > +}; > + > +static inline int > +random_rndr_read_one(u_long *buf) > +{ > + u_long val; > + int loop, ret; > + > + loop =3D 10; > + do { > + __asm __volatile( > + ".arch_extension rng \n" > + "mrs %0, rndrrs \n" /* Read the random number */ > + "cset %w1, ne \n" /* 1 on success, 0 on failure */ > + ".arch_extension norng \n" > + : "=3D&r" (val), "=3D&r"(ret) :: "cc"); Early clobber doesn=E2=80=99t make sense with no inputs. Jess > + } while (ret !=3D 0 && --loop > 0); > + > + if (ret !=3D 0) > + *buf =3D val; > + > + return (ret); > +} > + > +static u_int > +random_rndr_read(void *buf, u_int c) > +{ > + u_long *b; > + u_int count; > + > + b =3D buf; > + for (count =3D 0; count < c; count +=3D sizeof(*b)) { > + if (!random_rndr_read_one(b)) > + break; > + > + b++; > + } > + > + return (count); > +} > + > +static int > +rndr_modevent(module_t mod, int type, void *unused) > +{ > + uint64_t reg; > + int error =3D 0; > + > + switch (type) { > + case MOD_LOAD: > + has_rndr =3D false; > + if (get_kernel_reg(ID_AA64ISAR0_EL1, ®) && > + ID_AA64ISAR0_RNDR_VAL(reg) !=3D ID_AA64ISAR0_RNDR_NONE) { > + has_rndr =3D true; > + random_source_register(&random_armv8_rndr); > + printf("random: fast provider: \"%s\"\n", > + random_armv8_rndr.rs_ident); > + } > + break; > + > + case MOD_UNLOAD: > + if (has_rndr) > + random_source_deregister(&random_armv8_rndr); > + break; > + > + case MOD_SHUTDOWN: > + break; > + > + default: > + error =3D EOPNOTSUPP; > + break; > + > + } > + > + return (error); > +} > + > +static moduledata_t rndr_mod =3D { > + "rndr", > + rndr_modevent, > + 0 > +}; > + > +DECLARE_MODULE(rndr, rndr_mod, SI_SUB_RANDOM, SI_ORDER_FOURTH); > +MODULE_VERSION(rndr, 1); > +MODULE_DEPEND(rndr, random_harvestq, 1, 1, 1); > diff --git a/sys/dev/random/random_harvestq.c = b/sys/dev/random/random_harvestq.c > index 09b81950281b..dce0878513db 100644 > --- a/sys/dev/random/random_harvestq.c > +++ b/sys/dev/random/random_harvestq.c > @@ -385,6 +385,7 @@ static const char = *random_source_descr[ENTROPYSOURCE] =3D { > [RANDOM_PURE_TPM] =3D "PURE_TPM", > [RANDOM_PURE_VMGENID] =3D "PURE_VMGENID", > [RANDOM_PURE_QUALCOMM] =3D "PURE_QUALCOMM", > + [RANDOM_PURE_ARMV8] =3D "PURE_ARMV8", > /* "ENTROPYSOURCE" */ > }; >=20 > diff --git a/sys/modules/Makefile b/sys/modules/Makefile > index 3eff75312fd3..f9079498dc1f 100644 > --- a/sys/modules/Makefile > +++ b/sys/modules/Makefile > @@ -41,6 +41,7 @@ SUBDIR=3D \ > ${_arcmsr} \ > ${_allwinner} \ > ${_armv8crypto} \ > + ${_armv8_rng} \ > ${_asmc} \ > ata \ > ath \ > @@ -674,6 +675,7 @@ _cxgb=3D cxgb >=20 > .if ${MACHINE_CPUARCH} =3D=3D "aarch64" > _armv8crypto=3D armv8crypto > +_armv8_rng=3D armv8_rng > _dpaa2=3D dpaa2 > _sff=3D sff > _em=3D em > diff --git a/sys/modules/armv8_rng/Makefile = b/sys/modules/armv8_rng/Makefile > new file mode 100644 > index 000000000000..29d2907aed06 > --- /dev/null > +++ b/sys/modules/armv8_rng/Makefile > @@ -0,0 +1,11 @@ > +# $FreeBSD$ > + > +.PATH: ${SRCTOP}/sys/dev/random > + > +KMOD=3D armv8_rng > +SRCS=3D armv8rng.c > +SRCS+=3D bus_if.h device_if.h > + > +CFLAGS+=3D -I${SRCTOP}/sys > + > +.include <bsd.kmod.mk> > diff --git a/sys/sys/random.h b/sys/sys/random.h > index 0e6ae02ac078..aa4457fc8c22 100644 > --- a/sys/sys/random.h > +++ b/sys/sys/random.h > @@ -102,6 +102,7 @@ enum random_entropy_source { > RANDOM_PURE_TPM, > RANDOM_PURE_VMGENID, > RANDOM_PURE_QUALCOMM, > + RANDOM_PURE_ARMV8, > ENTROPYSOURCE > }; > _Static_assert(ENTROPYSOURCE <=3D 32,
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?E302C81B-CAA0-4122-8754-FE9F055C3FBB>