From 646f68aa4b24d47d8cd8589d8208b51bc5ced41e Mon Sep 17 00:00:00 2001 From: Janik Schlemminger Date: Fri, 11 Apr 2014 16:05:35 +0200 Subject: [PATCH] added refresh checker --- dram/.cproject | 12 +-- dram/.settings/language.settings.xml | 2 +- dram/.settings/org.eclipse.cdt.core.prefs | 2 +- dram/src/core/powerdown/PowerDownManager.cpp | 81 ++++++++++--------- dram/src/core/powerdown/PowerDownManager.h | 3 +- dram/src/core/refresh/IRefreshManager.h | 4 +- dram/src/core/refresh/RefreshManager.cpp | 25 +++--- dram/src/core/refresh/RefreshManager.h | 3 +- .../core/refresh/RefreshManagerBankwise.cpp | 45 +++++------ .../src/core/refresh/RefreshManagerBankwise.h | 6 +- .../checker/PrechargeAllChecker.cpp | 24 +++--- .../scheduling/checker/PrechargeChecker.cpp | 2 +- .../core/scheduling/checker/ReadChecker.cpp | 2 +- .../scheduling/checker/RefreshChecker.cpp | 52 ++++++++++++ .../core/scheduling/checker/RefreshChecker.h | 40 +++++++++ dram/src/simulation/Controller.h | 13 +-- dram/src/simulation/main.cpp | 2 +- 17 files changed, 207 insertions(+), 111 deletions(-) create mode 100644 dram/src/core/scheduling/checker/RefreshChecker.cpp create mode 100644 dram/src/core/scheduling/checker/RefreshChecker.h diff --git a/dram/.cproject b/dram/.cproject index 356d1f93..49a1ca7b 100644 --- a/dram/.cproject +++ b/dram/.cproject @@ -97,24 +97,24 @@ - + - - - + + + - + @@ -166,4 +166,4 @@ - \ No newline at end of file + diff --git a/dram/.settings/language.settings.xml b/dram/.settings/language.settings.xml index b20c7d94..127cd8ac 100644 --- a/dram/.settings/language.settings.xml +++ b/dram/.settings/language.settings.xml @@ -4,7 +4,7 @@ - + diff --git a/dram/.settings/org.eclipse.cdt.core.prefs b/dram/.settings/org.eclipse.cdt.core.prefs index e2661c56..ac28a4dd 100644 --- a/dram/.settings/org.eclipse.cdt.core.prefs +++ b/dram/.settings/org.eclipse.cdt.core.prefs @@ -166,7 +166,7 @@ org.eclipse.cdt.core.formatter.keep_else_statement_on_same_line=false org.eclipse.cdt.core.formatter.keep_empty_array_initializer_on_one_line=false org.eclipse.cdt.core.formatter.keep_imple_if_on_one_line=false org.eclipse.cdt.core.formatter.keep_then_statement_on_same_line=false -org.eclipse.cdt.core.formatter.lineSplit=100 +org.eclipse.cdt.core.formatter.lineSplit=130 org.eclipse.cdt.core.formatter.number_of_empty_lines_to_preserve=1 org.eclipse.cdt.core.formatter.put_empty_statement_on_new_line=true org.eclipse.cdt.core.formatter.tabulation.char=tab diff --git a/dram/src/core/powerdown/PowerDownManager.cpp b/dram/src/core/powerdown/PowerDownManager.cpp index 55d343f7..bf6294ca 100644 --- a/dram/src/core/powerdown/PowerDownManager.cpp +++ b/dram/src/core/powerdown/PowerDownManager.cpp @@ -25,14 +25,11 @@ void PowerDownManager::sleep(Bank bank, sc_time time) assert(canSleep(bank)); PowerDownState state = getPowerDownState(bank); + sc_time minTime = controller.config.Timings.tCKE; + if (state == PowerDownState::Awake) //coming from active { - if (controller.state.bankStates.rowBufferIsOpen(bank)) - setState(PowerDownState::PDNActive, bank); - else - setState(PowerDownState::PDNPrecharge, bank); - - sendPowerDownPayload(time, bank, getSleepCommand(getPowerDownState(bank))); + state = controller.state.bankStates.rowBufferIsOpen(bank) ? PowerDownState::PDNActive : PowerDownState::PDNPrecharge; } else if (state == PowerDownState::AwakeForRefresh) //coming from refresh interrupting power down { @@ -40,12 +37,24 @@ void PowerDownManager::sleep(Bank bank, sc_time time) if (controller.state.getLastCommand(Command::PDNA, bank).getStart() > controller.state.getLastCommand(Command::PDNP, bank).getStart()) - setState(PowerDownState::PDNPrecharge, bank); + state = PowerDownState::PDNPrecharge; else - setState(PowerDownState::PDNSelfRefresh, bank); - - sendPowerDownPayload(time, bank, getSleepCommand(getPowerDownState(bank))); + { + state = PowerDownState::PDNSelfRefresh; + minTime = controller.config.Timings.tCKESR; + } } + + ScheduledCommand pdn(getSleepCommand(state), time, minTime, DramExtension::getExtension(getPayload(bank))); + + //check if pdna or pdnp tcke collides with next refresh + if (state != PowerDownState::PDNSelfRefresh && controller.refreshManager->hasCollision(pdn)) + { + return; + } + + setState(state, bank); + sendPowerDownPayload(pdn); } void PowerDownManager::wakeUp(Bank bank, sc_time time) @@ -57,33 +66,34 @@ void PowerDownManager::wakeUp(Bank bank, sc_time time) } else if (isInPowerDown(bank)) { + time = clkAlign(time); //Request wakes up power down - sc_time delay(SC_ZERO_TIME); + sc_time start(SC_ZERO_TIME); + switch (getPowerDownState(bank)) { case PowerDownState::PDNActive: + start = max(time, controller.state.getLastCommand(Command::PDNA).getEnd()); break; case PowerDownState::PDNPrecharge: + start = max(time, controller.state.getLastCommand(Command::PDNP).getEnd()); break; case PowerDownState::PDNSelfRefresh: - delay = getDelayToMeetConstraint( - controller.state.getLastCommand(Command::SREF).getStart(), time, - controller.config.Timings.tCKESR); + start = max(time, controller.state.getLastCommand(Command::SREF).getEnd()); + controller.refreshManager->reInitialize(bank, start + controller.config.Timings.clk); break; default: break; } - if (delay == SC_ZERO_TIME) - { - sendPowerDownPayload(time, bank, getWakeUpCommand(getPowerDownState(bank))); - setState(PowerDownState::Awake, bank); - } - else - { - tlm_generic_payload& p = getPayload(bank); - controller.wrapper.send(WakeUpTrigger, time + delay, p); - } + + + ScheduledCommand pdn(getWakeUpCommand(getPowerDownState(bank)), start, controller.config.Timings.clk, + DramExtension::getExtension(getPayload(bank))); + + setState(PowerDownState::Awake, bank); + sendPowerDownPayload(pdn); + } } @@ -91,8 +101,10 @@ void PowerDownManager::wakeUpForRefresh(Bank bank, sc_time time) { if (isInPowerDown(bank)) { - sendPowerDownPayload(time, bank, getWakeUpCommand(getPowerDownState(bank))); + ScheduledCommand pdn(getWakeUpCommand(getPowerDownState(bank)), time, controller.config.Timings.clk, + DramExtension::getExtension(getPayload(bank))); setState(PowerDownState::AwakeForRefresh, bank); + sendPowerDownPayload(pdn); } } @@ -106,8 +118,8 @@ void PowerDownManager::wakeUpAllForRefresh(sc_time time) bool PowerDownManager::isInPowerDown(Bank bank) { - return isIn(getPowerDownState(bank), { PowerDownState::PDNActive, PowerDownState::PDNPrecharge, - PowerDownState::PDNSelfRefresh }); + return isIn(getPowerDownState(bank), + { PowerDownState::PDNActive, PowerDownState::PDNPrecharge, PowerDownState::PDNSelfRefresh }); } bool PowerDownManager::isInSelfRefresh(Bank bank) @@ -119,8 +131,8 @@ bool PowerDownManager::allBanksInSelfRefresh() { for (Bank bank : controller.getBanks()) { - if(!isInSelfRefresh(bank)) - return false; + if (!isInSelfRefresh(bank)) + return false; } return true; } @@ -206,15 +218,11 @@ Command PowerDownManager::getWakeUpCommand(PowerDownState state) return cmd; } -void PowerDownManager::sendPowerDownPayload(sc_time time, Bank bank, Command cmd) +void PowerDownManager::sendPowerDownPayload(ScheduledCommand& pdn) { - time = clkAlign(time); //TODO is clkaligned already? - - tlm_generic_payload& payload = getPayload(bank); - ScheduledCommand pdn(cmd, time, controller.config.Timings.clk, DramExtension::getExtension(payload)); controller.state.bus.moveCommandToNextFreeSlot(pdn); controller.state.change(pdn); - controller.wrapper.send(pdn, payload); + controller.wrapper.send(pdn, powerDownPayloads[pdn.getBank()]); } PowerDownState& PowerDownManager::getPowerDownState(Bank bank) @@ -255,8 +263,7 @@ void PowerDownManager::init() setUpDummy(payload, bank); //send payload - ScheduledCommand pdn(Command::PDNP, SC_ZERO_TIME, SC_ZERO_TIME, - DramExtension::getExtension(payload)); + ScheduledCommand pdn(Command::PDNP, SC_ZERO_TIME, SC_ZERO_TIME, DramExtension::getExtension(payload)); controller.state.change(pdn); controller.wrapper.send(pdn, payload); powerDownStates[bank] = PowerDownState::PDNPrecharge; diff --git a/dram/src/core/powerdown/PowerDownManager.h b/dram/src/core/powerdown/PowerDownManager.h index 62b274dc..be1ed821 100644 --- a/dram/src/core/powerdown/PowerDownManager.h +++ b/dram/src/core/powerdown/PowerDownManager.h @@ -14,6 +14,7 @@ #include #include "../Command.h" #include "../../common/dramExtension.h" +#include "../scheduling/ScheduledCommand.h" namespace core { @@ -58,7 +59,7 @@ protected: Command getWakeUpCommand(PowerDownState state); Command getSleepCommand(PowerDownState state); - void sendPowerDownPayload(sc_time time, Bank bank, Command cmd); + void sendPowerDownPayload(ScheduledCommand& pdn); void init(); }; diff --git a/dram/src/core/refresh/IRefreshManager.h b/dram/src/core/refresh/IRefreshManager.h index e0bbe426..b924f566 100644 --- a/dram/src/core/refresh/IRefreshManager.h +++ b/dram/src/core/refresh/IRefreshManager.h @@ -11,8 +11,10 @@ class IRefreshManager public: virtual ~IRefreshManager(){}; virtual bool hasCollision(const CommandSchedule& schedule) = 0; + virtual bool hasCollision(const ScheduledCommand& command) = 0; virtual void scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time time) = 0; - virtual void reInitialize(tlm::tlm_generic_payload& payload, sc_time time) = 0; + virtual void reInitialize(Bank bank, sc_time time) = 0; + virtual bool isInvalidated(tlm::tlm_generic_payload& payload, sc_time time) = 0; }; diff --git a/dram/src/core/refresh/RefreshManager.cpp b/dram/src/core/refresh/RefreshManager.cpp index 7e784289..a2fd970f 100644 --- a/dram/src/core/refresh/RefreshManager.cpp +++ b/dram/src/core/refresh/RefreshManager.cpp @@ -29,20 +29,21 @@ bool RefreshManager::hasCollision(const CommandSchedule& schedule) return !(schedule.getEnd() < nextPlannedRefresh); } +bool RefreshManager::hasCollision(const ScheduledCommand& command) +{ + return !(command.getEnd() < nextPlannedRefresh); +} + void RefreshManager::scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time time) { sc_assert(!isInvalidated(payload, time)); - ScheduledCommand nextRefresh(Command::AutoRefresh, time, timing.tRFC, - DramExtension::getExtension(refreshPayloads[Bank(0)])); - if (!controller.state.bankStates.allRowBuffersAreClosed()) { ScheduledCommand precharge(Command::PrechargeAll, time, controller.config.Timings.tRP, DramExtension::getExtension(refreshPayloads[Bank(0)])); controller.getCommandChecker(Command::PrechargeAll).delayToSatisfyConstraints(precharge); - nextRefresh.setStart(precharge.getEnd()); for (Bank bank : controller.getBanks()) { @@ -53,11 +54,13 @@ void RefreshManager::scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time controller.wrapper.send(prechargeToSend, payload); } } - else - { - //no precharge all - controller.state.bus.moveCommandToNextFreeSlot(nextRefresh); - } + + + ScheduledCommand nextRefresh(Command::AutoRefresh, time, timing.tRFC, + DramExtension::getExtension(refreshPayloads[Bank(0)])); + + controller.getCommandChecker(Command::AutoRefresh).delayToSatisfyConstraints(nextRefresh); + for (Bank bank : controller.getBanks()) { tlm_generic_payload& payload = refreshPayloads[bank]; @@ -67,11 +70,9 @@ void RefreshManager::scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time DramExtension::getExtension(payload)); controller.state.change(refreshToSend); controller.wrapper.send(refreshToSend, payload); - } planNextRefresh(); - } void RefreshManager::planNextRefresh() @@ -80,7 +81,7 @@ void RefreshManager::planNextRefresh() controller.wrapper.send(RefreshTrigger, nextPlannedRefresh, refreshPayloads[Bank(0)]); } -void RefreshManager::reInitialize(tlm::tlm_generic_payload& payload, sc_time time) +void RefreshManager::reInitialize(Bank bank, sc_time time) { nextPlannedRefresh = clkAlign(time, Alignment::DOWN); planNextRefresh(); diff --git a/dram/src/core/refresh/RefreshManager.h b/dram/src/core/refresh/RefreshManager.h index 46d5a33f..43f472ba 100644 --- a/dram/src/core/refresh/RefreshManager.h +++ b/dram/src/core/refresh/RefreshManager.h @@ -22,9 +22,10 @@ public: virtual ~RefreshManager(); bool hasCollision(const CommandSchedule& schedule) override; + bool hasCollision(const ScheduledCommand& command) override; void scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time time) override; - void reInitialize(tlm::tlm_generic_payload& payload, sc_time time) override; + void reInitialize(Bank bank, sc_time time) override; bool isInvalidated(tlm::tlm_generic_payload& payload, sc_time time) override; diff --git a/dram/src/core/refresh/RefreshManagerBankwise.cpp b/dram/src/core/refresh/RefreshManagerBankwise.cpp index cde123b7..bba98978 100644 --- a/dram/src/core/refresh/RefreshManagerBankwise.cpp +++ b/dram/src/core/refresh/RefreshManagerBankwise.cpp @@ -16,8 +16,6 @@ namespace core { RefreshManagerBankwise::RefreshManagerBankwise(ControllerCore& controller) : controller(controller) { - assert(!controller.config.Timings.refreshTimings.empty()); - for (Bank bank : controller.getBanks()) { refreshManagerForBanks[bank] = new RefreshManagerForBank(controller, bank); @@ -38,18 +36,22 @@ bool RefreshManagerBankwise::hasCollision(const CommandSchedule& schedule) return manager.hasCollision(schedule); } +bool RefreshManagerBankwise::hasCollision(const ScheduledCommand& command) +{ + RefreshManagerForBank& manager = *refreshManagerForBanks[command.getBank()]; + return manager.hasCollision(command); +} + void RefreshManagerBankwise::scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time time) { sc_assert(!isInvalidated(payload, time)); - RefreshManagerForBank& manager = - *refreshManagerForBanks[DramExtension::getExtension(payload).getBank()]; + RefreshManagerForBank& manager = *refreshManagerForBanks[DramExtension::getExtension(payload).getBank()]; manager.scheduleRefresh(time); } -RefreshManagerBankwise::RefreshManagerForBank::RefreshManagerForBank(ControllerCore& controller, - Bank bank) : - controller(controller), timing(controller.config.Timings.refreshTimings[bank]), bank( - bank), nextPlannedRefresh(SC_ZERO_TIME) +RefreshManagerBankwise::RefreshManagerForBank::RefreshManagerForBank(ControllerCore& controller, Bank bank) : + controller(controller), timing(controller.config.Timings.refreshTimings[bank]), bank(bank), nextPlannedRefresh( + SC_ZERO_TIME) { setupTransaction(); planNextRefresh(); @@ -59,21 +61,18 @@ RefreshManagerBankwise::RefreshManagerForBank::~RefreshManagerForBank() { } -/* - * Checks for a scheduled CommandSequence, if there is a collision with the current planned, - * not yet scheduled, refresh command. In case of a collision the manager schedules the refresh - * (sends it out) and plans the next refresh. Afterwards the CommandSequence is re-scheduled - * with the new controller state (earliest start time is the end of the just scheduled refresh). - */ bool RefreshManagerBankwise::RefreshManagerForBank::hasCollision(const CommandSchedule& schedule) { return !(schedule.getEnd() < nextPlannedRefresh); } +bool RefreshManagerBankwise::RefreshManagerForBank::hasCollision(const ScheduledCommand& command) +{ + return !(command.getEnd() < nextPlannedRefresh); +} void RefreshManagerBankwise::RefreshManagerForBank::scheduleRefresh(sc_time time) { - ScheduledCommand nextRefresh(Command::AutoRefresh, time, timing.tRFC, - DramExtension::getExtension(refreshPayload)); + ScheduledCommand nextRefresh(Command::AutoRefresh, time, timing.tRFC, DramExtension::getExtension(refreshPayload)); if (controller.state.bankStates.rowBufferIsOpen(bank)) { @@ -89,8 +88,7 @@ void RefreshManagerBankwise::RefreshManagerForBank::scheduleRefresh(sc_time time controller.state.bus.moveCommandToNextFreeSlot(nextRefresh); controller.state.change(nextRefresh); Row currentrow = DramExtension::getExtension(refreshPayload).getRow(); - DramExtension::getExtension(refreshPayload).setRow( - Row((currentrow.ID() + 1) % Configuration::getInstance().NumberOfBanks)); + DramExtension::getExtension(refreshPayload).setRow(Row((currentrow.ID() + 1) % Configuration::getInstance().NumberOfBanks)); controller.wrapper.send(nextRefresh, refreshPayload); planNextRefresh(); @@ -102,8 +100,7 @@ void RefreshManagerBankwise::RefreshManagerForBank::planNextRefresh() controller.wrapper.send(RefreshTrigger, nextPlannedRefresh, refreshPayload); } -void RefreshManagerBankwise::RefreshManagerForBank::reInitialize(tlm::tlm_generic_payload& payload, - sc_time time) +void RefreshManagerBankwise::RefreshManagerForBank::reInitialize(Bank bank, sc_time time) { nextPlannedRefresh = clkAlign(time, Alignment::DOWN); planNextRefresh(); @@ -119,17 +116,15 @@ void RefreshManagerBankwise::RefreshManagerForBank::setupTransaction() setUpDummy(refreshPayload, bank); } -void RefreshManagerBankwise::reInitialize(tlm::tlm_generic_payload& payload, sc_time time) +void RefreshManagerBankwise::reInitialize(Bank bank, sc_time time) { - refreshManagerForBanks[DramExtension::getExtension(payload).getBank()]->reInitialize(payload, - time); + refreshManagerForBanks[bank]->reInitialize(bank, time); } bool RefreshManagerBankwise::isInvalidated(tlm::tlm_generic_payload& payload, sc_time time) { - RefreshManagerForBank& manager = - *refreshManagerForBanks[DramExtension::getExtension(payload).getBank()]; + RefreshManagerForBank& manager = *refreshManagerForBanks[DramExtension::getExtension(payload).getBank()]; return manager.isInvalidated(time); } diff --git a/dram/src/core/refresh/RefreshManagerBankwise.h b/dram/src/core/refresh/RefreshManagerBankwise.h index 34eac9ed..8361e650 100644 --- a/dram/src/core/refresh/RefreshManagerBankwise.h +++ b/dram/src/core/refresh/RefreshManagerBankwise.h @@ -24,9 +24,10 @@ public: virtual ~RefreshManagerBankwise(); virtual bool hasCollision(const CommandSchedule& schedule) override; + virtual bool hasCollision(const ScheduledCommand& command) override; virtual void scheduleRefresh(tlm::tlm_generic_payload& payload, sc_time time) override; - void reInitialize(tlm::tlm_generic_payload& payload, sc_time time) override; + void reInitialize(Bank bank, sc_time time) override; bool isInvalidated(tlm::tlm_generic_payload& payload,sc_time time) override; @@ -39,9 +40,10 @@ private: ~RefreshManagerForBank(); bool hasCollision(const CommandSchedule& schedule); + bool hasCollision(const ScheduledCommand& command); void scheduleRefresh(sc_time time); - void reInitialize(tlm::tlm_generic_payload& payload, sc_time time); + void reInitialize(Bank bank, sc_time time); bool isInvalidated(sc_time); private: diff --git a/dram/src/core/scheduling/checker/PrechargeAllChecker.cpp b/dram/src/core/scheduling/checker/PrechargeAllChecker.cpp index 39cf5e97..522e5a2c 100644 --- a/dram/src/core/scheduling/checker/PrechargeAllChecker.cpp +++ b/dram/src/core/scheduling/checker/PrechargeAllChecker.cpp @@ -21,36 +21,40 @@ void PrechargeAllChecker::delayToSatisfyConstraints(ScheduledCommand& command) c { if (lastCommand.getCommand() == Command::Read) { - command.delayToMeetConstraint(lastCommand.getStart(), - lastCommand.getBurstLength() * config.Timings.clk); + command.delayToMeetConstraint(lastCommand.getStart(), lastCommand.getBurstLength() * config.Timings.clk); } else if (lastCommand.getCommand() == Command::Write) { command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tWR); } - else if(lastCommand.getCommand() == Command::WriteA) + else if (lastCommand.getCommand() == Command::WriteA) { command.delayToMeetConstraint(lastCommand.getEnd(), SC_ZERO_TIME); - if(config.Timings.tWR > config.Timings.tRP) + if (config.Timings.tWR > config.Timings.tRP) command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tWR - config.Timings.tRP); } - else if (lastCommand.commandIsIn( {Command::ReadA, Command::PDNAX, Command::PDNPX, Command::SREFX, - Command::AutoRefresh })) + else if (lastCommand.commandIsIn( { Command::PDNAX, Command::PDNPX })) + { + command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tXP); + } + else if (lastCommand.getCommand() == Command::SREFX) + { + command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tXSR); + } + else if (lastCommand.commandIsIn( { Command::ReadA, Command::AutoRefresh })) { command.delayToMeetConstraint(lastCommand.getEnd(), SC_ZERO_TIME); } else reportFatal("Precharge All Checker", - "Precharge All can not follow " - + commandToString(lastCommand.getCommand())); + "Precharge All can not follow " + commandToString(lastCommand.getCommand())); } } state.bus.moveCommandToNextFreeSlot(command); } -sc_time PrechargeAllChecker::getExecutionTime(const tlm::tlm_generic_payload& payload, - Command command) const +sc_time PrechargeAllChecker::getExecutionTime(const tlm::tlm_generic_payload& payload, Command command) const { sc_assert(command == Command::PrechargeAll); return config.Timings.tRP; diff --git a/dram/src/core/scheduling/checker/PrechargeChecker.cpp b/dram/src/core/scheduling/checker/PrechargeChecker.cpp index 85fe737e..5c8dda3c 100644 --- a/dram/src/core/scheduling/checker/PrechargeChecker.cpp +++ b/dram/src/core/scheduling/checker/PrechargeChecker.cpp @@ -31,7 +31,7 @@ void PrechargeChecker::delayToSatisfyConstraints(ScheduledCommand& command) cons } else if (lastCommand.getCommand() == Command::PDNAX) { - command.delayToMeetConstraint(lastCommand.getEnd(), SC_ZERO_TIME); + command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tXP);//TODO right? } else reportFatal("Precharge Checker", diff --git a/dram/src/core/scheduling/checker/ReadChecker.cpp b/dram/src/core/scheduling/checker/ReadChecker.cpp index 7720783e..7324081b 100644 --- a/dram/src/core/scheduling/checker/ReadChecker.cpp +++ b/dram/src/core/scheduling/checker/ReadChecker.cpp @@ -29,7 +29,7 @@ void ReadChecker::delayToSatisfyConstraints(ScheduledCommand& command) const } else if (lastCommand.getCommand() == Command::PDNAX) { - command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tXP); + command.delayToMeetConstraint(lastCommand.getEnd(), config.Timings.tXP);//TODO DLL also for PDNP and SREF .. not onyl last command } else reportFatal("Read Checker", diff --git a/dram/src/core/scheduling/checker/RefreshChecker.cpp b/dram/src/core/scheduling/checker/RefreshChecker.cpp new file mode 100644 index 00000000..6e790338 --- /dev/null +++ b/dram/src/core/scheduling/checker/RefreshChecker.cpp @@ -0,0 +1,52 @@ +/* + * RefreshChecker.cpp + * + * Created on: Apr 11, 2014 + * Author: jonny + */ + +#include "RefreshChecker.h" +#include "../../../common/Utils.h" + +namespace core { + +void RefreshChecker::delayToSatisfyConstraints(ScheduledCommand& command) const +{ + sc_assert(command.getCommand() == Command::AutoRefresh); + + ScheduledCommand lastCommandOnBank = state.getLastScheduledCommand(command.getBank()); + + if (lastCommandOnBank.isValidCommand()) + { + if (lastCommandOnBank.getCommand() == Command::Precharge || lastCommandOnBank.getCommand() == Command::PrechargeAll ) + { + command.delayToMeetConstraint(lastCommandOnBank.getEnd(), SC_ZERO_TIME); + } + else if (lastCommandOnBank.getCommand() == Command::PDNPX) + { + command.delayToMeetConstraint(lastCommandOnBank.getEnd(), config.Timings.tXP); + } + else if (lastCommandOnBank.getCommand() == Command::SREFX) + { + command.delayToMeetConstraint(lastCommandOnBank.getEnd(), config.Timings.tXSR); + } + else + reportFatal("Refresh Checker", "Refresh can not follow " + commandToString(lastCommandOnBank.getCommand())); + } + + while (!state.bus.isFree(command.getStart())) + { + command.delayStart(config.Timings.clk); + } +} + +sc_time RefreshChecker::getExecutionTime(const tlm::tlm_generic_payload& payload, Command command) const +{ + assert(command == Command::AutoRefresh); + Bank bank = DramExtension::getExtension(payload).getBank(); + RefreshTiming timing = config.Timings.refreshTimings.at(bank); + return timing.tRFC; +} + +} /* namespace core */ + diff --git a/dram/src/core/scheduling/checker/RefreshChecker.h b/dram/src/core/scheduling/checker/RefreshChecker.h new file mode 100644 index 00000000..3f2c43b0 --- /dev/null +++ b/dram/src/core/scheduling/checker/RefreshChecker.h @@ -0,0 +1,40 @@ +/* + * RefreshChecker.h + * + * Created on: Apr 11, 2014 + * Author: jonny + */ + +#ifndef REFRESHCHECKER_H_ +#define REFRESHCHECKER_H_ + +#include "ICommandChecker.h" +#include "../../ControllerState.h" +#include "../../configuration/Configuration.h" +#include + +namespace core { + +class RefreshChecker: ICommandChecker +{ +public: + RefreshChecker(const Configuration& config, ControllerState& state) : + config(config), state(state) + { + } + virtual ~RefreshChecker() + { + } + + virtual void delayToSatisfyConstraints(ScheduledCommand& command) const override; + virtual sc_time getExecutionTime(const tlm::tlm_generic_payload& payload, Command command) const override; + +private: + const Configuration& config; + ControllerState& state; + +}; + +} /* namespace core */ + +#endif /* REFRESHCHECKER_H_ */ diff --git a/dram/src/simulation/Controller.h b/dram/src/simulation/Controller.h index 4cce3eb7..4619ad0d 100644 --- a/dram/src/simulation/Controller.h +++ b/dram/src/simulation/Controller.h @@ -265,12 +265,6 @@ private: void scheduleNextPayload(Bank bank) { - if (bank.ID() == 5) - { - int i = 5; - ++i; - } - printDebugMessage("Triggering schedule next payload on bank " + to_string(bank.ID())); if (scheduler->hasTransactionForBank(bank)) { @@ -280,11 +274,11 @@ private: printDebugMessage("\t-> break: controller is busy"); return; } + if (controller->powerDownManager->isInPowerDown(bank)) { - printDebugMessage("\t-> break: wake up bank first"); + printDebugMessage("\t-> wake up bank first"); controller->powerDownManager->wakeUp(bank, sc_time_stamp()); - return; } else if (controller->powerDownManager->isAwakeForRefresh(bank)) { @@ -401,9 +395,6 @@ private: "Leaving PowerDown " + phaseNameToString(phase) + " on bank " + to_string(bank.ID())); sendToDram(payload, phase, SC_ZERO_TIME); - if (phase == END_SREF) - controller->refreshManager->reInitialize(payload, sc_time_stamp()); - scheduleNextPayload(bank); } else if (phase == BEGIN_AUTO_REFRESH) { diff --git a/dram/src/simulation/main.cpp b/dram/src/simulation/main.cpp index 65d05f10..9383da0f 100644 --- a/dram/src/simulation/main.cpp +++ b/dram/src/simulation/main.cpp @@ -99,7 +99,7 @@ int sc_main(int argc, char **argv) string trace2 = "empty.stl"; string trace1 = "chstone-jpeg_32.stl"; - trace1 = "trace.stl"; + //trace1 = "trace.stl"; if (runSimulation(resources, traceName, setup, { Device(trace1), Device(trace2) })) startTraceAnalyzer(traceName);