summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndreas Hansson <andreas.hansson@arm.com>2013-04-22 13:20:34 -0400
committerAndreas Hansson <andreas.hansson@arm.com>2013-04-22 13:20:34 -0400
commite23e3bea8bc332626e026078dc8b23c983fc890f (patch)
tree80ef9eff694a07b7d0907198e1ca825475552c36
parente61799aa7cfa7c9f9d4b1099ac4fd9ecbadd4b7b (diff)
downloadgem5-e23e3bea8bc332626e026078dc8b23c983fc890f.tar.xz
mem: Address mapping with fine-grained channel interleaving
This patch adds an address mapping scheme where the channel interleaving takes place on a cache line granularity. It is similar to the existing RaBaChCo that interleaves on a DRAM page, but should give higher performance when there is less locality in the address stream.
-rw-r--r--src/mem/SimpleDRAM.py10
-rw-r--r--src/mem/simple_dram.cc45
2 files changed, 37 insertions, 18 deletions
diff --git a/src/mem/SimpleDRAM.py b/src/mem/SimpleDRAM.py
index 9cc56189e..e16c99e0f 100644
--- a/src/mem/SimpleDRAM.py
+++ b/src/mem/SimpleDRAM.py
@@ -44,11 +44,11 @@ from AbstractMemory import *
class MemSched(Enum): vals = ['fcfs', 'frfcfs']
# Enum for the address mapping. With Ra, Co, Ba and Ch denoting rank,
-# column, bank and channel, respectively, and going from MSB to LSB,
-# the two schemes available are RaBaChCo and CoRaBaCh, either
-# optimising for sequential accesses hitting in the open row, or
-# maximising parallelism.
-class AddrMap(Enum): vals = ['RaBaChCo', 'CoRaBaCh']
+# column, bank and channel, respectively, and going from MSB to LSB.
+# Available are RaBaChCo and RaBaCoCh, that are suitable for an
+# open-page policy, optimising for sequential accesses hitting in the
+# open row. For a closed-page policy, CoRaBaCh maximises parallelism.
+class AddrMap(Enum): vals = ['RaBaChCo', 'RaBaCoCh', 'CoRaBaCh']
# Enum for the page policy, either open or close.
class PageManage(Enum): vals = ['open', 'close']
diff --git a/src/mem/simple_dram.cc b/src/mem/simple_dram.cc
index bb9230e97..310530a69 100644
--- a/src/mem/simple_dram.cc
+++ b/src/mem/simple_dram.cc
@@ -118,6 +118,11 @@ SimpleDRAM::init()
panic("Interleaving of %s doesn't match RaBaChCo address map\n",
name());
}
+ } else if (addrMapping == Enums::RaBaCoCh) {
+ if (bytesPerCacheLine != range.granularity()) {
+ panic("Interleaving of %s doesn't match RaBaCoCh address map\n",
+ name());
+ }
} else if (addrMapping == Enums::CoRaBaCh) {
if (bytesPerCacheLine != range.granularity())
panic("Interleaving of %s doesn't match CoRaBaCh address map\n",
@@ -173,11 +178,9 @@ SimpleDRAM::writeQueueFull() const
SimpleDRAM::DRAMPacket*
SimpleDRAM::decodeAddr(PacketPtr pkt)
{
- // decode the address based on the address mapping scheme
- //
- // with Ra, Co, Ba and Ch denoting rank, column, bank and channel,
- // respectively, and going from MSB to LSB, the two schemes are
- // RaBaChCo and CoRaBaCh
+ // decode the address based on the address mapping scheme, with
+ // Ra, Co, Ba and Ch denoting rank, column, bank and channel,
+ // respectively
uint8_t rank;
uint16_t bank;
uint16_t row;
@@ -188,20 +191,36 @@ SimpleDRAM::decodeAddr(PacketPtr pkt)
addr = addr / bytesPerCacheLine;
// we have removed the lowest order address bits that denote the
- // position within the cache line, proceed and select the
- // appropriate bits for bank, rank and row (no column address is
- // needed)
+ // position within the cache line
if (addrMapping == Enums::RaBaChCo) {
// the lowest order bits denote the column to ensure that
// sequential cache lines occupy the same row
addr = addr / linesPerRowBuffer;
- // take out the channel part of the address, note that this has
- // to match with how accesses are interleaved between the
- // controllers in the address mapping
+ // take out the channel part of the address
+ addr = addr / channels;
+
+ // after the channel bits, get the bank bits to interleave
+ // over the banks
+ bank = addr % banksPerRank;
+ addr = addr / banksPerRank;
+
+ // after the bank, we get the rank bits which thus interleaves
+ // over the ranks
+ rank = addr % ranksPerChannel;
+ addr = addr / ranksPerChannel;
+
+ // lastly, get the row bits
+ row = addr % rowsPerBank;
+ addr = addr / rowsPerBank;
+ } else if (addrMapping == Enums::RaBaCoCh) {
+ // take out the channel part of the address
addr = addr / channels;
- // after the channel bits, we get the bank bits to interleave
+ // next, the column
+ addr = addr / linesPerRowBuffer;
+
+ // after the column bits, we get the bank bits to interleave
// over the banks
bank = addr % banksPerRank;
addr = addr / banksPerRank;
@@ -474,7 +493,7 @@ SimpleDRAM::printParams() const
string scheduler = memSchedPolicy == Enums::fcfs ? "FCFS" : "FR-FCFS";
string address_mapping = addrMapping == Enums::RaBaChCo ? "RaBaChCo" :
- "CoRaBaCh";
+ (addrMapping == Enums::RaBaCoCh ? "RaBaCoCh" : "CoRaBaCh");
string page_policy = pageMgmt == Enums::open ? "OPEN" : "CLOSE";
DPRINTF(DRAM,