3
0
Fork 0
mirror of https://github.com/YosysHQ/yosys synced 2025-04-23 09:05:32 +00:00

Added "eval" pass

This commit is contained in:
Clifford Wolf 2013-06-19 09:30:37 +02:00
parent a046a302f0
commit 21e38bed98
6 changed files with 316 additions and 189 deletions

View file

@ -19,6 +19,7 @@
#include "kernel/rtlil.h"
#include "kernel/log.h"
#include "frontends/verilog/verilog_frontend.h"
#include <assert.h>
#include <algorithm>
@ -1062,6 +1063,90 @@ bool RTLIL::SigSpec::match(std::string pattern) const
return true;
}
static void sigspec_parse_split(std::vector<std::string> &tokens, const std::string &text, char sep)
{
size_t start = 0, end = 0;
while ((end = text.find(sep, start)) != std::string::npos) {
tokens.push_back(text.substr(start, end - start));
start = end + 1;
}
tokens.push_back(text.substr(start));
}
static int sigspec_parse_get_dummy_line_num()
{
return 0;
}
bool RTLIL::SigSpec::parse(RTLIL::SigSpec &sig, RTLIL::Module *module, std::string str)
{
std::vector<std::string> tokens;
sigspec_parse_split(tokens, str, ',');
sig = RTLIL::SigSpec();
for (auto &tok : tokens)
{
std::string netname = tok;
std::string indices;
if (netname.size() == 0)
continue;
if ('0' <= netname[0] && netname[0] <= '9') {
AST::get_line_num = sigspec_parse_get_dummy_line_num;
AST::AstNode *ast = VERILOG_FRONTEND::const2ast(netname);
if (ast == NULL)
return false;
sig.append(RTLIL::Const(ast->bits));
delete ast;
continue;
}
if (netname[0] != '$' && netname[0] != '\\')
netname = "\\" + netname;
if (module->wires.count(netname) == 0) {
size_t indices_pos = netname.size()-1;
if (indices_pos > 2 && netname[indices_pos] == ']')
{
indices_pos--;
while (indices_pos > 0 && ('0' <= netname[indices_pos] && netname[indices_pos] <= '9')) indices_pos--;
if (indices_pos > 0 && netname[indices_pos] == ':') {
indices_pos--;
while (indices_pos > 0 && ('0' <= netname[indices_pos] && netname[indices_pos] <= '9')) indices_pos--;
}
if (indices_pos > 0 && netname[indices_pos] == '[') {
indices = netname.substr(indices_pos);
netname = netname.substr(0, indices_pos);
}
}
}
if (module->wires.count(netname) == 0)
return false;
RTLIL::Wire *wire = module->wires.at(netname);
if (!indices.empty()) {
std::vector<std::string> index_tokens;
sigspec_parse_split(index_tokens, indices.substr(1, indices.size()-2), ':');
if (index_tokens.size() == 1)
sig.append(RTLIL::SigSpec(wire, 1, atoi(index_tokens.at(0).c_str())));
else {
int a = atoi(index_tokens.at(0).c_str());
int b = atoi(index_tokens.at(1).c_str());
if (a > b) {
int tmp = a;
a = b, b = tmp;
}
sig.append(RTLIL::SigSpec(wire, b-a+1, a));
}
} else
sig.append(wire);
}
return true;
}
RTLIL::CaseRule::~CaseRule()
{
for (auto it = switches.begin(); it != switches.end(); it++)

View file

@ -327,6 +327,7 @@ struct RTLIL::SigSpec {
std::string as_string() const;
RTLIL::Const as_const() const;
bool match(std::string pattern) const;
static bool parse(RTLIL::SigSpec &sig, RTLIL::Module *module, std::string str);
};
struct RTLIL::CaseRule {