aboutsummaryrefslogtreecommitdiffstats
path: root/kernel
diff options
context:
space:
mode:
Diffstat (limited to 'kernel')
-rw-r--r--kernel/cost.cc75
-rw-r--r--kernel/cost.h51
-rw-r--r--kernel/driver.cc8
-rw-r--r--kernel/rtlil.cc111
-rw-r--r--kernel/rtlil.h33
-rw-r--r--kernel/yosys.cc38
-rw-r--r--kernel/yosys.h13
7 files changed, 244 insertions, 85 deletions
diff --git a/kernel/cost.cc b/kernel/cost.cc
deleted file mode 100644
index 175f01e64..000000000
--- a/kernel/cost.cc
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * yosys -- Yosys Open SYnthesis Suite
- *
- * Copyright (C) 2012 Clifford Wolf <clifford@clifford.at>
- *
- * Permission to use, copy, modify, and/or distribute this software for any
- * purpose with or without fee is hereby granted, provided that the above
- * copyright notice and this permission notice appear in all copies.
- *
- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
- *
- */
-
-#include "kernel/yosys.h"
-#include "kernel/cost.h"
-
-YOSYS_NAMESPACE_BEGIN
-
-int get_cell_cost(RTLIL::IdString type, const dict<RTLIL::IdString, RTLIL::Const> &parameters,
- RTLIL::Design *design, dict<RTLIL::IdString, int> *mod_cost_cache)
-{
- static dict<RTLIL::IdString, int> gate_cost = {
- { "$_BUF_", 1 },
- { "$_NOT_", 2 },
- { "$_AND_", 4 },
- { "$_NAND_", 4 },
- { "$_OR_", 4 },
- { "$_NOR_", 4 },
- { "$_ANDNOT_", 4 },
- { "$_ORNOT_", 4 },
- { "$_XOR_", 8 },
- { "$_XNOR_", 8 },
- { "$_AOI3_", 6 },
- { "$_OAI3_", 6 },
- { "$_AOI4_", 8 },
- { "$_OAI4_", 8 },
- { "$_MUX_", 4 }
- };
-
- if (gate_cost.count(type))
- return gate_cost.at(type);
-
- if (parameters.empty() && design && design->module(type))
- {
- RTLIL::Module *mod = design->module(type);
-
- if (mod->attributes.count("\\cost"))
- return mod->attributes.at("\\cost").as_int();
-
- dict<RTLIL::IdString, int> local_mod_cost_cache;
- if (mod_cost_cache == nullptr)
- mod_cost_cache = &local_mod_cost_cache;
-
- if (mod_cost_cache->count(mod->name))
- return mod_cost_cache->at(mod->name);
-
- int module_cost = 1;
- for (auto c : mod->cells())
- module_cost += get_cell_cost(c, mod_cost_cache);
-
- (*mod_cost_cache)[mod->name] = module_cost;
- return module_cost;
- }
-
- log_warning("Can't determine cost of %s cell (%d parameters).\n", log_id(type), GetSize(parameters));
- return 1;
-}
-
-YOSYS_NAMESPACE_END
diff --git a/kernel/cost.h b/kernel/cost.h
index 7d7822fa0..41a09eb63 100644
--- a/kernel/cost.h
+++ b/kernel/cost.h
@@ -26,8 +26,55 @@ YOSYS_NAMESPACE_BEGIN
int get_cell_cost(RTLIL::Cell *cell, dict<RTLIL::IdString, int> *mod_cost_cache = nullptr);
-int get_cell_cost(RTLIL::IdString type, const dict<RTLIL::IdString, RTLIL::Const> &parameters = dict<RTLIL::IdString, RTLIL::Const>(),
- RTLIL::Design *design = nullptr, dict<RTLIL::IdString, int> *mod_cost_cache = nullptr);
+inline int get_cell_cost(RTLIL::IdString type, const dict<RTLIL::IdString, RTLIL::Const> &parameters = dict<RTLIL::IdString, RTLIL::Const>(),
+ RTLIL::Design *design = nullptr, dict<RTLIL::IdString, int> *mod_cost_cache = nullptr)
+{
+ static dict<RTLIL::IdString, int> gate_cost = {
+ { "$_BUF_", 1 },
+ { "$_NOT_", 2 },
+ { "$_AND_", 4 },
+ { "$_NAND_", 4 },
+ { "$_OR_", 4 },
+ { "$_NOR_", 4 },
+ { "$_ANDNOT_", 4 },
+ { "$_ORNOT_", 4 },
+ { "$_XOR_", 8 },
+ { "$_XNOR_", 8 },
+ { "$_AOI3_", 6 },
+ { "$_OAI3_", 6 },
+ { "$_AOI4_", 8 },
+ { "$_OAI4_", 8 },
+ { "$_MUX_", 4 }
+ };
+
+ if (gate_cost.count(type))
+ return gate_cost.at(type);
+
+ if (parameters.empty() && design && design->module(type))
+ {
+ RTLIL::Module *mod = design->module(type);
+
+ if (mod->attributes.count("\\cost"))
+ return mod->attributes.at("\\cost").as_int();
+
+ dict<RTLIL::IdString, int> local_mod_cost_cache;
+ if (mod_cost_cache == nullptr)
+ mod_cost_cache = &local_mod_cost_cache;
+
+ if (mod_cost_cache->count(mod->name))
+ return mod_cost_cache->at(mod->name);
+
+ int module_cost = 1;
+ for (auto c : mod->cells())
+ module_cost += get_cell_cost(c, mod_cost_cache);
+
+ (*mod_cost_cache)[mod->name] = module_cost;
+ return module_cost;
+ }
+
+ log_warning("Can't determine cost of %s cell (%d parameters).\n", log_id(type), GetSize(parameters));
+ return 1;
+}
inline int get_cell_cost(RTLIL::Cell *cell, dict<RTLIL::IdString, int> *mod_cost_cache)
{
diff --git a/kernel/driver.cc b/kernel/driver.cc
index a0bb7e60a..c539ba569 100644
--- a/kernel/driver.cc
+++ b/kernel/driver.cc
@@ -110,6 +110,10 @@ int main(int argc, char **argv)
log_error_stderr = true;
yosys_banner();
yosys_setup();
+#ifdef WITH_PYTHON
+ PyRun_SimpleString(("sys.path.append(\""+proc_self_dirname()+"\")").c_str());
+ PyRun_SimpleString(("sys.path.append(\""+proc_share_dirname()+"plugins\")").c_str());
+#endif
if (argc == 2)
{
@@ -469,6 +473,10 @@ int main(int argc, char **argv)
#endif
yosys_setup();
+#ifdef WITH_PYTHON
+ PyRun_SimpleString(("sys.path.append(\""+proc_self_dirname()+"\")").c_str());
+ PyRun_SimpleString(("sys.path.append(\""+proc_share_dirname()+"plugins\")").c_str());
+#endif
log_error_atexit = yosys_atexit;
for (auto &fn : plugin_filenames)
diff --git a/kernel/rtlil.cc b/kernel/rtlil.cc
index 9ae20a317..7e1159cac 100644
--- a/kernel/rtlil.cc
+++ b/kernel/rtlil.cc
@@ -76,6 +76,13 @@ RTLIL::Const::Const(const std::vector<bool> &bits)
this->bits.push_back(b ? RTLIL::S1 : RTLIL::S0);
}
+RTLIL::Const::Const(const RTLIL::Const &c)
+{
+ flags = c.flags;
+ for (auto b : c.bits)
+ this->bits.push_back(b);
+}
+
bool RTLIL::Const::operator <(const RTLIL::Const &other) const
{
if (bits.size() != other.bits.size())
@@ -207,9 +214,12 @@ bool RTLIL::Const::is_fully_undef() const
return true;
}
-void RTLIL::AttrObject::set_bool_attribute(RTLIL::IdString id)
+void RTLIL::AttrObject::set_bool_attribute(RTLIL::IdString id, bool value)
{
- attributes[id] = RTLIL::Const(1);
+ if (value)
+ attributes[id] = RTLIL::Const(1);
+ else if (attributes.count(id))
+ attributes.erase(id);
}
bool RTLIL::AttrObject::get_bool_attribute(RTLIL::IdString id) const
@@ -360,6 +370,10 @@ RTLIL::Design::Design()
refcount_modules_ = 0;
selection_stack.push_back(RTLIL::Selection());
+
+#ifdef WITH_PYTHON
+ RTLIL::Design::get_all_designs()->insert(std::pair<unsigned int, RTLIL::Design*>(hashidx_, this));
+#endif
}
RTLIL::Design::~Design()
@@ -370,8 +384,19 @@ RTLIL::Design::~Design()
delete n;
for (auto n : verilog_globals)
delete n;
+#ifdef WITH_PYTHON
+ RTLIL::Design::get_all_designs()->erase(hashidx_);
+#endif
}
+#ifdef WITH_PYTHON
+static std::map<unsigned int, RTLIL::Design*> all_designs;
+std::map<unsigned int, RTLIL::Design*> *RTLIL::Design::get_all_designs(void)
+{
+ return &all_designs;
+}
+#endif
+
RTLIL::ObjRange<RTLIL::Module*> RTLIL::Design::modules()
{
return RTLIL::ObjRange<RTLIL::Module*>(&modules_, &refcount_modules_);
@@ -589,7 +614,7 @@ std::vector<RTLIL::Module*> RTLIL::Design::selected_modules() const
std::vector<RTLIL::Module*> result;
result.reserve(modules_.size());
for (auto &it : modules_)
- if (selected_module(it.first) && !it.second->get_bool_attribute("\\blackbox"))
+ if (selected_module(it.first) && !it.second->get_blackbox_attribute())
result.push_back(it.second);
return result;
}
@@ -599,7 +624,7 @@ std::vector<RTLIL::Module*> RTLIL::Design::selected_whole_modules() const
std::vector<RTLIL::Module*> result;
result.reserve(modules_.size());
for (auto &it : modules_)
- if (selected_whole_module(it.first) && !it.second->get_bool_attribute("\\blackbox"))
+ if (selected_whole_module(it.first) && !it.second->get_blackbox_attribute())
result.push_back(it.second);
return result;
}
@@ -609,7 +634,7 @@ std::vector<RTLIL::Module*> RTLIL::Design::selected_whole_modules_warn() const
std::vector<RTLIL::Module*> result;
result.reserve(modules_.size());
for (auto &it : modules_)
- if (it.second->get_bool_attribute("\\blackbox"))
+ if (it.second->get_blackbox_attribute())
continue;
else if (selected_whole_module(it.first))
result.push_back(it.second);
@@ -627,6 +652,10 @@ RTLIL::Module::Module()
design = nullptr;
refcount_wires_ = 0;
refcount_cells_ = 0;
+
+#ifdef WITH_PYTHON
+ RTLIL::Module::get_all_modules()->insert(std::pair<unsigned int, RTLIL::Module*>(hashidx_, this));
+#endif
}
RTLIL::Module::~Module()
@@ -639,7 +668,18 @@ RTLIL::Module::~Module()
delete it->second;
for (auto it = processes.begin(); it != processes.end(); ++it)
delete it->second;
+#ifdef WITH_PYTHON
+ RTLIL::Module::get_all_modules()->erase(hashidx_);
+#endif
+}
+
+#ifdef WITH_PYTHON
+static std::map<unsigned int, RTLIL::Module*> all_modules;
+std::map<unsigned int, RTLIL::Module*> *RTLIL::Module::get_all_modules(void)
+{
+ return &all_modules;
}
+#endif
void RTLIL::Module::makeblackbox()
{
@@ -2226,8 +2266,27 @@ RTLIL::Wire::Wire()
port_input = false;
port_output = false;
upto = false;
+
+#ifdef WITH_PYTHON
+ RTLIL::Wire::get_all_wires()->insert(std::pair<unsigned int, RTLIL::Wire*>(hashidx_, this));
+#endif
+}
+
+RTLIL::Wire::~Wire()
+{
+#ifdef WITH_PYTHON
+ RTLIL::Wire::get_all_wires()->erase(hashidx_);
+#endif
}
+#ifdef WITH_PYTHON
+static std::map<unsigned int, RTLIL::Wire*> all_wires;
+std::map<unsigned int, RTLIL::Wire*> *RTLIL::Wire::get_all_wires(void)
+{
+ return &all_wires;
+}
+#endif
+
RTLIL::Memory::Memory()
{
static unsigned int hashidx_count = 123456789;
@@ -2237,6 +2296,9 @@ RTLIL::Memory::Memory()
width = 1;
start_offset = 0;
size = 0;
+#ifdef WITH_PYTHON
+ RTLIL::Memory::get_all_memorys()->insert(std::pair<unsigned int, RTLIL::Memory*>(hashidx_, this));
+#endif
}
RTLIL::Cell::Cell() : module(nullptr)
@@ -2247,8 +2309,27 @@ RTLIL::Cell::Cell() : module(nullptr)
// log("#memtrace# %p\n", this);
memhasher();
+
+#ifdef WITH_PYTHON
+ RTLIL::Cell::get_all_cells()->insert(std::pair<unsigned int, RTLIL::Cell*>(hashidx_, this));
+#endif
}
+RTLIL::Cell::~Cell()
+{
+#ifdef WITH_PYTHON
+ RTLIL::Cell::get_all_cells()->erase(hashidx_);
+#endif
+}
+
+#ifdef WITH_PYTHON
+static std::map<unsigned int, RTLIL::Cell*> all_cells;
+std::map<unsigned int, RTLIL::Cell*> *RTLIL::Cell::get_all_cells(void)
+{
+ return &all_cells;
+}
+#endif
+
bool RTLIL::Cell::hasPort(RTLIL::IdString portname) const
{
return connections_.count(portname) != 0;
@@ -2508,6 +2589,14 @@ RTLIL::SigChunk::SigChunk(RTLIL::SigBit bit)
width = 1;
}
+RTLIL::SigChunk::SigChunk(const RTLIL::SigChunk &sigchunk) : data(sigchunk.data)
+{
+ wire = sigchunk.wire;
+ data = sigchunk.data;
+ width = sigchunk.width;
+ offset = sigchunk.offset;
+}
+
RTLIL::SigChunk RTLIL::SigChunk::extract(int offset, int length) const
{
RTLIL::SigChunk ret;
@@ -3892,5 +3981,15 @@ RTLIL::Process *RTLIL::Process::clone() const
return new_proc;
}
+#ifdef WITH_PYTHON
+RTLIL::Memory::~Memory()
+{
+ RTLIL::Memory::get_all_memorys()->erase(hashidx_);
+}
+static std::map<unsigned int, RTLIL::Memory*> all_memorys;
+std::map<unsigned int, RTLIL::Memory*> *RTLIL::Memory::get_all_memorys(void)
+{
+ return &all_memorys;
+}
+#endif
YOSYS_NAMESPACE_END
-
diff --git a/kernel/rtlil.h b/kernel/rtlil.h
index ef6eb9f83..757e0dfa4 100644
--- a/kernel/rtlil.h
+++ b/kernel/rtlil.h
@@ -523,6 +523,7 @@ struct RTLIL::Const
Const(RTLIL::State bit, int width = 1);
Const(const std::vector<RTLIL::State> &bits) : bits(bits) { flags = CONST_FLAG_NONE; }
Const(const std::vector<bool> &bits);
+ Const(const RTLIL::Const &c);
bool operator <(const RTLIL::Const &other) const;
bool operator ==(const RTLIL::Const &other) const;
@@ -572,9 +573,13 @@ struct RTLIL::AttrObject
{
dict<RTLIL::IdString, RTLIL::Const> attributes;
- void set_bool_attribute(RTLIL::IdString id);
+ void set_bool_attribute(RTLIL::IdString id, bool value=true);
bool get_bool_attribute(RTLIL::IdString id) const;
+ bool get_blackbox_attribute(bool ignore_wb=false) const {
+ return get_bool_attribute("\\blackbox") || (!ignore_wb && get_bool_attribute("\\whitebox"));
+ }
+
void set_strpool_attribute(RTLIL::IdString id, const pool<string> &data);
void add_strpool_attribute(RTLIL::IdString id, const pool<string> &data);
pool<string> get_strpool_attribute(RTLIL::IdString id) const;
@@ -597,6 +602,7 @@ struct RTLIL::SigChunk
SigChunk(int val, int width = 32);
SigChunk(RTLIL::State bit, int width = 1);
SigChunk(RTLIL::SigBit bit);
+ SigChunk(const RTLIL::SigChunk &sigchunk);
RTLIL::SigChunk extract(int offset, int length) const;
@@ -621,6 +627,7 @@ struct RTLIL::SigBit
SigBit(const RTLIL::SigChunk &chunk);
SigBit(const RTLIL::SigChunk &chunk, int index);
SigBit(const RTLIL::SigSpec &sig);
+ SigBit(const RTLIL::SigBit &sigbit);
bool operator <(const RTLIL::SigBit &other) const;
bool operator ==(const RTLIL::SigBit &other) const;
@@ -942,9 +949,13 @@ struct RTLIL::Design
}
}
+
std::vector<RTLIL::Module*> selected_modules() const;
std::vector<RTLIL::Module*> selected_whole_modules() const;
std::vector<RTLIL::Module*> selected_whole_modules_warn() const;
+#ifdef WITH_PYTHON
+ static std::map<unsigned int, RTLIL::Design*> *get_all_designs(void);
+#endif
};
struct RTLIL::Module : public RTLIL::AttrObject
@@ -1201,6 +1212,10 @@ public:
RTLIL::SigSpec Allconst (RTLIL::IdString name, int width = 1, const std::string &src = "");
RTLIL::SigSpec Allseq (RTLIL::IdString name, int width = 1, const std::string &src = "");
RTLIL::SigSpec Initstate (RTLIL::IdString name, const std::string &src = "");
+
+#ifdef WITH_PYTHON
+ static std::map<unsigned int, RTLIL::Module*> *get_all_modules(void);
+#endif
};
struct RTLIL::Wire : public RTLIL::AttrObject
@@ -1212,7 +1227,7 @@ protected:
// use module->addWire() and module->remove() to create or destroy wires
friend struct RTLIL::Module;
Wire();
- ~Wire() { };
+ ~Wire();
public:
// do not simply copy wires
@@ -1223,6 +1238,10 @@ public:
RTLIL::IdString name;
int width, start_offset, port_id;
bool port_input, port_output, upto;
+
+#ifdef WITH_PYTHON
+ static std::map<unsigned int, RTLIL::Wire*> *get_all_wires(void);
+#endif
};
struct RTLIL::Memory : public RTLIL::AttrObject
@@ -1234,6 +1253,10 @@ struct RTLIL::Memory : public RTLIL::AttrObject
RTLIL::IdString name;
int width, start_offset, size;
+#ifdef WITH_PYTHON
+ ~Memory();
+ static std::map<unsigned int, RTLIL::Memory*> *get_all_memorys(void);
+#endif
};
struct RTLIL::Cell : public RTLIL::AttrObject
@@ -1245,6 +1268,7 @@ protected:
// use module->addCell() and module->remove() to create or destroy cells
friend struct RTLIL::Module;
Cell();
+ ~Cell();
public:
// do not simply copy cells
@@ -1285,6 +1309,10 @@ public:
}
template<typename T> void rewrite_sigspecs(T &functor);
+
+#ifdef WITH_PYTHON
+ static std::map<unsigned int, RTLIL::Cell*> *get_all_cells(void);
+#endif
};
struct RTLIL::CaseRule
@@ -1345,6 +1373,7 @@ inline RTLIL::SigBit::SigBit(RTLIL::Wire *wire) : wire(wire), offset(0) { log_as
inline RTLIL::SigBit::SigBit(RTLIL::Wire *wire, int offset) : wire(wire), offset(offset) { log_assert(wire != nullptr); }
inline RTLIL::SigBit::SigBit(const RTLIL::SigChunk &chunk) : wire(chunk.wire) { log_assert(chunk.width == 1); if (wire) offset = chunk.offset; else data = chunk.data[0]; }
inline RTLIL::SigBit::SigBit(const RTLIL::SigChunk &chunk, int index) : wire(chunk.wire) { if (wire) offset = chunk.offset + index; else data = chunk.data[index]; }
+inline RTLIL::SigBit::SigBit(const RTLIL::SigBit &sigbit) : wire(sigbit.wire), data(sigbit.data){if(wire) offset = sigbit.offset;}
inline bool RTLIL::SigBit::operator<(const RTLIL::SigBit &other) const {
if (wire == other.wire)
diff --git a/kernel/yosys.cc b/kernel/yosys.cc
index 450e4e4cf..a12355f1d 100644
--- a/kernel/yosys.cc
+++ b/kernel/yosys.cc
@@ -57,6 +57,16 @@
# include <sys/sysctl.h>
#endif
+#ifdef WITH_PYTHON
+#if PY_MAJOR_VERSION >= 3
+# define INIT_MODULE PyInit_libyosys
+ extern "C" PyObject* INIT_MODULE();
+#else
+# define INIT_MODULE initlibyosys
+ extern "C" void INIT_MODULE();
+#endif
+#endif
+
#include <limits.h>
#include <errno.h>
@@ -477,21 +487,42 @@ int GetSize(RTLIL::Wire *wire)
return wire->width;
}
+bool already_setup = false;
+
void yosys_setup()
{
+ if(already_setup)
+ return;
+ already_setup = true;
// if there are already IdString objects then we have a global initialization order bug
IdString empty_id;
log_assert(empty_id.index_ == 0);
IdString::get_reference(empty_id.index_);
+ #ifdef WITH_PYTHON
+ PyImport_AppendInittab((char*)"libyosys", INIT_MODULE);
+ Py_Initialize();
+ PyRun_SimpleString("import sys");
+ #endif
+
Pass::init_register();
yosys_design = new RTLIL::Design;
yosys_celltypes.setup();
log_push();
}
+bool yosys_already_setup()
+{
+ return already_setup;
+}
+
+bool already_shutdown = false;
+
void yosys_shutdown()
{
+ if(already_shutdown)
+ return;
+ already_shutdown = true;
log_pop();
delete yosys_design;
@@ -519,9 +550,16 @@ void yosys_shutdown()
dlclose(it.second);
loaded_plugins.clear();
+#ifdef WITH_PYTHON
+ loaded_python_plugins.clear();
+#endif
loaded_plugin_aliases.clear();
#endif
+#ifdef WITH_PYTHON
+ Py_Finalize();
+#endif
+
IdString empty_id;
IdString::put_reference(empty_id.index_);
}
diff --git a/kernel/yosys.h b/kernel/yosys.h
index c9f973318..2cf6188b4 100644
--- a/kernel/yosys.h
+++ b/kernel/yosys.h
@@ -66,6 +66,10 @@
#include <stdio.h>
#include <limits.h>
+#ifdef WITH_PYTHON
+#include <Python.h>
+#endif
+
#ifndef _YOSYS_
# error It looks like you are trying to build Yosys without the config defines set. \
When building Yosys with a custom make system, make sure you set all the \
@@ -115,6 +119,7 @@ extern const char *Tcl_GetStringResult(Tcl_Interp *interp);
# define PATH_MAX 4096
#endif
+#define YOSYS_NAMESPACE Yosys
#define PRIVATE_NAMESPACE_BEGIN namespace {
#define PRIVATE_NAMESPACE_END }
#define YOSYS_NAMESPACE_BEGIN namespace Yosys {
@@ -276,6 +281,11 @@ namespace hashlib {
}
void yosys_setup();
+
+#ifdef WITH_PYTHON
+bool yosys_already_setup();
+#endif
+
void yosys_shutdown();
#ifdef YOSYS_ENABLE_TCL
@@ -317,6 +327,9 @@ extern std::vector<RTLIL::Design*> pushed_designs;
// from passes/cmds/pluginc.cc
extern std::map<std::string, void*> loaded_plugins;
+#ifdef WITH_PYTHON
+extern std::map<std::string, void*> loaded_python_plugins;
+#endif
extern std::map<std::string, std::string> loaded_plugin_aliases;
void load_plugin(std::string filename, std::vector<std::string> aliases);