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

View File

@ -24,6 +24,25 @@ module counter_ansi
end end
endmodule : counter_ansi 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*/ module t (/*AUTOARG*/
// Inputs // Inputs
clk clk
@ -52,11 +71,16 @@ module t (/*AUTOARG*/
.c_data(c4_data), .c_data(c4_data),
.i_value(4'h4)); .i_value(4'h4));
logic inout_we;
tri inout_d;
inout_mod_wrap inout_u (.we(inout_we), .d(inout_d));
initial begin initial begin
c1_data.value = 4'h4; c1_data.value = 4'h4;
c2_data.value = 4'h5; c2_data.value = 4'h5;
c3_data.value = 4'h6; c3_data.value = 4'h6;
c4_data.value = 4'h7; c4_data.value = 4'h7;
inout_we = 1'b0;
end end
always @ (posedge clk) begin always @ (posedge clk) begin