3
0
Fork 0
mirror of https://github.com/YosysHQ/yosys synced 2025-06-22 13:53:40 +00:00

neater errors, lost in the sauce of source

This commit is contained in:
Emil J. Tywoniak 2025-06-18 18:05:48 +02:00
parent 242853f1f2
commit 6ac9f79de6
13 changed files with 196 additions and 245 deletions

View file

@ -38,8 +38,7 @@ using namespace AST_INTERNAL;
// instantiate global variables (public API)
namespace AST {
std::string current_filename;
bool sv_mode;
bool sv_mode_but_global_and_used_for_literally_one_condition;
unsigned long long astnodes = 0;
unsigned long long astnode_count() { return astnodes; }
}
@ -200,7 +199,7 @@ bool AstNode::get_bool_attribute(RTLIL::IdString id)
// create new node (AstNode constructor)
// (the optional child arguments make it easier to create AST trees)
AstNode::AstNode(AstNodeType type, std::unique_ptr<AstNode> child1, std::unique_ptr<AstNode> child2, std::unique_ptr<AstNode> child3, std::unique_ptr<AstNode> child4)
AstNode::AstNode(AstSrcLocType loc, AstNodeType type, std::unique_ptr<AstNode> child1, std::unique_ptr<AstNode> child2, std::unique_ptr<AstNode> child3, std::unique_ptr<AstNode> child4)
{
static unsigned int hashidx_count = 123456789;
hashidx_count = mkhash_xorshift(hashidx_count);
@ -208,7 +207,7 @@ AstNode::AstNode(AstNodeType type, std::unique_ptr<AstNode> child1, std::unique_
astnodes++;
this->type = type;
filename = current_filename;
loc = loc;
is_input = false;
is_output = false;
is_reg = false;
@ -252,7 +251,7 @@ AstNode::AstNode(AstNodeType type, std::unique_ptr<AstNode> child1, std::unique_
// create a (deep recursive) copy of a node
std::unique_ptr<AstNode> AstNode::clone() const
{
auto that = std::make_unique<AstNode>(this->type);
auto that = std::make_unique<AstNode>(this->location, this->type);
cloneInto(*that.get());
return that;
}
@ -287,7 +286,6 @@ void AstNode::cloneInto(AstNode &other) const
other.id2ast = id2ast;
other.basic_prep = basic_prep;
other.lookahead = lookahead;
other.filename = filename;
other.location = location;
other.in_lvalue = in_lvalue;
other.in_param = in_param;
@ -842,9 +840,9 @@ bool AstNode::contains(const AstNode *other) const
}
// create an AST node for a constant (using a 32 bit int as value)
std::unique_ptr<AstNode> AstNode::mkconst_int(uint32_t v, bool is_signed, int width)
std::unique_ptr<AstNode> AstNode::mkconst_int(AstSrcLocType loc, uint32_t v, bool is_signed, int width)
{
auto node = std::make_unique<AstNode>(AST_CONSTANT);
auto node = std::make_unique<AstNode>(loc, AST_CONSTANT);
node->integer = v;
node->is_signed = is_signed;
for (int i = 0; i < width; i++) {
@ -858,9 +856,9 @@ std::unique_ptr<AstNode> AstNode::mkconst_int(uint32_t v, bool is_signed, int wi
}
// create an AST node for a constant (using a bit vector as value)
std::unique_ptr<AstNode> AstNode::mkconst_bits(const std::vector<RTLIL::State> &v, bool is_signed, bool is_unsized)
std::unique_ptr<AstNode> AstNode::mkconst_bits(AstSrcLocType loc, const std::vector<RTLIL::State> &v, bool is_signed, bool is_unsized)
{
auto node = std::make_unique<AstNode>(AST_CONSTANT);
auto node = std::make_unique<AstNode>(loc, AST_CONSTANT);
node->is_signed = is_signed;
node->bits = v;
for (size_t i = 0; i < 32; i++) {
@ -876,15 +874,15 @@ std::unique_ptr<AstNode> AstNode::mkconst_bits(const std::vector<RTLIL::State> &
return node;
}
std::unique_ptr<AstNode> AstNode::mkconst_bits(const std::vector<RTLIL::State> &v, bool is_signed)
std::unique_ptr<AstNode> AstNode::mkconst_bits(AstSrcLocType loc, const std::vector<RTLIL::State> &v, bool is_signed)
{
return mkconst_bits(v, is_signed, false);
return mkconst_bits(loc, v, is_signed, false);
}
// create an AST node for a constant (using a string in bit vector form as value)
std::unique_ptr<AstNode> AstNode::mkconst_str(const std::vector<RTLIL::State> &v)
std::unique_ptr<AstNode> AstNode::mkconst_str(AstSrcLocType loc, const std::vector<RTLIL::State> &v)
{
auto node = mkconst_str(RTLIL::Const(v).decode_string());
auto node = mkconst_str(loc, RTLIL::Const(v).decode_string());
while (GetSize(node->bits) < GetSize(v))
node->bits.push_back(RTLIL::State::S0);
log_assert(node->bits == v);
@ -892,14 +890,14 @@ std::unique_ptr<AstNode> AstNode::mkconst_str(const std::vector<RTLIL::State> &v
}
// create an AST node for a constant (using a string as value)
std::unique_ptr<AstNode> AstNode::mkconst_str(const std::string &str)
std::unique_ptr<AstNode> AstNode::mkconst_str(AstSrcLocType loc, const std::string &str)
{
std::unique_ptr<AstNode> node;
// LRM 1364-2005 5.2.3.3 The empty string literal ("") shall be considered
// equivalent to the ASCII NUL ("\0")
if (str.empty()) {
node = AstNode::mkconst_int(0, false, 8);
node = AstNode::mkconst_int(loc, 0, false, 8);
} else {
std::vector<RTLIL::State> data;
data.reserve(str.size() * 8);
@ -910,7 +908,7 @@ std::unique_ptr<AstNode> AstNode::mkconst_str(const std::string &str)
ch = ch >> 1;
}
}
node = AstNode::mkconst_bits(data, false);
node = AstNode::mkconst_bits(loc, data, false);
}
node->is_string = true;
@ -919,19 +917,19 @@ std::unique_ptr<AstNode> AstNode::mkconst_str(const std::string &str)
}
// create a temporary register
std::unique_ptr<AstNode> AstNode::mktemp_logic(const std::string &name, AstNode *mod, bool nosync, int range_left, int range_right, bool is_signed)
std::unique_ptr<AstNode> AstNode::mktemp_logic(AstSrcLocType loc, const std::string &name, AstNode *mod, bool nosync, int range_left, int range_right, bool is_signed)
{
auto wire_owned = std::make_unique<AstNode>(AST_WIRE, std::make_unique<AstNode>(AST_RANGE, mkconst_int(range_left, true), mkconst_int(range_right, true)));
auto wire_owned = std::make_unique<AstNode>(loc, AST_WIRE, std::make_unique<AstNode>(loc, AST_RANGE, mkconst_int(loc, range_left, true), mkconst_int(loc, range_right, true)));
auto* wire = wire_owned.get();
wire->str = stringf("%s%s:%d$%d", name.c_str(), RTLIL::encode_filename(filename).c_str(), location.first_line, autoidx++);
wire->str = stringf("%s%s:%d$%d", name.c_str(), RTLIL::encode_filename(location.filename).c_str(), location.first_line, autoidx++);
if (nosync)
wire->set_attribute(ID::nosync, AstNode::mkconst_int(1, false));
wire->set_attribute(ID::nosync, AstNode::mkconst_int(loc, 1, false));
wire->is_signed = is_signed;
wire->is_logic = true;
mod->children.push_back(std::move(wire_owned));
while (wire->simplify(true, 1, -1, false)) { }
auto ident = std::make_unique<AstNode>(AST_IDENTIFIER);
auto ident = std::make_unique<AstNode>(loc, AST_IDENTIFIER);
ident->str = wire->str;
ident->id2ast = wire;
@ -985,7 +983,7 @@ RTLIL::Const AstNode::asParaConst() const
{
if (type == AST_REALVALUE)
{
auto strnode = AstNode::mkconst_str(stringf("%f", realvalue));
auto strnode = AstNode::mkconst_str(location, stringf("%f", realvalue));
RTLIL::Const val = strnode->asAttrConst();
val.flags |= RTLIL::CONST_FLAG_REAL;
return val;
@ -1087,7 +1085,7 @@ RTLIL::Const AstNode::realAsConst(int width)
std::string AstNode::loc_string() const
{
return stringf("%s:%d.%d-%d.%d", filename.c_str(), location.first_line, location.first_column, location.last_line, location.last_column);
return stringf("%s:%d.%d-%d.%d", location.filename.c_str(), location.first_line, location.first_column, location.last_line, location.last_column);
}
void AST::set_src_attr(RTLIL::AttrObject *obj, const AstNode *ast)
@ -1445,7 +1443,7 @@ void AST::process(RTLIL::Design *design, AstNode *ast, bool nodisplay, bool dump
if (design->has(child->str)) {
RTLIL::Module *existing_mod = design->module(child->str);
if (!nooverwrite && !overwrite && !existing_mod->get_blackbox_attribute()) {
log_file_error(child->filename, child->location.first_line, "Re-definition of module `%s'!\n", child->str.c_str());
log_file_error(child->location.filename, child->location.first_line, "Re-definition of module `%s'!\n", child->str.c_str());
} else if (nooverwrite) {
log("Ignoring re-definition of module `%s' at %s.\n",
child->str.c_str(), child->loc_string().c_str());
@ -1924,7 +1922,7 @@ void AstNode::input_error(const char *format, ...) const
{
va_list ap;
va_start(ap, format);
logv_file_error(filename, location.first_line, format, ap);
logv_file_error(location.filename, location.first_line, format, ap);
}
YOSYS_NAMESPACE_END

View file

@ -163,10 +163,11 @@ namespace AST
};
struct AstSrcLocType {
std::string filename;
unsigned int first_line, last_line;
unsigned int first_column, last_column;
AstSrcLocType() : first_line(0), last_line(0), first_column(0), last_column(0) {}
AstSrcLocType(int _first_line, int _first_column, int _last_line, int _last_column) : first_line(_first_line), last_line(_last_line), first_column(_first_column), last_column(_last_column) {}
AstSrcLocType() : filename(""), first_line(0), last_line(0), first_column(0), last_column(0) {}
AstSrcLocType(std::string _filename, int _first_line, int _first_column, int _last_line, int _last_column) : filename(_filename), first_line(_first_line), last_line(_last_line), first_column(_first_column), last_column(_last_column) {}
};
// convert an node type to a string (e.g. for debug output)
@ -223,7 +224,6 @@ namespace AST
// this is the original sourcecode location that resulted in this AST node
// it is automatically set by the constructor using AST::current_filename and
// the AST::get_line_num() callback function.
std::string filename;
AstSrcLocType location;
// are we embedded in an lvalue, param?
@ -234,7 +234,7 @@ namespace AST
bool in_param_from_above;
// creating and deleting nodes
AstNode(AstNodeType type = AST_NONE, std::unique_ptr<AstNode> child1 = nullptr, std::unique_ptr<AstNode> child2 = nullptr, std::unique_ptr<AstNode> child3 = nullptr, std::unique_ptr<AstNode> child4 = nullptr);
AstNode(AstSrcLocType loc, AstNodeType type = AST_NONE, std::unique_ptr<AstNode> child1 = nullptr, std::unique_ptr<AstNode> child2 = nullptr, std::unique_ptr<AstNode> child3 = nullptr, std::unique_ptr<AstNode> child4 = nullptr);
std::unique_ptr<AstNode> clone() const;
void cloneInto(AstNode &other) const;
void delete_children();
@ -322,14 +322,14 @@ namespace AST
AstNode operator=(AstNode) = delete;
// helper functions for creating AST nodes for constants
static std::unique_ptr<AstNode> mkconst_int(uint32_t v, bool is_signed, int width = 32);
static std::unique_ptr<AstNode> mkconst_bits(const std::vector<RTLIL::State> &v, bool is_signed, bool is_unsized);
static std::unique_ptr<AstNode> mkconst_bits(const std::vector<RTLIL::State> &v, bool is_signed);
static std::unique_ptr<AstNode> mkconst_str(const std::vector<RTLIL::State> &v);
static std::unique_ptr<AstNode> mkconst_str(const std::string &str);
static std::unique_ptr<AstNode> mkconst_int(AstSrcLocType loc, uint32_t v, bool is_signed, int width = 32);
static std::unique_ptr<AstNode> mkconst_bits(AstSrcLocType loc, const std::vector<RTLIL::State> &v, bool is_signed, bool is_unsized);
static std::unique_ptr<AstNode> mkconst_bits(AstSrcLocType loc, const std::vector<RTLIL::State> &v, bool is_signed);
static std::unique_ptr<AstNode> mkconst_str(AstSrcLocType loc, const std::vector<RTLIL::State> &v);
static std::unique_ptr<AstNode> mkconst_str(AstSrcLocType loc, const std::string &str);
// helper function to create an AST node for a temporary register
std::unique_ptr<AstNode> mktemp_logic(const std::string &name, AstNode *mod, bool nosync, int range_left, int range_right, bool is_signed);
std::unique_ptr<AstNode> mktemp_logic(AstSrcLocType loc, const std::string &name, AstNode *mod, bool nosync, int range_left, int range_right, bool is_signed);
// helper function for creating sign-extended const objects
RTLIL::Const bitsAsConst(int width, bool is_signed);
@ -409,7 +409,7 @@ namespace AST
// to initialize the filename and linenum properties of new nodes
extern std::string current_filename;
// also set by the language frontend to control some AST processing
extern bool sv_mode;
extern bool sv_mode_but_global_and_used_for_literally_one_condition;
// for stats
unsigned long long astnode_count();
@ -419,7 +419,7 @@ namespace AST
void use_internal_line_num();
// call a DPI function
std::unique_ptr<AstNode> dpi_call(const std::string &rtype, const std::string &fname, const std::vector<std::string> &argtypes, const std::vector<std::unique_ptr<AstNode>> &args);
std::unique_ptr<AstNode> dpi_call(AstSrcLocType loc, const std::string &rtype, const std::string &fname, const std::vector<std::string> &argtypes, const std::vector<std::unique_ptr<AstNode>> &args);
// Helper functions related to handling SystemVerilog interfaces
std::pair<std::string,std::string> split_modport_from_type(std::string name_type);

View file

@ -64,7 +64,7 @@ static ffi_fptr resolve_fn (std::string symbol_name)
log_error("unable to resolve '%s'.\n", symbol_name.c_str());
}
std::unique_ptr<AST::AstNode> AST::dpi_call(const std::string &rtype, const std::string &fname, const std::vector<std::string> &argtypes, const std::vector<std::unique_ptr<AST::AstNode>> &args)
std::unique_ptr<AST::AstNode> AST::dpi_call(AstSrcLocType loc, const std::string &rtype, const std::string &fname, const std::vector<std::string> &argtypes, const std::vector<std::unique_ptr<AST::AstNode>> &args)
{
std::unique_ptr<AST::AstNode> newNode = nullptr;
union value { double f64; float f32; int32_t i32; void *ptr; };
@ -125,11 +125,11 @@ std::unique_ptr<AST::AstNode> AST::dpi_call(const std::string &rtype, const std:
ffi_call(&cif, resolve_fn(fname.c_str()), values[args.size()], values.data());
if (rtype == "real") {
newNode = std::make_unique<AstNode>(AST_REALVALUE);
newNode = std::make_unique<AstNode>(loc, AST_REALVALUE);
newNode->realvalue = value_store[args.size()].f64;
log(" return realvalue: %g\n", newNode->asReal(true));
} else if (rtype == "shortreal") {
newNode = std::make_unique<AstNode>(AST_REALVALUE);
newNode = std::make_unique<AstNode>(loc, AST_REALVALUE);
newNode->realvalue = value_store[args.size()].f32;
log(" return realvalue: %g\n", newNode->asReal(true));
} else if (rtype == "chandle") {
@ -137,10 +137,10 @@ std::unique_ptr<AST::AstNode> AST::dpi_call(const std::string &rtype, const std:
std::vector<RTLIL::State> bits(64);
for (int i = 0; i < 64; i++)
bits.at(i) = (rawval & (1ULL << i)) ? RTLIL::State::S1 : RTLIL::State::S0;
newNode = AstNode::mkconst_bits(bits, false);
newNode = AstNode::mkconst_bits(loc, bits, false);
log(" return chandle: %llx\n", (unsigned long long)newNode->asInt(false));
} else {
newNode = AstNode::mkconst_int(value_store[args.size()].i32, false);
newNode = AstNode::mkconst_int(loc, value_store[args.size()].i32, false);
log(" return integer: %lld\n", (long long)newNode->asInt(true));
}
@ -153,7 +153,7 @@ YOSYS_NAMESPACE_END
YOSYS_NAMESPACE_BEGIN
AST::AstNode *AST::dpi_call(const std::string&, const std::string &fname, const std::vector<std::string>&, const std::vector<AstNode*>&)
AST::AstNode *AST::dpi_call(AstSrcLocType loc, const std::string&, const std::string &fname, const std::vector<std::string>&, const std::vector<AstNode*>&)
{
log_error("Can't call DPI function `%s': this version of yosys is built without plugin support\n", fname.c_str());
}

View file

@ -45,7 +45,7 @@ using namespace AST_INTERNAL;
// helper function for creating RTLIL code for unary operations
static RTLIL::SigSpec uniop2rtlil(AstNode *that, IdString type, int result_width, const RTLIL::SigSpec &arg, bool gen_attributes = true)
{
IdString name = stringf("%s$%s:%d$%d", type.c_str(), RTLIL::encode_filename(that->filename).c_str(), that->location.first_line, autoidx++);
IdString name = stringf("%s$%s:%d$%d", type.c_str(), RTLIL::encode_filename(that->location.filename).c_str(), that->location.first_line, autoidx++);
RTLIL::Cell *cell = current_module->addCell(name, type);
set_src_attr(cell, that);
@ -77,7 +77,7 @@ static void widthExtend(AstNode *that, RTLIL::SigSpec &sig, int width, bool is_s
return;
}
IdString name = stringf("$extend$%s:%d$%d", RTLIL::encode_filename(that->filename).c_str(), that->location.first_line, autoidx++);
IdString name = stringf("$extend$%s:%d$%d", RTLIL::encode_filename(that->location.filename).c_str(), that->location.first_line, autoidx++);
RTLIL::Cell *cell = current_module->addCell(name, ID($pos));
set_src_attr(cell, that);
@ -104,7 +104,7 @@ static void widthExtend(AstNode *that, RTLIL::SigSpec &sig, int width, bool is_s
// helper function for creating RTLIL code for binary operations
static RTLIL::SigSpec binop2rtlil(AstNode *that, IdString type, int result_width, const RTLIL::SigSpec &left, const RTLIL::SigSpec &right)
{
IdString name = stringf("%s$%s:%d$%d", type.c_str(), RTLIL::encode_filename(that->filename).c_str(), that->location.first_line, autoidx++);
IdString name = stringf("%s$%s:%d$%d", type.c_str(), RTLIL::encode_filename(that->location.filename).c_str(), that->location.first_line, autoidx++);
RTLIL::Cell *cell = current_module->addCell(name, type);
set_src_attr(cell, that);
@ -138,7 +138,7 @@ static RTLIL::SigSpec mux2rtlil(AstNode *that, const RTLIL::SigSpec &cond, const
log_assert(cond.size() == 1);
std::stringstream sstr;
sstr << "$ternary$" << RTLIL::encode_filename(that->filename) << ":" << that->location.first_line << "$" << (autoidx++);
sstr << "$ternary$" << RTLIL::encode_filename(that->location.filename) << ":" << that->location.first_line << "$" << (autoidx++);
RTLIL::Cell *cell = current_module->addCell(sstr.str(), ID($mux));
set_src_attr(cell, that);
@ -347,7 +347,7 @@ struct AST_INTERNAL::ProcessGenerator
LookaheadRewriter la_rewriter(always.get());
// generate process and simple root case
proc = current_module->addProcess(stringf("$proc$%s:%d$%d", RTLIL::encode_filename(always->filename).c_str(), always->location.first_line, autoidx++));
proc = current_module->addProcess(stringf("$proc$%s:%d$%d", RTLIL::encode_filename(always->location.filename).c_str(), always->location.first_line, autoidx++));
set_src_attr(proc, always.get());
for (auto &attr : always->attributes) {
if (attr.second->type != AST_CONSTANT)
@ -723,7 +723,7 @@ struct AST_INTERNAL::ProcessGenerator
if (ast->str == "$display" || ast->str == "$displayb" || ast->str == "$displayh" || ast->str == "$displayo" ||
ast->str == "$write" || ast->str == "$writeb" || ast->str == "$writeh" || ast->str == "$writeo") {
std::stringstream sstr;
sstr << ast->str << "$" << ast->filename << ":" << ast->location.first_line << "$" << (autoidx++);
sstr << ast->str << "$" << ast->location.filename << ":" << ast->location.first_line << "$" << (autoidx++);
Wire *en = current_module->addWire(sstr.str() + "_EN", 1);
set_src_attr(en, ast);
@ -766,7 +766,7 @@ struct AST_INTERNAL::ProcessGenerator
node->detectSignWidth(width, is_signed, nullptr);
VerilogFmtArg arg = {};
arg.filename = node->filename;
arg.filename = node->location.filename;
arg.first_line = node->location.first_line;
if (node->type == AST_CONSTANT && node->is_string) {
arg.type = VerilogFmtArg::STRING;
@ -793,7 +793,7 @@ struct AST_INTERNAL::ProcessGenerator
fmt.append_literal("\n");
fmt.emit_rtlil(cell);
} else if (!ast->str.empty()) {
log_file_error(ast->filename, ast->location.first_line, "Found unsupported invocation of system task `%s'!\n", ast->str.c_str());
log_file_error(ast->location.filename, ast->location.first_line, "Found unsupported invocation of system task `%s'!\n", ast->str.c_str());
}
break;
@ -813,7 +813,7 @@ struct AST_INTERNAL::ProcessGenerator
IdString cellname;
if (ast->str.empty())
cellname = stringf("$%s$%s:%d$%d", flavor.c_str(), RTLIL::encode_filename(ast->filename).c_str(), ast->location.first_line, autoidx++);
cellname = stringf("$%s$%s:%d$%d", flavor.c_str(), RTLIL::encode_filename(ast->location.filename).c_str(), ast->location.first_line, autoidx++);
else
cellname = ast->str;
check_unique_id(current_module, cellname, ast, "procedural assertion");
@ -843,7 +843,7 @@ struct AST_INTERNAL::ProcessGenerator
set_src_attr(cell, ast);
for (auto &attr : ast->attributes) {
if (attr.second->type != AST_CONSTANT)
log_file_error(ast->filename, ast->location.first_line, "Attribute `%s' with non-constant value!\n", attr.first.c_str());
log_file_error(ast->location.filename, ast->location.first_line, "Attribute `%s' with non-constant value!\n", attr.first.c_str());
cell->attributes[attr.first] = attr.second->asAttrConst();
}
cell->setParam(ID::FLAVOR, flavor);
@ -1503,7 +1503,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
}
RTLIL::SigSpec sig = realAsConst(width_hint);
log_file_warning(filename, location.first_line, "converting real value %e to binary %s.\n", realvalue, log_signal(sig));
log_file_warning(location.filename, location.first_line, "converting real value %e to binary %s.\n", realvalue, log_signal(sig));
return sig;
}
@ -1535,7 +1535,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
if (dynamic_cast<RTLIL::Binding*>(current_module)) {
/* nothing to do here */
} else if (flag_autowire)
log_file_warning(filename, location.first_line, "Identifier `%s' is implicitly declared.\n", str.c_str());
log_file_warning(location.filename, location.first_line, "Identifier `%s' is implicitly declared.\n", str.c_str());
else
input_error("Identifier `%s' is implicitly declared and `default_nettype is set to none.\n", str.c_str());
}
@ -1640,10 +1640,10 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
chunk.offset = source_width - (chunk.offset + chunk.width);
if (chunk.offset > chunk_left || chunk.offset + chunk.width < chunk_right) {
if (chunk.width == 1)
log_file_warning(filename, location.first_line, "Range select out of bounds on signal `%s': Setting result bit to undef.\n",
log_file_warning(location.filename, location.first_line, "Range select out of bounds on signal `%s': Setting result bit to undef.\n",
str.c_str());
else
log_file_warning(filename, location.first_line, "Range select [%d:%d] out of bounds on signal `%s': Setting all %d result bits to undef.\n",
log_file_warning(location.filename, location.first_line, "Range select [%d:%d] out of bounds on signal `%s': Setting all %d result bits to undef.\n",
children[0]->range_left, children[0]->range_right, str.c_str(), chunk.width);
chunk = RTLIL::SigChunk(RTLIL::State::Sx, chunk.width);
} else {
@ -1657,10 +1657,10 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
chunk.offset += add_undef_bits_lsb;
}
if (add_undef_bits_lsb)
log_file_warning(filename, location.first_line, "Range [%d:%d] select out of bounds on signal `%s': Setting %d LSB bits to undef.\n",
log_file_warning(location.filename, location.first_line, "Range [%d:%d] select out of bounds on signal `%s': Setting %d LSB bits to undef.\n",
children[0]->range_left, children[0]->range_right, str.c_str(), add_undef_bits_lsb);
if (add_undef_bits_msb)
log_file_warning(filename, location.first_line, "Range [%d:%d] select out of bounds on signal `%s': Setting %d MSB bits to undef.\n",
log_file_warning(location.filename, location.first_line, "Range [%d:%d] select out of bounds on signal `%s': Setting %d MSB bits to undef.\n",
children[0]->range_left, children[0]->range_right, str.c_str(), add_undef_bits_msb);
}
}
@ -1934,7 +1934,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
case AST_MEMRD:
{
std::stringstream sstr;
sstr << "$memrd$" << str << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$memrd$" << str << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
RTLIL::Cell *cell = current_module->addCell(sstr.str(), ID($memrd));
set_src_attr(cell, this);
@ -1972,7 +1972,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
case AST_MEMINIT:
{
std::stringstream sstr;
sstr << "$meminit$" << str << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$meminit$" << str << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
SigSpec en_sig = children[2]->genRTLIL();
@ -2017,7 +2017,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
IdString cellname;
if (str.empty())
cellname = stringf("$%s$%s:%d$%d", flavor.c_str(), RTLIL::encode_filename(filename).c_str(), location.first_line, autoidx++);
cellname = stringf("$%s$%s:%d$%d", flavor.c_str(), RTLIL::encode_filename(location.filename).c_str(), location.first_line, autoidx++);
else
cellname = str;
check_unique_id(current_module, cellname, this, "procedural assertion");
@ -2060,7 +2060,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
new_left.append(left[i]);
new_right.append(right[i]);
}
log_file_warning(filename, location.first_line, "Ignoring assignment to constant bits:\n"
log_file_warning(location.filename, location.first_line, "Ignoring assignment to constant bits:\n"
" old assignment: %s = %s\n new assignment: %s = %s.\n",
log_signal(left), log_signal(right),
log_signal(new_left), log_signal(new_right));
@ -2095,7 +2095,7 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
IdString paraname = child->str.empty() ? stringf("$%d", ++para_counter) : child->str;
const AstNode *value = child->children[0].get();
if (value->type == AST_REALVALUE)
log_file_warning(filename, location.first_line, "Replacing floating point parameter %s.%s = %f with string.\n",
log_file_warning(location.filename, location.first_line, "Replacing floating point parameter %s.%s = %f with string.\n",
log_id(cell), log_id(paraname), value->realvalue);
else if (value->type != AST_CONSTANT)
input_error("Parameter %s.%s with non-constant value!\n",
@ -2192,14 +2192,14 @@ RTLIL::SigSpec AstNode::genRTLIL(int width_hint, bool sign_hint)
int sz = children.size();
if (str == "$info") {
if (sz > 0)
log_file_info(filename, location.first_line, "%s.\n", children[0]->str.c_str());
log_file_info(location.filename, location.first_line, "%s.\n", children[0]->str.c_str());
else
log_file_info(filename, location.first_line, "\n");
log_file_info(location.filename, location.first_line, "\n");
} else if (str == "$warning") {
if (sz > 0)
log_file_warning(filename, location.first_line, "%s.\n", children[0]->str.c_str());
log_file_warning(location.filename, location.first_line, "%s.\n", children[0]->str.c_str());
else
log_file_warning(filename, location.first_line, "\n");
log_file_warning(location.filename, location.first_line, "\n");
} else if (str == "$error") {
if (sz > 0)
input_error("%s.\n", children[0]->str.c_str());

View file

@ -155,7 +155,7 @@ Fmt AstNode::processFormat(int stage, bool sformat_like, int default_base, size_
while (node_arg->simplify(true, stage, -1, false)) { }
VerilogFmtArg arg = {};
arg.filename = filename;
arg.filename = location.filename;
arg.first_line = location.first_line;
if (node_arg->type == AST_CONSTANT && node_arg->is_string) {
arg.type = VerilogFmtArg::STRING;
@ -173,10 +173,10 @@ Fmt AstNode::processFormat(int stage, bool sformat_like, int default_base, size_
arg.sig = node_arg->bitsAsConst();
arg.signed_ = node_arg->is_signed;
} else if (may_fail) {
log_file_info(filename, location.first_line, "Skipping system task `%s' with non-constant argument at position %zu.\n", str.c_str(), index + 1);
log_file_info(location.filename, location.first_line, "Skipping system task `%s' with non-constant argument at position %zu.\n", str.c_str(), index + 1);
return Fmt();
} else {
log_file_error(filename, location.first_line, "Failed to evaluate system task `%s' with non-constant argument at position %zu.\n", str.c_str(), index + 1);
log_file_error(location.filename, location.first_line, "Failed to evaluate system task `%s' with non-constant argument at position %zu.\n", str.c_str(), index + 1);
}
args.push_back(arg);
}
@ -240,20 +240,20 @@ void AstNode::annotateTypedEnums(AstNode *template_node)
RTLIL::Const val = enum_item->children[0]->bitsAsConst(width, is_signed);
enum_item_str.append(val.as_string());
//set attribute for available val to enum item name mappings
set_attribute(enum_item_str.c_str(), mkconst_str(enum_item->str));
set_attribute(enum_item_str.c_str(), mkconst_str(location, enum_item->str));
}
}
}
static std::unique_ptr<AstNode> make_range(int left, int right, bool is_signed = false)
static std::unique_ptr<AstNode> make_range(AstSrcLocType loc, int left, int right, bool is_signed = false)
{
// generate a pre-validated range node for a fixed signal range.
auto range = std::make_unique<AstNode>(AST_RANGE);
auto range = std::make_unique<AstNode>(loc, AST_RANGE);
range->range_left = left;
range->range_right = right;
range->range_valid = true;
range->children.push_back(AstNode::mkconst_int(left, true));
range->children.push_back(AstNode::mkconst_int(right, true));
range->children.push_back(AstNode::mkconst_int(loc, left, true));
range->children.push_back(AstNode::mkconst_int(loc, right, true));
range->is_signed = is_signed;
return range;
}
@ -388,30 +388,32 @@ static int size_packed_struct(AstNode *snode, int base_offset)
return width;
}
static std::unique_ptr<AstNode> node_int(int ival)
static std::unique_ptr<AstNode> node_int(AstSrcLocType loc, int ival)
{
return AstNode::mkconst_int(ival, true);
return AstNode::mkconst_int(loc, ival, true);
}
static std::unique_ptr<AstNode> multiply_by_const(std::unique_ptr<AstNode> expr_node, int stride)
{
return std::make_unique<AstNode>(AST_MUL, std::move(expr_node), node_int(stride));
auto loc = expr_node->location;
return std::make_unique<AstNode>(loc, AST_MUL, std::move(expr_node), node_int(loc, stride));
}
static std::unique_ptr<AstNode> normalize_index(AstNode *expr, AstNode *decl_node, int dimension)
{
auto new_expr = expr->clone();
auto loc = expr->location;
int offset = decl_node->dimensions[dimension].range_right;
if (offset) {
new_expr = std::make_unique<AstNode>(AST_SUB, std::move(new_expr), node_int(offset));
new_expr = std::make_unique<AstNode>(loc, AST_SUB, std::move(new_expr), node_int(loc, offset));
}
// Packed dimensions are normally indexed by lsb, while unpacked dimensions are normally indexed by msb.
if ((dimension < decl_node->unpacked_dimensions) ^ decl_node->dimensions[dimension].range_swapped) {
// Swap the index if the dimension is declared the "wrong" way.
int left = decl_node->dimensions[dimension].range_width - 1;
new_expr = std::make_unique<AstNode>(AST_SUB, node_int(left), std::move(new_expr));
new_expr = std::make_unique<AstNode>(loc, AST_SUB, node_int(loc, left), std::move(new_expr));
}
return new_expr;
@ -433,7 +435,7 @@ static std::unique_ptr<AstNode> index_msb_offset(std::unique_ptr<AstNode> lsb_of
std::unique_ptr<AstNode> add_offset;
if (rnode->children.size() == 1) {
// Index, e.g. s.a[i]
add_offset = node_int(stride - 1);
add_offset = node_int(rnode->location, stride - 1);
}
else {
// rnode->children.size() == 2
@ -620,7 +622,7 @@ const RTLIL::Module* AstNode::lookup_cell_module()
auto reprocess_after = [this] (const std::string &modname) {
if (!attributes.count(ID::reprocess_after))
set_attribute(ID::reprocess_after, AstNode::mkconst_str(modname));
set_attribute(ID::reprocess_after, AstNode::mkconst_str(location, modname));
};
const AstNode *celltype = nullptr;
@ -929,7 +931,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
#if 0
log("-------------\n");
log("AST simplify[%d] depth %d at %s:%d on %s %p:\n", stage, recursion_counter, filename.c_str(), location.first_line, type2str(type).c_str(), this);
log("AST simplify[%d] depth %d at %s:%d on %s %p:\n", stage, recursion_counter, location.filename.c_str(), location.first_line, type2str(type).c_str(), this);
log("const_fold=%d, stage=%d, width_hint=%d, sign_hint=%d\n",
int(const_fold), int(stage), int(width_hint), int(sign_hint));
// dumpAst(nullptr, "> ");
@ -1020,7 +1022,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
for (auto &it : node->attributes)
if (it.first != ID::mem2reg)
reg->set_attribute(it.first, it.second->clone());
reg->filename = node->filename;
reg->location.filename = node->location.filename;
reg->location = node->location;
while (reg->simplify(true, 1, -1, false)) { }
children.push_back(std::move(reg));
@ -1049,7 +1051,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
// note that $display, $finish, and $stop are used for synthesis-time DRC so they're not in this list
if ((type == AST_FCALL || type == AST_TCALL) && (str == "$strobe" || str == "$monitor" || str == "$time" ||
str == "$dumpfile" || str == "$dumpvars" || str == "$dumpon" || str == "$dumpoff" || str == "$dumpall")) {
log_file_warning(filename, location.first_line, "Ignoring call to system %s %s.\n", type == AST_FCALL ? "function" : "task", str.c_str());
log_file_warning(location.filename, location.first_line, "Ignoring call to system %s %s.\n", type == AST_FCALL ? "function" : "task", str.c_str());
delete_children();
str = std::string();
}
@ -1059,7 +1061,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
str == "$write" || str == "$writeb" || str == "$writeh" || str == "$writeo"))
{
if (!current_always) {
log_file_warning(filename, location.first_line, "System task `%s' outside initial or always block is unsupported.\n", str.c_str());
log_file_warning(location.filename, location.first_line, "System task `%s' outside initial or always block is unsupported.\n", str.c_str());
delete_children();
str = std::string();
} else {
@ -1336,7 +1338,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
// create the indirection wire
std::stringstream sstr;
sstr << "$indirect$" << ref->name.c_str() << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$indirect$" << ref->name.c_str() << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
std::string tmp_str = sstr.str();
add_wire_for_ref(ref, tmp_str);
@ -2174,7 +2176,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
int width = std::abs(children[1]->range_left - children[1]->range_right) + 1;
if (children[0]->type == AST_REALVALUE) {
RTLIL::Const constvalue = children[0]->realAsConst(width);
log_file_warning(filename, location.first_line, "converting real value %e to binary %s.\n",
log_file_warning(location.filename, location.first_line, "converting real value %e to binary %s.\n",
children[0]->realvalue, log_signal(constvalue));
children[0] = mkconst_bits(constvalue.to_bits(), sign_hint);
fixup_hierarchy_flags();
@ -2316,7 +2318,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
std::swap(data_range_left, data_range_right);
std::stringstream sstr;
sstr << "$mem2bits$" << str << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$mem2bits$" << str << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
std::string wire_id = sstr.str();
auto wire_owned = std::make_unique<AstNode>(AST_WIRE, std::make_unique<AstNode>(AST_RANGE, mkconst_int(data_range_left, true), mkconst_int(data_range_right, true)));
@ -2536,7 +2538,7 @@ bool AstNode::simplify(bool const_fold, int stage, int width_hint, bool sign_hin
for (size_t i = 0; i < children.size(); i++)
if (children[i]->type == AST_WIRE || children[i]->type == AST_MEMORY || children[i]->type == AST_PARAMETER || children[i]->type == AST_LOCALPARAM || children[i]->type == AST_TYPEDEF)
{
log_assert(!sv_mode);
log_assert(!sv_mode_but_global_and_used_for_literally_one_condition);
children[i]->input_error("Local declaration in unnamed block is only supported in SystemVerilog mode!\n");
}
}
@ -3072,7 +3074,7 @@ skip_dynamic_range_lvalue_expansion:;
auto wire_tmp_owned = std::make_unique<AstNode>(AST_WIRE, std::make_unique<AstNode>(AST_RANGE, mkconst_int(width_hint-1, true), mkconst_int(0, true)));
auto wire_tmp = wire_tmp_owned.get();
wire_tmp->str = stringf("$splitcmplxassign$%s:%d$%d", RTLIL::encode_filename(filename).c_str(), location.first_line, autoidx++);
wire_tmp->str = stringf("$splitcmplxassign$%s:%d$%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line, autoidx++);
current_scope[wire_tmp->str] = wire_tmp;
current_ast_mod->children.push_back(std::move(wire_tmp_owned));
wire_tmp->set_attribute(ID::nosync, AstNode::mkconst_int(1, false));
@ -3114,7 +3116,7 @@ skip_dynamic_range_lvalue_expansion:;
input_error("Insufficient number of array indices for %s.\n", log_id(str));
std::stringstream sstr;
sstr << "$memwr$" << children[0]->str << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$memwr$" << children[0]->str << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
std::string id_addr = sstr.str() + "_ADDR", id_data = sstr.str() + "_DATA", id_en = sstr.str() + "_EN";
int mem_width, mem_size, addr_bits;
@ -3385,7 +3387,7 @@ skip_dynamic_range_lvalue_expansion:;
auto* reg = reg_owned.get();
current_ast_mod->children.push_back(std::move(reg_owned));
reg->str = stringf("$past$%s:%d$%d$%d", RTLIL::encode_filename(filename).c_str(), location.first_line, myidx, i);
reg->str = stringf("$past$%s:%d$%d$%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line, myidx, i);
reg->is_reg = true;
reg->is_signed = sign_hint;
@ -3761,7 +3763,7 @@ skip_dynamic_range_lvalue_expansion:;
input_error("Failed to evaluate DPI function with non-constant argument.\n");
}
newNode = dpi_call(rtype, fname, argtypes, args);
newNode = dpi_call(dpi_decl->location, rtype, fname, argtypes, args);
goto apply_newNode;
}
@ -3845,7 +3847,7 @@ skip_dynamic_range_lvalue_expansion:;
std::stringstream sstr;
sstr << str << "$func$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++) << '.';
sstr << str << "$func$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++) << '.';
std::string prefix = sstr.str();
auto* decl = current_scope[str];
@ -4375,7 +4377,7 @@ apply_newNode:
// newNode->dumpAst(stderr, "+ ");
log_assert(newNode != nullptr);
// newNode->null_check();
newNode->filename = filename;
newNode->location.filename = location.filename;
newNode->location = location;
newNode->cloneInto(*this);
fixup_hierarchy_flags();
@ -4422,7 +4424,7 @@ std::unique_ptr<AstNode> AstNode::readmem(bool is_readmemh, std::string mem_file
#else
char slash = '/';
#endif
std::string path = filename.substr(0, filename.find_last_of(slash)+1);
std::string path = location.filename.substr(0, location.filename.find_last_of(slash)+1);
f.open(path + mem_filename.c_str());
yosys_input_files.insert(path + mem_filename);
} else {
@ -4479,7 +4481,7 @@ std::unique_ptr<AstNode> AstNode::readmem(bool is_readmemh, std::string mem_file
continue;
}
VERILOG_FRONTEND::ConstParser p{mem_filename, std::nullopt};
VERILOG_FRONTEND::ConstParser p{memory->location};
auto value = p.const2ast(stringf("%d'%c", mem_width, is_readmemh ? 'h' : 'b') + token);
if (unconditional_init)
@ -4701,7 +4703,7 @@ static void mark_memories_assign_lhs_complex(dict<AstNode*, pool<std::string>> &
if (that->type == AST_IDENTIFIER && that->id2ast && that->id2ast->type == AST_MEMORY) {
AstNode *mem = that->id2ast;
if (!(mem2reg_candidates[mem] & AstNode::MEM2REG_FL_CMPLX_LHS))
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(that->filename).c_str(), that->location.first_line));
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(that->location.filename).c_str(), that->location.first_line));
mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_CMPLX_LHS;
}
}
@ -4729,14 +4731,14 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
// activate mem2reg if this is assigned in an async proc
if (flags & AstNode::MEM2REG_FL_ASYNC) {
if (!(mem2reg_candidates[mem] & AstNode::MEM2REG_FL_SET_ASYNC))
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(filename).c_str(), location.first_line));
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line));
mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_SET_ASYNC;
}
// remember if this is assigned blocking (=)
if (type == AST_ASSIGN_EQ) {
if (!(proc_flags[mem] & AstNode::MEM2REG_FL_EQ1))
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(filename).c_str(), location.first_line));
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line));
proc_flags[mem] |= AstNode::MEM2REG_FL_EQ1;
}
@ -4753,11 +4755,11 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
// remember where this is
if (flags & MEM2REG_FL_INIT) {
if (!(mem2reg_candidates[mem] & AstNode::MEM2REG_FL_SET_INIT))
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(filename).c_str(), location.first_line));
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line));
mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_SET_INIT;
} else {
if (!(mem2reg_candidates[mem] & AstNode::MEM2REG_FL_SET_ELSE))
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(filename).c_str(), location.first_line));
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line));
mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_SET_ELSE;
}
}
@ -4774,7 +4776,7 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
// flag if used after blocking assignment (in same proc)
if ((proc_flags[mem] & AstNode::MEM2REG_FL_EQ1) && !(mem2reg_candidates[mem] & AstNode::MEM2REG_FL_EQ2)) {
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(filename).c_str(), location.first_line));
mem2reg_places[mem].insert(stringf("%s:%d", RTLIL::encode_filename(location.filename).c_str(), location.first_line));
mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_EQ2;
}
}
@ -4960,7 +4962,7 @@ bool AstNode::mem2reg_as_needed_pass2(pool<AstNode*> &mem2reg_set, AstNode *mod,
children[0]->children[0]->children[0]->type != AST_CONSTANT)
{
std::stringstream sstr;
sstr << "$mem2reg_wr$" << children[0]->str << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$mem2reg_wr$" << children[0]->str << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
std::string id_addr = sstr.str() + "_ADDR", id_data = sstr.str() + "_DATA";
int mem_width, mem_size, addr_bits;
@ -5079,7 +5081,7 @@ bool AstNode::mem2reg_as_needed_pass2(pool<AstNode*> &mem2reg_set, AstNode *mod,
else
{
std::stringstream sstr;
sstr << "$mem2reg_rd$" << str << "$" << RTLIL::encode_filename(filename) << ":" << location.first_line << "$" << (autoidx++);
sstr << "$mem2reg_rd$" << str << "$" << RTLIL::encode_filename(location.filename) << ":" << location.first_line << "$" << (autoidx++);
std::string id_addr = sstr.str() + "_ADDR", id_data = sstr.str() + "_DATA";
int mem_width, mem_size, addr_bits;