V3Tristate: handle AstVarXRef as AstVarRef (#3466)

This commit is contained in:
Nick Brereton 2026-02-23 09:43:04 -05:00
parent 7c923bb330
commit 6ba6447483
2 changed files with 33 additions and 6 deletions

View File

@ -411,9 +411,9 @@ class TristateVisitor final : public TristateBaseVisitor {
// TYPES
struct RefStrength final {
AstVarRef* m_varrefp;
AstNodeVarRef* m_varrefp;
VStrength m_strength;
RefStrength(AstVarRef* varrefp, VStrength strength)
RefStrength(AstNodeVarRef* varrefp, VStrength strength)
: m_varrefp{varrefp}
, m_strength{strength} {}
};
@ -471,7 +471,7 @@ class TristateVisitor final : public TristateBaseVisitor {
}
AstNodeExpr* getEnp(AstNode* nodep) {
if (nodep->user1p()) {
if (AstVarRef* const refp = VN_CAST(nodep, VarRef)) {
if (AstNodeVarRef* const refp = VN_CAST(nodep, NodeVarRef)) {
if (refp->varp()->isIO()) {
// When reading a tri-state port, we can always use the value
// because such port will have resolution logic in upper module.
@ -561,7 +561,7 @@ class TristateVisitor final : public TristateBaseVisitor {
return newp;
}
void mapInsertLhsVarRef(AstVarRef* nodep) {
void mapInsertLhsVarRef(AstNodeVarRef* nodep) {
UINFO(9, " mapInsertLhsVarRef " << nodep);
AstVar* const key = nodep->varp();
const auto pair = m_lhsmap.emplace(key, nullptr);
@ -663,7 +663,7 @@ class TristateVisitor final : public TristateBaseVisitor {
AstNodeExpr* enp = nullptr;
for (auto it = beginStrength; it != endStrength; it++) {
AstVarRef* refp = it->m_varrefp;
AstNodeVarRef* refp = it->m_varrefp;
// create the new lhs driver for this var
AstVar* const newLhsp = new AstVar{varp->fileline(), VVarType::MODULETEMP,
@ -1752,7 +1752,7 @@ class TristateVisitor final : public TristateBaseVisitor {
}
}
void visit(AstVarRef* nodep) override {
void handleNodeVarRef(AstNodeVarRef* nodep) {
UINFO(9, dbgState() << nodep);
if (m_graphing) {
if (nodep->access().isWriteOrRW()) associateLogic(nodep, nodep->varp());
@ -1794,6 +1794,9 @@ class TristateVisitor final : public TristateBaseVisitor {
}
}
void visit(AstVarRef* nodep) override { handleNodeVarRef(nodep); }
void visit(AstVarXRef* nodep) override { handleNodeVarRef(nodep); }
void visit(AstVar* nodep) override {
iterateChildren(nodep);
UINFO(9, dbgState() << nodep);

View File

@ -24,6 +24,25 @@ module counter_ansi
end
endmodule : counter_ansi
// Issue 3466: inout inside interface modport
interface inout_if;
wire we;
wire d;
modport ctrl (output we, inout d);
modport prph (input we, inout d);
endinterface
module inout_mod(inout_if.prph io_if);
assign io_if.d = io_if.we ? 1'b1 : 1'bz;
endmodule
module inout_mod_wrap(input we, inout d);
inout_if io_if();
assign io_if.we = we;
assign io_if.d = d;
inout_mod prph (.*);
endmodule
module t (/*AUTOARG*/
// Inputs
clk
@ -52,11 +71,16 @@ module t (/*AUTOARG*/
.c_data(c4_data),
.i_value(4'h4));
logic inout_we;
tri inout_d;
inout_mod_wrap inout_u (.we(inout_we), .d(inout_d));
initial begin
c1_data.value = 4'h4;
c2_data.value = 4'h5;
c3_data.value = 4'h6;
c4_data.value = 4'h7;
inout_we = 1'b0;
end
always @ (posedge clk) begin