Date: Thu, 13 Oct 2011 08:29:47 +0000 (UTC) From: Adrian Chadd <adrian@FreeBSD.org> To: src-committers@freebsd.org, svn-src-user@freebsd.org Subject: svn commit: r226335 - in user/adrian/if_ath_tx/sys: conf dev/hwpmc Message-ID: <201110130829.p9D8Tlkr006690@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: adrian Date: Thu Oct 13 08:29:47 2011 New Revision: 226335 URL: http://svn.freebsd.org/changeset/base/226335 Log: Flesh out some more hwpmc mips24k sampling stuff. * Change DEBUG -> HWPMC_DEBUG; make it easier to deal with. * Flesh out the beginning of the hwpmc sample handling code. This doesn't (yet) support handling user/kernel call trees, so trying to use this (with the subsequent commit) w/ call tree enabled will cause all kinds of crash behaviour. Modified: user/adrian/if_ath_tx/sys/conf/options user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_logging.c user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mips24k.c user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mod.c Modified: user/adrian/if_ath_tx/sys/conf/options ============================================================================== --- user/adrian/if_ath_tx/sys/conf/options Thu Oct 13 08:26:28 2011 (r226334) +++ user/adrian/if_ath_tx/sys/conf/options Thu Oct 13 08:29:47 2011 (r226335) @@ -822,6 +822,7 @@ DCONS_FORCE_GDB opt_dcons.h # HWPMC options HWPMC_HOOKS +HWPMC_DEBUG opt_global.h # XBOX options for FreeBSD/i386, but some files are MI XBOX opt_xbox.h Modified: user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_logging.c ============================================================================== --- user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_logging.c Thu Oct 13 08:26:28 2011 (r226334) +++ user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_logging.c Thu Oct 13 08:29:47 2011 (r226335) @@ -210,7 +210,7 @@ pmclog_get_buffer(struct pmc_owner *po) PMCDBG(LOG,GTB,1, "po=%p plb=%p", po, plb); -#ifdef DEBUG +#ifdef HWPMC_DEBUG if (plb) KASSERT(plb->plb_ptr == plb->plb_base && plb->plb_base < plb->plb_fence, Modified: user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mips24k.c ============================================================================== --- user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mips24k.c Thu Oct 13 08:26:28 2011 (r226334) +++ user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mips24k.c Thu Oct 13 08:29:47 2011 (r226335) @@ -254,6 +254,8 @@ mips24k_allocate_pmc(int cpu, int ri, st config |= MIPS24K_PMC_USER_ENABLE; if ((caps & (PMC_CAP_USER | PMC_CAP_SYSTEM)) == 0) config |= MIPS24K_PMC_ENABLE; + if (caps & PMC_CAP_INTERRUPT) + config |= MIPS24K_PMC_INTERRUPT_ENABLE; pm->pm_md.pm_mips24k.pm_mips24k_evsel = config; @@ -384,6 +386,7 @@ mips24k_stop_pmc(int cpu, int ri) return 0; } + static int mips24k_release_pmc(int cpu, int ri, struct pmc *pmc) { @@ -404,7 +407,71 @@ mips24k_release_pmc(int cpu, int ri, str static int mips24k_intr(int cpu, struct trapframe *tf) { - return 0; + int error; + int retval, ri; + struct pmc *pm; + struct mips24k_cpu *pc; + uint32_t r, r0, r2; + + KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), + ("[mips24k,%d] CPU %d out of range", __LINE__, cpu)); + + retval = 0; + pc = mips24k_pcpu[cpu]; + + /* Stop PMCs without clearing the counter */ + r0 = mips_rd_perfcnt0(); + mips_wr_perfcnt0(r0 & ~(0x1f)); + r2 = mips_rd_perfcnt2(); + mips_wr_perfcnt2(r2 & ~(0x1f)); + + //printf("%s: called, cpu=%d, tf=%p\n", __func__, cpu, tf); + + for (ri = 0; ri < mips24k_npmcs; ri++) { + pm = mips24k_pcpu[cpu]->pc_mipspmcs[ri].phw_pmc; + if (pm == NULL) + continue; + if (! PMC_IS_SAMPLING_MODE(PMC_TO_MODE(pm))) + continue; + + r = mips24k_pmcn_read(ri); + //printf("%s: ri=%d; r=%x\n", __func__, ri, r); + + /* If bit 31 is set, the counter has overflowed */ + if ((r & 0x80000000) == 0) + continue; + + retval = 1; + if (pm->pm_state != PMC_STATE_RUNNING) + continue; + error = pmc_process_interrupt(cpu, pm, tf, + TRAPF_USERMODE(tf)); + if (error) { + /* XXX this is hacky! Fix before merging to -HEAD! */ + if (ri == 0) + r0 = 0; + else + r2 = 0; + mips24k_stop_pmc(cpu, ri); + } + + /* Reload sampling count */ + mips24k_write_pmc(cpu, ri, pm->pm_sc.pm_reloadcount); + } + + /* + * Re-enable the PMC counters. + * XXX does this reset the event counter values? + */ +#if 1 + mips_wr_perfcnt0(r0); + mips_wr_perfcnt2(r2); +#else + mips_wr_perfcnt0(0); + mips_wr_perfcnt2(0); +#endif + + return retval; } static int Modified: user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mod.c ============================================================================== --- user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mod.c Thu Oct 13 08:26:28 2011 (r226334) +++ user/adrian/if_ath_tx/sys/dev/hwpmc/hwpmc_mod.c Thu Oct 13 08:29:47 2011 (r226335) @@ -169,7 +169,7 @@ static struct pmc_classdep **pmc_rowinde * Prototypes */ -#ifdef DEBUG +#ifdef HWPMC_DEBUG static int pmc_debugflags_sysctl_handler(SYSCTL_HANDLER_ARGS); static int pmc_debugflags_parse(char *newstr, char *fence); #endif @@ -230,7 +230,7 @@ TUNABLE_INT(PMC_SYSCTL_NAME_PREFIX "call SYSCTL_INT(_kern_hwpmc, OID_AUTO, callchaindepth, CTLFLAG_TUN|CTLFLAG_RD, &pmc_callchaindepth, 0, "depth of call chain records"); -#ifdef DEBUG +#ifdef HWPMC_DEBUG struct pmc_debugflags pmc_debugflags = PMC_DEBUG_DEFAULT_FLAGS; char pmc_debugstr[PMC_DEBUG_STRSIZE]; TUNABLE_STR(PMC_SYSCTL_NAME_PREFIX "debugflags", pmc_debugstr, @@ -328,7 +328,7 @@ static moduledata_t pmc_mod = { DECLARE_MODULE(pmc, pmc_mod, SI_SUB_SMP, SI_ORDER_ANY); MODULE_VERSION(pmc, PMC_VERSION); -#ifdef DEBUG +#ifdef HWPMC_DEBUG enum pmc_dbgparse_state { PMCDS_WS, /* in whitespace */ PMCDS_MAJOR, /* seen a major keyword */ @@ -806,7 +806,7 @@ pmc_link_target_process(struct pmc *pm, PMCDBG(PRC,TLK,1, "link-target pmc=%p ri=%d pmc-process=%p", pm, ri, pp); -#ifdef DEBUG +#ifdef HWPMC_DEBUG LIST_FOREACH(pt, &pm->pm_targets, pt_next) if (pt->pt_process == pp) KASSERT(0, ("[pmc,%d] pp %p already in pmc %p targets", @@ -1821,7 +1821,7 @@ pmc_log_all_process_mappings(struct pmc_ */ -#ifdef DEBUG +#ifdef HWPMC_DEBUG const char *pmc_hooknames[] = { /* these strings correspond to PMC_FN_* in <sys/pmckern.h> */ "", @@ -1979,7 +1979,6 @@ pmc_hook_handler(struct thread *td, int * are being processed. */ case PMC_FN_DO_SAMPLES: - /* * Clear the cpu specific bit in the CPU mask before * do the rest of the processing. If the NMI handler @@ -2028,7 +2027,7 @@ pmc_hook_handler(struct thread *td, int break; default: -#ifdef DEBUG +#ifdef HWPMC_DEBUG KASSERT(0, ("[pmc,%d] unknown hook %d\n", __LINE__, function)); #endif break; @@ -2204,7 +2203,7 @@ pmc_destroy_pmc_descriptor(struct pmc *p { (void) pm; -#ifdef DEBUG +#ifdef HWPMC_DEBUG KASSERT(pm->pm_state == PMC_STATE_DELETED || pm->pm_state == PMC_STATE_FREE, ("[pmc,%d] destroying non-deleted PMC", __LINE__)); @@ -2221,7 +2220,7 @@ pmc_destroy_pmc_descriptor(struct pmc *p static void pmc_wait_for_pmc_idle(struct pmc *pm) { -#ifdef DEBUG +#ifdef HWPMC_DEBUG volatile int maxloop; maxloop = 100 * pmc_cpu_max(); @@ -2232,7 +2231,7 @@ pmc_wait_for_pmc_idle(struct pmc *pm) * comes down to zero. */ while (atomic_load_acq_32(&pm->pm_runcount) > 0) { -#ifdef DEBUG +#ifdef HWPMC_DEBUG maxloop--; KASSERT(maxloop > 0, ("[pmc,%d] (ri%d, rc%d) waiting too long for " @@ -2798,7 +2797,7 @@ pmc_stop(struct pmc *pm) } -#ifdef DEBUG +#ifdef HWPMC_DEBUG static const char *pmc_op_to_name[] = { #undef __PMC_OP #define __PMC_OP(N, D) #N , @@ -3775,7 +3774,7 @@ pmc_syscall_handler(struct thread *td, v pprw = (struct pmc_op_pmcrw *) arg; -#ifdef DEBUG +#ifdef HWPMC_DEBUG if (prw.pm_flags & PMC_F_NEWVALUE) PMCDBG(PMC,OPS,2, "rw id=%d new %jx -> old %jx", ri, prw.pm_value, oldvalue); @@ -4579,7 +4578,7 @@ pmc_initialize(void) md = NULL; error = 0; -#ifdef DEBUG +#ifdef HWPMC_DEBUG /* parse debug flags first */ if (TUNABLE_STR_FETCH(PMC_SYSCTL_NAME_PREFIX "debugflags", pmc_debugstr, sizeof(pmc_debugstr))) @@ -4775,7 +4774,7 @@ pmc_cleanup(void) struct pmc_ownerhash *ph; struct pmc_owner *po, *tmp; struct pmc_binding pb; -#ifdef DEBUG +#ifdef HWPMC_DEBUG struct pmc_processhash *prh; #endif @@ -4825,7 +4824,7 @@ pmc_cleanup(void) mtx_destroy(&pmc_processhash_mtx); if (pmc_processhash) { -#ifdef DEBUG +#ifdef HWPMC_DEBUG struct pmc_process *pp; PMCDBG(MOD,INI,3, "%s", "destroy process hash");
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201110130829.p9D8Tlkr006690>