diff --git a/src/Algorithm.cpp b/src/Algorithm.cpp index 5973158f..1302d5b6 100644 --- a/src/Algorithm.cpp +++ b/src/Algorithm.cpp @@ -167,11 +167,12 @@ void Algorithm::checkBlueprintsBindings(const t_instantiation_context &ictx) con // lint bindings { ExpressionLinter linter(this, ictx); + // produce instantiation context + t_instantiation_context local_ictx; + makeBlueprintInstantiationContext(bp.second, ictx, local_ictx); linter.lintBinding( sprint("instance '%s', binding '%s' to '%s'", bp.first.c_str(), br.c_str(), b.left.c_str()), - b.dir, b.srcloc, - get<0>(bp.second.blueprint->determineVIOTypeWidthAndTableSize(translateVIOName(b.left, nullptr), b.srcloc)), - get<0>(determineVIOTypeWidthAndTableSize(translateVIOName(br, nullptr), b.srcloc)) + bp.second.blueprint, local_ictx, b ); } } @@ -6143,7 +6144,7 @@ void Algorithm::determineBlueprintBoundVIO(const t_instantiation_context& ictx) // produce instantiation context t_instantiation_context local_ictx; makeBlueprintInstantiationContext(ib.second, ictx, local_ictx); - // verify width (mismatch not possible with inouts) + // verify width (mismatch not allowed with inouts) string iow = ib.second.blueprint->resolveWidthOf(b.left, local_ictx, b.srcloc); int iiow = -1; try { diff --git a/src/ExpressionLinter.cpp b/src/ExpressionLinter.cpp index c7830e09..f0e5b9c1 100644 --- a/src/ExpressionLinter.cpp +++ b/src/ExpressionLinter.cpp @@ -214,21 +214,45 @@ void ExpressionLinter::lintReadback( void ExpressionLinter::lintBinding( std::string msg, - Algorithm::e_BindingDir dir, - const t_source_loc& srcloc, - const t_type_nfo &left, - const t_type_nfo &right -) const + AutoPtr bp, + const Algorithm::t_instantiation_context& local_ictx, + const Algorithm::t_binding_nfo& bnfo + ) const { - // check - if (left.base_type == Parameterized || right.base_type == Parameterized) { - return; // skip if parameterized + // check width + std::string slw = bp->resolveWidthOf(bnfo.left, local_ictx, bnfo.srcloc); + int lw = -1; + e_Type rtype = Parameterized; + try { + lw = stoi(slw); + } catch (...) { + warn(Standard, bnfo.srcloc, "%s, cannot check binding bit-width", msg.c_str()); + return; + } + int rw = -1; + if (!std::holds_alternative(bnfo.right)) { + auto access = std::get(bnfo.right); + auto rnfo = m_Host->determineAccessTypeAndWidth(nullptr, access, nullptr); + rw = rnfo.width; + rtype = rnfo.base_type; + } else { + /// TODO: rtype in this case? + std::string srw = m_Host->resolveWidthOf(std::get(bnfo.right), m_Ictx, bnfo.srcloc); + try { + rw = stoi(srw); + } catch (...) { + warn(Standard, bnfo.srcloc, "%s, cannot check binding bit-width", msg.c_str()); + return; + } } - if (left.base_type != right.base_type) { - warn(Standard, srcloc, "%s, bindings have inconsistent signedness", msg.c_str()); + if (rw != lw) { + warn(Standard, bnfo.srcloc, "%s, bindings have inconsistent bit-widths", msg.c_str()); } - if (left.width != right.width) { - warn(Standard, srcloc, "%s, bindings have inconsistent bit-widths", msg.c_str()); + // check signdness + auto lnfo = bp->determineVIOTypeWidthAndTableSize(bnfo.left, bnfo.srcloc); + e_Type ltype = std::get<0>(lnfo).base_type; + if (ltype != rtype && rtype != Parameterized && ltype != Parameterized) { + warn(Standard, bnfo.srcloc, "%s, bindings have inconsistent signedness", msg.c_str()); } } diff --git a/src/ExpressionLinter.h b/src/ExpressionLinter.h index 9c0278a5..7cafd570 100644 --- a/src/ExpressionLinter.h +++ b/src/ExpressionLinter.h @@ -137,10 +137,9 @@ namespace Silice /// \brief Lint a binding void lintBinding( std::string msg, - Algorithm::e_BindingDir dir, - const Utils::t_source_loc& srcloc, - const t_type_nfo &left, - const t_type_nfo &right + AutoPtr bp, + const Algorithm::t_instantiation_context& local_ictx, + const Algorithm::t_binding_nfo& bnfo ) const; /// \brief Returns the type nfo of an expression