Refresh Manager
This commit is contained in:
60
DRAM/src/core/RefreshManager.cpp
Normal file
60
DRAM/src/core/RefreshManager.cpp
Normal file
@@ -0,0 +1,60 @@
|
||||
/*
|
||||
* RefreshManager.cpp
|
||||
*
|
||||
* Created on: Mar 6, 2014
|
||||
* Author: jonny
|
||||
*/
|
||||
|
||||
#include <core/RefreshManager.h>
|
||||
|
||||
namespace controller {
|
||||
|
||||
RefreshManager::RefreshManager(Configuration& configuration, InternalScheduler& internalScheduler) : controllerConfiguration(configuration), internalScheduler(internalScheduler)
|
||||
{
|
||||
lastRefresh.time = SC_ZERO_TIME;
|
||||
lastRefresh.delay = SC_ZERO_TIME;
|
||||
refreshFinished(SC_ZERO_TIME);
|
||||
}
|
||||
|
||||
/*
|
||||
* Is called from TLM Wrapper when end_refresh is sent from DRAM.
|
||||
*/
|
||||
void RefreshManager::refreshFinished(sc_time currentTime)
|
||||
{
|
||||
planNextRefresh(lastRefresh);
|
||||
assert(currentTime < lastRefresh.time);
|
||||
scheduleRefresh(lastRefresh);
|
||||
}
|
||||
|
||||
/*
|
||||
* Checks for a scheduled CommandSequence, if there is a collision with a refresh.
|
||||
* A refresh may be postponed for a certain time, to fit the scheduled sequence anyways,
|
||||
* depending on the refresh logic.
|
||||
*/
|
||||
bool RefreshManager::hasCollision(CommandSchedule schedule)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
* If a scheduled CommandSequence collides, the refresh manager provides the earliest
|
||||
* start time for the new scheduling of this sequence.
|
||||
*/
|
||||
sc_time RefreshManager::getEarliestStartTime(CommandSchedule schedule)
|
||||
{
|
||||
/*stub*/
|
||||
return SC_ZERO_TIME;
|
||||
}
|
||||
|
||||
void RefreshManager::scheduleRefresh(const PlannedRefresh& refresh) const
|
||||
{
|
||||
internalScheduler.scheduleCommand(ScheduledCommand(Command::Refresh, refresh.time + refresh.delay));
|
||||
}
|
||||
|
||||
void RefreshManager::planNextRefresh(PlannedRefresh& refresh)
|
||||
{
|
||||
refresh.time += controllerConfiguration.Timings.tREF;
|
||||
refresh.delay = SC_ZERO_TIME;
|
||||
}
|
||||
|
||||
} /* namespace controller */
|
||||
48
DRAM/src/core/RefreshManager.h
Normal file
48
DRAM/src/core/RefreshManager.h
Normal file
@@ -0,0 +1,48 @@
|
||||
/*
|
||||
* RefreshManager.h
|
||||
*
|
||||
* Created on: Mar 6, 2014
|
||||
* Author: jonny
|
||||
*/
|
||||
|
||||
#ifndef REFRESHMANAGER_H_
|
||||
#define REFRESHMANAGER_H_
|
||||
|
||||
#include <systemc.h>
|
||||
#include "scheduling/InternalScheduler.h"
|
||||
#include "Configuration.h"
|
||||
|
||||
namespace controller {
|
||||
|
||||
struct PlannedRefresh{
|
||||
PlannedRefresh():time(SC_ZERO_TIME), delay(SC_ZERO_TIME){}
|
||||
sc_time time;
|
||||
sc_time delay;
|
||||
};
|
||||
|
||||
class RefreshManager
|
||||
{
|
||||
public:
|
||||
RefreshManager(Configuration& configuration, InternalScheduler& internalScheduler);
|
||||
virtual ~RefreshManager() {}
|
||||
|
||||
void refreshFinished(sc_time currentTime);
|
||||
|
||||
bool hasCollision(CommandSchedule schedule);
|
||||
sc_time getEarliestStartTime(CommandSchedule schedule);
|
||||
|
||||
private:
|
||||
Configuration& controllerConfiguration;
|
||||
InternalScheduler& internalScheduler;
|
||||
|
||||
PlannedRefresh lastRefresh;
|
||||
|
||||
//void scheduleRefreshTrigger(PlannedRefresh& refresh); idea: schedule refresh only at the regular time. Up to this point refresh can be still shifted to fit a sequence before.
|
||||
|
||||
void planNextRefresh(PlannedRefresh& refresh);
|
||||
void scheduleRefresh(const PlannedRefresh& refresh) const;
|
||||
};
|
||||
|
||||
} /* namespace controller */
|
||||
|
||||
#endif /* REFRESHMANAGER_H_ */
|
||||
49
DRAM/testing/RefreshManager_test.cpp
Normal file
49
DRAM/testing/RefreshManager_test.cpp
Normal file
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* RefreshManager_test.cpp
|
||||
*
|
||||
* Created on: Mar 6, 2014
|
||||
* Author: jonny
|
||||
*/
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
#include <gmock/gmock.h>
|
||||
#include "core/RefreshManager.h"
|
||||
|
||||
using ::testing::_;
|
||||
using ::testing::AtLeast;
|
||||
using ::testing::Expectation;
|
||||
|
||||
namespace controller {
|
||||
|
||||
class MockInternalScheduler: public InternalScheduler
|
||||
{
|
||||
public:
|
||||
MOCK_METHOD1(scheduleCommand, void (ScheduledCommand command));
|
||||
};
|
||||
|
||||
TEST(RefreshManager, RefreshIsScheduledAfterStartup)
|
||||
{
|
||||
Configuration config;
|
||||
MockInternalScheduler internalScheduler;
|
||||
|
||||
auto init = ScheduledCommand(Command::Refresh, config.Timings.tREF);
|
||||
|
||||
EXPECT_CALL(internalScheduler, scheduleCommand(init));
|
||||
|
||||
RefreshManager manager(config, internalScheduler);
|
||||
}
|
||||
|
||||
TEST(RefreshManager, FinishedRefreshTriggersNewRefresh)
|
||||
{
|
||||
Configuration config;
|
||||
MockInternalScheduler internalScheduler;
|
||||
|
||||
EXPECT_CALL(internalScheduler, scheduleCommand(_)).Times(2);
|
||||
|
||||
//schedule first refresh in constructor
|
||||
RefreshManager manager(config, internalScheduler);
|
||||
//schedule second refresh in callback (end_refresh)
|
||||
manager.refreshFinished(config.Timings.tREF + config.Timings.tREFA);
|
||||
}
|
||||
|
||||
} /* namespace controller */
|
||||
Reference in New Issue
Block a user