diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-27 10:05:51 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-27 10:05:51 +0000 |
commit | 5d1646d90e1f2cceb9f0828f4b28318cd0ec7744 (patch) | |
tree | a94efe259b9009378be6d90eb30d2b019d95c194 /arch/x86/include/asm/archrandom.h | |
parent | Initial commit. (diff) | |
download | linux-5d1646d90e1f2cceb9f0828f4b28318cd0ec7744.tar.xz linux-5d1646d90e1f2cceb9f0828f4b28318cd0ec7744.zip |
Adding upstream version 5.10.209.upstream/5.10.209upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'arch/x86/include/asm/archrandom.h')
-rw-r--r-- | arch/x86/include/asm/archrandom.h | 101 |
1 files changed, 101 insertions, 0 deletions
diff --git a/arch/x86/include/asm/archrandom.h b/arch/x86/include/asm/archrandom.h new file mode 100644 index 000000000..ebc248e49 --- /dev/null +++ b/arch/x86/include/asm/archrandom.h @@ -0,0 +1,101 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +/* + * This file is part of the Linux kernel. + * + * Copyright (c) 2011-2014, Intel Corporation + * Authors: Fenghua Yu <fenghua.yu@intel.com>, + * H. Peter Anvin <hpa@linux.intel.com> + */ + +#ifndef ASM_X86_ARCHRANDOM_H +#define ASM_X86_ARCHRANDOM_H + +#include <asm/processor.h> +#include <asm/cpufeature.h> + +#define RDRAND_RETRY_LOOPS 10 + +/* Unconditional execution of RDRAND and RDSEED */ + +static inline bool __must_check rdrand_long(unsigned long *v) +{ + bool ok; + unsigned int retry = RDRAND_RETRY_LOOPS; + do { + asm volatile("rdrand %[out]" + CC_SET(c) + : CC_OUT(c) (ok), [out] "=r" (*v)); + if (ok) + return true; + } while (--retry); + return false; +} + +static inline bool __must_check rdrand_int(unsigned int *v) +{ + bool ok; + unsigned int retry = RDRAND_RETRY_LOOPS; + do { + asm volatile("rdrand %[out]" + CC_SET(c) + : CC_OUT(c) (ok), [out] "=r" (*v)); + if (ok) + return true; + } while (--retry); + return false; +} + +static inline bool __must_check rdseed_long(unsigned long *v) +{ + bool ok; + asm volatile("rdseed %[out]" + CC_SET(c) + : CC_OUT(c) (ok), [out] "=r" (*v)); + return ok; +} + +static inline bool __must_check rdseed_int(unsigned int *v) +{ + bool ok; + asm volatile("rdseed %[out]" + CC_SET(c) + : CC_OUT(c) (ok), [out] "=r" (*v)); + return ok; +} + +/* + * These are the generic interfaces; they must not be declared if the + * stubs in <linux/random.h> are to be invoked, + * i.e. CONFIG_ARCH_RANDOM is not defined. + */ +#ifdef CONFIG_ARCH_RANDOM + +static inline bool __must_check arch_get_random_long(unsigned long *v) +{ + return static_cpu_has(X86_FEATURE_RDRAND) ? rdrand_long(v) : false; +} + +static inline bool __must_check arch_get_random_int(unsigned int *v) +{ + return static_cpu_has(X86_FEATURE_RDRAND) ? rdrand_int(v) : false; +} + +static inline bool __must_check arch_get_random_seed_long(unsigned long *v) +{ + return static_cpu_has(X86_FEATURE_RDSEED) ? rdseed_long(v) : false; +} + +static inline bool __must_check arch_get_random_seed_int(unsigned int *v) +{ + return static_cpu_has(X86_FEATURE_RDSEED) ? rdseed_int(v) : false; +} + +extern void x86_init_rdrand(struct cpuinfo_x86 *c); + +#else /* !CONFIG_ARCH_RANDOM */ + +static inline void x86_init_rdrand(struct cpuinfo_x86 *c) { } + +#endif /* !CONFIG_ARCH_RANDOM */ + +#endif /* ASM_X86_ARCHRANDOM_H */ |