src/memory/memory.c
void init_uncores(void) {
  mem->uncores = (Uncore*)malloc(sizeof(Uncore) * NUM_CORES);

  /* Initialize MLC cache (shared only for now) */
  Ported_Cache* mlc = (Ported_Cache*)malloc(sizeof(Ported_Cache));
  init_cache(&mlc->cache, "MLC_CACHE", MLC_SIZE, MLC_ASSOC, MLC_LINE_SIZE,
             sizeof(MLC_Data), MLC_CACHE_REPL_POLICY);
  mlc->num_banks = MLC_BANKS;
  mlc->ports     = (Ports*)malloc(sizeof(Ports) * mlc->num_banks);
  for(uns ii = 0; ii < mlc->num_banks; ii++) {
    char name[MAX_STR_LENGTH + 1];
    snprintf(name, MAX_STR_LENGTH, "MLC BANK %d PORTS", ii);
    init_ports(&mlc->ports[ii], name, MLC_READ_PORTS, MLC_WRITE_PORTS, FALSE);
  }
  for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
    MLC(proc_id) = mlc;
  }

  /* Initialize LLC */
  if(PRIVATE_L1) {
    ASSERTM(
      0, L1_SIZE % NUM_CORES == 0,
      "Total L1_SIZE must be a multiple of NUM_CORES if PRIVATE_L1 is on\n");
    ASSERTM(
      0, L1_BANKS % NUM_CORES == 0,
      "Total L1_BANKS must be a multiple of NUM_CORES if PRIVATE_L1 is on\n");
    for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
      Ported_Cache* l1 = (Ported_Cache*)malloc(sizeof(Ported_Cache));

      char buf[MAX_STR_LENGTH + 1];
      sprintf(buf, "L1[%d]", proc_id);
      init_cache(&l1->cache, buf, L1_SIZE / NUM_CORES, L1_ASSOC, L1_LINE_SIZE,
                 sizeof(L1_Data), L1_CACHE_REPL_POLICY);

      l1->num_banks = L1_BANKS / NUM_CORES;
      l1->ports     = (Ports*)malloc(sizeof(Ports) * l1->num_banks);
      for(uns ii = 0; ii < l1->num_banks; ii++) {
        char name[MAX_STR_LENGTH + 1];
        snprintf(name, MAX_STR_LENGTH, "L1[%d] BANK %d PORTS", proc_id, ii);
        init_ports(&l1->ports[ii], name, L1_READ_PORTS, L1_WRITE_PORTS, FALSE);
      }
      L1(proc_id) = l1;
    }
  } else {
    Ported_Cache* l1 = (Ported_Cache*)malloc(sizeof(Ported_Cache));
    init_cache(&l1->cache, "L1_CACHE", L1_SIZE, L1_ASSOC, L1_LINE_SIZE,
               sizeof(L1_Data), L1_CACHE_REPL_POLICY);
    l1->num_banks = L1_BANKS;
    l1->ports     = (Ports*)malloc(sizeof(Ports) * l1->num_banks);
    for(uns ii = 0; ii < l1->num_banks; ii++) {
      char name[MAX_STR_LENGTH + 1];
      snprintf(name, MAX_STR_LENGTH, "L1 BANK %d PORTS", ii);
      init_ports(&l1->ports[ii], name, L1_READ_PORTS, L1_WRITE_PORTS, FALSE);
    }
    for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
      L1(proc_id) = l1;
    }
  }

  if(L1_CACHE_REPL_POLICY == REPL_PARTITION) {
    // initially equally partition
    uns num_ways = L1_ASSOC / NUM_CORES;
    for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
      set_partition_allocate(&L1(proc_id)->cache, proc_id, num_ways);
    }

    // set static partition (if used)
    if(L1_STATIC_PARTITION_ENABLE) {
      ASSERT(0, !L1_DYNAMIC_PARTITION_ENABLE);
      ASSERTM(0, L1_STATIC_PARTITION, "Please specify L1_STATIC_PARTITION\n");
      int ways_per_core[MAX_NUM_PROCS];
      int num_tokens = parse_int_array(ways_per_core, L1_STATIC_PARTITION,
                                       MAX_NUM_PROCS);
      ASSERT(0, num_tokens == NUM_CORES);
      for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
        set_partition_allocate(&L1(proc_id)->cache, proc_id,
                               ways_per_core[proc_id]);
      }
    }

    // set dynamic partition (if used)
    if(L1_DYNAMIC_PARTITION_ENABLE && L1_DYNAMIC_PARTITION_POLICY == UMON_DSS) {
      mem->umon_cache_core = (Cache*)malloc(sizeof(Cache) * NUM_CORES);
      mem->umon_cache_hit_count_core = (double**)malloc(sizeof(double*) *
                                                        NUM_CORES);
      int ii;

      for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
        init_cache(&mem->umon_cache_core[proc_id], "UMON_CACHE",
                   L1_SIZE / 32 / L1_LINE_SIZE, L1_ASSOC, 1,
                   sizeof(Umon_Cache_Data), REPL_TRUE_LRU);

        mem->umon_cache_hit_count_core[proc_id] = (double*)malloc(
          sizeof(double) * L1_ASSOC);
        for(ii = 0; ii < L1_ASSOC; ii++) {
          mem->umon_cache_hit_count_core[proc_id][ii] = 0;
        }
      }
    }
  }

  for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
    mem->uncores[proc_id].num_outstanding_l1_accesses = 0;
    mem->uncores[proc_id].num_outstanding_l1_misses   = 0;
    mem->uncores[proc_id].mem_block_start             = 0;
  }
}
/**
 * @brief this function should only be called once in warmup mode
 *
 */
@brief this function should only be called once in warmup mode
@brief this function should only be called once in warmup mode
void init_uncores(void) {
  mem->uncores = (Uncore*)malloc(sizeof(Uncore) * NUM_CORES);
  Ported_Cache* mlc = (Ported_Cache*)malloc(sizeof(Ported_Cache));
  init_cache(&mlc->cache, "MLC_CACHE", MLC_SIZE, MLC_ASSOC, MLC_LINE_SIZE,
             sizeof(MLC_Data), MLC_CACHE_REPL_POLICY);
  mlc->num_banks = MLC_BANKS;
  mlc->ports     = (Ports*)malloc(sizeof(Ports) * mlc->num_banks);
  for(uns ii = 0; ii < mlc->num_banks; ii++) {
    char name[MAX_STR_LENGTH + 1];
    snprintf(name, MAX_STR_LENGTH, "MLC BANK %d PORTS", ii);
    init_ports(&mlc->ports[ii], name, MLC_READ_PORTS, MLC_WRITE_PORTS, FALSE);
  }
  for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
    MLC(proc_id) = mlc;
  }
  if(PRIVATE_L1) {
    ASSERTM(
      0, L1_SIZE % NUM_CORES == 0,
      "Total L1_SIZE must be a multiple of NUM_CORES if PRIVATE_L1 is on\n");
    ASSERTM(
      0, L1_BANKS % NUM_CORES == 0,
      "Total L1_BANKS must be a multiple of NUM_CORES if PRIVATE_L1 is on\n");
    for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
      Ported_Cache* l1 = (Ported_Cache*)malloc(sizeof(Ported_Cache));
      char buf[MAX_STR_LENGTH + 1];
      sprintf(buf, "L1[%d]", proc_id);
      init_cache(&l1->cache, buf, L1_SIZE / NUM_CORES, L1_ASSOC, L1_LINE_SIZE,
                 sizeof(L1_Data), L1_CACHE_REPL_POLICY);
      l1->num_banks = L1_BANKS / NUM_CORES;
      l1->ports     = (Ports*)malloc(sizeof(Ports) * l1->num_banks);
      for(uns ii = 0; ii < l1->num_banks; ii++) {
        char name[MAX_STR_LENGTH + 1];
        snprintf(name, MAX_STR_LENGTH, "L1[%d] BANK %d PORTS", proc_id, ii);
        init_ports(&l1->ports[ii], name, L1_READ_PORTS, L1_WRITE_PORTS, FALSE);
      }
      L1(proc_id) = l1;
    }
  } else {
    Ported_Cache* l1 = (Ported_Cache*)malloc(sizeof(Ported_Cache));
    init_cache(&l1->cache, "L1_CACHE", L1_SIZE, L1_ASSOC, L1_LINE_SIZE,
               sizeof(L1_Data), L1_CACHE_REPL_POLICY);
    l1->num_banks = L1_BANKS;
    l1->ports     = (Ports*)malloc(sizeof(Ports) * l1->num_banks);
    for(uns ii = 0; ii < l1->num_banks; ii++) {
      char name[MAX_STR_LENGTH + 1];
      snprintf(name, MAX_STR_LENGTH, "L1 BANK %d PORTS", ii);
      init_ports(&l1->ports[ii], name, L1_READ_PORTS, L1_WRITE_PORTS, FALSE);
    }
    for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
      L1(proc_id) = l1;
    }
  }
  if(L1_CACHE_REPL_POLICY == REPL_PARTITION) {
    uns num_ways = L1_ASSOC / NUM_CORES;
    for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
      set_partition_allocate(&L1(proc_id)->cache, proc_id, num_ways);
    }
    if(L1_STATIC_PARTITION_ENABLE) {
      ASSERT(0, !L1_DYNAMIC_PARTITION_ENABLE);
      ASSERTM(0, L1_STATIC_PARTITION, "Please specify L1_STATIC_PARTITION\n");
      int ways_per_core[MAX_NUM_PROCS];
      int num_tokens = parse_int_array(ways_per_core, L1_STATIC_PARTITION,
                                       MAX_NUM_PROCS);
      ASSERT(0, num_tokens == NUM_CORES);
      for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
        set_partition_allocate(&L1(proc_id)->cache, proc_id,
                               ways_per_core[proc_id]);
      }
    }
    if(L1_DYNAMIC_PARTITION_ENABLE && L1_DYNAMIC_PARTITION_POLICY == UMON_DSS) {
      mem->umon_cache_core = (Cache*)malloc(sizeof(Cache) * NUM_CORES);
      mem->umon_cache_hit_count_core = (double**)malloc(sizeof(double*) *
                                                        NUM_CORES);
      int ii;
      for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
        init_cache(&mem->umon_cache_core[proc_id], "UMON_CACHE",
                   L1_SIZE / 32 / L1_LINE_SIZE, L1_ASSOC, 1,
                   sizeof(Umon_Cache_Data), REPL_TRUE_LRU);
        mem->umon_cache_hit_count_core[proc_id] = (double*)malloc(
          sizeof(double) * L1_ASSOC);
        for(ii = 0; ii < L1_ASSOC; ii++) {
          mem->umon_cache_hit_count_core[proc_id][ii] = 0;
        }
      }
    }
  }
  for(uns proc_id = 0; proc_id < NUM_CORES; proc_id++) {
    mem->uncores[proc_id].num_outstanding_l1_accesses = 0;
    mem->uncores[proc_id].num_outstanding_l1_misses   = 0;
    mem->uncores[proc_id].mem_block_start             = 0;
  }
}
void init_uncores ( void ) { mem -> uncores = ( Uncore * ) malloc ( sizeof ( Uncore ) * NUM_CORES ) ; Ported_Cache * mlc = ( Ported_Cache * ) malloc ( sizeof ( Ported_Cache ) ) ; init_cache ( & mlc -> cache , " " , MLC_SIZE , MLC_ASSOC , MLC_LINE_SIZE , sizeof ( MLC_Data ) , MLC_CACHE_REPL_POLICY ) ; mlc -> num_banks = MLC_BANKS ; mlc -> ports = ( Ports * ) malloc ( sizeof ( Ports ) * mlc -> num_banks ) ; for ( uns ii = 0 ; ii < mlc -> num_banks ; ii ++ ) { char name [ MAX_STR_LENGTH + 1 ] ; snprintf ( name , MAX_STR_LENGTH , " " , ii ) ; init_ports ( & mlc -> ports [ ii ] , name , MLC_READ_PORTS , MLC_WRITE_PORTS , FALSE ) ; } for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { MLC ( proc_id ) = mlc ; } if ( PRIVATE_L1 ) { ASSERTM ( 0 , L1_SIZE % NUM_CORES == 0 , " \n " ) ; ASSERTM ( 0 , L1_BANKS % NUM_CORES == 0 , " \n " ) ; for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { Ported_Cache * l1 = ( Ported_Cache * ) malloc ( sizeof ( Ported_Cache ) ) ; char buf [ MAX_STR_LENGTH + 1 ] ; sprintf ( buf , " " , proc_id ) ; init_cache ( & l1 -> cache , buf , L1_SIZE / NUM_CORES , L1_ASSOC , L1_LINE_SIZE , sizeof ( L1_Data ) , L1_CACHE_REPL_POLICY ) ; l1 -> num_banks = L1_BANKS / NUM_CORES ; l1 -> ports = ( Ports * ) malloc ( sizeof ( Ports ) * l1 -> num_banks ) ; for ( uns ii = 0 ; ii < l1 -> num_banks ; ii ++ ) { char name [ MAX_STR_LENGTH + 1 ] ; snprintf ( name , MAX_STR_LENGTH , " " , proc_id , ii ) ; init_ports ( & l1 -> ports [ ii ] , name , L1_READ_PORTS , L1_WRITE_PORTS , FALSE ) ; } L1 ( proc_id ) = l1 ; } } else { Ported_Cache * l1 = ( Ported_Cache * ) malloc ( sizeof ( Ported_Cache ) ) ; init_cache ( & l1 -> cache , " " , L1_SIZE , L1_ASSOC , L1_LINE_SIZE , sizeof ( L1_Data ) , L1_CACHE_REPL_POLICY ) ; l1 -> num_banks = L1_BANKS ; l1 -> ports = ( Ports * ) malloc ( sizeof ( Ports ) * l1 -> num_banks ) ; for ( uns ii = 0 ; ii < l1 -> num_banks ; ii ++ ) { char name [ MAX_STR_LENGTH + 1 ] ; snprintf ( name , MAX_STR_LENGTH , " " , ii ) ; init_ports ( & l1 -> ports [ ii ] , name , L1_READ_PORTS , L1_WRITE_PORTS , FALSE ) ; } for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { L1 ( proc_id ) = l1 ; } } if ( L1_CACHE_REPL_POLICY == REPL_PARTITION ) { uns num_ways = L1_ASSOC / NUM_CORES ; for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { set_partition_allocate ( & L1 ( proc_id ) -> cache , proc_id , num_ways ) ; } if ( L1_STATIC_PARTITION_ENABLE ) { ASSERT ( 0 , ! L1_DYNAMIC_PARTITION_ENABLE ) ; ASSERTM ( 0 , L1_STATIC_PARTITION , " \n " ) ; int ways_per_core [ MAX_NUM_PROCS ] ; int num_tokens = parse_int_array ( ways_per_core , L1_STATIC_PARTITION , MAX_NUM_PROCS ) ; ASSERT ( 0 , num_tokens == NUM_CORES ) ; for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { set_partition_allocate ( & L1 ( proc_id ) -> cache , proc_id , ways_per_core [ proc_id ] ) ; } } if ( L1_DYNAMIC_PARTITION_ENABLE && L1_DYNAMIC_PARTITION_POLICY == UMON_DSS ) { mem -> umon_cache_core = ( Cache * ) malloc ( sizeof ( Cache ) * NUM_CORES ) ; mem -> umon_cache_hit_count_core = ( double * * ) malloc ( sizeof ( double * ) * NUM_CORES ) ; int ii ; for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { init_cache ( & mem -> umon_cache_core [ proc_id ] , " " , L1_SIZE / 32 / L1_LINE_SIZE , L1_ASSOC , 1 , sizeof ( Umon_Cache_Data ) , REPL_TRUE_LRU ) ; mem -> umon_cache_hit_count_core [ proc_id ] = ( double * ) malloc ( sizeof ( double ) * L1_ASSOC ) ; for ( ii = 0 ; ii < L1_ASSOC ; ii ++ ) { mem -> umon_cache_hit_count_core [ proc_id ] [ ii ] = 0 ; } } } } for ( uns proc_id = 0 ; proc_id < NUM_CORES ; proc_id ++ ) { mem -> uncores [ proc_id ] . num_outstanding_l1_accesses = 0 ; mem -> uncores [ proc_id ] . num_outstanding_l1_misses = 0 ; mem -> uncores [ proc_id ] . mem_block_start = 0 ; } }
@brief this function should only be called once in warmup mode
@brief this function should only be called once in warmup mode
/* Initialize MLC cache (shared only for now) */ /* Initialize LLC */ // initially equally partition // set static partition (if used) // set dynamic partition (if used)