diff options
author | mdf <mdf@FreeBSD.org> | 2010-09-13 18:48:23 +0000 |
---|---|---|
committer | mdf <mdf@FreeBSD.org> | 2010-09-13 18:48:23 +0000 |
commit | 3ed6eac561ccce2958e668867ea38fd005bc635b (patch) | |
tree | b0bd953f5f99c28abddea5f8c7bb39d837607940 /sys/kern/subr_sleepqueue.c | |
parent | 9a10f7c4328c6763a33844ed9635ef3c2a7f1e84 (diff) | |
download | FreeBSD-src-3ed6eac561ccce2958e668867ea38fd005bc635b.zip FreeBSD-src-3ed6eac561ccce2958e668867ea38fd005bc635b.tar.gz |
Revert r212370, as it causes a LOR on powerpc. powerpc does a few
unexpected things in copyout(9) and so wiring the user buffer is not
sufficient to perform a copyout(9) while holding a random mutex.
Requested by: nwhitehorn
Diffstat (limited to 'sys/kern/subr_sleepqueue.c')
-rw-r--r-- | sys/kern/subr_sleepqueue.c | 14 |
1 files changed, 11 insertions, 3 deletions
diff --git a/sys/kern/subr_sleepqueue.c b/sys/kern/subr_sleepqueue.c index cdf7a47..b8be8f4 100644 --- a/sys/kern/subr_sleepqueue.c +++ b/sys/kern/subr_sleepqueue.c @@ -1018,7 +1018,7 @@ sleepq_abort(struct thread *td, int intrval) #ifdef SLEEPQUEUE_PROFILING #define SLEEPQ_PROF_LOCATIONS 1024 -#define SLEEPQ_SBUFSIZE 512 +#define SLEEPQ_SBUFSIZE (40 * 512) struct sleepq_prof { LIST_ENTRY(sleepq_prof) sp_link; const char *sp_wmesg; @@ -1123,13 +1123,15 @@ reset_sleepq_prof_stats(SYSCTL_HANDLER_ARGS) static int dump_sleepq_prof_stats(SYSCTL_HANDLER_ARGS) { + static int multiplier = 1; struct sleepq_prof *sp; struct sbuf *sb; int enabled; int error; int i; - sb = sbuf_new_for_sysctl(NULL, NULL, SLEEPQ_SBUFSIZE, req); +retry_sbufops: + sb = sbuf_new(NULL, NULL, SLEEPQ_SBUFSIZE * multiplier, SBUF_FIXEDLEN); sbuf_printf(sb, "\nwmesg\tcount\n"); enabled = prof_enabled; mtx_lock_spin(&sleepq_prof_lock); @@ -1139,13 +1141,19 @@ dump_sleepq_prof_stats(SYSCTL_HANDLER_ARGS) LIST_FOREACH(sp, &sleepq_hash[i], sp_link) { sbuf_printf(sb, "%s\t%ld\n", sp->sp_wmesg, sp->sp_count); + if (sbuf_error(sb) != 0) { + sbuf_delete(sb); + multiplier++; + goto retry_sbufops; + } } } mtx_lock_spin(&sleepq_prof_lock); prof_enabled = enabled; mtx_unlock_spin(&sleepq_prof_lock); - error = sbuf_finish(sb); + sbuf_finish(sb); + error = SYSCTL_OUT(req, sbuf_data(sb), sbuf_len(sb) + 1); sbuf_delete(sb); return (error); } |