mirror of
				https://github.com/YosysHQ/yosys
				synced 2025-11-04 05:19:11 +00:00 
			
		
		
		
	Added ScriptPass helper class for script-like passes
This commit is contained in:
		
							parent
							
								
									6cafd08ac1
								
							
						
					
					
						commit
						2553319081
					
				
					 5 changed files with 255 additions and 251 deletions
				
			
		| 
						 | 
				
			
			@ -80,6 +80,7 @@ Pass::pre_post_exec_state_t Pass::pre_execute()
 | 
			
		|||
	state.begin_ns = PerformanceTimer::query();
 | 
			
		||||
	state.parent_pass = current_pass;
 | 
			
		||||
	current_pass = this;
 | 
			
		||||
	clear_flags();
 | 
			
		||||
	return state;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -99,6 +100,10 @@ void Pass::help()
 | 
			
		|||
	log("\n");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Pass::clear_flags()
 | 
			
		||||
{
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Pass::cmd_log_args(const std::vector<std::string> &args)
 | 
			
		||||
{
 | 
			
		||||
	if (args.size() <= 1)
 | 
			
		||||
| 
						 | 
				
			
			@ -282,6 +287,60 @@ void Pass::call_on_module(RTLIL::Design *design, RTLIL::Module *module, std::vec
 | 
			
		|||
	design->selected_active_module = backup_selected_active_module;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool ScriptPass::check_label(std::string label, std::string info)
 | 
			
		||||
{
 | 
			
		||||
	if (active_design == nullptr) {
 | 
			
		||||
		log("\n");
 | 
			
		||||
		if (info.empty())
 | 
			
		||||
			log("    %s:\n", label.c_str());
 | 
			
		||||
		else
 | 
			
		||||
			log("    %s:    %s\n", label.c_str(), info.c_str());
 | 
			
		||||
		return true;
 | 
			
		||||
	} else {
 | 
			
		||||
		if (!active_run_from.empty() && active_run_from == active_run_to) {
 | 
			
		||||
			block_active = (label == active_run_from);
 | 
			
		||||
		} else {
 | 
			
		||||
			if (label == active_run_from)
 | 
			
		||||
				block_active = true;
 | 
			
		||||
			if (label == active_run_to)
 | 
			
		||||
				block_active = false;
 | 
			
		||||
		}
 | 
			
		||||
		return block_active;
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ScriptPass::run(std::string command, std::string info)
 | 
			
		||||
{
 | 
			
		||||
	if (active_design == nullptr) {
 | 
			
		||||
		if (info.empty())
 | 
			
		||||
			log("        %s\n", command.c_str());
 | 
			
		||||
		else
 | 
			
		||||
			log("        %s    %s\n", command.c_str(), info.c_str());
 | 
			
		||||
	} else
 | 
			
		||||
		Pass::call(active_design, command);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ScriptPass::run_script(RTLIL::Design *design, std::string run_from, std::string run_to)
 | 
			
		||||
{
 | 
			
		||||
	help_mode = false;
 | 
			
		||||
	active_design = design;
 | 
			
		||||
	block_active = run_from.empty();
 | 
			
		||||
	active_run_from = run_from;
 | 
			
		||||
	active_run_to = run_to;
 | 
			
		||||
	script();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ScriptPass::help_script()
 | 
			
		||||
{
 | 
			
		||||
	clear_flags();
 | 
			
		||||
	help_mode = true;
 | 
			
		||||
	active_design = nullptr;
 | 
			
		||||
	block_active = true;
 | 
			
		||||
	active_run_from.clear();
 | 
			
		||||
	active_run_to.clear();
 | 
			
		||||
	script();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Frontend::Frontend(std::string name, std::string short_help) :
 | 
			
		||||
		Pass(name.rfind("=", 0) == 0 ? name.substr(1) : "read_" + name, short_help),
 | 
			
		||||
		frontend_name(name.rfind("=", 0) == 0 ? name.substr(1) : name)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -31,6 +31,7 @@ struct Pass
 | 
			
		|||
	virtual ~Pass();
 | 
			
		||||
 | 
			
		||||
	virtual void help();
 | 
			
		||||
	virtual void clear_flags();
 | 
			
		||||
	virtual void execute(std::vector<std::string> args, RTLIL::Design *design) = 0;
 | 
			
		||||
 | 
			
		||||
	int call_counter;
 | 
			
		||||
| 
						 | 
				
			
			@ -63,6 +64,22 @@ struct Pass
 | 
			
		|||
	static void done_register();
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct ScriptPass : Pass
 | 
			
		||||
{
 | 
			
		||||
	bool block_active, help_mode;
 | 
			
		||||
	RTLIL::Design *active_design;
 | 
			
		||||
	std::string active_run_from, active_run_to;
 | 
			
		||||
 | 
			
		||||
	ScriptPass(std::string name, std::string short_help = "** document me **") : Pass(name, short_help) { }
 | 
			
		||||
 | 
			
		||||
	virtual void script() = 0;
 | 
			
		||||
 | 
			
		||||
	bool check_label(std::string label, std::string info = std::string());
 | 
			
		||||
	void run(std::string command, std::string info = std::string());
 | 
			
		||||
	void run_script(RTLIL::Design *design, std::string run_from = std::string(), std::string run_to = std::string());
 | 
			
		||||
	void help_script();
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct Frontend : Pass
 | 
			
		||||
{
 | 
			
		||||
	// for reading of here documents
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1100,8 +1100,8 @@ struct HistoryPass : public Pass {
 | 
			
		|||
} HistoryPass;
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
struct ScriptPass : public Pass {
 | 
			
		||||
	ScriptPass() : Pass("script", "execute commands from script file") { }
 | 
			
		||||
struct ScriptCmdPass : public Pass {
 | 
			
		||||
	ScriptCmdPass() : Pass("script", "execute commands from script file") { }
 | 
			
		||||
	virtual void help() {
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    script <filename> [<from_label>:<to_label>]\n");
 | 
			
		||||
| 
						 | 
				
			
			@ -1127,7 +1127,7 @@ struct ScriptPass : public Pass {
 | 
			
		|||
		else
 | 
			
		||||
			extra_args(args, 2, design, false);
 | 
			
		||||
	}
 | 
			
		||||
} ScriptPass;
 | 
			
		||||
} ScriptCmdPass;
 | 
			
		||||
 | 
			
		||||
YOSYS_NAMESPACE_END
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -25,22 +25,11 @@
 | 
			
		|||
USING_YOSYS_NAMESPACE
 | 
			
		||||
PRIVATE_NAMESPACE_BEGIN
 | 
			
		||||
 | 
			
		||||
bool check_label(bool &active, std::string run_from, std::string run_to, std::string label)
 | 
			
		||||
struct SynthPass : public ScriptPass
 | 
			
		||||
{
 | 
			
		||||
	if (!run_from.empty() && run_from == run_to) {
 | 
			
		||||
		active = (label == run_from);
 | 
			
		||||
	} else {
 | 
			
		||||
		if (label == run_from)
 | 
			
		||||
			active = true;
 | 
			
		||||
		if (label == run_to)
 | 
			
		||||
			active = false;
 | 
			
		||||
	}
 | 
			
		||||
	return active;
 | 
			
		||||
}
 | 
			
		||||
	SynthPass() : ScriptPass("synth", "generic synthesis script") { }
 | 
			
		||||
 | 
			
		||||
struct SynthPass : public Pass {
 | 
			
		||||
	SynthPass() : Pass("synth", "generic synthesis script") { }
 | 
			
		||||
	virtual void help()
 | 
			
		||||
	virtual void help() YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		//   |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|
 | 
			
		||||
		log("\n");
 | 
			
		||||
| 
						 | 
				
			
			@ -75,49 +64,28 @@ struct SynthPass : public Pass {
 | 
			
		|||
		log("\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("The following commands are executed by this synthesis command:\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    begin:\n");
 | 
			
		||||
		log("        hierarchy -check [-top <top>]\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    coarse:\n");
 | 
			
		||||
		log("        proc\n");
 | 
			
		||||
		log("        opt_expr\n");
 | 
			
		||||
		log("        opt_clean\n");
 | 
			
		||||
		log("        check\n");
 | 
			
		||||
		log("        opt\n");
 | 
			
		||||
		log("        wreduce\n");
 | 
			
		||||
		log("        alumacc\n");
 | 
			
		||||
		log("        share\n");
 | 
			
		||||
		log("        opt\n");
 | 
			
		||||
		log("        fsm\n");
 | 
			
		||||
		log("        opt -fast\n");
 | 
			
		||||
		log("        memory -nomap\n");
 | 
			
		||||
		log("        opt_clean\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    fine:\n");
 | 
			
		||||
		log("        opt -fast -full\n");
 | 
			
		||||
		log("        memory_map\n");
 | 
			
		||||
		log("        opt -full\n");
 | 
			
		||||
		log("        techmap\n");
 | 
			
		||||
		log("        opt -fast\n");
 | 
			
		||||
	#ifdef YOSYS_ENABLE_ABC
 | 
			
		||||
		log("        abc -fast\n");
 | 
			
		||||
		log("        opt -fast\n");
 | 
			
		||||
	#endif
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    check:\n");
 | 
			
		||||
		log("        hierarchy -check\n");
 | 
			
		||||
		log("        stat\n");
 | 
			
		||||
		log("        check\n");
 | 
			
		||||
		help_script();
 | 
			
		||||
		log("\n");
 | 
			
		||||
	}
 | 
			
		||||
	virtual void execute(std::vector<std::string> args, RTLIL::Design *design)
 | 
			
		||||
 | 
			
		||||
	std::string top_module, fsm_opts, memory_opts;
 | 
			
		||||
	bool noalumacc, nofsm, noabc;
 | 
			
		||||
 | 
			
		||||
	virtual void clear_flags() YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		std::string top_module, fsm_opts, memory_opts;
 | 
			
		||||
		std::string run_from, run_to;
 | 
			
		||||
		bool noalumacc = false;
 | 
			
		||||
		bool nofsm = false;
 | 
			
		||||
		bool noabc = false;
 | 
			
		||||
		top_module.clear();
 | 
			
		||||
		fsm_opts.clear();
 | 
			
		||||
		memory_opts.clear();
 | 
			
		||||
 | 
			
		||||
		noalumacc = false;
 | 
			
		||||
		nofsm = false;
 | 
			
		||||
		noabc = false;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	virtual void execute(std::vector<std::string> args, RTLIL::Design *design) YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		string run_from, run_to;
 | 
			
		||||
		clear_flags();
 | 
			
		||||
 | 
			
		||||
		size_t argidx;
 | 
			
		||||
		for (argidx = 1; argidx < args.size(); argidx++)
 | 
			
		||||
| 
						 | 
				
			
			@ -164,62 +132,69 @@ struct SynthPass : public Pass {
 | 
			
		|||
		if (!design->full_selection())
 | 
			
		||||
			log_cmd_error("This comannd only operates on fully selected designs!\n");
 | 
			
		||||
 | 
			
		||||
		bool active = run_from.empty();
 | 
			
		||||
 | 
			
		||||
		log_header("Executing SYNTH pass.\n");
 | 
			
		||||
		log_push();
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "begin"))
 | 
			
		||||
		run_script(design, run_from, run_to);
 | 
			
		||||
 | 
			
		||||
		log_pop();
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	virtual void script() YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		if (check_label("begin"))
 | 
			
		||||
		{
 | 
			
		||||
			if (top_module.empty())
 | 
			
		||||
				Pass::call(design, stringf("hierarchy -check"));
 | 
			
		||||
			else
 | 
			
		||||
				Pass::call(design, stringf("hierarchy -check -top %s", top_module.c_str()));
 | 
			
		||||
			if (help_mode) {
 | 
			
		||||
				run("hierarchy -check [-top <top>]");
 | 
			
		||||
			} else {
 | 
			
		||||
				if (top_module.empty())
 | 
			
		||||
					run(stringf("hierarchy -check"));
 | 
			
		||||
				else
 | 
			
		||||
					run(stringf("hierarchy -check -top %s", top_module.c_str()));
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "coarse"))
 | 
			
		||||
		if (check_label("coarse"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "proc");
 | 
			
		||||
			Pass::call(design, "opt_expr");
 | 
			
		||||
			Pass::call(design, "opt_clean");
 | 
			
		||||
			Pass::call(design, "check");
 | 
			
		||||
			Pass::call(design, "opt");
 | 
			
		||||
			Pass::call(design, "wreduce");
 | 
			
		||||
			run("proc");
 | 
			
		||||
			run("opt_expr");
 | 
			
		||||
			run("opt_clean");
 | 
			
		||||
			run("check");
 | 
			
		||||
			run("opt");
 | 
			
		||||
			run("wreduce");
 | 
			
		||||
			if (!noalumacc)
 | 
			
		||||
				Pass::call(design, "alumacc");
 | 
			
		||||
			Pass::call(design, "share");
 | 
			
		||||
			Pass::call(design, "opt");
 | 
			
		||||
				run("alumacc");
 | 
			
		||||
			run("share");
 | 
			
		||||
			run("opt");
 | 
			
		||||
			if (!nofsm)
 | 
			
		||||
				Pass::call(design, "fsm" + fsm_opts);
 | 
			
		||||
			Pass::call(design, "opt -fast");
 | 
			
		||||
			Pass::call(design, "memory -nomap" + memory_opts);
 | 
			
		||||
			Pass::call(design, "opt_clean");
 | 
			
		||||
				run("fsm" + fsm_opts);
 | 
			
		||||
			run("opt -fast");
 | 
			
		||||
			run("memory -nomap" + memory_opts);
 | 
			
		||||
			run("opt_clean");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "fine"))
 | 
			
		||||
		if (check_label("fine"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "opt -fast -full");
 | 
			
		||||
			Pass::call(design, "memory_map");
 | 
			
		||||
			Pass::call(design, "opt -full");
 | 
			
		||||
			Pass::call(design, "techmap");
 | 
			
		||||
			Pass::call(design, "opt -fast");
 | 
			
		||||
			run("opt -fast -full");
 | 
			
		||||
			run("memory_map");
 | 
			
		||||
			run("opt -full");
 | 
			
		||||
			run("techmap");
 | 
			
		||||
			run("opt -fast");
 | 
			
		||||
 | 
			
		||||
			if (!noabc) {
 | 
			
		||||
		#ifdef YOSYS_ENABLE_ABC
 | 
			
		||||
				Pass::call(design, "abc -fast");
 | 
			
		||||
				Pass::call(design, "opt -fast");
 | 
			
		||||
				run("abc -fast");
 | 
			
		||||
				run("opt -fast");
 | 
			
		||||
		#endif
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "check"))
 | 
			
		||||
		if (check_label("check"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "hierarchy -check");
 | 
			
		||||
			Pass::call(design, "stat");
 | 
			
		||||
			Pass::call(design, "check");
 | 
			
		||||
			run("hierarchy -check");
 | 
			
		||||
			run("stat");
 | 
			
		||||
			run("check");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		log_pop();
 | 
			
		||||
	}
 | 
			
		||||
} SynthPass;
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -25,18 +25,11 @@
 | 
			
		|||
USING_YOSYS_NAMESPACE
 | 
			
		||||
PRIVATE_NAMESPACE_BEGIN
 | 
			
		||||
 | 
			
		||||
bool check_label(bool &active, std::string run_from, std::string run_to, std::string label)
 | 
			
		||||
struct SynthIce40Pass : public ScriptPass
 | 
			
		||||
{
 | 
			
		||||
	if (label == run_from)
 | 
			
		||||
		active = true;
 | 
			
		||||
	if (label == run_to)
 | 
			
		||||
		active = false;
 | 
			
		||||
	return active;
 | 
			
		||||
}
 | 
			
		||||
	SynthIce40Pass() : ScriptPass("synth_ice40", "synthesis for iCE40 FPGAs") { }
 | 
			
		||||
 | 
			
		||||
struct SynthIce40Pass : public Pass {
 | 
			
		||||
	SynthIce40Pass() : Pass("synth_ice40", "synthesis for iCE40 FPGAs") { }
 | 
			
		||||
	virtual void help()
 | 
			
		||||
	virtual void help() YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		//   |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|
 | 
			
		||||
		log("\n");
 | 
			
		||||
| 
						 | 
				
			
			@ -77,73 +70,30 @@ struct SynthIce40Pass : public Pass {
 | 
			
		|||
		log("\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("The following commands are executed by this synthesis command:\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    begin:\n");
 | 
			
		||||
		log("        read_verilog -lib +/ice40/cells_sim.v\n");
 | 
			
		||||
		log("        hierarchy -check -top <top>\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    flatten:         (unless -noflatten)\n");
 | 
			
		||||
		log("        proc\n");
 | 
			
		||||
		log("        flatten\n");
 | 
			
		||||
		log("        tribuf -logic\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    coarse:\n");
 | 
			
		||||
		log("        synth -run coarse\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    bram:            (skip if -nobram)\n");
 | 
			
		||||
		log("        memory_bram -rules +/ice40/brams.txt\n");
 | 
			
		||||
		log("        techmap -map +/ice40/brams_map.v\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    fine:\n");
 | 
			
		||||
		log("        opt -fast -mux_undef -undriven -fine\n");
 | 
			
		||||
		log("        memory_map\n");
 | 
			
		||||
		log("        opt -undriven -fine\n");
 | 
			
		||||
		log("        techmap -map +/techmap.v [-map +/ice40/arith_map.v]\n");
 | 
			
		||||
		log("        abc -dff     (only if -retime)\n");
 | 
			
		||||
		log("        ice40_opt\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    map_ffs:\n");
 | 
			
		||||
		log("        dffsr2dff\n");
 | 
			
		||||
		log("        dff2dffe -direct-match $_DFF_*\n");
 | 
			
		||||
		log("        techmap -map +/ice40/cells_map.v\n");
 | 
			
		||||
		log("        opt_expr -mux_undef\n");
 | 
			
		||||
		log("        simplemap\n");
 | 
			
		||||
		log("        ice40_ffinit\n");
 | 
			
		||||
		log("        ice40_ffssr\n");
 | 
			
		||||
		log("        ice40_opt -full\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    map_luts:\n");
 | 
			
		||||
		log("        abc          (only if -abc2)\n");
 | 
			
		||||
		log("        ice40_opt    (only if -abc2)\n");
 | 
			
		||||
		log("        abc -lut 4\n");
 | 
			
		||||
		log("        clean\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    map_cells:\n");
 | 
			
		||||
		log("        techmap -map +/ice40/cells_map.v\n");
 | 
			
		||||
		log("        clean\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    check:\n");
 | 
			
		||||
		log("        hierarchy -check\n");
 | 
			
		||||
		log("        stat\n");
 | 
			
		||||
		log("        check -noinit\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    blif:\n");
 | 
			
		||||
		log("        write_blif -gates -attr -param <file-name>\n");
 | 
			
		||||
		log("\n");
 | 
			
		||||
		log("    edif:\n");
 | 
			
		||||
		log("        write_edif <file-name>\n");
 | 
			
		||||
		help_script();
 | 
			
		||||
		log("\n");
 | 
			
		||||
	}
 | 
			
		||||
	virtual void execute(std::vector<std::string> args, RTLIL::Design *design)
 | 
			
		||||
 | 
			
		||||
	string top_opt = "-auto-top";
 | 
			
		||||
	string blif_file, edif_file;
 | 
			
		||||
	bool nocarry, nobram, flatten, retime, abc2;
 | 
			
		||||
 | 
			
		||||
	virtual void clear_flags() YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		top_opt = "-auto-top";
 | 
			
		||||
		blif_file = "";
 | 
			
		||||
		edif_file = "";
 | 
			
		||||
		nocarry = false;
 | 
			
		||||
		nobram = false;
 | 
			
		||||
		flatten = true;
 | 
			
		||||
		retime = false;
 | 
			
		||||
		abc2 = false;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	virtual void execute(std::vector<std::string> args, RTLIL::Design *design) YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		std::string top_opt = "-auto-top";
 | 
			
		||||
		std::string run_from, run_to;
 | 
			
		||||
		std::string blif_file, edif_file;
 | 
			
		||||
		bool nocarry = false;
 | 
			
		||||
		bool nobram = false;
 | 
			
		||||
		bool flatten = true;
 | 
			
		||||
		bool retime = false;
 | 
			
		||||
		bool abc2 = false;
 | 
			
		||||
		clear_flags();
 | 
			
		||||
 | 
			
		||||
		size_t argidx;
 | 
			
		||||
		for (argidx = 1; argidx < args.size(); argidx++)
 | 
			
		||||
| 
						 | 
				
			
			@ -199,98 +149,101 @@ struct SynthIce40Pass : public Pass {
 | 
			
		|||
		if (!design->full_selection())
 | 
			
		||||
			log_cmd_error("This comannd only operates on fully selected designs!\n");
 | 
			
		||||
 | 
			
		||||
		bool active = run_from.empty();
 | 
			
		||||
 | 
			
		||||
		log_header("Executing SYNTH_ICE40 pass.\n");
 | 
			
		||||
		log_push();
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "begin"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "read_verilog -lib +/ice40/cells_sim.v");
 | 
			
		||||
			Pass::call(design, stringf("hierarchy -check %s", top_opt.c_str()));
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (flatten && check_label(active, run_from, run_to, "flatten"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "proc");
 | 
			
		||||
			Pass::call(design, "flatten");
 | 
			
		||||
			Pass::call(design, "tribuf -logic");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "coarse"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "synth -run coarse");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (!nobram && check_label(active, run_from, run_to, "bram"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "memory_bram -rules +/ice40/brams.txt");
 | 
			
		||||
			Pass::call(design, "techmap -map +/ice40/brams_map.v");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "fine"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "opt -fast -mux_undef -undriven -fine");
 | 
			
		||||
			Pass::call(design, "memory_map");
 | 
			
		||||
			Pass::call(design, "opt -undriven -fine");
 | 
			
		||||
			if (nocarry)
 | 
			
		||||
				Pass::call(design, "techmap");
 | 
			
		||||
			else
 | 
			
		||||
				Pass::call(design, "techmap -map +/techmap.v -map +/ice40/arith_map.v");
 | 
			
		||||
			if (retime)
 | 
			
		||||
				Pass::call(design, "abc -dff");
 | 
			
		||||
			Pass::call(design, "ice40_opt");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "map_ffs"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "dffsr2dff");
 | 
			
		||||
			Pass::call(design, "dff2dffe -direct-match $_DFF_*");
 | 
			
		||||
			Pass::call(design, "techmap -map +/ice40/cells_map.v");
 | 
			
		||||
			Pass::call(design, "opt_expr -mux_undef");
 | 
			
		||||
			Pass::call(design, "simplemap");
 | 
			
		||||
			Pass::call(design, "ice40_ffinit");
 | 
			
		||||
			Pass::call(design, "ice40_ffssr");
 | 
			
		||||
			Pass::call(design, "ice40_opt -full");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "map_luts"))
 | 
			
		||||
		{
 | 
			
		||||
			if (abc2) {
 | 
			
		||||
				Pass::call(design, "abc");
 | 
			
		||||
				Pass::call(design, "ice40_opt");
 | 
			
		||||
			}
 | 
			
		||||
			Pass::call(design, "abc -lut 4");
 | 
			
		||||
			Pass::call(design, "clean");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "map_cells"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "techmap -map +/ice40/cells_map.v");
 | 
			
		||||
			Pass::call(design, "clean");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "check"))
 | 
			
		||||
		{
 | 
			
		||||
			Pass::call(design, "hierarchy -check");
 | 
			
		||||
			Pass::call(design, "stat");
 | 
			
		||||
			Pass::call(design, "check -noinit");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "blif"))
 | 
			
		||||
		{
 | 
			
		||||
			if (!blif_file.empty())
 | 
			
		||||
				Pass::call(design, stringf("write_blif -gates -attr -param %s", blif_file.c_str()));
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label(active, run_from, run_to, "edif"))
 | 
			
		||||
		{
 | 
			
		||||
			if (!edif_file.empty())
 | 
			
		||||
				Pass::call(design, stringf("write_edif %s", edif_file.c_str()));
 | 
			
		||||
		}
 | 
			
		||||
		run_script(design, run_from, run_to);
 | 
			
		||||
 | 
			
		||||
		log_pop();
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	virtual void script() YS_OVERRIDE
 | 
			
		||||
	{
 | 
			
		||||
		if (check_label("begin"))
 | 
			
		||||
		{
 | 
			
		||||
			run("read_verilog -lib +/ice40/cells_sim.v");
 | 
			
		||||
			run(stringf("hierarchy -check %s", help_mode ? "-top <top>" : top_opt.c_str()));
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (flatten && check_label("flatten", "(unless -noflatten)"))
 | 
			
		||||
		{
 | 
			
		||||
			run("proc");
 | 
			
		||||
			run("flatten");
 | 
			
		||||
			run("tribuf -logic");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("coarse"))
 | 
			
		||||
		{
 | 
			
		||||
			run("synth -run coarse");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (!nobram && check_label("bram", "(skip if -nobram)"))
 | 
			
		||||
		{
 | 
			
		||||
			run("memory_bram -rules +/ice40/brams.txt");
 | 
			
		||||
			run("techmap -map +/ice40/brams_map.v");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("fine"))
 | 
			
		||||
		{
 | 
			
		||||
			run("opt -fast -mux_undef -undriven -fine");
 | 
			
		||||
			run("memory_map");
 | 
			
		||||
			run("opt -undriven -fine");
 | 
			
		||||
			if (nocarry)
 | 
			
		||||
				run("techmap");
 | 
			
		||||
			else
 | 
			
		||||
				run("techmap -map +/techmap.v -map +/ice40/arith_map.v");
 | 
			
		||||
			if (retime || help_mode)
 | 
			
		||||
				run("abc -dff", "(only if -retime)");
 | 
			
		||||
			run("ice40_opt");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("map_ffs"))
 | 
			
		||||
		{
 | 
			
		||||
			run("dffsr2dff");
 | 
			
		||||
			run("dff2dffe -direct-match $_DFF_*");
 | 
			
		||||
			run("techmap -map +/ice40/cells_map.v");
 | 
			
		||||
			run("opt_expr -mux_undef");
 | 
			
		||||
			run("simplemap");
 | 
			
		||||
			run("ice40_ffinit");
 | 
			
		||||
			run("ice40_ffssr");
 | 
			
		||||
			run("ice40_opt -full");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("map_luts"))
 | 
			
		||||
		{
 | 
			
		||||
			if (abc2 || help_mode) {
 | 
			
		||||
				run("abc", "      (only if -abc2)");
 | 
			
		||||
				run("ice40_opt", "(only if -abc2)");
 | 
			
		||||
			}
 | 
			
		||||
			run("abc -lut 4");
 | 
			
		||||
			run("clean");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("map_cells"))
 | 
			
		||||
		{
 | 
			
		||||
			run("techmap -map +/ice40/cells_map.v");
 | 
			
		||||
			run("clean");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("check"))
 | 
			
		||||
		{
 | 
			
		||||
			run("hierarchy -check");
 | 
			
		||||
			run("stat");
 | 
			
		||||
			run("check -noinit");
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("blif"))
 | 
			
		||||
		{
 | 
			
		||||
			if (!blif_file.empty() || help_mode)
 | 
			
		||||
				run(stringf("write_blif -gates -attr -param %s", help_mode ? "<file-name>" : blif_file.c_str()));
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if (check_label("edif"))
 | 
			
		||||
		{
 | 
			
		||||
			if (!edif_file.empty() || help_mode)
 | 
			
		||||
				run(stringf("write_edif %s", help_mode ? "<file-name>" : edif_file.c_str()));
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
} SynthIce40Pass;
 | 
			
		||||
 | 
			
		||||
PRIVATE_NAMESPACE_END
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue