All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL
@ 2022-07-27 14:32 Michael Ellerman
  2022-07-27 14:32 ` [PATCH v6 2/3] powerpc/powernv/kvm: Use darn for H_RANDOM on Power9 Michael Ellerman
                   ` (2 more replies)
  0 siblings, 3 replies; 4+ messages in thread
From: Michael Ellerman @ 2022-07-27 14:32 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Jason

On a bare-metal Power8 system that doesn't have an "ibm,power-rng", a
malicious QEMU and guest that ignore the absence of the
KVM_CAP_PPC_HWRNG flag, and calls H_RANDOM anyway, will dereference a
NULL pointer.

In practice all Power8 machines have an "ibm,power-rng", but let's not
rely on that, add a NULL check and early return in
powernv_get_random_real_mode().

Cc: stable@vger.kernel.org # v4.1+
Fixes: e928e9cb3601 ("KVM: PPC: Book3S HV: Add fast real-mode H_RANDOM implementation.")
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
---
 arch/powerpc/platforms/powernv/rng.c | 2 ++
 1 file changed, 2 insertions(+)

v6: New patch, though change log based on Jason's original.

diff --git a/arch/powerpc/platforms/powernv/rng.c b/arch/powerpc/platforms/powernv/rng.c
index 3805ad13b8f3..2287c9cd0cd5 100644
--- a/arch/powerpc/platforms/powernv/rng.c
+++ b/arch/powerpc/platforms/powernv/rng.c
@@ -63,6 +63,8 @@ int powernv_get_random_real_mode(unsigned long *v)
 	struct powernv_rng *rng;
 
 	rng = raw_cpu_read(powernv_rng);
+	if (!rng)
+		return 0;
 
 	*v = rng_whiten(rng, __raw_rm_readq(rng->regs_real));
 
-- 
2.35.3


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* [PATCH v6 2/3] powerpc/powernv/kvm: Use darn for H_RANDOM on Power9
  2022-07-27 14:32 [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman
@ 2022-07-27 14:32 ` Michael Ellerman
  2022-07-27 14:32 ` [PATCH v6 3/3] powerpc/powernv: rename remaining rng powernv_ functions to pnv_ Michael Ellerman
  2022-07-29 13:03 ` [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman
  2 siblings, 0 replies; 4+ messages in thread
From: Michael Ellerman @ 2022-07-27 14:32 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Jason

From: "Jason A. Donenfeld" <Jason@zx2c4.com>

The existing logic in KVM to support guests calling H_RANDOM only works
on Power8, because it looks for an RNG in the device tree, but on Power9
we just use darn.

In addition the existing code needs to work in real mode, so we have the
special cased powernv_get_random_real_mode() to deal with that.

Instead just have KVM call ppc_md.get_random_seed(), and do the real
mode check inside of there, that way we use whatever RNG is available,
including darn on Power9.

Cc: stable@vger.kernel.org # v4.1+
Tested-by: Sachin Sant <sachinp@linux.ibm.com>
Fixes: e928e9cb3601 ("KVM: PPC: Book3S HV: Add fast real-mode H_RANDOM implementation.")
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
[mpe: Rebase on previous commit, update change log appropriately]
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
---
 arch/powerpc/include/asm/archrandom.h |  5 ----
 arch/powerpc/kvm/book3s_hv_builtin.c  |  7 +++---
 arch/powerpc/platforms/powernv/rng.c  | 36 ++++++---------------------
 3 files changed, 12 insertions(+), 36 deletions(-)

v6: Rebased on previous fix commit.

diff --git a/arch/powerpc/include/asm/archrandom.h b/arch/powerpc/include/asm/archrandom.h
index 9a53e29680f4..258174304904 100644
--- a/arch/powerpc/include/asm/archrandom.h
+++ b/arch/powerpc/include/asm/archrandom.h
@@ -38,12 +38,7 @@ static inline bool __must_check arch_get_random_seed_int(unsigned int *v)
 #endif /* CONFIG_ARCH_RANDOM */
 
 #ifdef CONFIG_PPC_POWERNV
-int powernv_hwrng_present(void);
 int powernv_get_random_long(unsigned long *v);
-int powernv_get_random_real_mode(unsigned long *v);
-#else
-static inline int powernv_hwrng_present(void) { return 0; }
-static inline int powernv_get_random_real_mode(unsigned long *v) { return 0; }
 #endif
 
 #endif /* _ASM_POWERPC_ARCHRANDOM_H */
diff --git a/arch/powerpc/kvm/book3s_hv_builtin.c b/arch/powerpc/kvm/book3s_hv_builtin.c
index 88a8f6473c4e..3abaef5f9ac2 100644
--- a/arch/powerpc/kvm/book3s_hv_builtin.c
+++ b/arch/powerpc/kvm/book3s_hv_builtin.c
@@ -19,7 +19,7 @@
 #include <asm/interrupt.h>
 #include <asm/kvm_ppc.h>
 #include <asm/kvm_book3s.h>
-#include <asm/archrandom.h>
+#include <asm/machdep.h>
 #include <asm/xics.h>
 #include <asm/xive.h>
 #include <asm/dbell.h>
@@ -176,13 +176,14 @@ EXPORT_SYMBOL_GPL(kvmppc_hcall_impl_hv_realmode);
 
 int kvmppc_hwrng_present(void)
 {
-	return powernv_hwrng_present();
+	return ppc_md.get_random_seed != NULL;
 }
 EXPORT_SYMBOL_GPL(kvmppc_hwrng_present);
 
 long kvmppc_rm_h_random(struct kvm_vcpu *vcpu)
 {
-	if (powernv_get_random_real_mode(&vcpu->arch.regs.gpr[4]))
+	if (ppc_md.get_random_seed &&
+	    ppc_md.get_random_seed(&vcpu->arch.regs.gpr[4]))
 		return H_SUCCESS;
 
 	return H_HARDWARE;
diff --git a/arch/powerpc/platforms/powernv/rng.c b/arch/powerpc/platforms/powernv/rng.c
index 2287c9cd0cd5..d19305292e1e 100644
--- a/arch/powerpc/platforms/powernv/rng.c
+++ b/arch/powerpc/platforms/powernv/rng.c
@@ -29,15 +29,6 @@ struct powernv_rng {
 
 static DEFINE_PER_CPU(struct powernv_rng *, powernv_rng);
 
-int powernv_hwrng_present(void)
-{
-	struct powernv_rng *rng;
-
-	rng = get_cpu_var(powernv_rng);
-	put_cpu_var(rng);
-	return rng != NULL;
-}
-
 static unsigned long rng_whiten(struct powernv_rng *rng, unsigned long val)
 {
 	unsigned long parity;
@@ -58,19 +49,6 @@ static unsigned long rng_whiten(struct powernv_rng *rng, unsigned long val)
 	return val;
 }
 
-int powernv_get_random_real_mode(unsigned long *v)
-{
-	struct powernv_rng *rng;
-
-	rng = raw_cpu_read(powernv_rng);
-	if (!rng)
-		return 0;
-
-	*v = rng_whiten(rng, __raw_rm_readq(rng->regs_real));
-
-	return 1;
-}
-
 static int powernv_get_random_darn(unsigned long *v)
 {
 	unsigned long val;
@@ -107,12 +85,14 @@ int powernv_get_random_long(unsigned long *v)
 {
 	struct powernv_rng *rng;
 
-	rng = get_cpu_var(powernv_rng);
-
-	*v = rng_whiten(rng, in_be64(rng->regs));
-
-	put_cpu_var(rng);
-
+	if (mfmsr() & MSR_DR) {
+		rng = get_cpu_var(powernv_rng);
+		*v = rng_whiten(rng, in_be64(rng->regs));
+		put_cpu_var(rng);
+	} else {
+		rng = raw_cpu_read(powernv_rng);
+		*v = rng_whiten(rng, __raw_rm_readq(rng->regs_real));
+	}
 	return 1;
 }
 EXPORT_SYMBOL_GPL(powernv_get_random_long);
-- 
2.35.3


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* [PATCH v6 3/3] powerpc/powernv: rename remaining rng powernv_ functions to pnv_
  2022-07-27 14:32 [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman
  2022-07-27 14:32 ` [PATCH v6 2/3] powerpc/powernv/kvm: Use darn for H_RANDOM on Power9 Michael Ellerman
@ 2022-07-27 14:32 ` Michael Ellerman
  2022-07-29 13:03 ` [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman
  2 siblings, 0 replies; 4+ messages in thread
From: Michael Ellerman @ 2022-07-27 14:32 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Jason

From: "Jason A. Donenfeld" <Jason@zx2c4.com>

The preferred nomenclature is pnv_, not powernv_, but rng.c used
powernv_ for some reason, which isn't consistent with the rest. A recent
commit added a few pnv_ functions to rng.c, making the file a bit of a
mishmash. This commit just replaces the rest of them.

Tested-by: Sachin Sant <sachinp@linux.ibm.com>
Fixes: f3eac426657d ("powerpc/powernv: wire up rng during setup_arch")
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
[mpe: Reorder after bug fix commits]
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
---
 arch/powerpc/include/asm/archrandom.h |  2 +-
 arch/powerpc/platforms/powernv/rng.c  | 34 +++++++++++++--------------
 drivers/char/hw_random/powernv-rng.c  |  2 +-
 3 files changed, 19 insertions(+), 19 deletions(-)

v6: Reorderd after previous two fix commits.

diff --git a/arch/powerpc/include/asm/archrandom.h b/arch/powerpc/include/asm/archrandom.h
index 258174304904..3af27bb84a3d 100644
--- a/arch/powerpc/include/asm/archrandom.h
+++ b/arch/powerpc/include/asm/archrandom.h
@@ -38,7 +38,7 @@ static inline bool __must_check arch_get_random_seed_int(unsigned int *v)
 #endif /* CONFIG_ARCH_RANDOM */
 
 #ifdef CONFIG_PPC_POWERNV
-int powernv_get_random_long(unsigned long *v);
+int pnv_get_random_long(unsigned long *v);
 #endif
 
 #endif /* _ASM_POWERPC_ARCHRANDOM_H */
diff --git a/arch/powerpc/platforms/powernv/rng.c b/arch/powerpc/platforms/powernv/rng.c
index d19305292e1e..196aa70fe043 100644
--- a/arch/powerpc/platforms/powernv/rng.c
+++ b/arch/powerpc/platforms/powernv/rng.c
@@ -21,15 +21,15 @@
 
 #define DARN_ERR 0xFFFFFFFFFFFFFFFFul
 
-struct powernv_rng {
+struct pnv_rng {
 	void __iomem *regs;
 	void __iomem *regs_real;
 	unsigned long mask;
 };
 
-static DEFINE_PER_CPU(struct powernv_rng *, powernv_rng);
+static DEFINE_PER_CPU(struct pnv_rng *, pnv_rng);
 
-static unsigned long rng_whiten(struct powernv_rng *rng, unsigned long val)
+static unsigned long rng_whiten(struct pnv_rng *rng, unsigned long val)
 {
 	unsigned long parity;
 
@@ -49,7 +49,7 @@ static unsigned long rng_whiten(struct powernv_rng *rng, unsigned long val)
 	return val;
 }
 
-static int powernv_get_random_darn(unsigned long *v)
+static int pnv_get_random_darn(unsigned long *v)
 {
 	unsigned long val;
 
@@ -73,31 +73,31 @@ static int __init initialise_darn(void)
 		return -ENODEV;
 
 	for (i = 0; i < 10; i++) {
-		if (powernv_get_random_darn(&val)) {
-			ppc_md.get_random_seed = powernv_get_random_darn;
+		if (pnv_get_random_darn(&val)) {
+			ppc_md.get_random_seed = pnv_get_random_darn;
 			return 0;
 		}
 	}
 	return -EIO;
 }
 
-int powernv_get_random_long(unsigned long *v)
+int pnv_get_random_long(unsigned long *v)
 {
-	struct powernv_rng *rng;
+	struct pnv_rng *rng;
 
 	if (mfmsr() & MSR_DR) {
-		rng = get_cpu_var(powernv_rng);
+		rng = get_cpu_var(pnv_rng);
 		*v = rng_whiten(rng, in_be64(rng->regs));
 		put_cpu_var(rng);
 	} else {
-		rng = raw_cpu_read(powernv_rng);
+		rng = raw_cpu_read(pnv_rng);
 		*v = rng_whiten(rng, __raw_rm_readq(rng->regs_real));
 	}
 	return 1;
 }
-EXPORT_SYMBOL_GPL(powernv_get_random_long);
+EXPORT_SYMBOL_GPL(pnv_get_random_long);
 
-static __init void rng_init_per_cpu(struct powernv_rng *rng,
+static __init void rng_init_per_cpu(struct pnv_rng *rng,
 				    struct device_node *dn)
 {
 	int chip_id, cpu;
@@ -107,16 +107,16 @@ static __init void rng_init_per_cpu(struct powernv_rng *rng,
 		pr_warn("No ibm,chip-id found for %pOF.\n", dn);
 
 	for_each_possible_cpu(cpu) {
-		if (per_cpu(powernv_rng, cpu) == NULL ||
+		if (per_cpu(pnv_rng, cpu) == NULL ||
 		    cpu_to_chip_id(cpu) == chip_id) {
-			per_cpu(powernv_rng, cpu) = rng;
+			per_cpu(pnv_rng, cpu) = rng;
 		}
 	}
 }
 
 static __init int rng_create(struct device_node *dn)
 {
-	struct powernv_rng *rng;
+	struct pnv_rng *rng;
 	struct resource res;
 	unsigned long val;
 
@@ -142,7 +142,7 @@ static __init int rng_create(struct device_node *dn)
 
 	rng_init_per_cpu(rng, dn);
 
-	ppc_md.get_random_seed = powernv_get_random_long;
+	ppc_md.get_random_seed = pnv_get_random_long;
 
 	return 0;
 }
@@ -190,7 +190,7 @@ static int __init pnv_rng_late_init(void)
 	if (ppc_md.get_random_seed == pnv_get_random_long_early)
 		pnv_get_random_long_early(&v);
 
-	if (ppc_md.get_random_seed == powernv_get_random_long) {
+	if (ppc_md.get_random_seed == pnv_get_random_long) {
 		for_each_compatible_node(dn, NULL, "ibm,power-rng")
 			of_platform_device_create(dn, NULL, NULL);
 	}
diff --git a/drivers/char/hw_random/powernv-rng.c b/drivers/char/hw_random/powernv-rng.c
index 8da1d7917bdc..429e956f34e1 100644
--- a/drivers/char/hw_random/powernv-rng.c
+++ b/drivers/char/hw_random/powernv-rng.c
@@ -23,7 +23,7 @@ static int powernv_rng_read(struct hwrng *rng, void *data, size_t max, bool wait
 	buf = (unsigned long *)data;
 
 	for (i = 0; i < len; i++)
-		powernv_get_random_long(buf++);
+		pnv_get_random_long(buf++);
 
 	return len * sizeof(unsigned long);
 }
-- 
2.35.3


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* Re: [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL
  2022-07-27 14:32 [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman
  2022-07-27 14:32 ` [PATCH v6 2/3] powerpc/powernv/kvm: Use darn for H_RANDOM on Power9 Michael Ellerman
  2022-07-27 14:32 ` [PATCH v6 3/3] powerpc/powernv: rename remaining rng powernv_ functions to pnv_ Michael Ellerman
@ 2022-07-29 13:03 ` Michael Ellerman
  2 siblings, 0 replies; 4+ messages in thread
From: Michael Ellerman @ 2022-07-29 13:03 UTC (permalink / raw)
  To: Michael Ellerman, linuxppc-dev; +Cc: Jason

On Thu, 28 Jul 2022 00:32:17 +1000, Michael Ellerman wrote:
> On a bare-metal Power8 system that doesn't have an "ibm,power-rng", a
> malicious QEMU and guest that ignore the absence of the
> KVM_CAP_PPC_HWRNG flag, and calls H_RANDOM anyway, will dereference a
> NULL pointer.
> 
> In practice all Power8 machines have an "ibm,power-rng", but let's not
> rely on that, add a NULL check and early return in
> powernv_get_random_real_mode().
> 
> [...]

Applied to powerpc/next.

[1/3] powerpc/powernv: Avoid crashing if rng is NULL
      https://git.kernel.org/powerpc/c/90b5d4fe0b3ba7f589c6723c6bfb559d9e83956a
[2/3] powerpc/powernv/kvm: Use darn for H_RANDOM on Power9
      https://git.kernel.org/powerpc/c/7ef3d06f1bc4a5e62273726f3dc2bd258ae1c71f
[3/3] powerpc/powernv: rename remaining rng powernv_ functions to pnv_
      https://git.kernel.org/powerpc/c/978030f054ff97d9079b35f0178e2013918fb316

cheers

^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2022-07-29 13:17 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-07-27 14:32 [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman
2022-07-27 14:32 ` [PATCH v6 2/3] powerpc/powernv/kvm: Use darn for H_RANDOM on Power9 Michael Ellerman
2022-07-27 14:32 ` [PATCH v6 3/3] powerpc/powernv: rename remaining rng powernv_ functions to pnv_ Michael Ellerman
2022-07-29 13:03 ` [PATCH v6 1/3] powerpc/powernv: Avoid crashing if rng is NULL Michael Ellerman

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.