Example #1
0
void core_alloc_STM_t::reg_stats(xiosim::stats::StatsDatabase* sdb)
{
    int coreID = core->id;

    auto sim_cycle_st = stat_find_core_stat<tick_t>(sdb, coreID, "sim_cycle");
    assert(sim_cycle_st);

    stat_reg_note(sdb, "#### ALLOC STATS ####");
    auto& alloc_insn_st = stat_reg_core_counter(sdb, true, coreID, "alloc_insn",
                                                "total number of instructions alloced",
                                                &core->stat.alloc_insn, 0, true, NULL);
    auto& alloc_uops_st =
            stat_reg_core_counter(sdb, true, coreID, "alloc_uops", "total number of uops alloced",
                                  &core->stat.alloc_uops, 0, true, NULL);
    auto& alloc_eff_uops_st = stat_reg_core_counter(sdb, true, coreID, "alloc_eff_uops",
                                                    "total number of effective uops alloced",
                                                    &core->stat.alloc_eff_uops, 0, true, NULL);
    stat_reg_core_formula(sdb, true, coreID, "alloc_IPC", "IPC at alloc",
                          alloc_insn_st / *sim_cycle_st, NULL);
    stat_reg_core_formula(sdb, true, coreID, "alloc_uPC", "uPC at alloc",
                          alloc_uops_st / *sim_cycle_st, NULL);
    stat_reg_core_formula(sdb, true, coreID, "alloc_euPC", "euPC at alloc",
                          alloc_eff_uops_st / *sim_cycle_st, NULL);

    core->stat.alloc_stall = stat_reg_core_dist(
            sdb, coreID, "alloc_stall", "breakdown of stalls at alloc", 0, ASTALL_num,
            (PF_COUNT | PF_PDF), NULL, alloc_stall_str, true, NULL);
}
Example #2
0
void core_decode_DPM_t::reg_stats(xiosim::stats::StatsDatabase* sdb) {
    int coreID = core->id;

    stat_reg_note(sdb, "\n#### DECODE STATS ####");
    stat_reg_core_counter(sdb, true, coreID, "target_resteers", "decode-time target resteers",
                          &core->stat.target_resteers, 0, true, NULL);
    stat_reg_core_counter(sdb, true, coreID, "phantom_resteers", "decode-time phantom resteers",
                          &core->stat.phantom_resteers, 0, true, NULL);
    auto& decode_insn_st = stat_reg_core_counter(sdb, true, coreID, "decode_insn",
                           "total number of instructions decodeed",
                           &core->stat.decode_insn, 0, true, NULL);
    auto& decode_uops_st =
        stat_reg_core_counter(sdb, true, coreID, "decode_uops", "total number of uops decodeed",
                              &core->stat.decode_uops, 0, true, NULL);
    auto& decode_eff_uops_st = stat_reg_core_counter(sdb, true, coreID, "decode_eff_uops",
                               "total number of effective uops decodeed",
                               &core->stat.decode_eff_uops, 0, true, NULL);
    auto core_sim_cycles_st = stat_find_core_stat<tick_t>(sdb, coreID, "sim_cycle");
    assert(core_sim_cycles_st);
    stat_reg_core_formula(sdb, true, coreID, "decode_IPC", "IPC at decode",
                          decode_insn_st / *core_sim_cycles_st, NULL);
    stat_reg_core_formula(sdb, true, coreID, "decode_uPC", "uPC at decode",
                          decode_uops_st / *core_sim_cycles_st, NULL);
    stat_reg_core_formula(sdb, true, coreID, "decode_euPC", "effective uPC at decode",
                          decode_eff_uops_st / *core_sim_cycles_st, NULL);
    reg_core_queue_occupancy_stats(sdb, coreID, "uopQ", &core->stat.uopQ_occupancy,
                                   &core->stat.uopQ_empty_cycles,
                                   &core->stat.uopQ_full_cycles);
    core->stat.decode_stall = stat_reg_core_dist(
                                  sdb, coreID, "decode_stall", "breakdown of stalls at decode", 0, DSTALL_num,
                                  (PF_COUNT | PF_PDF), NULL, decode_stall_str, true, NULL);
}
Example #3
0
void
core_fetch_STM_t::reg_stats(struct stat_sdb_t * const sdb)
{
  char buf[1024];
  char buf2[1024];
  struct thread_t * arch = core->current_thread;

  stat_reg_note(sdb,"\n#### BPRED STATS ####");
  bpred->reg_stats(sdb,core);

  stat_reg_note(sdb,"\n#### INST CACHE STATS ####");
  cache_reg_stats(sdb, core, core->memory.IL1);
  cache_reg_stats(sdb, core, core->memory.ITLB);

  stat_reg_note(sdb,"\n#### FETCH STATS ####");
  sprintf(buf,"c%d.fetch_insn",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of instructions fetched", &core->stat.fetch_insn, 0, TRUE, NULL);
  sprintf(buf,"c%d.fetch_uops",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of uops fetched", &core->stat.fetch_uops, 0, TRUE, NULL);
  sprintf(buf,"c%d.fetch_IPC",arch->id);
  sprintf(buf2,"c%d.fetch_insn/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "IPC at fetch", buf2, NULL);
  sprintf(buf,"c%d.fetch_uPC",arch->id);
  sprintf(buf2,"c%d.fetch_uops/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uPC at fetch", buf2, NULL);

  sprintf(buf,"c%d.fetch_stall",core->current_thread->id);
  core->stat.fetch_stall = stat_reg_dist(sdb, buf,
                                          "breakdown of stalls in fetch",
                                          /* initial value */0,
                                          /* array size */FSTALL_num,
                                          /* bucket size */1,
                                          /* print format */(PF_COUNT|PF_PDF),
                                          /* format */NULL,
                                          /* index map */fetch_stall_str,
                                          /* scale_me */ TRUE,
                                          /* print fn */NULL);

  sprintf(buf,"c%d.byteQ_occupancy",arch->id);
  stat_reg_counter(sdb, false, buf, "total byteQ occupancy (in lines/entries)", &core->stat.byteQ_occupancy, 0, TRUE, NULL);
  sprintf(buf,"c%d.byteQ_avg",arch->id);
  sprintf(buf2,"c%d.byteQ_occupancy/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average byteQ occupancy (in insts)", buf2, NULL);
}
Example #4
0
void core_commit_STM_t::reg_stats(xiosim::stats::StatsDatabase* sdb) {
    int coreID = core->id;

    stat_reg_note(sdb, "\n#### COMMIT STATS ####");

    auto& sim_cycle_st = *stat_find_core_stat<tick_t>(sdb, coreID, "sim_cycle");
    auto& commit_insn_st = *stat_find_core_stat<counter_t>(sdb, coreID, "commit_insn");
    auto& commit_uops_st = *stat_find_core_stat<counter_t>(sdb, coreID, "commit_uops");

    stat_reg_core_formula(sdb, true, coreID, "commit_IPC", "IPC at commit",
                          commit_insn_st / sim_cycle_st, NULL);
    stat_reg_core_formula(sdb, true, coreID, "commit_uPC", "uPC at commit",
                          commit_uops_st / sim_cycle_st, NULL);
    stat_reg_core_formula(sdb, true, coreID, "avg_commit_flowlen",
                          "uops per instruction at commit", commit_uops_st / commit_insn_st, NULL);

    reg_core_queue_occupancy_stats(sdb, coreID, "ROB", &core->stat.ROB_occupancy,
                                   &core->stat.ROB_empty_cycles,
                                   &core->stat.ROB_full_cycles);

    core->stat.commit_stall = stat_reg_core_dist(
            sdb, coreID, "commit_stall", "breakdown of stalls at commit", 0, CSTALL_num,
            (PF_COUNT | PF_PDF), NULL, commit_stall_str, true, NULL);

    stat_reg_note(sdb, "#### TIMING STATS ####");
    /* instruction distribution stats */
    stat_reg_note(sdb, "\n#### INSTRUCTION STATS (no wrong-path) ####");
    stat_reg_core_formula(sdb, true, coreID, "num_insn", "total number of instructions committed",
                          commit_insn_st, NULL);
    auto& num_refs_st = stat_reg_core_counter(sdb, true, coreID, "num_refs",
                                              "total number of loads and stores committed",
                                              &core->stat.commit_refs, 0, true, NULL);
    auto& num_loads_st = stat_reg_core_counter(sdb, true, coreID, "num_loads",
                                               "total number of loads committed",
                                               &core->stat.commit_loads, 0, true, NULL);
    stat_reg_core_formula(sdb, true, coreID, "num_stores", "total number of stores committed",
                          num_refs_st - num_loads_st, "%12.0f");
}
Example #5
0
/* register memory system-specific statistics */
void reg_stats(xiosim::stats::StatsDatabase* sdb)
{
    char buf[512];

    stat_reg_note(sdb,"\n#### SIMULATED MEMORY STATS ####");

    stat_reg_counter(sdb, TRUE, "core_page_count", "total number of physical pages allocated",
        &phys_page_count, 0, FALSE, NULL);
    for (int i=0; i<num_address_spaces; i++) {
        sprintf(buf, "prog_%d.page_count", i);
        stat_reg_counter(sdb, TRUE, buf, "total number of pages allocated",
            (page_count + i), 0, FALSE, NULL);
    }
}
Example #6
0
void core_commit_NONE_t::reg_stats(struct stat_sdb_t * const sdb)
{
  char buf[1024];
  char buf2[1024];
  struct thread_t * arch = core->current_thread;

  stat_reg_note(sdb,"\n#### COMMIT STATS ####");

  sprintf(buf,"c%d.sim_cycle",arch->id);
  stat_reg_qword(sdb, true, buf, "total number of cycles when last instruction (or uop) committed", (qword_t*) &core->sim_cycle, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_insn",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of instructions committed", &core->stat.commit_insn, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_IPC",arch->id);
  sprintf(buf2,"c%d.commit_insn/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "IPC at commit", buf2, NULL);
}
Example #7
0
void
core_commit_IO_DPM_t::reg_stats(struct stat_sdb_t * const sdb)
{
  char buf[1024];
  char buf2[1024];
  struct thread_t * arch = core->current_thread;

  stat_reg_note(sdb,"\n#### COMMIT STATS ####");

  sprintf(buf,"c%d.commit_bytes",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of bytes committed", &core->stat.commit_bytes, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_insn",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of instructions committed", &core->stat.commit_insn, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_uops",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of uops committed", &core->stat.commit_uops, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_eff_uops",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of effective uops committed", &core->stat.commit_eff_uops, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_BPC",arch->id);
  sprintf(buf2,"c%d.commit_bytes/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "BPC (bytes per cycle) at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_IPC",arch->id);
  sprintf(buf2,"c%d.commit_insn/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "IPC at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_uPC",arch->id);
  sprintf(buf2,"c%d.commit_uops/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uPC at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_euPC",arch->id);
  sprintf(buf2,"c%d.commit_eff_uops/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "effective uPC at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_byte_per_inst",arch->id);
  sprintf(buf2,"c%d.commit_bytes/c%d.commit_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average bytes per instruction", buf2, NULL);
  sprintf(buf,"c%d.commit_byte_per_uop",arch->id);
  sprintf(buf2,"c%d.commit_bytes/c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average bytes per uop", buf2, NULL);
  sprintf(buf,"c%d.commit_byte_per_eff_uop",arch->id);
  sprintf(buf2,"c%d.commit_bytes/c%d.commit_eff_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average bytes per effective uop", buf2, NULL);
  sprintf(buf,"c%d.avg_commit_flowlen",arch->id);
  sprintf(buf2,"c%d.commit_uops/c%d.commit_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uops per instruction at commit", buf2, NULL);
  sprintf(buf,"c%d.avg_commit_eff_flowlen",arch->id);
  sprintf(buf2,"c%d.commit_eff_uops/c%d.commit_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "effective uops per instruction at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_fusions",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of fused uops committed", &core->stat.commit_fusions, 0, TRUE, NULL);
  sprintf(buf,"c%d.commit_fusion_uops",arch->id);
  sprintf(buf2,"(c%d.commit_eff_uops - c%d.commit_uops) + c%d.commit_fusions",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "fused uops at commit", buf2, "%12.0f");
  sprintf(buf,"c%d.commit_frac_fusion_uops",arch->id);
  sprintf(buf2,"c%d.commit_fusion_uops / c%d.commit_eff_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "fraction of effective uops fused at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_fusion_compression",arch->id);
  sprintf(buf2,"(c%d.commit_eff_uops - c%d.commit_uops) / c%d.commit_eff_uops",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "fraction of effective uops compressed via fusion at commit", buf2, NULL);
  sprintf(buf,"c%d.commit_fusion_expansion",arch->id);
  sprintf(buf2,"c%d.commit_eff_uops / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average number of effective uops per uop (fused or standalone) commit", buf2, NULL);

  sprintf(buf,"c%d.commit_dead_lock_flushes",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of pipe-flushes due to dead-locked pipeline", &core->stat.commit_deadlock_flushes, 0, FALSE, NULL);
  sprintf(buf,"c%d.ROB_empty",arch->id);
  sprintf(buf,"c%d.ROB_occupancy",arch->id);
  stat_reg_counter(sdb, false, buf, "total ROB occupancy", &core->stat.ROB_occupancy, 0, TRUE, NULL);
  sprintf(buf,"c%d.ROB_eff_occupancy",arch->id);
  stat_reg_counter(sdb, false, buf, "total ROB effective_occupancy", &core->stat.ROB_eff_occupancy, 0, TRUE, NULL);
  sprintf(buf,"c%d.ROB_empty",arch->id);
  stat_reg_counter(sdb, false, buf, "total cycles ROB was empty", &core->stat.ROB_empty_cycles, 0, TRUE, NULL);
  sprintf(buf,"c%d.ROB_full",arch->id);
  stat_reg_counter(sdb, false, buf, "total cycles ROB was full", &core->stat.ROB_full_cycles, 0, TRUE, NULL);
  sprintf(buf,"c%d.ROB_avg",arch->id);
  sprintf(buf2,"c%d.ROB_occupancy/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average ROB occupancy", buf2, NULL);
  sprintf(buf,"c%d.ROB_eff_avg",arch->id);
  sprintf(buf2,"c%d.ROB_eff_occupancy/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average ROB effective occupancy", buf2, NULL);
  sprintf(buf,"c%d.ROB_frac_empty",arch->id);
  sprintf(buf2,"c%d.ROB_empty/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "fraction of cycles ROB was empty", buf2, NULL);
  sprintf(buf,"c%d.ROB_frac_full",arch->id);
  sprintf(buf2,"c%d.ROB_full/c%d.sim_cycle",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "fraction of cycles ROB was full", buf2, NULL);
  sprintf(buf,"c%d.DL1_store_split_accesses",arch->id);
  stat_reg_counter(sdb, true, buf, "number of stores requiring split accesses", &core->stat.DL1_store_split_accesses, 0, TRUE, NULL);
  sprintf(buf,"c%d.DL1_store_split_frac",arch->id);
  sprintf(buf2,"c%d.DL1_store_split_accesses/(c%d.DL1.store_lookups-c%d.DL1_store_split_accesses)",arch->id,arch->id,arch->id); /* need to subtract since each split access generated two store accesses */
  stat_reg_formula(sdb, true, buf, "fraction of stores requiring split accesses", buf2, NULL);

  sprintf(buf,"c%d.commit_stall",core->current_thread->id);
  core->stat.commit_stall = stat_reg_dist(sdb, buf,
                                           "breakdown of stalls at commit",
                                           /* initial value */0,
                                           /* array size */CSTALL_num,
                                           /* bucket size */1,
                                           /* print format */(PF_COUNT|PF_PDF),
                                           /* format */NULL,
                                           /* index map */commit_stall_str,
                                           /* scale_me */TRUE,
                                           /* print fn */NULL);

  stat_reg_note(sdb,"#### TIMING STATS ####");
  sprintf(buf,"c%d.sim_cycle",arch->id);
  stat_reg_qword(sdb, true, buf, "total number of cycles when last instruction (or uop) committed", (qword_t*) &core->stat.final_sim_cycle, 0, TRUE, NULL);
  /* cumulative slip cycles (not printed) */
  sprintf(buf,"c%d.Mop_fetch_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total Mop fetch slip cycles", (qword_t*) &core->stat.Mop_fetch_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.Mop_f2d_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total Mop fetch-to-decode slip cycles", (qword_t*) &core->stat.Mop_fetch2decode_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.Mop_decode_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total Mop decode slip cycles", (qword_t*) &core->stat.Mop_decode_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.uop_d2a_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total uop decode-to-alloc slip cycles", (qword_t*) &core->stat.uop_decode2alloc_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.uop_a2r_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total uop alloc-to-ready slip cycles", (qword_t*) &core->stat.uop_alloc2ready_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.uop_r2i_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total uop ready-to-issue slip cycles", (qword_t*) &core->stat.uop_ready2issue_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.uop_i2e_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total uop issue-to-exec slip cycles", (qword_t*) &core->stat.uop_issue2exec_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.uop_e2w_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total uop exec-to-WB slip cycles", (qword_t*) &core->stat.uop_exec2complete_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.uop_w2c_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total uop WB-to-commit slip cycles", (qword_t*) &core->stat.uop_complete2commit_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.Mop_d2c_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total Mop decode-to-commit slip cycles", (qword_t*) &core->stat.Mop_decode2commit_slip, 0, TRUE, NULL);
  sprintf(buf,"c%d.Mop_commit_Tslip",core->current_thread->id);
  stat_reg_qword(sdb, false, buf, "total Mop commit slip cycles", (qword_t*) &core->stat.Mop_commit_slip, 0, TRUE, NULL);
  /* average slip cycles */
  sprintf(buf,"c%d.Mop_fetch_avg_slip",arch->id);
  sprintf(buf2,"c%d.Mop_fetch_Tslip / (c%d.commit_insn - c%d.num_traps)",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "Mop fetch average delay", buf2, NULL);
  sprintf(buf,"c%d.Mop_f2d_avg_slip",arch->id);
  sprintf(buf2,"c%d.Mop_f2d_Tslip / (c%d.commit_insn - c%d.num_traps)",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "Mop fetch-to-decode average delay", buf2, NULL);
  sprintf(buf,"c%d.Mop_decode_avg_slip",arch->id);
  sprintf(buf2,"c%d.Mop_decode_Tslip / (c%d.commit_insn - c%d.num_traps)",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "Mop decode average delay", buf2, NULL);
  sprintf(buf,"c%d.uop_d2a_avg_slip",arch->id);
  sprintf(buf2,"c%d.uop_d2a_Tslip / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uop decode-to-alloc average delay", buf2, NULL);
  sprintf(buf,"c%d.uop_a2r_avg_slip",arch->id);
  sprintf(buf2,"c%d.uop_a2r_Tslip / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uop alloc-to-ready average delay", buf2, NULL);
  sprintf(buf,"c%d.uop_r2i_avg_slip",arch->id);
  sprintf(buf2,"c%d.uop_r2i_Tslip / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uop ready-to-issue average delay", buf2, NULL);
  sprintf(buf,"c%d.uop_i2e_avg_slip",arch->id);
  sprintf(buf2,"c%d.uop_i2e_Tslip / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uop issue-to-exec average delay", buf2, NULL);
  sprintf(buf,"c%d.uop_e2w_avg_slip",arch->id);
  sprintf(buf2,"c%d.uop_e2w_Tslip / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uop exec-to-WB average delay", buf2, NULL);
  sprintf(buf,"c%d.uop_w2c_avg_slip",arch->id);
  sprintf(buf2,"c%d.uop_w2c_Tslip / c%d.commit_uops",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "uop WB-to-commit average delay", buf2, NULL);
  sprintf(buf,"c%d.Mop_d2c_avg_slip",arch->id);
  sprintf(buf2,"c%d.Mop_d2c_Tslip / (c%d.commit_insn - c%d.num_traps)",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "Mop decode-to-commit average delay", buf2, NULL);
  sprintf(buf,"c%d.Mop_commit_avg_slip",arch->id);
  sprintf(buf2,"c%d.Mop_commit_Tslip / (c%d.commit_insn - c%d.num_traps)",arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "Mop commit average delay", buf2, NULL);
  sprintf(buf,"c%d.Mop_avg_end_to_end",arch->id);
  sprintf(buf2,"c%d.Mop_fetch_avg_slip + c%d.Mop_f2d_avg_slip + c%d.Mop_d2c_avg_slip + c%d.Mop_commit_avg_slip",arch->id,arch->id,arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "Mop average end-to-end pipeline delay", buf2, NULL);
  /* instruction distribution stats */
  stat_reg_note(sdb,"\n#### INSTRUCTION STATS (no wrong-path) ####");
  sprintf(buf,"c%d.num_insn",arch->id);
  sprintf(buf2,"c%d.commit_insn",arch->id);
  stat_reg_formula(sdb, true, buf, "total number of instructions committed", buf2, NULL);
  sprintf(buf,"c%d.num_refs",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of loads and stores committed", &core->stat.commit_refs, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_loads",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of loads committed", &core->stat.commit_loads, 0, TRUE, NULL);
  sprintf(buf2,"c%d.num_refs - c%d.num_loads",arch->id,arch->id);
  sprintf(buf,"c%d.num_stores",arch->id);
  stat_reg_formula(sdb, true, buf, "total number of stores committed", buf2, "%12.0f");
  sprintf(buf,"c%d.num_branches",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of branches committed", &core->stat.commit_branches, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_traps",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of traps committed", &core->stat.commit_traps, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_rep_insn",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of REP insts committed", &core->stat.commit_rep_insn, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_rep_iter",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of REP iterations committed", &core->stat.commit_rep_iterations, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_rep_uops",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of uops in REP insts committed", &core->stat.commit_rep_uops, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_avg_reps",arch->id);
  sprintf(buf2,"c%d.num_rep_iter/c%d.num_rep_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average iterations per REP inst", buf2, "%12.2f");
  sprintf(buf,"c%d.num_avg_rep_uops",arch->id);
  sprintf(buf2,"c%d.num_rep_uops/c%d.num_rep_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average uops per REP inst", buf2, "%12.2f");
  sprintf(buf,"c%d.num_UROM_insn",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of insn using the UROM committed", &core->stat.commit_UROM_insn, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_UROM_uops",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of uops using the UROM committed", &core->stat.commit_UROM_uops, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_UROM_eff_uops",arch->id);
  stat_reg_counter(sdb, true, buf, "total number of effective uops using the UROM committed", &core->stat.commit_UROM_eff_uops, 0, TRUE, NULL);
  sprintf(buf,"c%d.num_avg_UROM_uops",arch->id);
  sprintf(buf2,"c%d.num_UROM_uops/c%d.num_UROM_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average uops per UROM inst", buf2, "%12.2f");
  sprintf(buf,"c%d.avg_flowlen",arch->id);
  sprintf(buf2,"c%d.commit_uops/c%d.commit_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average uops per instruction", buf2, NULL);
  sprintf(buf,"c%d.avg_eff_flowlen",arch->id);
  sprintf(buf2,"c%d.commit_eff_uops/c%d.commit_insn",arch->id,arch->id);
  stat_reg_formula(sdb, true, buf, "average effective uops per instruction", buf2, NULL);
  sprintf(buf,"c%d.regfile_writes",arch->id);
  stat_reg_counter(sdb, true, buf, "number of register file writes", &core->stat.regfile_writes, 0, TRUE, NULL);
  sprintf(buf,"c%d.fp_regfile_writes",arch->id);
  stat_reg_counter(sdb, true, buf, "number of fp refister file writes", &core->stat.fp_regfile_writes, 0, TRUE, NULL);
  sprintf(buf,"c%d.flow_lengths",core->current_thread->id);
  core->stat.flow_histo = stat_reg_dist(sdb, buf,
                                           "histogram of uop flow lengths",
                                           /* initial value */0,
                                           /* array size */FLOW_HISTO_SIZE,
                                           /* bucket size */1,
                                           /* print format */(PF_COUNT|PF_PDF),
                                           /* format */NULL,
                                           /* index map */NULL,
                                           /* scale_me */TRUE,
                                           /* print fn */NULL);
  sprintf(buf,"c%d.eff_flow_lengths",core->current_thread->id);
  core->stat.eff_flow_histo = stat_reg_dist(sdb, buf,
                                           "histogram of effective uop flow lengths",
                                           /* initial value */0,
                                           /* array size */FLOW_HISTO_SIZE,
                                           /* bucket size */1,
                                           /* print format */(PF_COUNT|PF_PDF),
                                           /* format */NULL,
                                           /* index map */NULL,
                                           /* scale_me */TRUE,
                                           /* print fn */NULL);

}