Code cleanup.

This commit is contained in:
Lukas Steiner
2022-03-01 16:18:10 +01:00
parent 8d288e5062
commit 17e224229d
15 changed files with 85 additions and 73 deletions

View File

@@ -40,7 +40,7 @@
using namespace sc_core;
using namespace tlm;
BankMachine::BankMachine(SchedulerIF *scheduler, CheckerIF *checker, Bank bank)
BankMachine::BankMachine(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank)
: scheduler(scheduler), checker(checker), bank(bank)
{
memSpec = Configuration::getInstance().memSpec;
@@ -155,7 +155,7 @@ bool BankMachine::isPrecharged() const
return state == State::Precharged;
}
BankMachineOpen::BankMachineOpen(SchedulerIF *scheduler, CheckerIF *checker, Bank bank)
BankMachineOpen::BankMachineOpen(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank)
: BankMachine(scheduler, checker, bank) {}
sc_time BankMachineOpen::start()
@@ -165,7 +165,7 @@ sc_time BankMachineOpen::start()
if (!(sleeping || blocked))
{
currentPayload = scheduler->getNextRequest(this);
currentPayload = scheduler.getNextRequest(this);
if (currentPayload != nullptr)
{
if (state == State::Precharged) // bank precharged
@@ -184,13 +184,13 @@ sc_time BankMachineOpen::start()
else // row miss
nextCommand = Command::PREPB;
}
timeToSchedule = checker->timeToSatisfyConstraints(nextCommand, *currentPayload);
timeToSchedule = checker.timeToSatisfyConstraints(nextCommand, *currentPayload);
}
}
return timeToSchedule;
}
BankMachineClosed::BankMachineClosed(SchedulerIF *scheduler, CheckerIF *checker, Bank bank)
BankMachineClosed::BankMachineClosed(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank)
: BankMachine(scheduler, checker, bank) {}
sc_time BankMachineClosed::start()
@@ -200,7 +200,7 @@ sc_time BankMachineClosed::start()
if (!(sleeping || blocked))
{
currentPayload = scheduler->getNextRequest(this);
currentPayload = scheduler.getNextRequest(this);
if (currentPayload != nullptr)
{
if (state == State::Precharged) // bank precharged
@@ -214,13 +214,13 @@ sc_time BankMachineClosed::start()
else
SC_REPORT_FATAL("BankMachine", "Wrong TLM command");
}
timeToSchedule = checker->timeToSatisfyConstraints(nextCommand, *currentPayload);
timeToSchedule = checker.timeToSatisfyConstraints(nextCommand, *currentPayload);
}
}
return timeToSchedule;
}
BankMachineOpenAdaptive::BankMachineOpenAdaptive(SchedulerIF *scheduler, CheckerIF *checker, Bank bank)
BankMachineOpenAdaptive::BankMachineOpenAdaptive(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank)
: BankMachine(scheduler, checker, bank) {}
sc_time BankMachineOpenAdaptive::start()
@@ -230,7 +230,7 @@ sc_time BankMachineOpenAdaptive::start()
if (!(sleeping || blocked))
{
currentPayload = scheduler->getNextRequest(this);
currentPayload = scheduler.getNextRequest(this);
if (currentPayload != nullptr)
{
if (state == State::Precharged) // bank precharged
@@ -239,7 +239,7 @@ sc_time BankMachineOpenAdaptive::start()
{
if (DramExtension::getRow(currentPayload) == openRow) // row hit
{
if (scheduler->hasFurtherRequest(bank) && !scheduler->hasFurtherRowHit(bank, openRow))
if (scheduler.hasFurtherRequest(bank) && !scheduler.hasFurtherRowHit(bank, openRow))
{
if (currentPayload->is_read())
nextCommand = Command::RDA;
@@ -261,13 +261,13 @@ sc_time BankMachineOpenAdaptive::start()
else // row miss
nextCommand = Command::PREPB;
}
timeToSchedule = checker->timeToSatisfyConstraints(nextCommand, *currentPayload);
timeToSchedule = checker.timeToSatisfyConstraints(nextCommand, *currentPayload);
}
}
return timeToSchedule;
}
BankMachineClosedAdaptive::BankMachineClosedAdaptive(SchedulerIF *scheduler, CheckerIF *checker, Bank bank)
BankMachineClosedAdaptive::BankMachineClosedAdaptive(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank)
: BankMachine(scheduler, checker, bank) {}
sc_time BankMachineClosedAdaptive::start()
@@ -277,7 +277,7 @@ sc_time BankMachineClosedAdaptive::start()
if (!(sleeping || blocked))
{
currentPayload = scheduler->getNextRequest(this);
currentPayload = scheduler.getNextRequest(this);
if (currentPayload != nullptr)
{
if (state == State::Precharged && !blocked) // bank precharged
@@ -286,7 +286,7 @@ sc_time BankMachineClosedAdaptive::start()
{
if (DramExtension::getRow(currentPayload) == openRow) // row hit
{
if (scheduler->hasFurtherRowHit(bank, openRow))
if (scheduler.hasFurtherRowHit(bank, openRow))
{
if (currentPayload->is_read())
nextCommand = Command::RD;
@@ -308,7 +308,7 @@ sc_time BankMachineClosedAdaptive::start()
else // row miss, should never happen
SC_REPORT_FATAL("BankMachine", "Should never be reached for this policy");
}
timeToSchedule = checker->timeToSatisfyConstraints(nextCommand, *currentPayload);
timeToSchedule = checker.timeToSatisfyConstraints(nextCommand, *currentPayload);
}
}
return timeToSchedule;

View File

@@ -63,11 +63,11 @@ public:
protected:
enum class State {Precharged, Activated} state = State::Precharged;
BankMachine(SchedulerIF *, CheckerIF *, Bank);
BankMachine(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank);
const MemSpec* memSpec;
tlm::tlm_generic_payload *currentPayload = nullptr;
SchedulerIF *scheduler;
CheckerIF *checker;
const SchedulerIF& scheduler;
const CheckerIF& checker;
Command nextCommand = Command::NOP;
Row openRow;
sc_core::sc_time timeToSchedule = sc_core::sc_max_time();
@@ -83,28 +83,28 @@ protected:
class BankMachineOpen final : public BankMachine
{
public:
BankMachineOpen(SchedulerIF *, CheckerIF *, Bank);
BankMachineOpen(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank);
sc_core::sc_time start() override;
};
class BankMachineClosed final : public BankMachine
{
public:
BankMachineClosed(SchedulerIF *, CheckerIF *, Bank);
BankMachineClosed(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank);
sc_core::sc_time start() override;
};
class BankMachineOpenAdaptive final : public BankMachine
{
public:
BankMachineOpenAdaptive(SchedulerIF *, CheckerIF *, Bank);
BankMachineOpenAdaptive(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank);
sc_core::sc_time start() override;
};
class BankMachineClosedAdaptive final : public BankMachine
{
public:
BankMachineClosedAdaptive(SchedulerIF *, CheckerIF *, Bank);
BankMachineClosedAdaptive(const SchedulerIF& scheduler, const CheckerIF& checker, Bank bank);
sc_core::sc_time start() override;
};

View File

@@ -143,22 +143,22 @@ Controller::Controller(const sc_module_name &name) :
if (config.pagePolicy == Configuration::PagePolicy::Open)
{
for (unsigned bankID = 0; bankID < memSpec->numberOfBanks; bankID++)
bankMachines.emplace_back(std::make_unique<BankMachineOpen>(scheduler.get(), checker.get(), Bank(bankID)));
bankMachines.emplace_back(std::make_unique<BankMachineOpen>(*scheduler, *checker, Bank(bankID)));
}
else if (config.pagePolicy == Configuration::PagePolicy::OpenAdaptive)
{
for (unsigned bankID = 0; bankID < memSpec->numberOfBanks; bankID++)
bankMachines.emplace_back(std::make_unique<BankMachineOpenAdaptive>(scheduler.get(), checker.get(), Bank(bankID)));
bankMachines.emplace_back(std::make_unique<BankMachineOpenAdaptive>(*scheduler, *checker, Bank(bankID)));
}
else if (config.pagePolicy == Configuration::PagePolicy::Closed)
{
for (unsigned bankID = 0; bankID < memSpec->numberOfBanks; bankID++)
bankMachines.emplace_back(std::make_unique<BankMachineClosed>(scheduler.get(), checker.get(), Bank(bankID)));
bankMachines.emplace_back(std::make_unique<BankMachineClosed>(*scheduler, *checker, Bank(bankID)));
}
else if (config.pagePolicy == Configuration::PagePolicy::ClosedAdaptive)
{
for (unsigned bankID = 0; bankID < memSpec->numberOfBanks; bankID++)
bankMachines.emplace_back(std::make_unique<BankMachineClosedAdaptive>(scheduler.get(), checker.get(), Bank(bankID)));
bankMachines.emplace_back(std::make_unique<BankMachineClosedAdaptive>(*scheduler, *checker, Bank(bankID)));
}
bankMachinesOnRank = std::vector<std::vector<BankMachine*>>(memSpec->numberOfRanks,
@@ -212,7 +212,7 @@ Controller::Controller(const sc_module_name &name) :
{
// TODO: remove bankMachines in constructor
refreshManagers.emplace_back(std::make_unique<RefreshManagerPerBank>
(bankMachinesOnRank[rankID], powerDownManagers[rankID].get(), Rank(rankID), checker.get()));
(bankMachinesOnRank[rankID], *powerDownManagers[rankID], Rank(rankID), *checker));
}
}
else if (config.refreshPolicy == Configuration::RefreshPolicy::Per2Bank)
@@ -330,7 +330,8 @@ void Controller::controllerMethod()
if (ranksNumberOfPayloads[rank.ID()] == 0)
powerDownManagers[rank.ID()]->triggerEntry();
sendToDram(command, payload, thinkDelayFw + phyDelayFw);
sc_time fwDelay = thinkDelayFw + phyDelayFw;
sendToDram(command, *payload, fwDelay);
}
else
readyCmdBlocked = true;
@@ -423,7 +424,9 @@ void Controller::manageRequests(const sc_time &delay)
bankMachines[bank.ID()]->start();
transToAcquire.payload->set_response_status(TLM_OK_RESPONSE);
sendToFrontend(transToAcquire.payload, END_REQ, delay);
tlm_phase bwPhase = END_REQ;
sc_time bwDelay = delay;
sendToFrontend(*transToAcquire.payload, bwPhase, bwDelay);
transToAcquire.payload = nullptr;
}
else
@@ -459,7 +462,9 @@ void Controller::manageResponses()
if (transToRelease.payload != nullptr)
{
// last payload was released in this cycle
sendToFrontend(transToRelease.payload, BEGIN_RESP, memSpec->tCK);
tlm_phase bwPhase = BEGIN_RESP;
sc_time bwDelay = memSpec->tCK;
sendToFrontend(*transToRelease.payload, bwPhase, bwDelay);
transToRelease.time = sc_max_time();
}
else
@@ -477,11 +482,14 @@ void Controller::manageResponses()
if (transToRelease.payload != nullptr)
{
tlm_phase bwPhase = BEGIN_RESP;
sc_time bwDelay;
if (transToRelease.time == sc_time_stamp()) // last payload was released in this cycle
sendToFrontend(transToRelease.payload, BEGIN_RESP, memSpec->tCK);
bwDelay = memSpec->tCK;
else
sendToFrontend(transToRelease.payload, BEGIN_RESP, SC_ZERO_TIME);
bwDelay = SC_ZERO_TIME;
sendToFrontend(*transToRelease.payload, bwPhase, bwDelay);
transToRelease.time = sc_max_time();
}
else
@@ -493,13 +501,13 @@ void Controller::manageResponses()
}
}
void Controller::sendToFrontend(tlm_generic_payload *payload, tlm_phase phase, sc_time delay)
void Controller::sendToFrontend(tlm_generic_payload& payload, tlm_phase& phase, sc_time& delay)
{
tSocket->nb_transport_bw(*payload, phase, delay);
tSocket->nb_transport_bw(payload, phase, delay);
}
void Controller::sendToDram(Command command, tlm_generic_payload *payload, sc_time delay)
void Controller::sendToDram(Command command, tlm_generic_payload& payload, sc_time& delay)
{
tlm_phase phase = command.toPhase();
iSocket->nb_transport_fw(*payload, phase, delay);
iSocket->nb_transport_fw(payload, phase, delay);
}

View File

@@ -56,14 +56,14 @@ public:
SC_HAS_PROCESS(Controller);
protected:
tlm::tlm_sync_enum nb_transport_fw(tlm::tlm_generic_payload &trans, tlm::tlm_phase &phase,
sc_core::sc_time &delay) override;
tlm::tlm_sync_enum nb_transport_bw(tlm::tlm_generic_payload &trans, tlm::tlm_phase &phase,
sc_core::sc_time &delay) override;
unsigned int transport_dbg(tlm::tlm_generic_payload &trans) override;
tlm::tlm_sync_enum nb_transport_fw(tlm::tlm_generic_payload& trans, tlm::tlm_phase& phase,
sc_core::sc_time& delay) override;
tlm::tlm_sync_enum nb_transport_bw(tlm::tlm_generic_payload& trans, tlm::tlm_phase& phase,
sc_core::sc_time& delay) override;
unsigned int transport_dbg(tlm::tlm_generic_payload& trans) override;
virtual void sendToFrontend(tlm::tlm_generic_payload *, tlm::tlm_phase, sc_core::sc_time);
virtual void sendToDram(Command, tlm::tlm_generic_payload *, sc_core::sc_time);
virtual void sendToFrontend(tlm::tlm_generic_payload& trans, tlm::tlm_phase& phase, sc_core::sc_time& delay);
virtual void sendToDram(Command, tlm::tlm_generic_payload& trans, sc_core::sc_time& delay);
void end_of_simulation() override;

View File

@@ -99,7 +99,7 @@ public:
protected:
// Bind sockets with virtual functions
explicit ControllerIF(const sc_core::sc_module_name &name)
explicit ControllerIF(const sc_core::sc_module_name& name)
: sc_core::sc_module(name), tSocket("tSocket"), iSocket("iSocket")
{
tSocket.register_nb_transport_fw(this, &ControllerIF::nb_transport_fw);
@@ -109,9 +109,11 @@ protected:
SC_HAS_PROCESS(ControllerIF);
// Virtual transport functions
virtual tlm::tlm_sync_enum nb_transport_fw(tlm::tlm_generic_payload &, tlm::tlm_phase &, sc_core::sc_time &) = 0;
virtual unsigned int transport_dbg(tlm::tlm_generic_payload &) = 0;
virtual tlm::tlm_sync_enum nb_transport_bw(tlm::tlm_generic_payload &, tlm::tlm_phase &, sc_core::sc_time &) = 0;
virtual tlm::tlm_sync_enum nb_transport_fw(tlm::tlm_generic_payload& trans, tlm::tlm_phase& phase,
sc_core::sc_time& delay) = 0;
virtual unsigned int transport_dbg(tlm::tlm_generic_payload& trans) = 0;
virtual tlm::tlm_sync_enum nb_transport_bw(tlm::tlm_generic_payload& trans, tlm::tlm_phase& phase,
sc_core::sc_time& delay) = 0;
// Bandwidth related
class IdleTimeCollector

View File

@@ -67,23 +67,23 @@ tlm_sync_enum ControllerRecordable::nb_transport_bw(tlm_generic_payload &,
return TLM_ACCEPTED;
}
void ControllerRecordable::sendToFrontend(tlm_generic_payload *payload, tlm_phase phase, sc_time delay)
void ControllerRecordable::sendToFrontend(tlm_generic_payload& payload, tlm_phase& phase, sc_time& delay)
{
recordPhase(*payload, phase, delay);
tSocket->nb_transport_bw(*payload, phase, delay);
recordPhase(payload, phase, delay);
tSocket->nb_transport_bw(payload, phase, delay);
}
void ControllerRecordable::sendToDram(Command command, tlm_generic_payload *payload, sc_time delay)
void ControllerRecordable::sendToDram(Command command, tlm_generic_payload& payload, sc_time& delay)
{
if (command.isCasCommand())
{
TimeInterval dataStrobe = Configuration::getInstance().memSpec->getIntervalOnDataStrobe(command, *payload);
TimeInterval dataStrobe = Configuration::getInstance().memSpec->getIntervalOnDataStrobe(command, payload);
tlmRecorder.updateDataStrobe(sc_time_stamp() + delay + dataStrobe.start,
sc_time_stamp() + delay + dataStrobe.end, *payload);
sc_time_stamp() + delay + dataStrobe.end, payload);
}
tlm_phase phase = command.toPhase();
iSocket->nb_transport_fw(*payload, phase, delay);
iSocket->nb_transport_fw(payload, phase, delay);
}
void ControllerRecordable::recordPhase(tlm_generic_payload &trans, const tlm_phase &phase, const sc_time &delay)

View File

@@ -52,8 +52,8 @@ protected:
tlm::tlm_sync_enum nb_transport_bw(tlm::tlm_generic_payload &trans, tlm::tlm_phase &phase,
sc_core::sc_time &delay) override;
void sendToFrontend(tlm::tlm_generic_payload *, tlm::tlm_phase, sc_core::sc_time) override;
void sendToDram(Command, tlm::tlm_generic_payload *, sc_core::sc_time) override;
void sendToFrontend(tlm::tlm_generic_payload& trans, tlm::tlm_phase& phase, sc_core::sc_time& delay) override;
void sendToDram(Command command, tlm::tlm_generic_payload& trans, sc_core::sc_time& delay) override;
void controllerMethod() override;

View File

@@ -44,7 +44,7 @@ using namespace sc_core;
using namespace tlm;
RefreshManagerAllBank::RefreshManagerAllBank(std::vector<BankMachine*>& bankMachinesOnRank,
PowerDownManagerIF& powerDownManager, Rank rank, CheckerIF& checker)
PowerDownManagerIF& powerDownManager, Rank rank, const CheckerIF& checker)
: bankMachinesOnRank(bankMachinesOnRank), powerDownManager(powerDownManager), checker(checker)
{
Configuration &config = Configuration::getInstance();

View File

@@ -50,7 +50,7 @@ class RefreshManagerAllBank final : public RefreshManagerIF
{
public:
RefreshManagerAllBank(std::vector<BankMachine*>& bankMachinesOnRank,
PowerDownManagerIF& powerDownManager, Rank rank, CheckerIF& checker);
PowerDownManagerIF& powerDownManager, Rank rank, const CheckerIF& checker);
CommandTuple::Type getNextCommand() override;
sc_core::sc_time start() override;
@@ -64,7 +64,7 @@ private:
tlm::tlm_generic_payload refreshPayload;
sc_core::sc_time timeForNextTrigger = sc_core::sc_max_time();
sc_core::sc_time timeToSchedule = sc_core::sc_max_time();
CheckerIF& checker;
const CheckerIF& checker;
Command nextCommand = Command::NOP;
unsigned activatedBanks = 0;

View File

@@ -43,7 +43,8 @@ using namespace sc_core;
using namespace tlm;
RefreshManagerPer2Bank::RefreshManagerPer2Bank(std::vector<BankMachine*>& bankMachinesOnRank,
PowerDownManagerIF& powerDownManager, Rank rank, CheckerIF& checker)
PowerDownManagerIF& powerDownManager, Rank rank,
const CheckerIF& checker)
: powerDownManager(powerDownManager), checker(checker)
{
Configuration &config = Configuration::getInstance();

View File

@@ -52,7 +52,7 @@ class RefreshManagerPer2Bank final : public RefreshManagerIF
{
public:
RefreshManagerPer2Bank(std::vector<BankMachine*>& bankMachinesOnRank,
PowerDownManagerIF& powerDownManager, Rank rank, CheckerIF& checker);
PowerDownManagerIF& powerDownManager, Rank rank, const CheckerIF& checker);
CommandTuple::Type getNextCommand() override;
sc_core::sc_time start() override;
@@ -66,7 +66,7 @@ private:
tlm::tlm_generic_payload *currentRefreshPayload;
sc_core::sc_time timeForNextTrigger = sc_core::sc_max_time();
sc_core::sc_time timeToSchedule = sc_core::sc_max_time();
CheckerIF& checker;
const CheckerIF& checker;
Command nextCommand = Command::NOP;
std::list<std::vector<BankMachine*>> remainingBankMachines;

View File

@@ -42,8 +42,8 @@
using namespace sc_core;
using namespace tlm;
RefreshManagerPerBank::RefreshManagerPerBank(std::vector<BankMachine *> &bankMachinesOnRank,
PowerDownManagerIF *powerDownManager, Rank rank, CheckerIF *checker)
RefreshManagerPerBank::RefreshManagerPerBank(std::vector<BankMachine*>& bankMachinesOnRank,
PowerDownManagerIF& powerDownManager, Rank rank, const CheckerIF& checker)
: powerDownManager(powerDownManager), checker(checker)
{
Configuration &config = Configuration::getInstance();
@@ -75,7 +75,7 @@ sc_time RefreshManagerPerBank::start()
if (sc_time_stamp() >= timeForNextTrigger)
{
powerDownManager->triggerInterruption();
powerDownManager.triggerInterruption();
if (sleeping)
return timeToSchedule;
@@ -127,7 +127,7 @@ sc_time RefreshManagerPerBank::start()
}
}
timeToSchedule = checker->timeToSatisfyConstraints(nextCommand, refreshPayloads[*currentIterator]);
timeToSchedule = checker.timeToSatisfyConstraints(nextCommand, refreshPayloads[*currentIterator]);
return timeToSchedule;
}
}
@@ -158,7 +158,7 @@ sc_time RefreshManagerPerBank::start()
else
nextCommand = Command::REFPB;
timeToSchedule = checker->timeToSatisfyConstraints(nextCommand, refreshPayloads[*currentIterator]);
timeToSchedule = checker.timeToSatisfyConstraints(nextCommand, refreshPayloads[*currentIterator]);
return timeToSchedule;
}
}

View File

@@ -51,7 +51,8 @@ class PowerDownManagerIF;
class RefreshManagerPerBank final : public RefreshManagerIF
{
public:
RefreshManagerPerBank(std::vector<BankMachine *> &, PowerDownManagerIF *, Rank, CheckerIF *);
RefreshManagerPerBank(std::vector<BankMachine *>& bankMachinesOnRank, PowerDownManagerIF& powerDownManager,
Rank rank, const CheckerIF& checker);
CommandTuple::Type getNextCommand() override;
sc_core::sc_time start() override;
@@ -60,11 +61,11 @@ public:
private:
enum class State {Regular, Pulledin} state = State::Regular;
const MemSpec *memSpec;
PowerDownManagerIF *powerDownManager;
PowerDownManagerIF& powerDownManager;
std::unordered_map<BankMachine*, tlm::tlm_generic_payload> refreshPayloads;
sc_core::sc_time timeForNextTrigger = sc_core::sc_max_time();
sc_core::sc_time timeToSchedule = sc_core::sc_max_time();
CheckerIF *checker;
const CheckerIF& checker;
Command nextCommand = Command::NOP;
std::list<BankMachine *> remainingBankMachines;

View File

@@ -43,7 +43,7 @@ using namespace sc_core;
using namespace tlm;
RefreshManagerSameBank::RefreshManagerSameBank(std::vector<BankMachine*>& bankMachinesOnRank,
PowerDownManagerIF& powerDownManager, Rank rank, CheckerIF& checker)
PowerDownManagerIF& powerDownManager, Rank rank, const CheckerIF& checker)
: powerDownManager(powerDownManager), checker(checker)
{
Configuration &config = Configuration::getInstance();

View File

@@ -51,7 +51,7 @@ class RefreshManagerSameBank final : public RefreshManagerIF
{
public:
RefreshManagerSameBank(std::vector<BankMachine *>& bankMachinesOnRank, PowerDownManagerIF& powerDownManager,
Rank rank, CheckerIF& checker);
Rank rank, const CheckerIF& checker);
CommandTuple::Type getNextCommand() override;
sc_core::sc_time start() override;
@@ -64,7 +64,7 @@ private:
std::vector<tlm::tlm_generic_payload> refreshPayloads;
sc_core::sc_time timeForNextTrigger = sc_core::sc_max_time();
sc_core::sc_time timeToSchedule = sc_core::sc_max_time();
CheckerIF& checker;
const CheckerIF& checker;
Command nextCommand = Command::NOP;
std::list<std::vector<BankMachine *>> remainingBankMachines;