Merge pull request #160 from Silimate/reg-rename

[CUS-514] Reg rename fixes
This commit is contained in:
Akash Levy 2026-04-30 15:00:27 -07:00 committed by GitHub
commit cd16928385
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 32 additions and 21 deletions

View File

@ -188,9 +188,17 @@ struct SplitcellsWorker
std::string base_name = cell->name.str();
IdString slice_name;
if (blast) {
// Strip existing brackets from cell name
size_t bracket_pos = base_name.find('[');
// Strip existing '[' or '.' from cell name
size_t bracket_pos = base_name.find_first_of("[.");
bool strip_reg = false;
if (bracket_pos != std::string::npos) {
// Check if we will strip off _reg suffix from base name
size_t reg_pos = base_name.rfind("_reg");
if (reg_pos != std::string::npos && reg_pos > bracket_pos) {
base_name = base_name.substr(0, reg_pos);
strip_reg = true;
}
base_name = base_name.substr(0, bracket_pos);
}
@ -198,19 +206,19 @@ struct SplitcellsWorker
std::string wire_indices;
if (slice_lsb < GetSize(raw_q) && raw_q[slice_lsb].is_wire()) {
// Extract wire name (ex: \Memory[0])
// Extract wire name (ex: \Memory[0] or \Memory.attr)
Wire *w = raw_q[slice_lsb].wire;
std::string wire_name = w->name.str();
// Extract bit offset from the wire (ex: 0)
int bit_offset = user_index(slice_lsb);
// Concatenate wire index (ex: \Memory[0] -> [0]) to the bit offset (ex: [0][bit])
size_t bracket_pos = wire_name.find('[');
// Concatenate struct attribute or wire index (ex: \Memory[0] -> [0]) to the bit offset
size_t bracket_pos = wire_name.find_first_of("[.");
if (bracket_pos != std::string::npos) {
wire_indices = wire_name.substr(bracket_pos) + stringf(
wire_indices = wire_name.substr(bracket_pos) + (strip_reg ? "_reg" : "") + stringf(
"%c%d%c", format[0], bit_offset, format[1]);
} else { // no brackets, so no concatenation using wire, use slice_lsb + name_lsb offset instead
} else { // no '[' or '.', so no concatenation using wire, use slice_lsb + name_lsb offset instead
wire_indices = stringf(
"%c%d%c", format[0], slice_lsb + wire_offset, format[1]);
}

View File

@ -64,7 +64,7 @@ struct RegRenameInstance {
// Processes registers in a given module hierarchy
// and renames to allow for correct register annotation
void process_registers(dict<std::pair<std::string, std::string>, RegInfo> &vcd_reg_widths)
void process_registers(dict<std::string, RegInfo> &vcd_reg_widths)
{
if (debug)
log("Processing registers in scope: %s (module: %s)\n",
@ -103,16 +103,17 @@ struct RegRenameInstance {
cellName.erase(reg_pos, 4);
// Index comes from the right-most brackets
std::string wireName;
std::string wireName = cellName;
int bitIndex = 0;
size_t last_open = cellName.rfind('[');
size_t last_close = cellName.rfind(']');
if (last_open != std::string::npos && last_close != std::string::npos && last_close > last_open) {
// Validate bracket content is just a single bit slice
std::string inner = cellName.substr(last_open + 1, last_close - last_open - 1);
if (!inner.empty() && inner.find_first_not_of("0123456789") == std::string::npos) {
wireName = cellName.substr(0, last_open);
bitIndex = std::stoi(cellName.substr(last_open + 1, last_close - last_open - 1));
} else {
wireName = cellName;
bitIndex = 0;
bitIndex = std::stoi(inner);
}
}
// Process Q output connection for the cell
@ -124,7 +125,7 @@ struct RegRenameInstance {
// Lookup wire information from VCD
std::string regName = RTLIL::unescape_id(wireName);
RegInfo regInfo = vcd_reg_widths[{vcd_scope, regName}];
RegInfo regInfo = vcd_reg_widths[vcd_scope + "." + regName];
int wireWidth = regInfo.width;
int wireOffset = regInfo.offset;
@ -218,7 +219,7 @@ struct RegRenameInstance {
module->remove(wireRemoveCache);
}
void process_all(dict<std::pair<std::string, std::string>, RegInfo> &vcd_reg_widths)
void process_all(dict<std::string, RegInfo> &vcd_reg_widths)
{
process_registers(vcd_reg_widths);
for (auto &it : children)
@ -280,7 +281,7 @@ struct RegRenamePass : public Pass {
log_error("No top module found!\n");
// Extract pre-optimization signal widths from VCD file
dict<std::pair<std::string, std::string>, RegInfo> vcd_reg_widths;
dict<std::string, RegInfo> vcd_reg_widths;
if (!vcd_filename.empty()) {
log("Reading VCD file: %s\n", vcd_filename.c_str());
try {
@ -301,10 +302,12 @@ struct RegRenamePass : public Pass {
std::string signal_bits = "";
// Use the bracket notation to extract the bit range and construct true reg name.
size_t bit_pos = signal_name.rfind('[');
if (bit_pos != std::string::npos) {
signal_bits = signal_name.substr(bit_pos);
signal_name.erase(bit_pos);
if (!signal_name.empty() && signal_name.back() == ']') {
size_t open = signal_name.rfind('[');
if (open != std::string::npos) {
signal_bits = signal_name.substr(open);
signal_name.erase(open);
}
}
// Extract the LSB and MSB indices if present.
@ -323,7 +326,7 @@ struct RegRenamePass : public Pass {
// Map the register's vcd scope and name to
// its original width and offset for later lookup.
signal_name = RTLIL::unescape_id(signal_name);
vcd_reg_widths[{vcd_scope, signal_name}] = {width, offset};
vcd_reg_widths[vcd_scope + "." + signal_name] = {width, offset};
if (debug)
log("Found signal '%s' in scope '%s' with range [%d:%d] (width %d)\n",
signal_name.c_str(), vcd_scope.c_str(),