From owner-freebsd-bugs@FreeBSD.ORG Sun Mar 13 14:40:03 2005 Return-Path: Delivered-To: freebsd-bugs@hub.freebsd.org Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id 4BBD216A4CE for ; Sun, 13 Mar 2005 14:40:03 +0000 (GMT) Received: from freefall.freebsd.org (freefall.freebsd.org [216.136.204.21]) by mx1.FreeBSD.org (Postfix) with ESMTP id ED0B643D75 for ; Sun, 13 Mar 2005 14:40:02 +0000 (GMT) (envelope-from gnats@FreeBSD.org) Received: from freefall.freebsd.org (gnats@localhost [127.0.0.1]) by freefall.freebsd.org (8.13.3/8.13.3) with ESMTP id j2DEe2fN019164 for ; Sun, 13 Mar 2005 14:40:02 GMT (envelope-from gnats@freefall.freebsd.org) Received: (from gnats@localhost) by freefall.freebsd.org (8.13.3/8.13.1/Submit) id j2DEe2tA019163; Sun, 13 Mar 2005 14:40:02 GMT (envelope-from gnats) Resent-Date: Sun, 13 Mar 2005 14:40:02 GMT Resent-Message-Id: <200503131440.j2DEe2tA019163@freefall.freebsd.org> Resent-From: FreeBSD-gnats-submit@FreeBSD.org (GNATS Filer) Resent-To: freebsd-bugs@FreeBSD.org Resent-Reply-To: FreeBSD-gnats-submit@FreeBSD.org, Pete French Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id 753AC16A4CE for ; Sun, 13 Mar 2005 14:35:54 +0000 (GMT) Received: from mail.ticketswitch.com (mail.ticketswitch.com [194.200.93.188]) by mx1.FreeBSD.org (Postfix) with ESMTP id A0BBC43D5C for ; Sun, 13 Mar 2005 14:35:53 +0000 (GMT) (envelope-from petefrench@ticketswitch.com) Received: from [172.16.1.6] (helo=dilbert.firstcallgroup.co.uk) by mail.ticketswitch.com with esmtp (Exim 4.50 (FreeBSD)) id 1DAUC5-000JVM-Rn for FreeBSD-gnats-submit@freebsd.org; Sun, 13 Mar 2005 14:35:49 +0000 Received: from petefrench by dilbert.firstcallgroup.co.uk with local (Exim 4.43 (FreeBSD)) id 1DAUC1-0002RC-9C for FreeBSD-gnats-submit@freebsd.org; Sun, 13 Mar 2005 14:35:45 +0000 Message-Id: Date: Sun, 13 Mar 2005 14:35:45 +0000 From: Pete French To: FreeBSD-gnats-submit@FreeBSD.org X-Send-Pr-Version: 3.113 Subject: kern/78787: sysconf(_SC_CLK_TCK) may return incorrect value X-BeenThere: freebsd-bugs@freebsd.org X-Mailman-Version: 2.1.1 Precedence: list Reply-To: Pete French List-Id: Bug reports List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 13 Mar 2005 14:40:03 -0000 >Number: 78787 >Category: kern >Synopsis: sysconf(_SC_CLK_TCK) may return incorrect value >Confidential: no >Severity: non-critical >Priority: low >Responsible: freebsd-bugs >State: open >Quarter: >Keywords: >Date-Required: >Class: sw-bug >Submitter-Id: current-users >Arrival-Date: Sun Mar 13 14:40:02 GMT 2005 >Closed-Date: >Last-Modified: >Originator: Pete French >Release: FreeBSD 4.11-RELEASE i386 >Organization: TicketSwitch Limited >Environment: System: FreeBSD dilbert.rattatosk 4.11-RELEASE FreeBSD 4.11-RELEASE #0: Wed Jan 26 12:22:35 GMT 2005 petefrench@dilbert.rattatosk:/usr/obj/usr/src/sys/DILBERT i386 >Description: sysconf(_SC_CLK_TCK) returns a contstant value defined in src/sys/i386/include/ansi.h this is not correct as the actual value of the statistics clock is not a constnat. In particular it is 100Hz on my system, but the constant returned is 128. The stat clock may be 100Hz is apm is enabled with flags 0x20 in the kernel file >How-To-Repeat: Build a kernel which has a statistics clock other tahn 128 and observe that sysconf(_SC_CLK_TCK) returns the wrong value! >Fix: The call to sysconf(_SC_CLK_TCK) should actuallyy query the kernel to get the correct value. Note that this is how /usr/bin/time gets the frequency of the clock. I have included below an analysis of the problem done by someone else on the FreeBSD stable mailing lists, which follwos the code through in more depth. I do not know if this problem still exists in 5 or CURRENT. Response from Jon Noack to my query on -stable ------------------------------------------------------------------- I infer from your kern.clockrate output that you are running 4.x. Why does sysconf(_SC_CLK_TCK) always returns 128? Check out sysconf() in src/lib/libc/gen/sysconf.c (lines 83-84 of rev. 1.10): ********************************************************************** case _SC_CLK_TCK: return (CLK_TCK); ********************************************************************** CLK_TCK is defined in src/include/time.h (line 52 of rev. 1.15): ********************************************************************** #define CLK_TCK _BSD_CLK_TCK_ ********************************************************************** _BSD_CLK_TCK_ is defined in src/sys/i386/include/ansi.h (line 101 of rev. 1.18.2.4): ********************************************************************** #define _BSD_CLK_TCK_ 128 ********************************************************************** So on i386 (and FreeBSD 4.x), sysconf(_SC_CLK_TCK) will always return 128. If you look in src/sys/alpha/include/ansi.h, you'll see that on alpha it will always return 100. To determine how stathz can vary, we'll have to dig deeper. Check out initclocks() in src/sys/kern/kern_clock.c (lines 196-213 of rev. 1.105.2.11): ********************************************************************** /* * Set divisors to 1 (normal case) and let the machine-specific * code do its bit. */ psdiv = pscnt = 1; cpu_initclocks(); #ifdef DEVICE_POLLING init_device_poll(); #endif /* * Compute profhz/stathz, and fix profhz if needed. */ i = stathz ? stathz : hz; if (profhz == 0) profhz = i; psratio = profhz / i; ********************************************************************** stathz and profhz are originally set by cpu_initclocks() (which is MD). If they are not set at this point, hz is used. This must be the case for some of your machines as both stathz and profhz equal hz. So why aren't stathz and profhz being set earlier? Check out cpu_initclocks() in src/sys/i386/isa/clock.c (lines 995-1008 of rev. 1.149.2.6): ********************************************************************** if (statclock_disable) { /* * The stat interrupt mask is different without the * statistics clock. Also, don't set the interrupt * flag which would normally cause the RTC to generate * interrupts. */ stat_imask = HWI_MASK | SWI_MASK; rtc_statusb = RTCSB_24HR; } else { /* Setting stathz to nonzero early helps avoid races. */ stathz = RTC_NOPROFRATE; profhz = RTC_PROFRATE; } ********************************************************************** If you look in src/sys/isa/rtc.h, you'll see that RTC_NOPROFRATE=128 and RTC_PROFRATE=1024. The only way stathz and profhz will not be set here is if statclock_disable is true. Where is statclock_disable set? Check out apm_attach() in src/sys/i386/apm/apm.c (lines 1032-1033 of rev. 1.114.2.6): ********************************************************************** if (flags & 0x20) statclock_disable = 1; ********************************************************************** Thus, you must have "device apm0 flags 0x20" or something similar in your kernel config file for you to get stathz and profhz as 100. apm is disabled in GENERIC, so by default this is not a problem; apm_attach won't be called if apm is disabled, so the fact that GENERIC includes "flags 0x20" is irrelevant. Jon >Release-Note: >Audit-Trail: >Unformatted: