⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cache_init.c

📁 ml-rsim 多处理器模拟器 支持类bsd操作系统
💻 C
📖 第 1 页 / 共 2 页
字号:
static void L1ICache_init(CACHE *captr, int nodeid, int procid){  int i;  if (cparam.L1I_size <= 0)    YS__errmsg(nodeid, "L1 I-cache size must be greater then zero");  /*   * Common fields: identity, configuration, etc.   */  captr->nodeid      = nodeid;  captr->procid      = procid;  captr->gid         = nodeid * ARCH_cpus + procid;  captr->type        = L1CACHE;  captr->size        = ARCH_cacsz1i;  captr->linesz      = ARCH_linesz1i;  captr->setsz       = ARCH_setsz1i;  captr->replacement = LRU;    /*   * Initialize data array. For perfect cache, we always fake a hit   * for each request, so no needs for data array.   */  Cache_init_aux(captr);  captr->data = (char*)memalign(sizeof(long long),				ARCH_cacsz1i *				(1024 / SIZE_OF_SPARC_INSTRUCTION) *				SIZEOF_INSTR);  if (captr->data == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);    /*   * Initialize MSHRs (Miss Status Hold Register?).   */  captr->max_mshrs = L1I_NUM_MSHRS;  captr->mshrs = RSIM_CALLOC(MSHR, captr->max_mshrs);  if (captr->mshrs == NULL)    YS__errmsg(nodeid, "Malloc failed in %s:%i", __FILE__, __LINE__);    for (i = 0; i < captr->max_mshrs; i++)    captr->mshrs[i].valid = 0;    captr->mshr_count = 0;       /* counts WRBs in MSHRs, etc */  captr->reqmshr_count = 0;    /* only counting data requests */  captr->reqs_at_mshr_count = 0;    /*   *  Initialize input queues   *  1. "request queue" contains request from processor.   *  2. "reply queue" contains replies from L2 cache.   *  3. "cohe queue" contains cohe request from other processor.   */  lqueue_init(&(captr->request_queue),	      L1I_REQUEST_QUEUE_SIZE > MEM_UNITS ?	      L1I_REQUEST_QUEUE_SIZE : MEM_UNITS);  lqueue_init(&(captr->reply_queue), L1I_REPLY_QUEUE_SIZE);  lqueue_init(&(captr->cohe_queue), L1I_COHE_QUEUE_SIZE);  captr->inq_empty = 1;    /*   * Tag pipelines. Unlike L2 cache, L1 cache has only a tag array.   */  captr->tag_pipe = RSIM_CALLOC(Pipeline *, L1I_TAG_PIPES);  if (captr->tag_pipe == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);  for (i = 0; i < L1I_TAG_PIPES; i++)    captr->tag_pipe[i] = NewPipeline(L1I_TAG_PORTS[i], 				     cparam.frequency * L1I_TAG_DELAY,				     cparam.frequency * L1I_TAG_REPEAT,				     L1I_TAG_DELAY / cparam.frequency);    captr->num_in_pipes = 0;    /*   * Statistics related stuff: capacity/conflict miss detector,   * prefetch earliness and lateness.   */  captr->ccd = NewCapConfDetector(captr->num_lines);  captr->pref_lateness  = NewStatrec(nodeid,				     "Prefetch Lateness", POINT, MEANS,				     HIST, 20, 0, 200);  captr->pref_earliness = NewStatrec(nodeid,				     "Prefetch Earlyness", POINT, MEANS,				     HIST, 20, 0, 200);}/*=========================================================================== * Initialization of the L1 D-cache. */static void L1DCache_init(CACHE *captr, int nodeid, int procid){  int i;  if (cparam.L1D_size == 0)    YS__errmsg(nodeid, "L1 D-cache size must be greater then zero");  /*   * Common fields: identity, configuration, etc.   */  captr->nodeid      = nodeid;  captr->procid      = procid;  captr->gid         = nodeid * ARCH_cpus + procid;  captr->type        = L1CACHE;  captr->size        = ARCH_cacsz1d;  captr->linesz      = ARCH_linesz1d;  captr->setsz       = ARCH_setsz1d;  captr->replacement = LRU;    /*   * Initialize data array. For perfect cache, we always fake a hit   * for each request, so no needs for data array.   */  if (cparam.L1D_perfect == 0)    Cache_init_aux(captr);  captr->data = NULL;    /*   * Initialize MSHRs (Miss Status Hold Register?).   */  captr->max_mshrs = L1D_NUM_MSHRS;  captr->mshrs = RSIM_CALLOC(MSHR, captr->max_mshrs);  if (captr->mshrs == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);    for (i = 0; i < captr->max_mshrs; i++)    captr->mshrs[i].valid = 0;    captr->mshr_count = 0;       /* counts WRBs in MSHRs, etc */  captr->reqmshr_count = 0;    /* only counting data requests */  captr->reqs_at_mshr_count = 0;    /*   *  Initialize input queues   *  1. "request queue" contains request from processor.   *  2. "reply queue" contains replies from L2 cache.   *  3. "cohe queue" contains cohe request from other processor.   */  lqueue_init(&(captr->request_queue),	      L1D_REQUEST_QUEUE_SIZE > MEM_UNITS ?	      L1D_REQUEST_QUEUE_SIZE : MEM_UNITS);  lqueue_init(&(captr->reply_queue), L1D_REPLY_QUEUE_SIZE);  lqueue_init(&(captr->cohe_queue), L1D_COHE_QUEUE_SIZE);  captr->inq_empty = 1;    /*   * Tag pipelines. Unlike L2 cache, L1 cache has only a tag array.   */  captr->tag_pipe = RSIM_CALLOC(Pipeline *, L1D_TAG_PIPES);  if (captr->tag_pipe == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);  for (i = 0; i < L1D_TAG_PIPES; i++)    captr->tag_pipe[i] = NewPipeline(L1D_TAG_PORTS[i], 				     cparam.frequency * L1D_TAG_DELAY,				     cparam.frequency * L1D_TAG_REPEAT,				     L1D_TAG_DELAY / cparam.frequency);    captr->num_in_pipes = 0;    /*   * Statistics related stuff: capacity/conflict miss detector,   * prefetch earliness and lateness.   */  captr->ccd = NewCapConfDetector(captr->num_lines);  captr->pref_lateness  = NewStatrec(nodeid,				     "Prefetch Lateness", POINT, MEANS,				     HIST, 20, 0, 200);  captr->pref_earliness = NewStatrec(nodeid,				     "Prefetch Earlyness", POINT, MEANS,				     HIST, 20, 0, 200);}/*=========================================================================== * Initialize the L2 cache */static void L2Cache_init(CACHE *captr, int nodeid, int procid){  int i;  /*   * Common field: identity, configuration   */  captr->nodeid      = nodeid;  captr->procid      = procid;  captr->gid         = nodeid * ARCH_cpus + procid;  captr->type        = L2CACHE;  captr->size        = ARCH_cacsz2;  captr->linesz      = ARCH_linesz2;  captr->setsz       = ARCH_setsz2;  captr->replacement = LRU;  /*   * Initialize data array.   */  if (cparam.L2_perfect == 0)    Cache_init_aux(captr);  captr->data = 0;    /*   * Intialize MSHRs   */  captr->max_mshrs = L2_NUM_MSHRS;  captr->mshrs = RSIM_CALLOC(MSHR, captr->max_mshrs);  if (captr->mshrs == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);  for (i = 0; i < captr->max_mshrs; i++)    captr->mshrs[i].valid = 0;  captr->mshr_count = 0;  captr->reqmshr_count = 0;  captr->reqs_at_mshr_count = 0;  /*   * Initialize input queues. As in L1 cache, it has three input queues.   */  lqueue_init(&(captr->request_queue), L2_REQUEST_QUEUE_SIZE);  lqueue_init(&(captr->reply_queue), L2_REPLY_QUEUE_SIZE);  lqueue_init(&(captr->cohe_queue), L2_COHE_QUEUE_SIZE);  lqueue_init(&(captr->noncohe_queue), IO_MAX_TRANS);  captr->cohe_reply_queue = &(captr->cohe_queue);  captr->inq_empty     = 1;  /*   * Pipelines. Unlike L1 cache, L2 cache is split into a "tag SRAM"   * array and a "data SRAM" array.   */  captr->data_pipe = RSIM_CALLOC(Pipeline *, L2_DATA_PIPES);  if (captr->data_pipe == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);  for (i = 0; i < L2_DATA_PIPES; i++)    captr->data_pipe[i] = NewPipeline(L2_DATA_PORTS[i], 				      cparam.frequency * L2_DATA_DELAY,				      cparam.frequency * L2_DATA_REPEAT,				      L2_DATA_REPEAT ?				      (L2_DATA_DELAY / cparam.frequency) : 1);  captr->tag_pipe = RSIM_CALLOC(Pipeline*, L2_TAG_PIPES);  if (captr->tag_pipe == NULL)    YS__errmsg(nodeid, "Malloc failed at %s:%i", __FILE__, __LINE__);  for (i = 0; i < L2_TAG_PIPES; i++)    captr->tag_pipe[i] = NewPipeline(L2_TAG_PORTS[i], 				     cparam.frequency * L2_TAG_DELAY,				     cparam.frequency * L2_TAG_REPEAT,				     L2_TAG_DELAY / cparam.frequency);  captr->num_in_pipes = 0;  /*   * Interface to bus. (L1 cache doesn't have the equivalent part.)   */  dqueue_init(&(captr->reqbuffer), REQUEST_BUFFER_SIZE);  lqueue_init(&(captr->outbuffer), OUT_BUFFER_SIZE);  lqueue_init(&(captr->arbwaiters), MAX_ARB_WAITERS);  captr->arbwaiters_count  = 0;  captr->stall_request     = 0;  captr->stall_reply       = 0;  captr->stall_cohe        = 0;  captr->cohe_reply        = 0;  captr->data_cohe_pending = 0;  captr->pending_writeback = 0;  captr->pending_request   = 0;    /*   * Statistics related stuffs: capacity/conflict miss detector; prefetch   * earliness and lateness.   */  captr->ccd = NewCapConfDetector(captr->num_lines);  captr->pref_lateness  = NewStatrec(nodeid,				     "Prefetch Lateness",				     POINT, MEANS,				     HIST, 20, 0, 200);  captr->pref_earliness = NewStatrec(nodeid,				     "Prefetch Earlyness",				     POINT, MEANS,				     HIST, 20, 0, 200);}/*=========================================================================== * This routine initializes the tag SRAM array of a specified cache. * It allocates space for each cache line. Since there is no real data * flowing around in the memory system, each line is represented by * its associated control information: state, physical tag, age, and some  * other information needed by the simulator to collect statistics. */void Cache_init_aux(CACHE * captr){  int i, j;  int nof_sets, num_lines;  int cachesize, blocksize, setsize;  cachesize = captr->size;  blocksize = captr->linesz;  setsize   = captr->setsz;  /*   * Sanity check on cache configuration.   */  if (cachesize == INFINITE)    YS__errmsg(captr->nodeid,	       "No infinite cache in this version.");  if (blocksize < WORDSZ)    YS__errmsg(captr->nodeid,	       "NewCache(): line size %d is too small.", blocksize);  if (NumOfBits(blocksize, 1) < 0)    YS__errmsg(captr->nodeid,	       "NewCache(): line size(%d) isn't a power of 2", blocksize);  if (setsize != FULL_ASS)    if (NumOfBits(setsize, 1) < 0)      YS__errmsg(captr->nodeid,		 "NewCache(): set size(%d) isn't a power of 2", setsize);    if ((cachesize * 1024) % blocksize)    YS__errmsg(captr->nodeid,	       "NewCache(): cache-size(%dKbytes) / line-size(%dbytes) != 0",	       cachesize, blocksize);  num_lines = (cachesize * 1024) / blocksize;  if (setsize != FULL_ASS)  /* set associativity */    {      if (setsize > num_lines)	YS__errmsg(captr->nodeid,		   "setsize(%d) > num_lines(%d)", setsize, num_lines);      nof_sets = num_lines / setsize;    }  else    { /* set size is fully associative; */      setsize      = num_lines;      captr->setsz = setsize;      nof_sets     = 1;    }  /*   * Some facilitator variables to speed up the address manipulation   * in cache search functions.   */  captr->num_lines   = num_lines;  captr->set_mask    = setsize - 1;  captr->set_shift   = NumOfBits(setsize, 1);  captr->idx_mask    = nof_sets - 1;  captr->idx_shift   = NumOfBits(nof_sets, 1);  captr->block_mask  = blocksize - 1;  captr->block_shift = NumOfBits(blocksize, 1);  captr->tag_shift   = captr->block_shift + captr->idx_shift;  /*   * initialize the data SRAM array.   */  captr->tags = RSIM_CALLOC(cline_t, num_lines);  if (captr->tags == NULL)    YS__errmsg(captr->nodeid,	       "NewCache(): malloc failed at %s:%i",	       __FILE__, __LINE__);  for (i = 0; i < num_lines; i += setsize)    for (j = 0; j < setsize; j++)      {	captr->tags[i+j].index         = i+j;	captr->tags[i+j].state         = INVALID;	captr->tags[i+j].tag           = -1;	captr->tags[i+j].age           = setsize;	captr->tags[i+j].mshr_out      = 0;	captr->tags[i+j].pref          = 0;	captr->tags[i+j].pref_tag_repl = -1;      }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -