Changeset View
Changeset View
Standalone View
Standalone View
head/sys/dev/hwpmc/hwpmc_ppro.c
Show First 20 Lines • Show All 333 Lines • ▼ Show 20 Lines | p6_pcpu_init(struct pmc_mdep *md, int cpu) | ||||
int first_ri, n; | int first_ri, n; | ||||
struct p6_cpu *p6c; | struct p6_cpu *p6c; | ||||
struct pmc_cpu *pc; | struct pmc_cpu *pc; | ||||
struct pmc_hw *phw; | struct pmc_hw *phw; | ||||
KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | ||||
("[p6,%d] bad cpu %d", __LINE__, cpu)); | ("[p6,%d] bad cpu %d", __LINE__, cpu)); | ||||
PMCDBG(MDP,INI,0,"p6-init cpu=%d", cpu); | PMCDBG1(MDP,INI,0,"p6-init cpu=%d", cpu); | ||||
p6c = malloc(sizeof (struct p6_cpu), M_PMC, M_WAITOK|M_ZERO); | p6c = malloc(sizeof (struct p6_cpu), M_PMC, M_WAITOK|M_ZERO); | ||||
pc = pmc_pcpu[cpu]; | pc = pmc_pcpu[cpu]; | ||||
KASSERT(pc != NULL, ("[p6,%d] cpu %d null per-cpu", __LINE__, cpu)); | KASSERT(pc != NULL, ("[p6,%d] cpu %d null per-cpu", __LINE__, cpu)); | ||||
phw = p6c->pc_p6pmcs; | phw = p6c->pc_p6pmcs; | ||||
p6_pcpu[cpu] = p6c; | p6_pcpu[cpu] = p6c; | ||||
Show All 15 Lines | |||||
{ | { | ||||
int first_ri, n; | int first_ri, n; | ||||
struct p6_cpu *p6c; | struct p6_cpu *p6c; | ||||
struct pmc_cpu *pc; | struct pmc_cpu *pc; | ||||
KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | ||||
("[p6,%d] bad cpu %d", __LINE__, cpu)); | ("[p6,%d] bad cpu %d", __LINE__, cpu)); | ||||
PMCDBG(MDP,INI,0,"p6-cleanup cpu=%d", cpu); | PMCDBG1(MDP,INI,0,"p6-cleanup cpu=%d", cpu); | ||||
p6c = p6_pcpu[cpu]; | p6c = p6_pcpu[cpu]; | ||||
p6_pcpu[cpu] = NULL; | p6_pcpu[cpu] = NULL; | ||||
KASSERT(p6c != NULL, ("[p6,%d] null pcpu", __LINE__)); | KASSERT(p6c != NULL, ("[p6,%d] null pcpu", __LINE__)); | ||||
free(p6c, M_PMC); | free(p6c, M_PMC); | ||||
Show All 24 Lines | KASSERT(pm, | ||||
("[p6,%d] cpu %d ri %d pmc not configured", __LINE__, cpu, ri)); | ("[p6,%d] cpu %d ri %d pmc not configured", __LINE__, cpu, ri)); | ||||
tmp = rdmsr(pd->pm_pmc_msr) & P6_PERFCTR_READ_MASK; | tmp = rdmsr(pd->pm_pmc_msr) & P6_PERFCTR_READ_MASK; | ||||
if (PMC_IS_SAMPLING_MODE(PMC_TO_MODE(pm))) | if (PMC_IS_SAMPLING_MODE(PMC_TO_MODE(pm))) | ||||
*v = P6_PERFCTR_VALUE_TO_RELOAD_COUNT(tmp); | *v = P6_PERFCTR_VALUE_TO_RELOAD_COUNT(tmp); | ||||
else | else | ||||
*v = tmp; | *v = tmp; | ||||
PMCDBG(MDP,REA,1, "p6-read cpu=%d ri=%d msr=0x%x -> v=%jx", cpu, ri, | PMCDBG4(MDP,REA,1, "p6-read cpu=%d ri=%d msr=0x%x -> v=%jx", cpu, ri, | ||||
pd->pm_pmc_msr, *v); | pd->pm_pmc_msr, *v); | ||||
return (0); | return (0); | ||||
} | } | ||||
static int | static int | ||||
p6_write_pmc(int cpu, int ri, pmc_value_t v) | p6_write_pmc(int cpu, int ri, pmc_value_t v) | ||||
{ | { | ||||
struct pmc *pm; | struct pmc *pm; | ||||
struct p6pmc_descr *pd; | struct p6pmc_descr *pd; | ||||
KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | ||||
("[p6,%d] illegal cpu value %d", __LINE__, cpu)); | ("[p6,%d] illegal cpu value %d", __LINE__, cpu)); | ||||
KASSERT(ri >= 0 && ri < P6_NPMCS, | KASSERT(ri >= 0 && ri < P6_NPMCS, | ||||
("[p6,%d] illegal row-index %d", __LINE__, ri)); | ("[p6,%d] illegal row-index %d", __LINE__, ri)); | ||||
pm = p6_pcpu[cpu]->pc_p6pmcs[ri].phw_pmc; | pm = p6_pcpu[cpu]->pc_p6pmcs[ri].phw_pmc; | ||||
pd = &p6_pmcdesc[ri]; | pd = &p6_pmcdesc[ri]; | ||||
KASSERT(pm, | KASSERT(pm, | ||||
("[p6,%d] cpu %d ri %d pmc not configured", __LINE__, cpu, ri)); | ("[p6,%d] cpu %d ri %d pmc not configured", __LINE__, cpu, ri)); | ||||
PMCDBG(MDP,WRI,1, "p6-write cpu=%d ri=%d msr=0x%x v=%jx", cpu, ri, | PMCDBG4(MDP,WRI,1, "p6-write cpu=%d ri=%d msr=0x%x v=%jx", cpu, ri, | ||||
pd->pm_pmc_msr, v); | pd->pm_pmc_msr, v); | ||||
if (PMC_IS_SAMPLING_MODE(PMC_TO_MODE(pm))) | if (PMC_IS_SAMPLING_MODE(PMC_TO_MODE(pm))) | ||||
v = P6_RELOAD_COUNT_TO_PERFCTR_VALUE(v); | v = P6_RELOAD_COUNT_TO_PERFCTR_VALUE(v); | ||||
wrmsr(pd->pm_pmc_msr, v & P6_PERFCTR_WRITE_MASK); | wrmsr(pd->pm_pmc_msr, v & P6_PERFCTR_WRITE_MASK); | ||||
return (0); | return (0); | ||||
} | } | ||||
static int | static int | ||||
p6_config_pmc(int cpu, int ri, struct pmc *pm) | p6_config_pmc(int cpu, int ri, struct pmc *pm) | ||||
{ | { | ||||
KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | ||||
("[p6,%d] illegal CPU %d", __LINE__, cpu)); | ("[p6,%d] illegal CPU %d", __LINE__, cpu)); | ||||
KASSERT(ri >= 0 && ri < P6_NPMCS, | KASSERT(ri >= 0 && ri < P6_NPMCS, | ||||
("[p6,%d] illegal row-index %d", __LINE__, ri)); | ("[p6,%d] illegal row-index %d", __LINE__, ri)); | ||||
PMCDBG(MDP,CFG,1, "p6-config cpu=%d ri=%d pm=%p", cpu, ri, pm); | PMCDBG3(MDP,CFG,1, "p6-config cpu=%d ri=%d pm=%p", cpu, ri, pm); | ||||
KASSERT(p6_pcpu[cpu] != NULL, ("[p6,%d] null per-cpu %d", __LINE__, | KASSERT(p6_pcpu[cpu] != NULL, ("[p6,%d] null per-cpu %d", __LINE__, | ||||
cpu)); | cpu)); | ||||
p6_pcpu[cpu]->pc_p6pmcs[ri].phw_pmc = pm; | p6_pcpu[cpu]->pc_p6pmcs[ri].phw_pmc = pm; | ||||
return (0); | return (0); | ||||
} | } | ||||
Show All 36 Lines | p6_allocate_pmc(int cpu, int ri, struct pmc *pm, | ||||
KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | ||||
("[p6,%d] illegal CPU %d", __LINE__, cpu)); | ("[p6,%d] illegal CPU %d", __LINE__, cpu)); | ||||
KASSERT(ri >= 0 && ri < P6_NPMCS, | KASSERT(ri >= 0 && ri < P6_NPMCS, | ||||
("[p6,%d] illegal row-index value %d", __LINE__, ri)); | ("[p6,%d] illegal row-index value %d", __LINE__, ri)); | ||||
pd = &p6_pmcdesc[ri]; | pd = &p6_pmcdesc[ri]; | ||||
PMCDBG(MDP,ALL,1, "p6-allocate ri=%d class=%d pmccaps=0x%x " | PMCDBG4(MDP,ALL,1, "p6-allocate ri=%d class=%d pmccaps=0x%x " | ||||
"reqcaps=0x%x", ri, pd->pm_descr.pd_class, pd->pm_descr.pd_caps, | "reqcaps=0x%x", ri, pd->pm_descr.pd_class, pd->pm_descr.pd_caps, | ||||
pm->pm_caps); | pm->pm_caps); | ||||
/* check class */ | /* check class */ | ||||
if (pd->pm_descr.pd_class != a->pm_class) | if (pd->pm_descr.pd_class != a->pm_class) | ||||
return (EINVAL); | return (EINVAL); | ||||
/* check requested capabilities */ | /* check requested capabilities */ | ||||
▲ Show 20 Lines • Show All 54 Lines • ▼ Show 20 Lines | if (caps & PMC_CAP_EDGE) | ||||
config |= P6_EVSEL_E; | config |= P6_EVSEL_E; | ||||
if (caps & PMC_CAP_INVERT) | if (caps & PMC_CAP_INVERT) | ||||
config |= P6_EVSEL_INV; | config |= P6_EVSEL_INV; | ||||
if (caps & PMC_CAP_INTERRUPT) | if (caps & PMC_CAP_INTERRUPT) | ||||
config |= P6_EVSEL_INT; | config |= P6_EVSEL_INT; | ||||
pm->pm_md.pm_ppro.pm_ppro_evsel = config; | pm->pm_md.pm_ppro.pm_ppro_evsel = config; | ||||
PMCDBG(MDP,ALL,2, "p6-allocate config=0x%x", config); | PMCDBG1(MDP,ALL,2, "p6-allocate config=0x%x", config); | ||||
return (0); | return (0); | ||||
} | } | ||||
static int | static int | ||||
p6_release_pmc(int cpu, int ri, struct pmc *pm) | p6_release_pmc(int cpu, int ri, struct pmc *pm) | ||||
{ | { | ||||
(void) pm; | (void) pm; | ||||
PMCDBG(MDP,REL,1, "p6-release cpu=%d ri=%d pm=%p", cpu, ri, pm); | PMCDBG3(MDP,REL,1, "p6-release cpu=%d ri=%d pm=%p", cpu, ri, pm); | ||||
KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | KASSERT(cpu >= 0 && cpu < pmc_cpu_max(), | ||||
("[p6,%d] illegal CPU value %d", __LINE__, cpu)); | ("[p6,%d] illegal CPU value %d", __LINE__, cpu)); | ||||
KASSERT(ri >= 0 && ri < P6_NPMCS, | KASSERT(ri >= 0 && ri < P6_NPMCS, | ||||
("[p6,%d] illegal row-index %d", __LINE__, ri)); | ("[p6,%d] illegal row-index %d", __LINE__, ri)); | ||||
KASSERT(p6_pcpu[cpu]->pc_p6pmcs[ri].phw_pmc == NULL, | KASSERT(p6_pcpu[cpu]->pc_p6pmcs[ri].phw_pmc == NULL, | ||||
("[p6,%d] PHW pmc non-NULL", __LINE__)); | ("[p6,%d] PHW pmc non-NULL", __LINE__)); | ||||
Show All 17 Lines | p6_start_pmc(int cpu, int ri) | ||||
pc = p6_pcpu[cpu]; | pc = p6_pcpu[cpu]; | ||||
pm = pc->pc_p6pmcs[ri].phw_pmc; | pm = pc->pc_p6pmcs[ri].phw_pmc; | ||||
pd = &p6_pmcdesc[ri]; | pd = &p6_pmcdesc[ri]; | ||||
KASSERT(pm, | KASSERT(pm, | ||||
("[p6,%d] starting cpu%d,ri%d with no pmc configured", | ("[p6,%d] starting cpu%d,ri%d with no pmc configured", | ||||
__LINE__, cpu, ri)); | __LINE__, cpu, ri)); | ||||
PMCDBG(MDP,STA,1, "p6-start cpu=%d ri=%d", cpu, ri); | PMCDBG2(MDP,STA,1, "p6-start cpu=%d ri=%d", cpu, ri); | ||||
config = pm->pm_md.pm_ppro.pm_ppro_evsel; | config = pm->pm_md.pm_ppro.pm_ppro_evsel; | ||||
PMCDBG(MDP,STA,2, "p6-start/2 cpu=%d ri=%d evselmsr=0x%x config=0x%x", | PMCDBG4(MDP,STA,2, "p6-start/2 cpu=%d ri=%d evselmsr=0x%x config=0x%x", | ||||
cpu, ri, pd->pm_evsel_msr, config); | cpu, ri, pd->pm_evsel_msr, config); | ||||
P6_MARK_STARTED(pc, ri); | P6_MARK_STARTED(pc, ri); | ||||
wrmsr(pd->pm_evsel_msr, config); | wrmsr(pd->pm_evsel_msr, config); | ||||
P6_SYNC_CTR_STATE(pc); | P6_SYNC_CTR_STATE(pc); | ||||
return (0); | return (0); | ||||
Show All 14 Lines | p6_stop_pmc(int cpu, int ri) | ||||
pc = p6_pcpu[cpu]; | pc = p6_pcpu[cpu]; | ||||
pm = pc->pc_p6pmcs[ri].phw_pmc; | pm = pc->pc_p6pmcs[ri].phw_pmc; | ||||
pd = &p6_pmcdesc[ri]; | pd = &p6_pmcdesc[ri]; | ||||
KASSERT(pm, | KASSERT(pm, | ||||
("[p6,%d] cpu%d ri%d no configured PMC to stop", __LINE__, | ("[p6,%d] cpu%d ri%d no configured PMC to stop", __LINE__, | ||||
cpu, ri)); | cpu, ri)); | ||||
PMCDBG(MDP,STO,1, "p6-stop cpu=%d ri=%d", cpu, ri); | PMCDBG2(MDP,STO,1, "p6-stop cpu=%d ri=%d", cpu, ri); | ||||
wrmsr(pd->pm_evsel_msr, 0); /* stop hw */ | wrmsr(pd->pm_evsel_msr, 0); /* stop hw */ | ||||
P6_MARK_STOPPED(pc, ri); /* update software state */ | P6_MARK_STOPPED(pc, ri); /* update software state */ | ||||
P6_SYNC_CTR_STATE(pc); /* restart CTR1 if need be */ | P6_SYNC_CTR_STATE(pc); /* restart CTR1 if need be */ | ||||
PMCDBG(MDP,STO,2, "p6-stop/2 cpu=%d ri=%d", cpu, ri); | PMCDBG2(MDP,STO,2, "p6-stop/2 cpu=%d ri=%d", cpu, ri); | ||||
return (0); | return (0); | ||||
} | } | ||||
static int | static int | ||||
p6_intr(int cpu, struct trapframe *tf) | p6_intr(int cpu, struct trapframe *tf) | ||||
{ | { | ||||
int error, retval, ri; | int error, retval, ri; | ||||
▲ Show 20 Lines • Show All 106 Lines • ▼ Show 20 Lines | |||||
int | int | ||||
pmc_p6_initialize(struct pmc_mdep *md, int ncpus) | pmc_p6_initialize(struct pmc_mdep *md, int ncpus) | ||||
{ | { | ||||
struct pmc_classdep *pcd; | struct pmc_classdep *pcd; | ||||
KASSERT(cpu_vendor_id == CPU_VENDOR_INTEL, | KASSERT(cpu_vendor_id == CPU_VENDOR_INTEL, | ||||
("[p6,%d] Initializing non-intel processor", __LINE__)); | ("[p6,%d] Initializing non-intel processor", __LINE__)); | ||||
PMCDBG(MDP,INI,1, "%s", "p6-initialize"); | PMCDBG0(MDP,INI,1, "p6-initialize"); | ||||
/* Allocate space for pointers to per-cpu descriptors. */ | /* Allocate space for pointers to per-cpu descriptors. */ | ||||
p6_pcpu = malloc(sizeof(struct p6_cpu **) * ncpus, M_PMC, | p6_pcpu = malloc(sizeof(struct p6_cpu **) * ncpus, M_PMC, | ||||
M_ZERO|M_WAITOK); | M_ZERO|M_WAITOK); | ||||
/* Fill in the class dependent descriptor. */ | /* Fill in the class dependent descriptor. */ | ||||
pcd = &md->pmd_classdep[PMC_MDEP_CLASS_INDEX_P6]; | pcd = &md->pmd_classdep[PMC_MDEP_CLASS_INDEX_P6]; | ||||
▲ Show 20 Lines • Show All 67 Lines • Show Last 20 Lines |