Skip to content

Commit

Permalink
target/ppc: finalize pre-EBB PMU logic
Browse files Browse the repository at this point in the history
There are still PMU exclusive bits to handle in fire_PMC_interrupt()
before implementing the EBB support. Let's finalize it now to avoid
dealing with PMU and EBB logic at the same time in the next patches.

fire_PMC_interrupt() will fire an Performance Monitor alert depending on
MMCR0_PMAE. If we are required to freeze the timers (MMCR0_FCECE) we'll
also need to update summaries and delete the existing overflow timers.
In all cases we're going to update the cycle counters.

Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com>
Message-Id: <20220225101140.1054160-3-danielhb413@gmail.com>
Signed-off-by: Cédric Le Goater <clg@kaod.org>
  • Loading branch information
danielhb authored and legoater committed Mar 2, 2022
1 parent 33edcde commit adc4eda
Showing 1 changed file with 34 additions and 2 deletions.
36 changes: 34 additions & 2 deletions target/ppc/power8-pmu.c
Expand Up @@ -222,6 +222,20 @@ static void pmu_update_overflow_timers(CPUPPCState *env)
}
}

static void pmu_delete_timers(CPUPPCState *env)
{
QEMUTimer *pmc_overflow_timer;
int sprn;

for (sprn = SPR_POWER_PMC1; sprn <= SPR_POWER_PMC6; sprn++) {
pmc_overflow_timer = get_cyc_overflow_timer(env, sprn);

if (pmc_overflow_timer) {
timer_del(pmc_overflow_timer);
}
}
}

void helper_store_mmcr0(CPUPPCState *env, target_ulong value)
{
bool hflags_pmcc0 = (value & MMCR0_PMCC0) != 0;
Expand Down Expand Up @@ -271,8 +285,26 @@ static void fire_PMC_interrupt(PowerPCCPU *cpu)
{
CPUPPCState *env = &cpu->env;

if (!(env->spr[SPR_POWER_MMCR0] & MMCR0_EBE)) {
return;
pmu_update_cycles(env);

if (env->spr[SPR_POWER_MMCR0] & MMCR0_FCECE) {
env->spr[SPR_POWER_MMCR0] &= ~MMCR0_FCECE;
env->spr[SPR_POWER_MMCR0] |= MMCR0_FC;

/* Changing MMCR0_FC requires a new HFLAGS_INSN_CNT calc */
pmu_update_summaries(env);

/*
* Delete all pending timers if we need to freeze
* the PMC. We'll restart them when the PMC starts
* running again.
*/
pmu_delete_timers(env);
}

if (env->spr[SPR_POWER_MMCR0] & MMCR0_PMAE) {
env->spr[SPR_POWER_MMCR0] &= ~MMCR0_PMAE;
env->spr[SPR_POWER_MMCR0] |= MMCR0_PMAO;
}

/* PMC interrupt not implemented yet */
Expand Down

0 comments on commit adc4eda

Please sign in to comment.