This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc project.
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |
Other format: | [Raw text] |
On Thu, Jun 12, 2014 at 11:37:16AM -0500, Meador Inge wrote: > The implementation of __get_nprocs uses a stactic variable to cache > the value of the current number of processors. The caching breaks when > 'time (NULL) == 0': > > $ cat nproc.c > #include <stdio.h> > #include <time.h> > #include <sys/time.h> > > int main(int argc, char *argv[]) > { > time_t t; > struct timeval tv = {0, 0}; > printf("settimeofday({0, 0}, NULL) = %d\n", settimeofday(&tv, NULL)); > t = time(NULL); > printf("Time: %d, CPUs: %d\n", (unsigned int)t, get_nprocs()); > return 0; > } > $ gcc -O3 nproc.c > $ ./a.out > settimeofday({0, 0}, NULL) = -1 > Time: 1401311578, CPUs: 4 > $ sudo ./a.out > settimeofday({0, 0}, NULL) = 0 > Time: 0, CPUs: 0 > > The problem is with the condition used to check whether a cached > value should be returned or not: > > static int cached_result; > static time_t timestamp; > > time_t now = time (NULL); > time_t prev = timestamp; > atomic_read_barrier (); > if (now == prev) > return cached_result; > > When 'timestamp == 0', as in the above test case, an unitialized > cache value is returned. > > This patch fixes the problem by ensuring that 'cached_result' has > been set at least once before returning it. > > I checked for regressions with 'make check' and verified that the > described test case works, but couldn't find a good way to automate > the test in the GLIBC testsuite. > > OK? > > 2014-06-12 Meador Inge <meadori@codesourcery.com> > > [BZ #16996] > sysdeps/unix/sysv/linux/getsysstats.c (__get_nprocs): Ensure that > the cached result has been set before returning it. > > --- > sysdeps/unix/sysv/linux/getsysstats.c | 4 ++-- > 1 file changed, 2 insertions(+), 2 deletions(-) > > diff --git a/sysdeps/unix/sysv/linux/getsysstats.c b/sysdeps/unix/sysv/linux/getsysstats.c > index b6a6fe3..755c259 100644 > --- a/sysdeps/unix/sysv/linux/getsysstats.c > +++ b/sysdeps/unix/sysv/linux/getsysstats.c > @@ -126,13 +126,13 @@ next_line (int fd, char *const buffer, char **cp, char **re, > int > __get_nprocs (void) > { > - static int cached_result; > + static int cached_result = -1; > static time_t timestamp; > > time_t now = time (NULL); > time_t prev = timestamp; > atomic_read_barrier (); > - if (now == prev) > + if (now == prev && cached_result > -1) Wouldn't (now == prev && now > 0) be nicer? Siddhesh > return cached_result; > > /* XXX Here will come a test for the new system call. */ > -- > 1.7.9.5 >
Attachment:
pgpiQAAirp31f.pgp
Description: PGP signature
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |