summaryrefslogtreecommitdiff
path: root/src/mem
diff options
context:
space:
mode:
authorAndreas Hansson <andreas.hansson@arm.com>2012-03-30 12:57:48 -0400
committerAndreas Hansson <andreas.hansson@arm.com>2012-03-30 12:57:48 -0400
commit74043c4f5c6f4b4d43c518f47da4cd1bd68b9e08 (patch)
treec2da6f291c42463e6cb0adb4d59a275c97ac33f1 /src/mem
parenta128ba7cd1ab506e3468c82c1060a7fb4ad909b1 (diff)
downloadgem5-74043c4f5c6f4b4d43c518f47da4cd1bd68b9e08.tar.xz
MEM: Remove legacy DRAM in preparation for memory updates
This patch removes the DRAM memory class in preparation for updates to the memory system, with the first one introducing an abstract memory class, and removing the assumption of a single physical memory.
Diffstat (limited to 'src/mem')
-rw-r--r--src/mem/PhysicalMemory.py18
-rw-r--r--src/mem/SConscript1
-rw-r--r--src/mem/dram.cc2672
-rw-r--r--src/mem/dram.hh161
4 files changed, 0 insertions, 2852 deletions
diff --git a/src/mem/PhysicalMemory.py b/src/mem/PhysicalMemory.py
index c5f80b4c9..756117972 100644
--- a/src/mem/PhysicalMemory.py
+++ b/src/mem/PhysicalMemory.py
@@ -39,21 +39,3 @@ class PhysicalMemory(MemObject):
latency_var = Param.Latency('0ns', "access variablity")
zero = Param.Bool(False, "zero initialize memory")
null = Param.Bool(False, "do not store data, always return zero")
-
-class DRAMMemory(PhysicalMemory):
- type = 'DRAMMemory'
- # Many of these should be observed from the configuration
- cpu_ratio = Param.Int(5,"ratio between CPU speed and memory bus speed")
- mem_type = Param.String("SDRAM", "Type of DRAM (DRDRAM, SDRAM)")
- mem_actpolicy = Param.String("open", "Open/Close policy")
- memctrladdr_type = Param.String("interleaved", "Mapping interleaved or direct")
- bus_width = Param.Int(16, "")
- act_lat = Param.Latency("2ns", "RAS to CAS delay")
- cas_lat = Param.Latency("1ns", "CAS delay")
- war_lat = Param.Latency("2ns", "write after read delay")
- pre_lat = Param.Latency("2ns", "precharge delay")
- dpl_lat = Param.Latency("2ns", "data in to precharge delay")
- trc_lat = Param.Latency("6ns", "row cycle delay")
- num_banks = Param.Int(4, "Number of Banks")
- num_cpus = Param.Int(4, "Number of CPUs connected to DRAM")
-
diff --git a/src/mem/SConscript b/src/mem/SConscript
index cc5e3a37a..d30fd7fcb 100644
--- a/src/mem/SConscript
+++ b/src/mem/SConscript
@@ -48,7 +48,6 @@ Source('se_translating_port_proxy.cc')
if env['TARGET_ISA'] != 'no':
SimObject('PhysicalMemory.py')
- Source('dram.cc')
Source('page_table.cc')
Source('physical.cc')
diff --git a/src/mem/dram.cc b/src/mem/dram.cc
deleted file mode 100644
index 6253f9828..000000000
--- a/src/mem/dram.cc
+++ /dev/null
@@ -1,2672 +0,0 @@
-/*
- * Copyright (c) 2004 The Regents of The University of Michigan
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met: redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer;
- * redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution;
- * neither the name of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Authors: Ali Saidi
- * Ron Dreslinski
- */
-
-/*
- Copyright (c) 2000 Computer Engineering and Communication Networks Lab (TIK)
- Swiss Federal Institute of Technology (ETH) Zurich, Switzerland
-
- All rights reserved.
- Permission is hereby granted, without written agreement and without
- license or royalty fees, to use, copy, modify, and distribute this
- software and its documentation for any purpose, provided that the above
- copyright notice and the following two paragraphs appear in all copies
- of this software.
-
- IN NO EVENT SHALL THE TIK OR THE ETH ZURICH BE LIABLE TO ANY PARTY
- FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
- THE TIK OR THE ETH ZURICH HAVE BEEN ADVISED OF THE POSSIBILITY OF
- SUCH DAMAGE.
-
- THE TIK AND THE ETH ZURICH SPECIFICALLY DISCLAIM ANY WARRANTIES,
- INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
- MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE
- PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND TIK AND THE ETH ZURICH
- HAVE NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, UPDATES,
- ENHANCEMENTS, OR MODIFICATIONS.
-*/
-
-/* authors: Andreas Romer 4/99 - 7/99
- Matthias Gries 4/99 - 2/01
-
-
-References: http://www.tik.ee.ethz.ch/
-======================================
--> Publications http://www.tik.ee.ethz.ch/db/tik/publications/form_search_publications.php3
-
-
-Matthias Gries: A Survey of Synchronous RAM Architectures.
-TIK Report Nr. 71, Computer Engineering and Networks Lab (TIK),
-Swiss Federal Institute of Technology (ETH) Zurich, April, 1999
-
--> DRAM survey
-
-
-Matthias Gries, Andreas Romer: Performance Evaluation of Recent
-DRAM Architectures for Embedded Systems.
-TIK Report Nr. 82, Computer Engineering and Networks Lab (TIK),
-Swiss Federal Institute of Technology (ETH) Zurich, November, 1999.
-
--> description of the DRAM and controller models for SimpleScalar in the appendix
-(note that the current software version additionally supports overlapping in
- closed-page mode with slightly modified timing)
-
-
-Matthias Gries: The Impact of Recent DRAM Architectures on Embedded Systems Performance.
-Euromicro2000, Symposium on Digital Systems Design, IEEE Computer, Maastricht, Netherlands,
-Vol. 1, pages 282-289, September, 2000.
-
--> performance study with SimpleScalar
-
-
-Matthias Gries: Modeling a Memory Subsystem with Petri Nets: a Case Study.
-A. Yakovlev, L. Gomes, and L. Lavagno (Eds), Hardware Design and Petri Nets,
-Kluwer Academic, pages 291-310, March, 2000.
-
--> SDRAM + controller performance model as a high-level Petri net
-*/
-
-/**
- * @file
- * Definition of a DRAM like main memory.
- */
-
-#include <cstdlib>
-#include <string>
-
-#include "mem/dram.hh"
-
-extern int maxThreadsPerCPU;
-
-/* SDRAM system: PC100/PC133 2-2-2 DIMM timing according to
- PC SDRAM Specification, Rev. 1.7, Intel Corp, Nov. 1999.
-
- 64 bit DIMM consists of four 16x organized 256 Mbit SDRAMs, 128 MByte of main memory in total.*/
-/* the settings above must be changed if another memory is used */
-/* DRDRAM system: 16 bit channel, four chips (single RIMM), 128 MByte of main memory in total.
- Timing: Rambus Inc, Direct RDRAM, preliminary information, 256/288Mbit: 40-800 timing */
-
-
-#define DR_STACK_BASE 0x8000000 /* total size of memory: 128 Mbyte */
-#define DR_BANK_SIZE 0x100000 /* size of a bank : 1 Mbyte */
-#define DR_ROW_SIZE 0x800 /* size of a row : 2 Kbyte */
-#define DR_NUM_BANKS (DR_STACK_BASE/DR_BANK_SIZE) /* number of banks : 128 */
-#define DR_NUM_ROWS (DR_BANK_SIZE/DR_ROW_SIZE) /* number of rows per bank: 512 */
-#define DR_DATA_BASE 0x4000000 /* Size of textsegment : 64 Mbyte */
-#define DR_NUM_BYTE_MEM 16 /* data packet capacity: 16 byte */
-#define DR_NUM_DEVS 4 /* number of devices along channel */
-#define DR_BANK_SAMP 16 /* 16 banks are together in one group in each device: bank 15 and 16 have no shared SAMPs */
-#define DR_T_PACKET 4 /* number of cycles (in 400 MHz) the memory needs to deliver a data packet */
-#define DR_T_RCD 7 /* RAS to CAS delay */
-#define DR_T_CAC 8 /* read access delay: number of cylces from read to data (trailing to leading edge of packet!) */
-#define DR_T_CWD 6 /* Write delay: number of cylces from write to write data (trailing to leading edge of packet!) */
-#define DR_T_RP 8 /* row precharge delay */
-#define DR_T_RTR 8 /* retire delay*/
-#define DR_T_RDP 4 /* min delay from read to precharge in cycles */
-#define DR_T_PP 8 /* precharge to precharge time to any bank in the same device */
-#define DR_T_RAS 20 /* minimal row active time */
-/*the settings above need to be changed if the memory is altered*/
-#define DR_DYNAMIC_SIZE (DR_STACK_BASE - DR_DATA_BASE) /* size of the heap and stack at most: 64 Mbyte */
-// #define DR_NUM_BANKS (DR_STACK_BASE/DR_BANK_SIZE) /* number of banks : 128 */
-// #define DR_NUM_ROWS (DR_BANK_SIZE/DR_ROW_SIZE) /* number of rows per bank: 512 */
-#define DR_T_OWR (DR_T_CWD + DR_T_PACKET - DR_T_RTR) /* overlap after write retire */
-#define DR_T_HELP (DR_T_CAC+DR_T_PACKET-DR_T_RDP+DR_T_PACKET) /* used for read after read with precharge */
-/*delays until data is ready/written to the memory for the DRDRAM*/
-#define DR_T_READ_READ_SROW (DR_T_CAC + DR_T_PACKET) /* RAR, row hit, current bank */
-#define DR_T_READ_WRITE_SROW (DR_T_CAC + DR_T_PACKET) /* RAW, row hit, current bank */
-#define DR_T_WRITE_READ_SROW (DR_T_CWD + DR_T_PACKET) /* WAR, row hit, current bank */
-#define DR_T_WRITE_WRITE_SROW (DR_T_CWD + DR_T_PACKET) /* WAW, row hit, current bank */
-#define DR_T_READ_READ_SBANK (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET) /* RAR, row miss, current bank */
-#define DR_T_READ_WRITE_SBANK (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET) /* RAW, row miss, current bank */
-#define DR_T_WRITE_READ_SBANK (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET) /* WAR, row miss, current bank */
-#define DR_T_WRITE_WRITE_SBANK (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET) /* WAR, row miss, current bank */
-#define DR_T_READ_READ_OBANK (DR_T_PP+DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET) /* RAR, row miss, another bank */
-#define DR_T_READ_WRITE_OBANK (DR_T_PP+DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET) /* RAW, row miss, another bank */
-#define DR_T_WRITE_READ_OBANK (DR_T_PP+DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET) /* WAR, row miss, another bank */
-#define DR_T_WRITE_WRITE_OBANK (DR_T_PP+DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET) /* WAR, row miss, another bank */
-/* best-case latencies (due to overlap / row hits in another bank) */
-#define DR_BEST_T_READ_READ_SROW 0 /* RAR, row hit, current bank */
-#define DR_BEST_T_READ_WRITE_SROW (DR_T_CAC+DR_T_PACKET-DR_T_OWR) /* RAW, row hit, current bank */
-#define DR_BEST_T_WRITE_READ_SROW 0 /* WAR, row hit, current bank */
-#define DR_BEST_T_WRITE_WRITE_SROW (DR_T_CWD+DR_T_PACKET-DR_T_OWR) /* WAR, row hit, current bank */
-#define DR_BEST_T_READ_READ_SBANK (DR_T_RCD + DR_T_CAC) /* RAR, row miss, current bank */
-#define DR_BEST_T_READ_WRITE_SBANK (DR_T_RP-DR_T_OWR+DR_T_RCD+DR_T_CAC+DR_T_PACKET) /* RAW, row miss, current bank */
-#define DR_BEST_T_WRITE_READ_SBANK (DR_T_RCD+DR_T_CWD) /* WAR, row miss, current bank */
-#define DR_BEST_T_WRITE_WRITE_SBANK (DR_T_RP-DR_T_OWR+DR_T_RCD+DR_T_CWD+DR_T_PACKET) /* WAW, row miss, current bank */
-#define DR_BEST_T_READ_READ_OBANK 0 /* RAR, row miss/hit, another bank */
-#define DR_BEST_T_READ_WRITE_OBANK (DR_T_PACKET+DR_T_CAC-DR_T_OWR) /* RAW, row miss/hit, another bank */
-#define DR_BEST_T_WRITE_READ_OBANK 0 /* WAR, row miss/hit, another bank */
-#define DR_BEST_T_WRITE_WRITE_OBANK 0 /* WAW, row miss/hit, another bank */
-#define DR_BEST_T_READ_WRITE_ODEV (DR_T_CAC-DR_T_CWD) /* RAW, row miss/hit, another device */
-
-
-#define MIN(a,b) ((a<b) ? a : b)
-#define SD_ROW_SIZE 0x1000 /* size of a row : 4 Kbyte */
-
-
-
-DRAMMemory::DRAMMemory(const Params *p)
- : PhysicalMemory(p), cpu_ratio(p->cpu_ratio), bus_width(p->bus_width),
- mem_type(p->mem_type), mem_actpolicy(p->mem_actpolicy),
- memctrladdr_type(p->memctrladdr_type), act_lat(p->act_lat),
- cas_lat(p->cas_lat), war_lat(p->war_lat),
- pre_lat(p->pre_lat), dpl_lat(p->dpl_lat),
- trc_lat(p->trc_lat), num_banks(p->num_banks),
- num_cpus(p->num_cpus), last_dev(DR_NUM_DEVS+1),
- lastCmdIsRead(true), precharge(0), same_row_read_access(0), srr_after_read(0),
- srr_after_write(0), same_row_write_access(0), srw_after_read(0),
- srw_after_write(0), same_bank_read_access(0), sbr_after_read(0),
- sbr_after_write(0), same_bank_write_access(0), sbw_after_read(0),
- sbw_after_write(0), other_bank_read_access_hit(0), obr_after_read_hit(0),
- obr_after_write_hit(0), other_bank_write_access_hit(0),
- obw_after_read_hit(0), obw_after_write_hit(0), obr_after_read_miss(0),
- obr_after_write_miss(0),
- obw_after_read_miss(0), obw_after_write_miss(0), total_access(0),
- adjacent_access(0), adjacent_read(0), adjacent_write(0),
- command_overlapping(0), best_case(0), in_between_case(0), worst_case(0),
- full_overlapping(0), partial_overlapping(0), mem_access_details(false),
- memctrlpipe_enable(false), time_last_access(0)
-{
- warn("This DRAM module has not been tested with the new memory system at all!");
- bank_size = (p->range.size() + 1) / num_banks;
- num_rows = bank_size / SD_ROW_SIZE; /* 0x1000 size of row 4Kbtye */
- active_row = new int[num_banks];
- last_bank = num_banks+1;
- last_row = num_rows;
- busy_until = new Tick[num_banks];
- std::memset(busy_until,0,sizeof(Tick)*num_banks); /* initiliaze */
-
-}
-
-void
-DRAMMemory::regStats()
-{
- using namespace Stats;
-
- accesses
- .init(maxThreadsPerCPU)
- .name(name() + ".accesses")
- .desc("total number of accesses")
- .flags(total)
- ;
-
- bytesRequested
- .init(maxThreadsPerCPU)
- .name(name() + ".bytes_requested")
- .desc("total number of bytes requested")
- .flags(total)
- ;
-
- bytesSent
- .init(maxThreadsPerCPU)
- .name(name() + ".bytes_sent")
- .desc("total number of bytes sent")
- .flags(total)
- ;
-
- compressedAccesses
- .init(maxThreadsPerCPU)
- .name(name() + ".compressed_responses")
- .desc("total number of accesses that are compressed")
- .flags(total)
- ;
-
- // stats for power modelling
- cycles_nCKE
- .init(1)
- .name(name() + ".cycles_nCKE")
- .desc("cycles when CKE is low")
- .flags(total)
- ;
-
- cycles_all_precharge_CKE
- .init(1)
- .name(name() + ".cycles_all_precharge_CKE")
- .desc("cycles when all banks precharged")
- .flags(total)
- ;
-
- cycles_all_precharge_nCKE
- .init(1)
- .name(name() + ".cycles_all_precharge_nCKE")
- .desc("cycles when all banks precharged and CKE is low")
- .flags(total)
- ;
-
- cycles_bank_active_nCKE
- .init(1)
- .name(name() + ".cycles_bank_active_nCKE")
- .desc("cycles when banks active and CKE low")
- .flags(total)
- ;
-
- // we derive this from other stats later
- // so DR TODO for now this counter is unused
- cycles_avg_ACT
- .init(1)
- .name(name() + ".cycles_avg_ACT")
- .desc("avg cycles between ACT commands")
- .flags(total)
- ;
-
- cycles_read_out
- .init(1)
- .name(name() + ".cycles_read_out")
- .desc("cycles outputting read data")
- .flags(total)
- ;
-
- cycles_write_in
- .init(1)
- .name(name() + ".cycles_write_in")
- .desc("cycles inputting write data")
- .flags(total)
- ;
-
- cycles_between_misses
- .init(1)
- .name(name() + ".cycles_between_misses")
- .desc("cycles between open page misses")
- .flags(total)
- ;
-
- other_bank_read_access_miss
- .init(1)
- .name(name() + ".other_bank_read_access_miss")
- .desc("read miss count")
- .flags(total)
- ;
-
- other_bank_write_access_miss
- .init(1)
- .name(name() + ".other_bank_write_access_miss")
- .desc("write miss count")
- .flags(total)
- ;
-
- // DR TODO for now, only output stats which are involved in power equations
- total_latency
- .name(name() + ".total_latency")
- .desc("total DRAM latency")
- ;
-
- total_arb_latency
- .name(name() + ".total_arb_latency")
- .desc("total arbitration latency")
- ;
-
- avg_latency
- .name(name() + ".avg_latency")
- .desc("average DRAM latency")
- ;
-
- avg_arb_latency
- .name(name() + ".avg_arb_latency")
- .desc("average arbitration DRAM latency")
- ;
-
- bank_access_profile
- .init(num_banks,num_cpus)
- .name(name() + "[cpu][bank]")
- .desc("DRAM bank access profile")
- ;
-
- total_icache_req
- .name(name() + ".total_icache_req")
- .desc("total number of requests from icache")
- ;
-
- avg_latency = total_latency / accesses;
- avg_arb_latency = total_arb_latency / accesses;
-}
-
-
-
-
-// DR DEBUG: assume we have a 500 MHz CPU and 100 MHz RAM
-// static float cpu_ratio = 5; // ratio between CPU speed and memory bus speed
-// DR TODO: get this parameter from the simulation
-
-static char *mem_access_output=NULL;
- /* latency of access [CPU cycles]*/
-Tick
-DRAMMemory::calculateLatency(PacketPtr pkt)
-{
-
- bool cmdIsRead = pkt->isRead();
-
- int lat=0, temp=0, current_bank=0;
- int current_row=0, current_device=0;
-
- int was_miss = 0; // determines if there was an active row miss this access
-
- //md_addr_t physic_address; /* linear memory address to be accessed */
- Addr physic_address; /* linear memory address to be accessed */
-
- int num_blocks=0;
- int corrected_overlap, /* overlap of consecutive accesses [CPU cycles] */
- overlap=0; /* overlap of consecutive accesses [mem bus cycles] */
- int adjacent=0; /* 1 indicates that current bank is adjacent to the last accessed one*/
-
- int chunks = (pkt->getSize() + (bus_width - 1)) / bus_width; // burst length
- assert(chunks >0);
- physic_address = pkt->getAddr();
-
- ///////////////////////////////////////////////////////////////////////////
- // DR added more stats for power modelling
- // NOTE:
- // for DRAM closed-page, automatic precharge after read or write,
- // i.e. whenever idle
-
-
- // count number of cycles where dram is not busy, use for CKE low signal
- // calculate as percentage of all clock cycles
- // if busy, do not add to idle count. Else add cycles since last access
-/* #define SD_NUM_BANKS (SD_STACK_BASE/SD_BANK_SIZE) */ /* number of banks */
-/* #define SD_NUM_ROWS (SD_BANK_SIZE/SD_ROW_SIZE) */ /* number of rows per bank */
-/*delays until data is ready/written to the memory for the SDRAM*/
- int SD_T_READ_READ_SROW = cas_lat; /* RAR, row hit, current bank */
- int SD_T_READ_WRITE_SROW = cas_lat; /* RAW, row hit, current bank */
- int SD_T_WRITE_READ_SROW = war_lat-1; /* WAR, row hit, current bank */
- int SD_T_WRITE_WRITE_SROW = 0; /* WAW, row hit, current bank */
- int SD_T_READ_READ_SBANK = (pre_lat+act_lat+cas_lat); /* RAR, row miss, current bank */
- int SD_T_READ_WRITE_SBANK = (pre_lat+act_lat+cas_lat+(dpl_lat-1)); /* RAW, row miss, current bank */
- int SD_T_WRITE_READ_SBANK = (pre_lat+act_lat); /* WAR, row miss, current bank */
- int SD_T_WRITE_WRITE_SBANK = (pre_lat+act_lat+(dpl_lat-1)); /* WAW, row miss, current bank */
- int SD_T_READ_READ_OBANK = (pre_lat+act_lat+cas_lat); /* RAR, row miss, another bank */
- int SD_T_READ_WRITE_OBANK = (pre_lat+act_lat+cas_lat); /* RAW, row miss, another bank */
- int SD_T_WRITE_READ_OBANK = (pre_lat+act_lat); /* WAR, row miss, another bank */
- int SD_T_WRITE_WRITE_OBANK = (pre_lat+act_lat); /* WAW, row miss, another bank */
-/* best-case latencies (due to overlap / row hits in another bank) */
- int SD_BEST_T_READ_READ_SROW = 0; /* RAR, row hit, current bank */
- int SD_BEST_T_READ_READ_SBANK = (act_lat+cas_lat); /* RAR, row miss, current bank */
- int SD_BEST_T_WRITE_READ_SBANK = (act_lat); /* WAR, row miss, current bank */
- int SD_BEST_T_READ_READ_OBANK = 0; /* RAR, row miss/hit, another bank */
- int SD_BEST_T_READ_WRITE_OBANK = cas_lat; /* RAW, row miss/hit, another bank */
- int SD_BEST_T_WRITE_READ_OBANK = (war_lat -1); /* WAR, row miss/hit, another bank */
- int SD_BEST_T_WRITE_WRITE_OBANK = 0; /* WAW, row miss/hit, another bank */
-
- Tick time_since_last_access = curTick()-time_last_access;
- Tick time_last_miss = 0; // used for keeping track of times between activations (page misses)
- //int was_idle = (curTick() > busy_until);
- bool srow_flag = false;
- int timing_correction = 0;
-
- int was_idle = (curTick() > busy_until[current_bank]);
- cycles_nCKE[0] += was_idle ? MIN(curTick()-busy_until[current_bank], time_since_last_access) : 0;
-
- // bank is precharged
- //active_row[current_bank] == DR_NUM_ROWS
- int all_precharged = 1;
- int bank_max = num_banks;
- int row_max = num_rows;
-
- if( (mem_type == "SDRAM") && (mem_actpolicy == "closed") ) {
- // SDRAM does not use the active_row array in closed_page mode
- // TODO: handle closed page operation
-
- } else { // DRDRAM uses the active_row array
- for( int i = 0; i < bank_max; i++ ) {
- if( (active_row[current_bank] != row_max)) all_precharged = 0;
- }
- }
-
- if(all_precharged) {
- if(was_idle) {
- cycles_all_precharge_nCKE[0] += MIN(curTick()-busy_until[current_bank], time_since_last_access);
- cycles_all_precharge_CKE[0] += MIN(0, busy_until[current_bank]-time_last_access);
- }
- else {
- cycles_all_precharge_CKE[0] += time_since_last_access;
- }
- } else { // some bank is active
- if(was_idle) {
- cycles_bank_active_nCKE[0] += MIN(curTick()-busy_until[current_bank], time_since_last_access);
- }
- else {
- }
- }
-
- if( cmdIsRead ) {
- cycles_read_out[0] += chunks;
- } else {
- cycles_write_in[0] += chunks;
- }
-
-
- time_last_access = curTick();
- ////////////////////////////////////////////////////////////////////////////
-
- if ((mem_type == "SDRAM") && (mem_actpolicy == "open"))
- {
- /* Split transaction on m5 makes it challenging to */
- /* model the DRAM. A single cycle latency is assumed */
- /* for dequeueing an address bus request. In response to */
- /* that, the current DRAM implementation assumes that a */
- /* seperate DRAM command generator / controller exists per */
- /* bank and the dequeued addresses are queued to these */
- /* controllers. We can view this as an ideal scenario for */
- /* a shared DRAM command generator / controller with */
- /* support for overlapping DRAM commands. */
- /* Compare DRAM PRE,ACT,CAS etc. latencies, DRAM clock */
- /* frequency and the number of banks to determine whether */
- /* the ideal scenario with a shared DRAM command generator */
- /* is equivalent to having multiple DRAM command generators */
- /* per bank */
- if ((memctrladdr_type != "interleaved"))/* i.e. mc_type is linear */
- {
- current_bank=physic_address/bank_size;
- temp=physic_address-current_bank*bank_size;/*address in bank*/
- current_row=temp/SD_ROW_SIZE;
- }
- else/* mc_type interleaved */
- /* This memory controller maps the addresses differently
- * depending on the row_size, every row is mapped to another
- * bank. Thus, the text segment uses half of every bank, the heap
- * the next quarter of each bank, and the stack the rest.
- */
-
- {
- num_blocks = physic_address/SD_ROW_SIZE; /* row number */
- current_bank=num_blocks%num_banks;
- current_row=num_blocks/num_banks;
- }
-
- if (mem_access_details == true)
- {
- // DR TODO
- //fprintf(mem_accessfd," %09u %4d %3d\n",physic_address,current_row,current_bank);
- }
- else
- {
- if (mem_access_output!=0)
- {
- //fprintf(mem_accessfd,"\n");
- }
- }
- total_access++;
-
- if (memctrlpipe_enable == true)
- {
- overlap=(int)(busy_until[current_bank] - curTick());
- }
- else overlap = 0;
-
- if (cpu_ratio < 1.0)
- {
- corrected_overlap = overlap*((int)(1/cpu_ratio)); /* floor */
- }
- else
- {
- corrected_overlap = (int) (overlap/cpu_ratio);
- }
-
- /*fprintf(stderr,"%10.0f %10.0f %4d %4d ",(double)busy_until, (double)curTick(), overlap, corrected_overlap); debugging*/
-
- if (cmdIsRead == lastCmdIsRead)/*same command*/
- {
- if (current_bank == last_bank)/*same bank*/
- {
- if (current_row == last_row)/*same row*/
- {
- /* Page Hit */
- if (cmdIsRead)
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- /*best case*/
- if (corrected_overlap >= cas_lat)
- {
- lat=SD_BEST_T_READ_READ_SROW;
- srow_flag = true;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = cas_lat-corrected_overlap;
- srow_flag = true;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else
- {
- /*worst case*/
- lat = SD_T_READ_READ_SROW;
- srow_flag = true;
- worst_case++;
- }
- same_row_read_access++;
- srr_after_read++;
- }
- else/*write*/
- {/*no option case*/
- lat = SD_T_WRITE_WRITE_SROW;
- srow_flag = true;
- same_row_write_access++;
- srw_after_write++;
- worst_case++;
- }
- }
- else /*other row in same bank*/
- {
- /* Page miss */
- if (cmdIsRead)
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- if (corrected_overlap >= pre_lat)/*best case*/
- {
- lat = SD_BEST_T_READ_READ_SBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_READ_READ_SBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = SD_T_READ_READ_SBANK;
- worst_case++;
- }
- same_bank_read_access++;
- sbr_after_read++;
- }
- else/*write*/
- {/*no option case*/
- lat = SD_T_WRITE_WRITE_SBANK;
- same_bank_write_access++;
- sbw_after_write++;
- worst_case++;
- }
- }
- }
- else /*other bank*/
- {
- if (cmdIsRead)
- {
- /* Page empty */
- if (current_row == active_row[current_bank])/*row is still active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= pre_lat)/*best case*/
- {
- lat = SD_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_READ_READ_OBANK - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*in between case*/
- {
- lat = SD_T_READ_READ_OBANK;
- in_between_case++;
- }
- other_bank_read_access_hit++;
- obr_after_read_hit++;
- }
- else/*row is not active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= SD_T_READ_READ_OBANK )/*best case*/
- {
- lat = SD_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_READ_READ_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = SD_T_READ_READ_OBANK;
- worst_case++;
- }
-
- // DR keep track of time between misses
- was_miss = 1;
-
- other_bank_read_access_miss[0]++;
- obr_after_read_miss++;
- }
- }
- else/*write*/
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- { /*best_case*/
- lat = SD_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- other_bank_write_access_hit++;
- obw_after_write_hit++;
- }
- else/*row is not active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >=SD_T_WRITE_WRITE_OBANK)/*best case*/
- {
- lat = SD_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_WRITE_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = SD_T_WRITE_WRITE_OBANK;
- worst_case++;
- }
-
- // DR keep track of time between misses
- was_miss = 1;
-
- other_bank_write_access_miss[0]++;
- obw_after_write_miss++;
-
- }
- }
- }
- }
- else /*lastCmdIsRead != cmdIsRead*/
- {
- if (current_bank == last_bank)/*same bank*/
- {
- if (current_row == last_row)/*same row*/
- {
- /* Page Hit */
- if (cmdIsRead)
- {/*worst case*/
- lat = SD_T_READ_WRITE_SROW;
- srow_flag = true;
- same_row_read_access++;
- srr_after_write++;
- worst_case++;
- }
- else/*write*/
- {/*worst case*/
- lat = SD_T_WRITE_READ_SROW;
- srow_flag = true;
- same_row_write_access++;
- srw_after_read++;
- worst_case++;
- }
- }
- else /*other row in same bank*/
- {
- /* Page Miss */
- if (cmdIsRead)
- {/*worst case*/
- lat = SD_T_READ_WRITE_SBANK;
- same_bank_read_access++;
- sbr_after_write++;
- worst_case++;
- }
- else/*write*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if (corrected_overlap >= pre_lat)/*best case*/
- {
- lat = SD_BEST_T_WRITE_READ_SBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_WRITE_READ_SBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = SD_T_WRITE_READ_OBANK;
- worst_case++;
- }
- same_bank_write_access++;
- sbw_after_read++;
- }
- }
- }
- else /*other bank*/
- {
- /* Page empty */
- if (cmdIsRead)
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- { /*best case*/
- lat = SD_BEST_T_READ_WRITE_OBANK;
- best_case++;
- other_bank_read_access_hit++;
- obr_after_write_hit++;
- }
- else/*row is not active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (pre_lat+act_lat))/*best case*/
- {
- lat = SD_BEST_T_READ_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_READ_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = SD_T_READ_WRITE_OBANK;
- worst_case++;
- }
- // DR keep track of time between misses
- was_miss = 1;
-
- other_bank_read_access_miss[0]++;
- obr_after_write_miss++;
- }
- }
- else/*write*/
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- { /*best case*/
- lat = SD_BEST_T_WRITE_READ_OBANK;
- best_case++;
- other_bank_write_access_hit++;
- obw_after_read_hit++;
- }
- else/*row is not active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if (corrected_overlap >= (SD_T_WRITE_READ_OBANK-SD_BEST_T_WRITE_READ_OBANK))/*best case*/
- {/*best case*/
- lat = SD_BEST_T_WRITE_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = SD_T_WRITE_READ_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = SD_T_WRITE_READ_OBANK;
- worst_case++;
- }
-
- // DR keep track of time between misses
- was_miss = 1;
-
- other_bank_write_access_miss[0]++;
- obw_after_read_miss++;
- }
- }
- }
- }
- /*fprintf(stderr,"%4d %4d ",lat,active_row[current_bank]);debugging*/
-
- lat += chunks; /* burst length added*/
- if(srow_flag == false)
- timing_correction = cpu_ratio*(trc_lat - pre_lat - act_lat - cas_lat - 1);
-
-
- /*fprintf(stderr,"%4d ",lat);debugging*/
-
- active_row[current_bank]=current_row; /* open-page (hit) register */
- lastCmdIsRead = cmdIsRead;
- last_bank = current_bank;
- last_row = current_row;
-
- if (cpu_ratio < 1.0)
- {
- lat = (lat+((int)(1/cpu_ratio)-1))/(int)(1/cpu_ratio);
- }
- else
- {
- temp = (int)(lat*cpu_ratio);
- lat = (lat*cpu_ratio == temp)?temp:(temp+1); /*round up*/
- }
-
- /*fprintf(stderr,"%4d \n",lat);debugging*/
-
- if (overlap <= 0) /*memory interface is not busy*/
- {
- if (memctrlpipe_enable == true)
- {
- busy_until[current_bank]=curTick()+lat+
- timing_correction;
- }
- else
- {
- if (busy_until[current_bank] >= curTick())
- {
- busy_until[current_bank]+=(lat+
- timing_correction);
- total_arb_latency += (busy_until[current_bank]
- - curTick() - lat
- - timing_correction);
- lat=busy_until[current_bank] - curTick();
- }
- else busy_until[current_bank]=curTick()+lat+
- timing_correction;
- }
- }
- else/*the memory request will be satisfied temp cycles after curTick()*/
- {
- busy_until[current_bank] +=(lat+
- timing_correction);
- command_overlapping++;
- lat+=overlap;
- total_arb_latency += overlap;
- }
-
- // DR for power stats
- if( was_miss ) {
- cycles_between_misses[0] += (busy_until[current_bank] - time_last_miss);
- time_last_miss = busy_until[current_bank];
- }
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // bank_access_profile[_cpu_num][current_bank]++;
-
- return lat;
- }
-
-
- /***********************************************************/
- /******************** DRDRAM ***********************/
- /***********************************************************/
-
- else if ((mem_type == "DRDRAM") && (mem_actpolicy == "open"))/*DRDRAM*/ /*a closed bank has an activ_row number of DR_NUM_ROWS: highest +1*/
- {
- if ((memctrladdr_type != "interleaved"))/* i.e. mc_type is linear */
- {
- current_bank=physic_address/DR_BANK_SIZE;
- temp=physic_address-current_bank*DR_BANK_SIZE;/*address in bank*/
- current_row=temp/DR_ROW_SIZE;
- current_device=current_bank/(DR_NUM_BANKS/DR_NUM_DEVS);
- }
-
- else/*mc_type interleaved*/
- /* This memory controller maps the addresses differently
- * depending on the row-size, every row is mapped to another
- * bank. So the text segment uses half of every bank. The heap
- * the next quarter of each bank and the stack the rest.
- */
-
- {
- num_blocks = physic_address/DR_ROW_SIZE; /* row number */
- current_bank=(num_blocks%DR_NUM_BANKS)*2; /*every 'second' bank will be used*/
- /*banks above DR_NUM_BANKS are the uneven banks*/
- current_bank = ((current_bank < DR_NUM_BANKS) ? current_bank:(current_bank - DR_NUM_BANKS+1));
- current_row=num_blocks/DR_NUM_BANKS;
- current_device=current_bank/(DR_NUM_BANKS/DR_NUM_DEVS);
- }
- if (abs(current_bank-last_bank)==1)/*access to an adjacent bank*/
- {
- if (!((current_bank%DR_BANK_SAMP == (DR_BANK_SAMP-1))&&(last_bank%DR_BANK_SAMP == 0))/*not 15/16 (current/last)*/
- &&(!((last_bank%DR_BANK_SAMP == (DR_BANK_SAMP-1))&&(current_bank%DR_BANK_SAMP == 0))))/*not 16/15(current/last)*/
- {
- adjacent_access++;
- adjacent=1;/*an adjacent bank is accessed*/
- if (cmdIsRead)
- adjacent_read++;
- else
- adjacent_write++;
- }
- }
- precharge=0;/*at this moment no bank needs to be precharged*/
- if (active_row[current_bank] == DR_NUM_ROWS)/*bank is precharged*/
- {
- if (prechargeBanksAround(current_bank)> 0)/*a bank next to the current is activated*/
- {
- if ((adjacent==1)&&(precharge==1))
- {
- /*since adjacent banks share SAMPs, this access would be the same as (in terms of latency)
- *an access to another row in the same bank if only one adjacent bank was active*/
- last_bank = current_bank;
- last_row = current_row+1;
- precharge=0;/*set to 0 for next memory access*/
- }
- }
- }
- if (mem_access_details == true)
- {
- //fprintf(mem_accessfd," %09u %4d %3d %15d\n",physic_address,current_row,current_bank,(int)adjacent_access);
- }
- else
- {
- if (mem_access_output!=NULL)
- {
- //fprintf(mem_accessfd,"\n");
- }
- }
- total_access++;
-
- if (memctrlpipe_enable == true)
- {
- overlap=(int)(busy_until[current_bank] - curTick());
- }
- else overlap=0;
-
- if (cpu_ratio < 1.0)
- {
- corrected_overlap = overlap*((int)(1/cpu_ratio)); /* floor */
- }
- else
- {
- corrected_overlap = (int) (overlap/cpu_ratio);
- }
-
- /*fprintf(stderr,"%10.0f %10.0f %6d %6d %2d %2d ",(double)busy_until, (double)curTick(), overlap, corrected_overlap,precharge,adjacent);debugging*/
-
- if (cmdIsRead == lastCmdIsRead)/*same command*/
- {
- if (current_bank == last_bank)/*same bank*/
- {
- if (current_row == last_row)/*same row*/
- {
- if (cmdIsRead)
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- /*best case*/
- if (corrected_overlap >= DR_T_READ_READ_SROW)
- {
- lat=DR_BEST_T_READ_READ_SROW;
- srow_flag = true;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_READ_SROW-corrected_overlap;
- srow_flag = true;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else
- {
- /*worst case*/
- lat = DR_T_READ_READ_SROW;
- srow_flag = true;
- worst_case++;
- }
- same_row_read_access++;
- srr_after_read++;
- }
- else/*write, always retire the previous data*/
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- /*best case*/
- if (corrected_overlap >= DR_T_OWR)
- {
- lat=DR_BEST_T_WRITE_WRITE_SROW;
- srow_flag = true;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_WRITE_SROW-corrected_overlap;
- srow_flag = true;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else
- {
- /*worst case*/
- lat = DR_T_WRITE_WRITE_SROW;
- srow_flag = true;
- worst_case++;
- }
- same_row_write_access++;
- srw_after_write++;
- }
- }
- else /*other row in same bank*/
- {
- if (cmdIsRead)
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- if (corrected_overlap >= DR_T_HELP)/*best case*/
- {
- lat = DR_BEST_T_READ_READ_SBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_READ_SBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_READ_READ_SBANK;
- worst_case++;
- }
- same_bank_read_access++;
- sbr_after_read++;
- }
- else/*write*/
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- if (corrected_overlap >= DR_T_OWR)/*best case*/
- {
- lat = DR_BEST_T_WRITE_WRITE_SBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_WRITE_SBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_WRITE_WRITE_SBANK;
- worst_case++;
- }
- same_bank_write_access++;
- sbw_after_write++;
- }
- }
- }
- else /*other bank*/
- {
- if (cmdIsRead)
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_CAC+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*in between case*/
- {
- lat = DR_T_CAC+DR_T_PACKET;
- in_between_case++;
- }
- other_bank_read_access_hit++;
- obr_after_read_hit++;
- }
- else/*row is not active or bank is precharged/not active*/
- {
- if (active_row[current_bank]!=DR_NUM_ROWS)/*row is not active, but bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*current_row == DR_NUM_ROWS:precharged or inactive*/
- {
- if(precharge == 0)/*no adjacent bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RCD+DR_T_CAC+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RCD+DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RCD+DR_T_CAC+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*one ore two adjacent banks are active*/
- {
- if (precharge == 1)
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET)-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET);
- in_between_case++;
- }
- }
- else /*precharge ==2: two rows must be precharged*/
- {
- if (adjacent == 1)/*these banks are adjacent*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_PP+2*DR_T_PACKET-DR_T_RDP+DR_T_CAC)/*best case*/
- {
- lat = DR_T_RDP+DR_T_RP+DR_T_RCD-DR_T_PACKET;
- in_between_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_READ_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_READ_READ_OBANK;
- worst_case++;
- }
- }
- else/*adjacent == 0: two not adjacent banks need to be precharged*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_READ_READ_OBANK)/*best case*/
- {
- lat = DR_BEST_T_READ_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_READ_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_READ_READ_OBANK;
- worst_case++;
- }
- }
- }
- }
- }
- other_bank_read_access_miss[0]++;
- obr_after_read_miss++;
- }
- }
- else/*write*/
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_CWD+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_CWD+DR_T_PACKET;
- in_between_case++;
- }
- other_bank_write_access_hit++;
- obw_after_write_hit++;
- }
- else/*row is not active or bank is precharged/not active*/
- {
- if (active_row[current_bank] != DR_NUM_ROWS)/*row is not active,but bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*current_row == DR_NUM_ROWS:precharged or inactive*/
- {
- if(precharge == 0)/*no adjacent bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RCD+DR_T_CWD+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RCD+DR_T_CWD+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*one ore two adjacent banks are active*/
- {
- if (precharge == 1)/*last_bank is no adjacent*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET)-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET);
- in_between_case++;
- }
- }
- else /*precharge ==2: two rows have to be precharged*/
- {
- if (adjacent == 1)/*these banks are adjacent*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_OWR+DR_T_PP)/*best case*/
- {
- lat = DR_T_WRITE_WRITE_OBANK-DR_T_OWR-DR_T_PP;
- in_between_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_WRITE_WRITE_OBANK;
- worst_case++;
- }
- }
- else/*adjacent == 0: two not adjacent banks need to be precharged*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_WRITE_WRITE_OBANK)/*best case*/
- {
- lat = DR_BEST_T_WRITE_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_WRITE_WRITE_OBANK;
- worst_case++;
- }
- }
- }
- }
- }
- other_bank_write_access_miss[0]++;
- obw_after_write_miss++;
- }
- }
- }
- }
- else /*lastCmdIsRead != cmdIsRead*/
- {
- if (current_bank == last_bank)/*same bank*/
- {
- if (current_row == last_row)/*same row*/
- {
- if (cmdIsRead)
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- /*best case*/
- if (corrected_overlap >= DR_T_OWR)
- {
- lat=DR_BEST_T_READ_WRITE_SROW;
- srow_flag = true;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_WRITE_SROW-corrected_overlap;
- srow_flag = true;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else
- {
- /*worst case*/
- lat = DR_T_READ_WRITE_SROW;
- srow_flag = true;
- worst_case++;
- }
- same_row_read_access++;
- srr_after_write++;
- }
- else/*write*/
- {
- if (corrected_overlap > 0)/*overlapping*/
- {
- /*best case*/
- if (corrected_overlap >= DR_T_WRITE_READ_SROW)
- {
- lat=DR_BEST_T_WRITE_READ_SROW;
- srow_flag = true;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_READ_SROW-corrected_overlap;
- srow_flag = true;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else
- {
- /*worst case*/
- lat = DR_T_WRITE_READ_SROW;
- srow_flag = true;
- worst_case++;
- }
- same_row_write_access++;
- srw_after_read++;
- }
- }
- else /*other row in same bank*/
- {
- if (cmdIsRead)
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if (corrected_overlap >= DR_T_OWR)/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_SBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_WRITE_SBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_READ_WRITE_SBANK;
- worst_case++;
- }
- same_bank_read_access++;
- sbr_after_write++;
- }
- else/*write*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if (corrected_overlap >= DR_T_HELP)/*best case*/
- {
- lat = DR_BEST_T_WRITE_READ_SBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_READ_SBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_WRITE_READ_SBANK;
- worst_case++;
- }
- same_bank_write_access++;
- sbw_after_read++;
- }
- }
- }
- else /*other bank*/
- {
- if (cmdIsRead)
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(last_dev != current_device)
- {
- if(corrected_overlap >= DR_T_CWD+DR_T_PACKET)/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_ODEV;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else /* same device */
- {
- if(corrected_overlap >= DR_T_OWR)/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- }
- else/*in between case, no overlap*/
- {
- lat = DR_T_CAC+DR_T_PACKET;
- in_between_case++;
- }
- other_bank_read_access_hit++;
- obr_after_write_hit++;
- }
-
- else/*row is not active or bank is precharged/not active*/
- {
- if (active_row[current_bank] != DR_NUM_ROWS)/*row is not active,but bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if (last_dev != current_device)
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_ODEV;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else /* same device */
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_OWR))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*current_row == DR_NUM_ROWS:precharged or inactive*/
- {
- if(precharge == 0)/*no adjacent bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(last_dev != current_device)
- {
- if(corrected_overlap >= (DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_ODEV;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RCD+DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else /* same device */
- {
- if(corrected_overlap >= (DR_T_RCD+DR_T_OWR))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RCD+DR_T_CAC+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RCD+DR_T_CAC+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*one or two adjacent banks are active*/
- {
- if (precharge == 1)/*an adjacent bank (!=last_bank) needs to be precharged*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(last_dev != current_device)
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_ODEV;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET)-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else /* same device */
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_OWR))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET)-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- }
- else/*worst case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CAC+DR_T_PACKET);
- in_between_case++;
- }
- }
- else /*precharge ==2: two rows have to be precharged*/
- {
- if (adjacent == 1) /* the banks are adjacent */
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_OWR + DR_T_PP)/*best case*/
- {
- lat = DR_T_READ_WRITE_OBANK-DR_T_OWR - DR_T_PP;
- in_between_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_READ_WRITE_OBANK;
- worst_case++;
- }
- }
- else/*adjacent == 0: two not adjacent banks need to be precharged*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if (last_dev != current_device)
- {
- if(corrected_overlap >= (DR_T_PP+DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_ODEV;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else /* same device */
- {
- if(corrected_overlap >= (DR_T_PP+DR_T_RP+DR_T_RCD+DR_T_OWR))/*best case*/
- {
- lat = DR_BEST_T_READ_WRITE_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_READ_WRITE_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- }
- else/*worst case*/
- {
- lat = DR_T_READ_WRITE_OBANK;
- worst_case++;
- }
- }
- }
- }
- }
- other_bank_read_access_miss[0]++;
- obr_after_write_miss++;
- }
- }
- else/*write*/
- {
- if (current_row == active_row[current_bank])/*row is still active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_CWD+DR_T_PACKET)/*best case*/
- {
- lat = DR_BEST_T_WRITE_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_CWD+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*in between case*/
- {
- lat = DR_T_CWD+DR_T_PACKET;
- in_between_case++;
- }
- other_bank_write_access_hit++;
- obw_after_read_hit++;
- }
- else/*row is not active or bank is precharged/not active*/
- {
- if (active_row[current_bank] != DR_NUM_ROWS)/*row is not active,but bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*current_row == DR_NUM_ROWS:precharged or inactive*/
- {
- if(precharge == 0)/*no adjacent bank is active*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_RCD+DR_T_CWD+DR_T_PACKET-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_RCD+DR_T_CWD+DR_T_PACKET;
- in_between_case++;
- }
- }
- else/*one or two adjacent banks are active*/
- {
- if (precharge == 1)/*an adjacent bank (!=last_bank) needs to be precharged first*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET))/*best case*/
- {
- lat = DR_BEST_T_WRITE_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET)-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = (DR_T_RP+DR_T_RCD+DR_T_CWD+DR_T_PACKET);
- in_between_case++;
- }
- }
- else /*precharge ==2: two rows have to be precharged*/
- {
- if (adjacent == 1)/*these banks are adjacent*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_PP-DR_T_RDP+2*DR_T_PACKET+DR_T_CAC)/*best case*/
- {
- lat = DR_T_WRITE_READ_OBANK-(DR_T_PP-DR_T_RDP+2*DR_T_PACKET+DR_T_CAC);
- in_between_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_READ_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_WRITE_READ_OBANK;
- worst_case++;
- }
- }
- else/*adjacent == 0: two not adjacent banks need to be precharged*/
- {
- if (corrected_overlap > 0 )/*overlapping*/
- {
- if(corrected_overlap >= DR_T_WRITE_READ_OBANK)/*best case*/
- {
- lat = DR_BEST_T_WRITE_READ_OBANK;
- best_case++;
- full_overlapping++;
- }
- else/*in between case*/
- {
- lat = DR_T_WRITE_READ_OBANK-corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- }
- else/*worst case*/
- {
- lat = DR_T_WRITE_READ_OBANK;
- worst_case++;
- }
- }
- }
- }
- }
- other_bank_write_access_miss[0]++;
- obw_after_read_miss++;
- }
- }
- }
- }
- /*fprintf(stderr,"%4d %4d ",lat,active_row[current_bank]);debugging*/
-
- lat += chunks * DR_T_PACKET; /*every 128 bit need DR_NUM_CYCLES*/
-
- /*fprintf(stderr,"%4d ",lat);debugging*/
-
- if (cpu_ratio < 1.0)
- {
- lat = (lat+((int)(1/cpu_ratio)-1))/(int)(1/cpu_ratio);
- }
- else
- {
- temp = (int)(lat*cpu_ratio);
- lat = (lat*cpu_ratio == temp)?temp:(temp+1); /*round up*/
- }
-
- active_row[current_bank]=current_row;
- lastCmdIsRead = cmdIsRead;
- last_bank=current_bank;
- last_row = current_row;
- last_dev = current_device;
-
- /*fprintf(stderr,"%4d \n",lat);debugging*/
-
- if (overlap <= 0) /*memory interface is not busy*/
- {
- if (memctrlpipe_enable == true)
- {
- busy_until[current_bank] =curTick()+lat;
- }
- else
- {
- if (busy_until[current_bank] >= curTick())
- {
- busy_until[current_bank] +=lat;
- lat=busy_until[current_bank] - curTick();
- }
- else busy_until[current_bank] = curTick()+lat;
- }
- }
- else/*the memory request will be satisfied temp cycles after curTick()*/
- {
- busy_until[current_bank] +=lat;
- command_overlapping++;
- lat+=overlap;
- }
-
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // bank_access_profile[_cpu_num][current_bank]++;
- return lat;
- }
-
- /******************************************************************/
-
- else if ((mem_type== "SDRAM") && (mem_actpolicy == "closed") && (memctrlpipe_enable == true))
- /* SDRAM closed-page with overlap, 2/00 MG */
- {
- if ((memctrladdr_type != "interleaved"))/* i.e. mc_type is linear*/
- {
- // current_bank=physic_address/SD_BANK_SIZE;
- current_bank=physic_address/bank_size;
- }
- else/*mc_type interleaved*/
- /* This memory management unit maps the addresses different
- * depending on the row_size, every row is mapped to another
- * bank. So the text segment uses half of every bank. The heap
- * the next quarter of each bank and the stack the rest.
- */
- {
- num_blocks = physic_address/SD_ROW_SIZE; /* row number */
- // current_bank=num_blocks%SD_NUM_BANKS;
- current_bank=num_blocks%num_banks;
- }
-
- if (mem_access_details == true)
- {
- //fprintf(mem_accessfd," %09u %3d\n",physic_address,current_bank);
- }
- else
- {
- if (mem_access_output!=NULL)
- {
- //fprintf(mem_accessfd,"\n");
- }
- }
- total_access++;
-
- overlap=(int)(busy_until[current_bank] - curTick());
-
- if (current_bank == last_bank)/*same bank*/
- {
- if ((lastCmdIsRead == cmdIsRead) && (cmdIsRead))/* RAR */
- {
- lat = act_lat + cas_lat;
- }
- else if ((lastCmdIsRead == cmdIsRead) && (!cmdIsRead)) /* WAW */
- {
- lat = act_lat;
- }
- else if ((lastCmdIsRead != cmdIsRead) && (cmdIsRead)) /* RAW */
- {
- lat = act_lat + cas_lat;
- }
- else /* WAR */
- {
- lat = act_lat;
- }
- }
- else /* other bank */
- {
- if (cpu_ratio < 1.0)
- {
- corrected_overlap = overlap*((int)(1/cpu_ratio)); /* floor */
- }
- else
- {
- corrected_overlap = (int) (overlap/cpu_ratio);
- }
-
- if ((lastCmdIsRead == cmdIsRead) && (cmdIsRead))/* RAR */
- {
- if (corrected_overlap > act_lat + cas_lat)
- {
- lat = 0;
- best_case++;
- full_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = act_lat + cas_lat - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = act_lat + cas_lat;
- worst_case++;
- }
- }
- else if ((lastCmdIsRead == cmdIsRead) && (!cmdIsRead)) /* WAW */
- {
- if (corrected_overlap > act_lat + pre_lat + (dpl_lat-1))
- {
- lat = - pre_lat - dpl_lat +1;
- best_case++;
- full_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = act_lat - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = act_lat;
- worst_case++;
- }
- }
- else if ((lastCmdIsRead != cmdIsRead) && (cmdIsRead)) /* RAW */
- {
- if (corrected_overlap > cas_lat + pre_lat + dpl_lat - 1 )
- {
- lat = act_lat - (pre_lat + dpl_lat - 1);
- best_case++;
- partial_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = act_lat + cas_lat - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = act_lat + cas_lat;
- worst_case++;
- }
- }
- else /* WAR */
- {
- if (corrected_overlap > act_lat - (dpl_lat-1))
- {
- lat = dpl_lat-1;
- best_case++;
- partial_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = act_lat - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = act_lat;
- worst_case++;
- }
- }
- }
- lastCmdIsRead = cmdIsRead;
- last_bank=current_bank;
- last_row = current_row;
-
- lat += chunks;
-
- if (cpu_ratio < 1.0)
- {
- lat = (lat+((int)(1/cpu_ratio)-1))/(int)(1/cpu_ratio);
- }
- else
- {
- temp = (int)(lat*cpu_ratio);
- lat = (lat*cpu_ratio == temp)?temp:(temp+1); /*round up*/
- }
-
- /*fprintf(stderr,"%4d \n",lat); debugging */
-
- if (overlap <= 0) /*memory interface is not busy*/
- {
- busy_until[current_bank] = curTick()+lat;
- }
- else /*the memory request will be satisfied temp cycles after curTick()*/
- {
- busy_until[current_bank] +=lat;
- command_overlapping++;
- total_arb_latency += overlap;
- lat+=overlap;
- }
- if (!cmdIsRead)
- {
- temp = (int)(((dpl_lat-1) + pre_lat)*cpu_ratio);
- busy_until[current_bank] += (((dpl_lat-1) + pre_lat)*cpu_ratio == temp)?temp:(temp+1);
- }
-
-
-
- /*fprintf(stderr,"%10.0f %10.0f %4d %4d \n",(double)busy_until, (double)curTick(), overlap, lat);debug*/
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // bank_access_profile[_cpu_num][current_bank]++;
- return lat;
- }
-
- /******************************************************************/
-
- else if ((mem_type == "DRDRAM") && (mem_actpolicy == "closed") && (memctrlpipe_enable == true))
- /* DRDRAM closed-page with overlap*/
- {
-
- if ((memctrladdr_type != "interleaved"))/*i.e. mc_type is linear*/
- {
- current_bank=physic_address/DR_BANK_SIZE;
- current_device=current_bank/(DR_NUM_BANKS/DR_NUM_DEVS);
- }
- else/*mc_type interleaved*/
- /* This memory management unit maps the addresses different
- * depending on the row-size, every row is mapped to another
- * bank. So the text segment uses half of every bank. The heap
- * the next quarter of each bank and the stack the rest.
- */
- {
- num_blocks = physic_address/DR_ROW_SIZE; /* row number */
- current_bank=(num_blocks%DR_NUM_BANKS)*2; /*every 'second' bank will be used*/
- /*banks above DR_NUM_BANKS are the uneven banks*/
- current_bank = ((current_bank < DR_NUM_BANKS) ? current_bank:(current_bank - DR_NUM_BANKS+1));
- current_device=current_bank/(DR_NUM_BANKS/DR_NUM_DEVS);
- }
-
-
- if (mem_access_details == true)
- {
- //fprintf(mem_accessfd," %09u %3d \n",physic_address,current_bank);
- }
- else
- {
- if (mem_access_output!=NULL)
- {
- //fprintf(mem_accessfd,"\n");
- }
- }
- total_access++;
-
- overlap=(int)(busy_until[current_bank] - curTick());
-
- if (cpu_ratio < 1.0)
- {
- corrected_overlap = overlap*((int)(1/cpu_ratio)); /* floor */
- }
- else
- {
- corrected_overlap = (int) (overlap/cpu_ratio);
- }
-
- if (current_bank == last_bank)/*same bank*/
- {
- if ((lastCmdIsRead == cmdIsRead) && (cmdIsRead))/* RAR */
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET;
- worst_case++;
- }
- else if ((lastCmdIsRead == cmdIsRead) && (!cmdIsRead)) /* WAW */
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET;
- worst_case++;
- }
- else if ((lastCmdIsRead != cmdIsRead) && (cmdIsRead)) /* RAW */
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET;
- worst_case++;
- }
- else /* WAR */
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET;
- worst_case++;
- }
- }
- else /* other bank */
- {
- if ((lastCmdIsRead == cmdIsRead) && (cmdIsRead))/* RAR */
- {
- if (corrected_overlap > DR_T_RAS + DR_T_RP - 2 * DR_T_PACKET)
- {
- lat = - DR_T_RAS + DR_T_RCD + DR_T_PACKET + DR_T_CAC;
- best_case++;
- full_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET;
- worst_case++;
- }
- }
- else if ((lastCmdIsRead == cmdIsRead) && (!cmdIsRead)) /* WAW */
- {
- if (corrected_overlap > DR_T_RCD + DR_T_RTR + DR_T_RP)
- {
- lat = - DR_T_CWD - 2 * DR_T_PACKET + DR_T_RTR;
- best_case++;
- full_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET;
- worst_case++;
- }
- }
- else if ((lastCmdIsRead != cmdIsRead) && (cmdIsRead)) /* RAW */
- {
- if (current_device == last_dev) /* same device */
- {
- if (corrected_overlap > DR_T_RCD + DR_T_RP)
- {
- lat = DR_T_PACKET + DR_T_CAC - DR_T_RP;
- best_case++;
- partial_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET;
- worst_case++;
- }
- }
- else /* other device */
- {
- if (corrected_overlap > DR_T_RCD + DR_T_RP + 2 * DR_T_PACKET)
- {
- lat = - DR_T_PACKET + DR_T_CAC - DR_T_RP;
- best_case++;
- partial_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET;
- worst_case++;
- }
- }
- }
- else /* WAR */
- {
- if (corrected_overlap > DR_T_RAS + DR_T_RP - 2 * DR_T_PACKET - (DR_T_CAC - DR_T_CWD))
- {
- lat = - DR_T_RAS + DR_T_RCD + DR_T_PACKET + DR_T_CAC;
- best_case++;
- full_overlapping++;
- }
- else if (corrected_overlap > 0)
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET - corrected_overlap;
- in_between_case++;
- partial_overlapping++;
- }
- else
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET;
- worst_case++;
- }
- }
- }
-
- lat += chunks * DR_T_PACKET; /*every 128 bit need DR_NUM_CYCLES*/
-
- /*fprintf(stderr,"%4d ",lat);debugging*/
-
- if (cpu_ratio < 1.0)
- {
- lat = (lat+((int)(1/cpu_ratio)-1))/(int)(1/cpu_ratio);
- }
- else
- {
- temp = (int)(lat*cpu_ratio);
- lat = (lat*cpu_ratio == temp)?temp:(temp+1); /*round up*/
- }
-
- lastCmdIsRead=cmdIsRead;
- last_bank=current_bank;
- last_dev = current_device;
-
- /*fprintf(stderr,"%4d \n",lat);debugging*/
-
- if (overlap <= 0) /*memory interface is not busy*/
- {
- busy_until[current_bank] = curTick()+lat;
- }
- else/*the memory request will be satisfied temp cycles after curTick()*/
- {
- busy_until[current_bank] +=lat;
- command_overlapping++;
- lat+=overlap;
- }
-
- /*fprintf(stderr,"%10.0f %10.0f %4d %4d \n",(double)busy_until, (double)curTick(), overlap, lat);*/
-
- if (cmdIsRead)
- {
- if (cpu_ratio < 1.0)
- {
- busy_until[current_bank] += abs(((DR_T_RAS - (DR_T_RCD + DR_T_PACKET + DR_T_CAC)) + 1)/((int)(1/cpu_ratio))); /* CPU clock cycles */
- }
- else
- {
- busy_until[current_bank] += (int) abs(((DR_T_RAS - (DR_T_RCD + DR_T_PACKET + DR_T_CAC)) + 1)*cpu_ratio); /* CPU clock cycles */
- }
- }
- else /* !cmdIsRead */
- {
- if (cpu_ratio < 1.0)
- {
- busy_until[current_bank] += abs((-DR_T_PACKET + DR_T_RTR + DR_T_RP - DR_T_CWD + 1)/((int)(1/cpu_ratio))); /* CPU clock cycles */
- }
- else
- {
- busy_until[current_bank] += (int) abs((-DR_T_PACKET + DR_T_RTR + DR_T_RP - DR_T_CWD + 1)*cpu_ratio); /* CPU clock cycles */
- }
- }
-
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // bank_access_profile[_cpu_num][current_bank]++;
- return lat;
- }
-
- /******************************************************************/
-
- else if ((mem_type == "SDRAM") && (mem_actpolicy == "closed") && (memctrlpipe_enable == false))
- /* SDRAM closed-page without overlap, 7/99 MG */
- {
- if (mem_access_output != NULL)
- {
- //fprintf(mem_accessfd,"\n");
- }
- assert(chunks >0);
-
- if (cmdIsRead)
- {
- lat = act_lat + cas_lat;
- }
- else /* !cmdIsRead */
- {
- lat = act_lat;
- }
- total_access++;
- lat += chunks;
-
- overlap=(int)(busy_until[current_bank] - curTick());
- lastCmdIsRead=cmdIsRead;
-
- if (cpu_ratio < 1.0)
- {
- lat = (lat+((int)(1/cpu_ratio)-1))/(int)(1/cpu_ratio);
- }
- else
- {
- temp = (int)(lat*cpu_ratio);
- lat = (lat*cpu_ratio == temp)?temp:(temp+1); /*round up*/
- }
-
- if (overlap <= 0) /*memory interface is not busy*/
- {
- busy_until[current_bank] = curTick()+lat;
- }
- else/*the memory request will be satisfied temp cycles after curTick()*/
- {
- busy_until[current_bank] +=lat;
- command_overlapping++;
- lat+=overlap;
- }
- if (!cmdIsRead)
- {
- temp = (int)(((dpl_lat-1) + pre_lat)*cpu_ratio);
- busy_until[current_bank] += (((dpl_lat-1) + pre_lat)*cpu_ratio == temp)?temp:(temp+1);
- }
-
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // bank_access_profile[_cpu_num][current_bank]++;
- return lat;
- }
-
- /******************************************************************/
-
- else if ((mem_type == "DRDRAM") && (mem_actpolicy == "closed") && (memctrlpipe_enable == false))
- /* DRDRAM closed-page without overlap */
- {
- if (cmdIsRead)
- {
- lat = DR_T_RCD + DR_T_CAC + DR_T_PACKET; /* DR_T_RP + */
- }
- else /* !cmdIsRead */
- {
- lat = DR_T_RCD + DR_T_CWD + DR_T_PACKET; /* DR_T_RP + */
- }
- total_access++;
- overlap=(int)(busy_until[current_bank] - curTick());
- lat += chunks * DR_T_PACKET; /*every 128 bit need DR_NUM_CYCLES*/
-
- if (cpu_ratio < 1.0)
- {
- lat = (lat+((int)(1/cpu_ratio)-1))/(int)(1/cpu_ratio);
- }
- else
- {
- temp = (int)(lat*cpu_ratio);
- lat = (lat*cpu_ratio == temp)?temp:(temp+1); /*round up*/
- }
-
- lastCmdIsRead=cmdIsRead;
-
- if (overlap <= 0) /*memory interface is not busy*/
- {
- busy_until[current_bank] = curTick()+lat;
- }
- else/*the memory request will be satisfied temp cycles after curTick()*/
- {
- busy_until[current_bank] += lat;
- command_overlapping++;
- lat+=overlap;
- }
-
- if (cmdIsRead)
- {
- if (cpu_ratio < 1.0)
- {
- busy_until[current_bank] += abs(((DR_T_RAS - (DR_T_RCD + DR_T_PACKET + DR_T_CAC)) + 1)/((int)(1/cpu_ratio))); /* CPU clock cycles */
- }
- else
- {
- busy_until[current_bank] += (int) abs(((DR_T_RAS - (DR_T_RCD + DR_T_PACKET + DR_T_CAC)) + 1)*cpu_ratio); /* CPU clock cycles */
- }
- }
- else /* !cmdIsRead */
- {
- if (cpu_ratio < 1.0)
- {
- busy_until[current_bank] += abs((-DR_T_PACKET + DR_T_RTR + DR_T_RP - DR_T_CWD + 1)/((int)(1/cpu_ratio))); /* CPU clock cycles */
- }
- else
- {
- busy_until[current_bank] += (int) abs((-DR_T_PACKET + DR_T_RTR + DR_T_RP - DR_T_CWD + 1)*cpu_ratio); /* CPU clock cycles */
- }
- }
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // bank_access_profile[_cpu_num][current_bank]++;
- return lat;
- }
-
- /******************************************************************/
-
- else /*STD*/
- {
- if (mem_access_output != NULL)
- {
- //fprintf(mem_accessfd,"\n");
- }
- assert(chunks >0);
- // if((_cpu_num < num_cpus) && (_cpu_num >= 0))
- // cout <<"cpu id = " << _cpu_num << "current_bank = " << current_bank << endl;
- // bank_access_profile[_cpu_num][current_bank]++;
- return(/* first chunk latency */act_lat +
- (/* remainder chunk latency */cas_lat * (chunks - 1)));
- }
-
-}
-
-/*end added by ar, MG*/
-
-/*begin added by ar, MG*/
-
-/* ================ helper functions ========================= */
-
-/****** DRDRAM specific: shared sense amplifiers ******/
-/* precharges the adjacent banks and returns the number of them (1 or 2)*/
-int /*number of precharged banks*/
-DRAMMemory::prechargeBanksAround(int bank)/*access to bank */
-{
-int temp;
-
-temp=bank%DR_BANK_SAMP;
-
-if (temp == 0) /*bank 0, 16,32 ....*/
- {
- if (active_row[bank+1]!=DR_NUM_ROWS)
- {
- precharge++;
- active_row[bank+1]=DR_NUM_ROWS;
- }
- }
-else
- {
- if (temp==DR_BANK_SAMP-1)/*banks 15,31 ...*/
- {
- if (active_row[bank-1]!=DR_NUM_ROWS)
- {
- precharge++;
- active_row[bank-1]=DR_NUM_ROWS;
- }
- }
- else
- {
- if (active_row[bank-1]!=DR_NUM_ROWS)
- {
- precharge++;
- active_row[bank-1]=DR_NUM_ROWS;
- }
- if (active_row[bank+1]!=DR_NUM_ROWS)
- {
- precharge++;
- active_row[bank+1]=DR_NUM_ROWS;
- }
- }
- }
-return precharge;
-}
-
-DRAMMemory *
-DRAMMemoryParams::create()
-{
- return new DRAMMemory(this);
-}
diff --git a/src/mem/dram.hh b/src/mem/dram.hh
deleted file mode 100644
index 1745fa52b..000000000
--- a/src/mem/dram.hh
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * Copyright (c) 2003-2004 The Regents of The University of Michigan
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met: redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer;
- * redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution;
- * neither the name of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Authors: Ron Dreslinski
- * Ali Saidi
- */
-
-/**
- * @file
- * Derrive a class from PhysicalMemory that support DRAM like timing access.
- */
-#ifndef __MEM_DRAM_HH__
-#define __MEM_DRAM_HH__
-
-#include "base/statistics.hh"
-#include "mem/physical.hh"
-#include "params/DRAMMemory.hh"
-
-class DRAMMemory : public PhysicalMemory
-{
- protected:
- /* added for dram support */
- const int cpu_ratio; // ratio between CPU speed and memory bus speed
- const int bus_width; // memory access bus width (in bytes)
- /* memory access latency (<first_chunk> <inter_chunk>) */
- const std::string mem_type;
- const std::string mem_actpolicy;
- const std::string memctrladdr_type;
- const int act_lat;
- const int cas_lat;
- const int war_lat;
- const int pre_lat;
- const int dpl_lat;
- const int trc_lat;
- const int num_banks;
- const int num_cpus;
-
- int bank_size;
- int num_rows;
- int *active_row;
- int last_bank;
- int last_row;
- Tick *busy_until;
- int last_dev;
- bool lastCmdIsRead;
- int precharge;
-
- /* memory access statistics */
- int same_row_read_access;
- int srr_after_read;
- int srr_after_write;
- int same_row_write_access;
- int srw_after_read;
- int srw_after_write;
-
- int same_bank_read_access;
- int sbr_after_read;
- int sbr_after_write;
- int same_bank_write_access;
- int sbw_after_read;
- int sbw_after_write;
-
- int other_bank_read_access_hit;
- int obr_after_read_hit;
- int obr_after_write_hit;
- int other_bank_write_access_hit;
- int obw_after_read_hit;
- int obw_after_write_hit;
- // DR
- // int other_bank_read_access_miss;
- int obr_after_read_miss;
- int obr_after_write_miss;
- // DR
- // int other_bank_write_access_miss;
- int obw_after_read_miss;
- int obw_after_write_miss;
-
- int total_access;
-
- int adjacent_access;
- int adjacent_read;
- int adjacent_write;
- int command_overlapping;
- int best_case;
- int in_between_case;
- int worst_case;
- int full_overlapping;
- int partial_overlapping;
-
- int mem_access_details;
- int memctrlpipe_enable;
-
- Tick time_last_access;
-
-
- Stats::Vector accesses;
- Stats::Vector bytesRequested;
- Stats::Vector bytesSent;
- Stats::Vector compressedAccesses;
-
- Stats::Vector cycles_nCKE;
- Stats::Vector cycles_all_precharge_CKE;
- Stats::Vector cycles_all_precharge_nCKE;
- Stats::Vector cycles_bank_active_nCKE;
- Stats::Vector cycles_avg_ACT;
- Stats::Vector cycles_read_out;
- Stats::Vector cycles_write_in;
- Stats::Vector cycles_between_misses;
- Stats::Vector other_bank_read_access_miss;
- Stats::Vector other_bank_write_access_miss;
- Stats::Scalar total_latency;
- Stats::Scalar total_icache_req;
- Stats::Scalar total_arb_latency;
- Stats::Formula avg_latency;
- Stats::Formula avg_arb_latency;
- Stats::Vector2d bank_access_profile;
-
-
- protected:
- Tick calculateLatency(PacketPtr pkt);
- int prechargeBanksAround(int bank);
-
- public:
- typedef DRAMMemoryParams Params;
- DRAMMemory(const Params *p);
-
- const Params *
- params() const
- {
- return dynamic_cast<const Params *>(_params);
- }
-
- virtual void regStats();
-};
-
-#endif// __MEM_DRAM_HH__
-