From: Matthew Dillon Date: Mon, 20 Jun 2005 07:58:39 +0000 (+0000) Subject: Add a DEBUG_TOKENS option which causes token operations to be logged to X-Git-Tag: v2.0.1~6857 X-Git-Url: https://gitweb.dragonflybsd.org/dragonfly.git/commitdiff_plain/790e4db7fd448163e6421e9652bd73c2dd73f5b7 Add a DEBUG_TOKENS option which causes token operations to be logged to a static array, suitable for post-morten investigation. --- diff --git a/sys/conf/options b/sys/conf/options index 9ced4d7722..c173216253 100644 --- a/sys/conf/options +++ b/sys/conf/options @@ -1,5 +1,5 @@ # $FreeBSD: src/sys/conf/options,v 1.191.2.53 2003/06/04 17:56:58 sam Exp $ -# $DragonFly: src/sys/conf/options,v 1.31 2005/03/01 00:43:02 corecode Exp $ +# $DragonFly: src/sys/conf/options,v 1.32 2005/06/20 07:58:37 dillon Exp $ # # On the handling of kernel options # @@ -406,6 +406,7 @@ BLKDEV_IOSIZE opt_global.h DEBUG opt_global.h DEBUG_LOCKS opt_global.h DEBUG_VFS_LOCKS opt_global.h +DEBUG_TOKENS opt_global.h DIAGNOSTIC opt_global.h INVARIANT_SUPPORT opt_global.h INVARIANTS opt_global.h diff --git a/sys/kern/lwkt_token.c b/sys/kern/lwkt_token.c index 55f8578253..c38e816b82 100644 --- a/sys/kern/lwkt_token.c +++ b/sys/kern/lwkt_token.c @@ -31,7 +31,7 @@ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $DragonFly: src/sys/kern/lwkt_token.c,v 1.17 2005/06/20 07:40:30 dillon Exp $ + * $DragonFly: src/sys/kern/lwkt_token.c,v 1.18 2005/06/20 07:58:39 dillon Exp $ */ #ifdef _KERNEL @@ -102,6 +102,52 @@ static void lwkt_reqtoken_remote(void *data); static lwkt_token pool_tokens[LWKT_NUM_POOL_TOKENS]; +/* + * Token debugging code, log token operations and who called them. + */ +#ifdef DEBUG_TOKENS + +static struct toklog { + enum tokenum { TOKTRY, TOKGET, TOKREL1, TOKREL2, TOKREMOTE, + TOKREQREMOTE, TOKREQFAIL, TOKDRAIN } type; + int toremote; + lwkt_tokref_t ref; + lwkt_token_t tok; + thread_t td; + void *caller; +} toklog[SMP_MAXCPU][2048]; + +static int tokindex[SMP_MAXCPU]; + +static void +logtoken(lwkt_tokref_t ref, void *stackptr, enum tokenum type) +{ + struct toklog *log; + globaldata_t gd; + + if (panicstr == NULL) { + gd = mycpu; + crit_enter(); + log = &toklog[gd->gd_cpuid][tokindex[gd->gd_cpuid]]; + log->type = type; + log->ref = ref; + log->tok = ref->tr_tok; + if (stackptr) + log->caller = ((void **)stackptr)[-1]; + else + log->caller = NULL; + log->td = gd->gd_curthread; + tokindex[gd->gd_cpuid] = (tokindex[gd->gd_cpuid] + 1) & 2047; + crit_exit(); + } +} + +#else + +#define logtoken(ref, stackptr, type) + +#endif + #ifdef _KERNEL #ifdef INVARIANTS @@ -152,9 +198,14 @@ lwkt_chktokens(thread_t td) refs->tr_magic = LWKT_TOKREF_MAGIC2; /* MP synched slowreq*/ refs->tr_reqgd = gd; tok->t_reqcpu = gd; /* MP unsynchronized 'fast' req */ + + logtoken(refs, &td, TOKREQREMOTE); + if (lwkt_send_ipiq_nowait(dgd, lwkt_reqtoken_remote, refs)) { /* failed */ refs->tr_magic = LWKT_TOKREF_MAGIC1; + + logtoken(refs, &td, TOKREQFAIL); break; } } else if (magic != LWKT_TOKREF_MAGIC2) { @@ -380,12 +431,14 @@ void lwkt_gettoken(lwkt_tokref_t ref, lwkt_token_t tok) { lwkt_tokref_init(ref, tok); + logtoken(ref, &ref, TOKGET); _lwkt_gettokref(ref); } void lwkt_gettokref(lwkt_tokref_t ref) { + logtoken(ref, &ref, TOKGET); _lwkt_gettokref(ref); } @@ -393,12 +446,14 @@ int lwkt_trytoken(lwkt_tokref_t ref, lwkt_token_t tok) { lwkt_tokref_init(ref, tok); + logtoken(ref, &ref, TOKTRY); return(_lwkt_trytokref(ref)); } int lwkt_trytokref(lwkt_tokref_t ref) { + logtoken(ref, &ref, TOKTRY); return(_lwkt_trytokref(ref)); } @@ -416,6 +471,7 @@ lwkt_reltoken(lwkt_tokref *_ref) thread_t td; int giveaway; + logtoken(_ref, &_ref, TOKREL1); /* * Guard check and stack check (if in the same stack page). We must * also wait for any action pending on remote cpus which we do by @@ -527,6 +583,7 @@ lwkt_reqtoken_remote(void *data) globaldata_t gd = mycpu; lwkt_token_t tok = ref->tr_tok; + logtoken(ref, &data, TOKREMOTE); /* * We do not have to queue the token if we can give it away * immediately. Otherwise we queue it to our globaldata structure.