Date: Sat, 9 Oct 2004 22:37:39 GMT From: Robert Watson <rwatson@FreeBSD.org> To: Perforce Change Reviews <perforce@freebsd.org> Subject: PERFORCE change 62928 for review Message-ID: <200410092237.i99Mbd61027942@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=62928 Change 62928 by rwatson@rwatson_fledge on 2004/10/09 22:36:38 Integrate netperf_socket: - Loop back /dev/random locking strategy revitalization from rwatson_netperf. Affected files ... .. //depot/projects/netperf_socket/sys/dev/random/randomdev_soft.c#5 integrate .. //depot/projects/netperf_socket/sys/ufs/ffs/fs.h#6 integrate Differences ... ==== //depot/projects/netperf_socket/sys/dev/random/randomdev_soft.c#5 (text+ko) ==== @@ -1,5 +1,6 @@ /*- * Copyright (c) 2000-2004 Mark R V Murray + * Copyright (c) 2004 Robert N. M. Watson * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -72,9 +73,14 @@ MALLOC_DEFINE(M_ENTROPY, "entropy", "Entropy harvesting buffers"); +/* + * The harvest mutex protects the consistency of the entropy fifos and + * empty fifo. + */ +struct mtx harvest_mtx; + /* Lockable FIFO queue holding entropy buffers */ struct entropyfifo { - struct mtx lock; int count; STAILQ_HEAD(harvestlist, harvest) head; }; @@ -166,7 +172,6 @@ /* Initialise the harvest fifos */ STAILQ_INIT(&emptyfifo.head); emptyfifo.count = 0; - mtx_init(&emptyfifo.lock, "entropy harvest buffers", NULL, MTX_SPIN); for (i = 0; i < EMPTYBUFFERS; i++) { np = malloc(sizeof(struct harvest), M_ENTROPY, M_WAITOK); STAILQ_INSERT_TAIL(&emptyfifo.head, np, next); @@ -174,10 +179,10 @@ for (e = RANDOM_START; e < ENTROPYSOURCE; e++) { STAILQ_INIT(&harvestfifo[e].head); harvestfifo[e].count = 0; - mtx_init(&harvestfifo[e].lock, "entropy harvest", NULL, - MTX_SPIN); } + mtx_init(&harvest_mtx, "entropy harvest mutex", NULL, MTX_SPIN); + /* Start the hash/reseed thread */ error = kthread_create(random_kthread, NULL, &random_kthread_proc, RFHIGHPID, 0, "yarrow"); @@ -211,18 +216,18 @@ STAILQ_REMOVE_HEAD(&emptyfifo.head, next); free(np, M_ENTROPY); } - mtx_destroy(&emptyfifo.lock); for (e = RANDOM_START; e < ENTROPYSOURCE; e++) { while (!STAILQ_EMPTY(&harvestfifo[e].head)) { np = STAILQ_FIRST(&harvestfifo[e].head); STAILQ_REMOVE_HEAD(&harvestfifo[e].head, next); free(np, M_ENTROPY); } - mtx_destroy(&harvestfifo[e].lock); } random_yarrow_deinit_alg(); + mtx_destroy(&harvest_mtx); + sysctl_ctx_free(&random_clist); } @@ -230,52 +235,52 @@ static void random_kthread(void *arg __unused) { + STAILQ_HEAD(, harvest) local_queue; struct harvest *event = NULL; - int found, active; + int active; enum esource source; + STAILQ_INIT(&local_queue); + /* Process until told to stop */ for (; random_kthread_control == 0;) { active = 0; /* Cycle through all the entropy sources */ + mtx_lock_spin(&harvest_mtx); for (source = RANDOM_START; source < ENTROPYSOURCE; source++) { - - found = 0; - - /* Lock up queue draining */ - mtx_lock_spin(&harvestfifo[source].lock); - - if (!STAILQ_EMPTY(&harvestfifo[source].head)) { - + /* + * Drain entropy source records into a thread-local + * queue for processing while not holding the mutex. + */ + while ((event = + STAILQ_FIRST(&harvestfifo[source].head)) != NULL) { /* Get a harvested entropy event */ harvestfifo[source].count--; - event = STAILQ_FIRST(&harvestfifo[source].head); STAILQ_REMOVE_HEAD(&harvestfifo[source].head, next); - - active = found = 1; - + STAILQ_INSERT_TAIL(&local_queue, event, next); } - /* Unlock the queue */ - mtx_unlock_spin(&harvestfifo[source].lock); + } - /* Deal with the event and dispose of it */ - if (found) { - + /* + * Deal with events, if any, dropping the mutex as we process + * each event. Then push the events back into the empty + * fifo. + */ + if (!STAILQ_EMPTY(&local_queue)) { + mtx_unlock_spin(&harvest_mtx); + STAILQ_FOREACH(event, &local_queue, next) random_process_event(event); - - /* Lock the empty event buffer fifo */ - mtx_lock_spin(&emptyfifo.lock); - + mtx_lock_spin(&harvest_mtx); + while ((event = STAILQ_FIRST(&local_queue)) != NULL) { + STAILQ_REMOVE_HEAD(&local_queue, next); STAILQ_INSERT_TAIL(&emptyfifo.head, event, next); - - mtx_unlock_spin(&emptyfifo.lock); - } } + mtx_unlock_spin(&harvest_mtx); /* Found nothing, so don't belabour the issue */ if (!active) @@ -300,30 +305,17 @@ if (harvestfifo[origin].count >= RANDOM_FIFO_MAX) return; - /* Lock the particular fifo */ - mtx_lock_spin(&harvestfifo[origin].lock); + mtx_lock_spin(&harvest_mtx); /* * Don't make the harvest queues too big - help to prevent low-grade * entropy swamping */ if (harvestfifo[origin].count < RANDOM_FIFO_MAX) { - - /* Lock the empty event buffer fifo */ - mtx_lock_spin(&emptyfifo.lock); - - if (!STAILQ_EMPTY(&emptyfifo.head)) { - event = STAILQ_FIRST(&emptyfifo.head); + event = STAILQ_FIRST(&emptyfifo.head); + if (event != NULL) { + /* Add the harvested data to the fifo */ STAILQ_REMOVE_HEAD(&emptyfifo.head, next); - } else - event = NULL; - - mtx_unlock_spin(&emptyfifo.lock); - - /* If we didn't obtain a buffer, tough */ - if (event) { - - /* Add the harvested data to the fifo */ harvestfifo[origin].count++; event->somecounter = somecounter; event->size = count; @@ -339,8 +331,7 @@ event, next); } } - mtx_unlock_spin(&harvestfifo[origin].lock); - + mtx_unlock_spin(&harvest_mtx); } void ==== //depot/projects/netperf_socket/sys/ufs/ffs/fs.h#6 (text+ko) ==== @@ -27,7 +27,7 @@ * SUCH DAMAGE. * * @(#)fs.h 8.13 (Berkeley) 3/21/95 - * $FreeBSD: src/sys/ufs/ffs/fs.h,v 1.44 2004/08/19 11:09:13 jhb Exp $ + * $FreeBSD: src/sys/ufs/ffs/fs.h,v 1.45 2004/10/09 20:16:06 njl Exp $ */ #ifndef _UFS_FFS_FS_H_ @@ -486,7 +486,7 @@ * Turn filesystem block numbers into disk block addresses. * This maps filesystem blocks to device size blocks. */ -#define fsbtodb(fs, b) ((b) << (fs)->fs_fsbtodb) +#define fsbtodb(fs, b) ((daddr_t)(b) << (fs)->fs_fsbtodb) #define dbtofsb(fs, b) ((b) >> (fs)->fs_fsbtodb) /*
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200410092237.i99Mbd61027942>