Merge branch 'push-kqrypxmkxkvw' into 'develop'
refactor(am): improve checking and reporting See merge request ems/astdm/modeling.dram/dram.sys.5!157
This commit is contained in:
@@ -198,34 +198,55 @@ void AddressDecoder::checkMemorySize(const MemSpec& memSpec) {
|
||||
(memSpec.getSimMemSizeInBytes() < upperBoundAddress + 1 && !np2Flag);
|
||||
|
||||
if (isMemorySizeMismatch) {
|
||||
SC_REPORT_FATAL("AddressDecoder", "The mapped bits do not match the memory size");
|
||||
std::ostringstream o;
|
||||
o << "The mapped bits do not match the memory size field (MemSpec size: "
|
||||
<< memSpec.getSimMemSizeInBytes() << ", mapping=" << upperBoundAddress + 1 << ")";
|
||||
SC_REPORT_FATAL("AddressDecoder", o.str().c_str());
|
||||
}
|
||||
}
|
||||
|
||||
void AddressDecoder::checkMemSpecCompatibility(const MemSpec& memSpec) {
|
||||
unsigned channels = std::lround(std::pow(2, channelBits.length));
|
||||
unsigned ranks = std::lround(std::pow(2, rankBits.length));
|
||||
unsigned rows = std::lround(std::pow(2, rowBits.length));
|
||||
unsigned columns = std::lround(std::pow(2, columnBits.length));
|
||||
unsigned pseudochannels = std::lround(std::pow(2, pseudochannelBits.length));
|
||||
const unsigned channels = std::lround(std::pow(2, channelBits.length));
|
||||
const unsigned ranks = std::lround(std::pow(2, rankBits.length));
|
||||
const unsigned rows = std::lround(std::pow(2, rowBits.length));
|
||||
const unsigned columns = std::lround(std::pow(2, columnBits.length));
|
||||
const unsigned pseudochannels = std::lround(std::pow(2, pseudochannelBits.length));
|
||||
|
||||
unsigned absoluteBankGroups = bankgroupsPerRank * (ranks * pseudochannels);
|
||||
unsigned absoluteBanks = banksPerGroup * absoluteBankGroups;
|
||||
const unsigned absoluteBankGroups = bankgroupsPerRank * (ranks * pseudochannels);
|
||||
const unsigned absoluteBanks = banksPerGroup * absoluteBankGroups;
|
||||
const unsigned effectiveRanksPerChannel = static_cast<uint64_t>(ranks) * static_cast<uint64_t>(pseudochannels);
|
||||
|
||||
// Depending on the NP2 flag we must adapt the strictness of this check
|
||||
if (np2Flag) {
|
||||
if (memSpec.numberOfChannels > channels || memSpec.ranksPerChannel > (ranks * pseudochannels) ||
|
||||
memSpec.bankGroupsPerChannel > absoluteBankGroups ||
|
||||
memSpec.banksPerChannel > absoluteBanks || memSpec.rowsPerBank > rows ||
|
||||
memSpec.columnsPerRow > columns)
|
||||
SC_REPORT_FATAL("AddressDecoder", "Memspec and address mapping do not match");
|
||||
}
|
||||
else {
|
||||
if (memSpec.numberOfChannels != channels || memSpec.ranksPerChannel != (ranks * pseudochannels) ||
|
||||
memSpec.bankGroupsPerChannel != absoluteBankGroups ||
|
||||
memSpec.banksPerChannel != absoluteBanks || memSpec.rowsPerBank != rows ||
|
||||
memSpec.columnsPerRow != columns)
|
||||
SC_REPORT_FATAL("AddressDecoder", "Memspec and address mapping do not match");
|
||||
// Depending on the NP2 flag we might need to adapt the strictness of the checks
|
||||
auto cmp = np2Flag
|
||||
? std::function<bool(uint64_t,uint64_t)>([](uint64_t a, uint64_t b){ return a <= b; })
|
||||
: std::function<bool(uint64_t,uint64_t)>([](uint64_t a, uint64_t b){ return a == b; });
|
||||
|
||||
// Check all and collect the errors
|
||||
std::vector<std::string> errors;
|
||||
const char* rel = np2Flag ? "<=" : "==";
|
||||
auto check = [&](const char* field, uint64_t mem, uint64_t map) {
|
||||
if (!cmp(mem, map)) {
|
||||
std::ostringstream o;
|
||||
o << field << ": memSpec=" << mem << ", mapping=" << map
|
||||
<< " (required: memSpec " << rel << " mapping)";
|
||||
errors.push_back(o.str());
|
||||
}
|
||||
};
|
||||
|
||||
check("numberOfChannels", memSpec.numberOfChannels, channels);
|
||||
check("ranksPerChannel", memSpec.ranksPerChannel, effectiveRanksPerChannel);
|
||||
check("bankGroupsPerChannel", memSpec.bankGroupsPerChannel, absoluteBankGroups);
|
||||
check("banksPerChannel", memSpec.banksPerChannel, absoluteBanks);
|
||||
check("rowsPerBank", memSpec.rowsPerBank, rows);
|
||||
check("columnsPerRow", memSpec.columnsPerRow, columns);
|
||||
|
||||
// Handle collected errors
|
||||
if (!errors.empty()) {
|
||||
std::ostringstream all;
|
||||
all << "Unexpected deviations between MemSpec and Address Mapping:\n";
|
||||
for (auto& e : errors) all << " - " << e << '\n';
|
||||
std::string msg = all.str();
|
||||
SC_REPORT_FATAL("AddressDecoder", msg.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user