On Tue, Jul 17, 2018 at 05:01:42PM +0200, Peter Zijlstra wrote: > On Thu, Jul 12, 2018 at 01:29:40PM -0400, Johannes Weiner wrote: > > +static bool psi_update_stats(struct psi_group *group) > > +{ > > + u64 some[NR_PSI_RESOURCES] = { 0, }; > > + u64 full[NR_PSI_RESOURCES] = { 0, }; > > + unsigned long nonidle_total = 0; > > + unsigned long missed_periods; > > + unsigned long expires; > > + int cpu; > > + int r; > > + > > + mutex_lock(&group->stat_lock); > > + > > + /* > > + * Collect the per-cpu time buckets and average them into a > > + * single time sample that is normalized to wallclock time. > > + * > > + * For averaging, each CPU is weighted by its non-idle time in > > + * the sampling period. This eliminates artifacts from uneven > > + * loading, or even entirely idle CPUs. > > + * > > + * We could pin the online CPUs here, but the noise introduced > > + * by missing up to one sample period from CPUs that are going > > + * away shouldn't matter in practice - just like the noise of > > + * previously offlined CPUs returning with a non-zero sample. > > But why!? cpuu_read_lock() is neither expensive nor complicated. So why > try and avoid it? Hm, I don't feel strongly about it either way. I'll add it. > > + /* total= */ > > + for (r = 0; r < NR_PSI_RESOURCES; r++) { > > + do_div(some[r], max(nonidle_total, 1UL)); > > + do_div(full[r], max(nonidle_total, 1UL)); > > + > > + group->some[r] += some[r]; > > + group->full[r] += full[r]; > > group->some[r] = div64_ul(some[r], max(nonidle_total, 1UL)); > group->full[r] = div64_ul(full[r], max(nonidle_total, 1UL)); > > Is easier to read imo. Sounds good to me, I'll change that.