Date: Wed, 21 Jan 2009 20:53:37 +0000 (UTC) From: Jung-uk Kim <jkim@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-7@freebsd.org Subject: svn commit: r187567 - in stable/7/sys: . amd64/amd64 amd64/include contrib/altq/altq contrib/pf dev/ath/ath_hal dev/cxgb i386/i386 i386/include i386/isa Message-ID: <200901212053.n0LKrbEt090963@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: jkim Date: Wed Jan 21 20:53:36 2009 New Revision: 187567 URL: http://svn.freebsd.org/changeset/base/187567 Log: MFC: Turn off CPU frequency change notifiers when the TSC is P-state invariant or it is forced by setting 'kern.timecounter.invariant_tsc' tunable to non-zero. Modified: stable/7/sys/ (props changed) stable/7/sys/amd64/amd64/identcpu.c stable/7/sys/amd64/amd64/prof_machdep.c stable/7/sys/amd64/amd64/tsc.c stable/7/sys/amd64/include/clock.h stable/7/sys/contrib/altq/altq/altq_subr.c stable/7/sys/contrib/pf/ (props changed) stable/7/sys/dev/ath/ath_hal/ (props changed) stable/7/sys/dev/cxgb/ (props changed) stable/7/sys/i386/i386/identcpu.c stable/7/sys/i386/i386/tsc.c stable/7/sys/i386/include/clock.h stable/7/sys/i386/isa/prof_machdep.c Modified: stable/7/sys/amd64/amd64/identcpu.c ============================================================================== --- stable/7/sys/amd64/amd64/identcpu.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/amd64/amd64/identcpu.c Wed Jan 21 20:53:36 2009 (r187567) @@ -345,6 +345,12 @@ printcpuinfo(void) "AuthenticAMD") == 0) cpu_feature &= ~CPUID_HTT; + if (!tsc_is_invariant && + (amd_pminfo & AMDPM_TSC_INVARIANT)) { + tsc_is_invariant = 1; + printf("\n P-state invariant TSC"); + } + /* * If this CPU supports HTT or CMP then mention the * number of physical/logical cores it contains. @@ -405,8 +411,11 @@ panicifcpuunsupported(void) static void tsc_freq_changed(void *arg, const struct cf_level *level, int status) { - /* If there was an error during the transition, don't do anything. */ - if (status != 0) + /* + * If there was an error during the transition or + * TSC is P-state invariant, don't do anything. + */ + if (status != 0 || tsc_is_invariant) return; /* Total setting for this level gives the new frequency in MHz. */ Modified: stable/7/sys/amd64/amd64/prof_machdep.c ============================================================================== --- stable/7/sys/amd64/amd64/prof_machdep.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/amd64/amd64/prof_machdep.c Wed Jan 21 20:53:36 2009 (r187567) @@ -387,8 +387,11 @@ static void tsc_freq_changed(void *arg, const struct cf_level *level, int status) { - /* If there was an error during the transition, don't do anything. */ - if (status != 0) + /* + * If there was an error during the transition or + * TSC is P-state invariant, don't do anything. + */ + if (status != 0 || tsc_is_invariant) return; if (cputime_prof_active && cputime_clock == CPUTIME_CLOCK_TSC) printf("warning: cpu freq changed while profiling active\n"); Modified: stable/7/sys/amd64/amd64/tsc.c ============================================================================== --- stable/7/sys/amd64/amd64/tsc.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/amd64/amd64/tsc.c Wed Jan 21 20:53:36 2009 (r187567) @@ -53,8 +53,13 @@ __FBSDID("$FreeBSD$"); uint64_t tsc_freq; int tsc_is_broken; +int tsc_is_invariant; static eventhandler_tag tsc_levels_tag, tsc_pre_tag, tsc_post_tag; +SYSCTL_INT(_kern_timecounter, OID_AUTO, invariant_tsc, CTLFLAG_RDTUN, + &tsc_is_invariant, 0, "Indicates whether the TSC is P-state invariant"); +TUNABLE_INT("kern.timecounter.invariant_tsc", &tsc_is_invariant); + #ifdef SMP static int smp_tsc; SYSCTL_INT(_kern_timecounter, OID_AUTO, smp_tsc, CTLFLAG_RDTUN, &smp_tsc, 0, @@ -179,11 +184,12 @@ static void tsc_freq_changing(void *arg, const struct cf_level *level, int *status) { - if (*status != 0 || timecounter != &tsc_timecounter) + if (*status != 0 || timecounter != &tsc_timecounter || + tsc_is_invariant) return; printf("timecounter TSC must not be in use when " - "changing frequencies; change denied\n"); + "changing frequencies; change denied\n"); *status = EBUSY; } @@ -191,8 +197,11 @@ tsc_freq_changing(void *arg, const struc static void tsc_freq_changed(void *arg, const struct cf_level *level, int status) { - /* If there was an error during the transition, don't do anything. */ - if (status != 0) + /* + * If there was an error during the transition or + * TSC is P-state invariant, don't do anything. + */ + if (status != 0 || tsc_is_invariant) return; /* Total setting for this level gives the new frequency in MHz. */ Modified: stable/7/sys/amd64/include/clock.h ============================================================================== --- stable/7/sys/amd64/include/clock.h Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/amd64/include/clock.h Wed Jan 21 20:53:36 2009 (r187567) @@ -22,6 +22,7 @@ extern u_int timer_freq; extern int timer0_max_count; extern uint64_t tsc_freq; extern int tsc_is_broken; +extern int tsc_is_invariant; void i8254_init(void); Modified: stable/7/sys/contrib/altq/altq/altq_subr.c ============================================================================== --- stable/7/sys/contrib/altq/altq/altq_subr.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/contrib/altq/altq/altq_subr.c Wed Jan 21 20:53:36 2009 (r187567) @@ -910,6 +910,12 @@ tsc_freq_changed(void *arg, const struct if (status != 0) return; +#if (__FreeBSD_version >= 701102) && (defined(__amd64__) || defined(__i386__)) + /* If TSC is P-state invariant, don't do anything. */ + if (tsc_is_invariant) + return; +#endif + /* Total setting for this level gives the new frequency in MHz. */ init_machclk(); } Modified: stable/7/sys/i386/i386/identcpu.c ============================================================================== --- stable/7/sys/i386/i386/identcpu.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/i386/i386/identcpu.c Wed Jan 21 20:53:36 2009 (r187567) @@ -842,6 +842,12 @@ printcpuinfo(void) "AuthenticAMD") == 0) cpu_feature &= ~CPUID_HTT; + if (!tsc_is_invariant && + (amd_pminfo & AMDPM_TSC_INVARIANT)) { + tsc_is_invariant = 1; + printf("\n P-state invariant TSC"); + } + /* * If this CPU supports HTT or CMP then mention the * number of physical/logical cores it contains. @@ -1058,8 +1064,11 @@ identifycyrix(void) static void tsc_freq_changed(void *arg, const struct cf_level *level, int status) { - /* If there was an error during the transition, don't do anything. */ - if (status != 0) + /* + * If there was an error during the transition or + * TSC is P-state invariant, don't do anything. + */ + if (status != 0 || tsc_is_invariant) return; /* Total setting for this level gives the new frequency in MHz. */ Modified: stable/7/sys/i386/i386/tsc.c ============================================================================== --- stable/7/sys/i386/i386/tsc.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/i386/i386/tsc.c Wed Jan 21 20:53:36 2009 (r187567) @@ -48,9 +48,14 @@ __FBSDID("$FreeBSD$"); uint64_t tsc_freq; int tsc_is_broken; +int tsc_is_invariant; u_int tsc_present; static eventhandler_tag tsc_levels_tag, tsc_pre_tag, tsc_post_tag; +SYSCTL_INT(_kern_timecounter, OID_AUTO, invariant_tsc, CTLFLAG_RDTUN, + &tsc_is_invariant, 0, "Indicates whether the TSC is P-state invariant"); +TUNABLE_INT("kern.timecounter.invariant_tsc", &tsc_is_invariant); + #ifdef SMP static int smp_tsc; SYSCTL_INT(_kern_timecounter, OID_AUTO, smp_tsc, CTLFLAG_RDTUN, &smp_tsc, 0, @@ -198,11 +203,12 @@ static void tsc_freq_changing(void *arg, const struct cf_level *level, int *status) { - if (*status != 0 || timecounter != &tsc_timecounter) + if (*status != 0 || timecounter != &tsc_timecounter || + tsc_is_invariant) return; printf("timecounter TSC must not be in use when " - "changing frequencies; change denied\n"); + "changing frequencies; change denied\n"); *status = EBUSY; } @@ -210,8 +216,11 @@ tsc_freq_changing(void *arg, const struc static void tsc_freq_changed(void *arg, const struct cf_level *level, int status) { - /* If there was an error during the transition, don't do anything. */ - if (status != 0) + /* + * If there was an error during the transition or + * TSC is P-state invariant, don't do anything. + */ + if (status != 0 || tsc_is_invariant) return; /* Total setting for this level gives the new frequency in MHz. */ Modified: stable/7/sys/i386/include/clock.h ============================================================================== --- stable/7/sys/i386/include/clock.h Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/i386/include/clock.h Wed Jan 21 20:53:36 2009 (r187567) @@ -22,6 +22,7 @@ extern u_int timer_freq; extern int timer0_max_count; extern uint64_t tsc_freq; extern int tsc_is_broken; +extern int tsc_is_invariant; void i8254_init(void); Modified: stable/7/sys/i386/isa/prof_machdep.c ============================================================================== --- stable/7/sys/i386/isa/prof_machdep.c Wed Jan 21 20:44:42 2009 (r187566) +++ stable/7/sys/i386/isa/prof_machdep.c Wed Jan 21 20:53:36 2009 (r187567) @@ -357,8 +357,11 @@ static void tsc_freq_changed(void *arg, const struct cf_level *level, int status) { - /* If there was an error during the transition, don't do anything. */ - if (status != 0) + /* + * If there was an error during the transition or + * TSC is P-state invariant, don't do anything. + */ + if (status != 0 || tsc_is_invariant) return; if (cputime_prof_active && cputime_clock == CPUTIME_CLOCK_TSC) printf("warning: cpu freq changed while profiling active\n");
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200901212053.n0LKrbEt090963>