Module Name: src Committed By: riastradh Date: Mon Dec 20 23:05:55 UTC 2021
Modified Files: src/sys/dev/ic: tpm.c tpmvar.h Log Message: tpm(4): Fix disabling of rnd source if tpm is deactivated. Nothing prevents a second worker from being queued when the first one is about to do rnd_detach_source. Instead, just set a flag so future requests don't bother running a new thread; if there's a concurrent one that's already been scheduled on another CPU, well, too bad, we get a couple extra log messages but that's fine. A better way to do this would probably be to detect whether the tpm is deactivated at attach time, but that requires reading more of the tpm spec than I care to do when there are alternative ways to procrastinate like scrubbing the toilet. To generate a diff of this commit: cvs rdiff -u -r1.22 -r1.23 src/sys/dev/ic/tpm.c cvs rdiff -u -r1.9 -r1.10 src/sys/dev/ic/tpmvar.h Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/dev/ic/tpm.c diff -u src/sys/dev/ic/tpm.c:1.22 src/sys/dev/ic/tpm.c:1.23 --- src/sys/dev/ic/tpm.c:1.22 Wed Jun 2 21:35:17 2021 +++ src/sys/dev/ic/tpm.c Mon Dec 20 23:05:55 2021 @@ -1,4 +1,4 @@ -/* $NetBSD: tpm.c,v 1.22 2021/06/02 21:35:17 riastradh Exp $ */ +/* $NetBSD: tpm.c,v 1.23 2021/12/20 23:05:55 riastradh Exp $ */ /* * Copyright (c) 2019 The NetBSD Foundation, Inc. @@ -48,7 +48,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: tpm.c,v 1.22 2021/06/02 21:35:17 riastradh Exp $"); +__KERNEL_RCSID(0, "$NetBSD: tpm.c,v 1.23 2021/12/20 23:05:55 riastradh Exp $"); #include <sys/param.h> #include <sys/types.h> @@ -650,7 +650,7 @@ tpm_rng_work(struct work *wk, void *cook */ if (rv) { device_printf(sc->sc_dev, "deactivating entropy source\n"); - rnd_detach_source(&sc->sc_rnd); + atomic_store_relaxed(&sc->sc_rnddisabled, true); /* XXX worker thread can't workqueue_destroy its own queue */ } @@ -666,6 +666,8 @@ tpm_rng_get(size_t nbytes, void *cookie) { struct tpm_softc *sc = cookie; + if (atomic_load_relaxed(&sc->sc_rnddisabled)) + return; /* tough */ if (atomic_swap_uint(&sc->sc_rndpending, MIN(nbytes, UINT_MAX/NBBY)) == 0) workqueue_enqueue(sc->sc_rndwq, &sc->sc_rndwk, NULL); Index: src/sys/dev/ic/tpmvar.h diff -u src/sys/dev/ic/tpmvar.h:1.9 src/sys/dev/ic/tpmvar.h:1.10 --- src/sys/dev/ic/tpmvar.h:1.9 Mon Jan 4 18:26:59 2021 +++ src/sys/dev/ic/tpmvar.h Mon Dec 20 23:05:55 2021 @@ -1,4 +1,4 @@ -/* $NetBSD: tpmvar.h,v 1.9 2021/01/04 18:26:59 riastradh Exp $ */ +/* $NetBSD: tpmvar.h,v 1.10 2021/12/20 23:05:55 riastradh Exp $ */ /* * Copyright (c) 2019 The NetBSD Foundation, Inc. @@ -98,6 +98,7 @@ struct tpm_softc { struct workqueue *sc_rndwq; struct work sc_rndwk; volatile unsigned sc_rndpending; + bool sc_rnddisabled; }; bool tpm_suspend(device_t, const pmf_qual_t *);