mem: Add a GDDR5 DRAM config
This patch adds a first cut GDDR5 config to accommodate the users combining gem5 and GPUSim. The config is based on a SK Hynix datasheet, and the Nvidia GTX580 specification. Someone from the GPUSim user-camp should tweak the default page-policy and static frontend and backend latencies.
This commit is contained in:
parent
b0aa5a326d
commit
0e63d2cd62
3 changed files with 93 additions and 3 deletions
|
@ -736,3 +736,88 @@ class LPDDR3_1600_x32(DRAMCtrl):
|
|||
IDD52 = '150mA'
|
||||
VDD = '1.8V'
|
||||
VDD2 = '1.2V'
|
||||
|
||||
# A single GDDR5 x64 interface, with
|
||||
# default timings based on a GDDR5-4000 1 Gbit part (SK Hynix
|
||||
# H5GQ1H24AFR) in a 2x32 configuration.
|
||||
class GDDR5_4000_x64(DRAMCtrl):
|
||||
# size of device
|
||||
device_size = '128MB'
|
||||
|
||||
# 2x32 configuration, 1 device with a 32-bit interface
|
||||
device_bus_width = 32
|
||||
|
||||
# GDDR5 is a BL8 device
|
||||
burst_length = 8
|
||||
|
||||
# Each device has a page (row buffer) size of 2Kbits (256Bytes)
|
||||
device_rowbuffer_size = '256B'
|
||||
|
||||
# 2x32 configuration, so 2 devices
|
||||
devices_per_rank = 2
|
||||
|
||||
# assume single rank
|
||||
ranks_per_channel = 1
|
||||
|
||||
# GDDR5 has 4 bank groups
|
||||
bank_groups_per_rank = 4
|
||||
|
||||
# GDDR5 has 16 banks with 4 bank groups
|
||||
banks_per_rank = 16
|
||||
|
||||
# 1000 MHz
|
||||
tCK = '1ns'
|
||||
|
||||
# 8 beats across an x64 interface translates to 2 clocks @ 1000 MHz
|
||||
# Data bus runs @2000 Mhz => DDR ( data runs at 4000 MHz )
|
||||
# 8 beats at 4000 MHz = 2 beats at 1000 MHz
|
||||
# tBURST is equivalent to the CAS-to-CAS delay (tCCD)
|
||||
# With bank group architectures, tBURST represents the CAS-to-CAS
|
||||
# delay for bursts to different bank groups (tCCD_S)
|
||||
tBURST = '2ns'
|
||||
|
||||
# @1000MHz data rate, tCCD_L is 3 CK
|
||||
# CAS-to-CAS delay for bursts to the same bank group
|
||||
# tBURST is equivalent to tCCD_S; no explicit parameter required
|
||||
# for CAS-to-CAS delay for bursts to different bank groups
|
||||
tCCD_L = '3ns';
|
||||
|
||||
tRCD = '12ns'
|
||||
|
||||
# tCL is not directly found in datasheet and assumed equal tRCD
|
||||
tCL = '12ns'
|
||||
|
||||
tRP = '12ns'
|
||||
tRAS = '28ns'
|
||||
|
||||
# RRD_S (different bank group)
|
||||
# RRD_S is 5.5 ns in datasheet.
|
||||
# rounded to the next multiple of tCK
|
||||
tRRD = '6ns'
|
||||
|
||||
# RRD_L (same bank group)
|
||||
# RRD_L is 5.5 ns in datasheet.
|
||||
# rounded to the next multiple of tCK
|
||||
tRRD_L = '6ns'
|
||||
|
||||
tXAW = '23ns'
|
||||
|
||||
# tXAW < 4 x tRRD.
|
||||
# Therefore, activation limit is set to 0
|
||||
activation_limit = 0
|
||||
|
||||
tRFC = '65ns'
|
||||
tWR = '12ns'
|
||||
|
||||
# Here using the average of WTR_S and WTR_L
|
||||
tWTR = '5ns'
|
||||
|
||||
# Read-to-Precharge 2 CK
|
||||
tRTP = '2ns'
|
||||
|
||||
# Assume 2 cycles
|
||||
tRTW = '2ns'
|
||||
|
||||
# Default different rank bus delay to 2 CK, @1000 MHz = 2 ns
|
||||
tCS = '2ns'
|
||||
tREFI = '3.9us'
|
||||
|
|
|
@ -115,6 +115,9 @@ DRAMCtrl::DRAMCtrl(const DRAMCtrlParams* p) :
|
|||
for (int b = 0; b < banksPerRank; b++) {
|
||||
banks[r][b].rank = r;
|
||||
banks[r][b].bank = b;
|
||||
// GDDR addressing of banks to BG is linear.
|
||||
// Here we assume that all DRAM generations address bank groups as
|
||||
// follows:
|
||||
if (bankGroupArch) {
|
||||
// Simply assign lower bits to bank group in order to
|
||||
// rotate across bank groups as banks are incremented
|
||||
|
@ -224,7 +227,8 @@ DRAMCtrl::DRAMCtrl(const DRAMCtrlParams* p) :
|
|||
tCCD_L, tBURST, bankGroupsPerRank);
|
||||
}
|
||||
// tRRD_L is greater than minimal, same bank group ACT-to-ACT delay
|
||||
if (tRRD_L <= tRRD) {
|
||||
// some datasheets might specify it equal to tRRD
|
||||
if (tRRD_L < tRRD) {
|
||||
fatal("tRRD_L (%d) should be larger than tRRD (%d) when "
|
||||
"bank groups per rank (%d) is greater than 1\n",
|
||||
tRRD_L, tRRD, bankGroupsPerRank);
|
||||
|
|
|
@ -155,7 +155,8 @@ DRAMPower::getDataRate(const DRAMCtrlParams* p)
|
|||
{
|
||||
uint32_t burst_cycles = divCeil(p->tBURST, p->tCK);
|
||||
uint8_t data_rate = p->burst_length / burst_cycles;
|
||||
if (data_rate != 1 && data_rate != 2)
|
||||
fatal("Got unexpected data rate %d, should be 1 or 2\n");
|
||||
// 4 for GDDR5
|
||||
if (data_rate != 1 && data_rate != 2 && data_rate != 4)
|
||||
fatal("Got unexpected data rate %d, should be 1 or 2 or 4\n");
|
||||
return data_rate;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue