mirror of
				https://github.com/YosysHQ/yosys
				synced 2025-10-31 11:42:30 +00:00 
			
		
		
		
	machxo2: Create basic techlibs and synth_machxo2 pass.
This commit is contained in:
		
							parent
							
								
									cc7d18d29a
								
							
						
					
					
						commit
						88c8f81260
					
				
					 4 changed files with 320 additions and 0 deletions
				
			
		
							
								
								
									
										5
									
								
								techlibs/machxo2/Makefile.inc
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										5
									
								
								techlibs/machxo2/Makefile.inc
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,5 @@ | ||||||
|  | 
 | ||||||
|  | OBJS += techlibs/machxo2/synth_machxo2.o | ||||||
|  | 
 | ||||||
|  | $(eval $(call add_share_file,share/machxo2,techlibs/machxo2/cells_map.v)) | ||||||
|  | $(eval $(call add_share_file,share/machxo2,techlibs/machxo2/cells_sim.v)) | ||||||
							
								
								
									
										23
									
								
								techlibs/machxo2/cells_map.v
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										23
									
								
								techlibs/machxo2/cells_map.v
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,23 @@ | ||||||
|  | module \$lut (A, Y); | ||||||
|  | 	parameter WIDTH = 0; | ||||||
|  | 	parameter LUT = 0; | ||||||
|  | 	input [WIDTH-1:0] A; | ||||||
|  | 	output Y; | ||||||
|  | 
 | ||||||
|  | 	localparam rep = 1<<(4-WIDTH); | ||||||
|  | 	wire [3:0] I; | ||||||
|  | 
 | ||||||
|  | 	generate | ||||||
|  | 		if(WIDTH == 2) begin | ||||||
|  | 			assign I = {1'b0, 1'b0, A[1], A[0]}; | ||||||
|  | 		end else if(WIDTH == 3) begin | ||||||
|  | 			assign I = {1'b0, A[2], A[1], A[0]}; | ||||||
|  | 		end else if(WIDTH == 4) begin | ||||||
|  | 			assign I = {A[3], A[2], A[1], A[0]}; | ||||||
|  | 		end | ||||||
|  | 	endgenerate | ||||||
|  | 
 | ||||||
|  | 	LUT4 #(.INIT({rep{LUT}})) _TECHMAP_REPLACE_ (.A(I[0]), .B(I[1]), .C(I[2]), .D(I[3]), .F(Y)); | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
|  | module  \$_DFF_P_ (input D, C, output Q); FACADE_FF #(.CEMUX("1"), .CLKMUX("CLK"), .LSRMUX("LSR"), .REGSET("RESET")) _TECHMAP_REPLACE_ (.CLK(C), .LSR(1'b0), .D(D), .Q(Q)); endmodule | ||||||
							
								
								
									
										62
									
								
								techlibs/machxo2/cells_sim.v
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										62
									
								
								techlibs/machxo2/cells_sim.v
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,62 @@ | ||||||
|  | module LUT4 #( | ||||||
|  | 	parameter [15:0] INIT = 0 | ||||||
|  | ) ( | ||||||
|  | 	input A, B, C, D, | ||||||
|  | 	output F | ||||||
|  | ); | ||||||
|  | 	wire [3:0] I; | ||||||
|  | 	wire [3:0] I_pd; | ||||||
|  | 
 | ||||||
|  | 	genvar ii; | ||||||
|  | 	generate | ||||||
|  | 		for (ii = 0; ii < 4; ii = ii + 1'b1) | ||||||
|  | 			assign I_pd[ii] = (I[ii] === 1'bz) ? 1'b0 : I[ii]; | ||||||
|  | 	endgenerate | ||||||
|  | 
 | ||||||
|  | 	assign I = {D, C, B, A}; | ||||||
|  | 	assign F = INIT[I_pd]; | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
|  | module FACADE_FF #( | ||||||
|  | 	parameter GSR = "ENABLED", | ||||||
|  | 	parameter CEMUX = "1", | ||||||
|  | 	parameter CLKMUX = "0", | ||||||
|  | 	parameter LSRMUX = "LSR", | ||||||
|  | 	parameter LSRONMUX = "LSRMUX", | ||||||
|  | 	parameter SRMODE = "LSR_OVER_CE", | ||||||
|  | 	parameter REGSET = "SET" | ||||||
|  | ) ( | ||||||
|  | 	input CLK, D, LSR, CE, | ||||||
|  | 	output reg Q | ||||||
|  | ); | ||||||
|  | 
 | ||||||
|  | 	wire muxce; | ||||||
|  | 	generate | ||||||
|  | 		case (CEMUX) | ||||||
|  | 			"1": assign muxce = 1'b1; | ||||||
|  | 			"0": assign muxce = 1'b0; | ||||||
|  | 			"INV": assign muxce = ~CE; | ||||||
|  | 			default: assign muxce = CE; | ||||||
|  | 		endcase | ||||||
|  | 	endgenerate | ||||||
|  | 
 | ||||||
|  | 	wire muxlsr = (LSRMUX == "INV") ? ~LSR : LSR; | ||||||
|  | 	wire muxclk = (CLKMUX == "INV") ? ~CLK : CLK; | ||||||
|  | 	assign srval = (REGSET == "SET") ? 1'b1 : 1'b0; | ||||||
|  | 
 | ||||||
|  | 	generate | ||||||
|  | 		if (SRMODE == "ASYNC") begin | ||||||
|  | 			always @(posedge muxclk, posedge muxlsr) | ||||||
|  | 				if (muxlsr) | ||||||
|  | 					Q <= srval; | ||||||
|  | 				else if (muxce) | ||||||
|  | 					Q <= DI; | ||||||
|  | 		end else begin | ||||||
|  | 			always @(posedge muxclk) | ||||||
|  | 				if (muxlsr) | ||||||
|  | 					Q <= srval; | ||||||
|  | 				else if (muxce) | ||||||
|  | 					Q <= DI; | ||||||
|  | 		end | ||||||
|  | 	endgenerate | ||||||
|  | endmodule | ||||||
							
								
								
									
										230
									
								
								techlibs/machxo2/synth_machxo2.cc
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										230
									
								
								techlibs/machxo2/synth_machxo2.cc
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,230 @@ | ||||||
|  | /*
 | ||||||
|  |  *  yosys -- Yosys Open SYnthesis Suite | ||||||
|  |  * | ||||||
|  |  *  Copyright (C) 2020 William D. Jones <wjones@wdj-consulting.com> | ||||||
|  |  * | ||||||
|  |  *  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/register.h" | ||||||
|  | #include "kernel/celltypes.h" | ||||||
|  | #include "kernel/rtlil.h" | ||||||
|  | #include "kernel/log.h" | ||||||
|  | 
 | ||||||
|  | USING_YOSYS_NAMESPACE | ||||||
|  | PRIVATE_NAMESPACE_BEGIN | ||||||
|  | 
 | ||||||
|  | struct SynthMachXO2Pass : public ScriptPass | ||||||
|  | { | ||||||
|  | 	SynthMachXO2Pass() : ScriptPass("synth_machxo2", "synthesis for MachXO2 FPGAs") { } | ||||||
|  | 
 | ||||||
|  | 	void help() override | ||||||
|  | 	{ | ||||||
|  | 		//   |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|
 | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    synth_machxo2 [options]\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("This command runs synthesis for ECP5 FPGAs.\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -top <module>\n"); | ||||||
|  | 		log("        use the specified module as top module\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -blif <file>\n"); | ||||||
|  | 		log("        write the design to the specified BLIF file. writing of an output file\n"); | ||||||
|  | 		log("        is omitted if this parameter is not specified.\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -edif <file>\n"); | ||||||
|  | 		log("        write the design to the specified EDIF file. writing of an output file\n"); | ||||||
|  | 		log("        is omitted if this parameter is not specified.\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -json <file>\n"); | ||||||
|  | 		log("        write the design to the specified JSON file. writing of an output file\n"); | ||||||
|  | 		log("        is omitted if this parameter is not specified.\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -run <from_label>:<to_label>\n"); | ||||||
|  | 		log("        only run the commands between the labels (see below). an empty\n"); | ||||||
|  | 		log("        from label is synonymous to 'begin', and empty to label is\n"); | ||||||
|  | 		log("        synonymous to the end of the command list.\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -noflatten\n"); | ||||||
|  | 		log("        do not flatten design before synthesis\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("    -vpr\n"); | ||||||
|  | 		log("        generate an output netlist (and BLIF file) suitable for VPR\n"); | ||||||
|  | 		log("        (this feature is experimental and incomplete)\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("\n"); | ||||||
|  | 		log("The following commands are executed by this synthesis command:\n"); | ||||||
|  | 		help_script(); | ||||||
|  | 		log("\n"); | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	string top_opt, blif_file, edif_file, json_file; | ||||||
|  | 	bool flatten, vpr; | ||||||
|  | 
 | ||||||
|  | 	void clear_flags() override | ||||||
|  | 	{ | ||||||
|  | 		top_opt = "-auto-top"; | ||||||
|  | 		blif_file = ""; | ||||||
|  | 		edif_file = ""; | ||||||
|  | 		json_file = ""; | ||||||
|  | 		flatten = true; | ||||||
|  | 		vpr = false; | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	void execute(std::vector<std::string> args, RTLIL::Design *design) override | ||||||
|  | 	{ | ||||||
|  | 		string run_from, run_to; | ||||||
|  | 		clear_flags(); | ||||||
|  | 
 | ||||||
|  | 		size_t argidx; | ||||||
|  | 		for (argidx = 1; argidx < args.size(); argidx++) | ||||||
|  | 		{ | ||||||
|  | 			if (args[argidx] == "-top" && argidx+1 < args.size()) { | ||||||
|  | 				top_opt = "-top " + args[++argidx]; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-blif" && argidx+1 < args.size()) { | ||||||
|  | 				blif_file = args[++argidx]; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-edif" && argidx+1 < args.size()) { | ||||||
|  | 				edif_file = args[++argidx]; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-json" && argidx+1 < args.size()) { | ||||||
|  | 				json_file = args[++argidx]; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-run" && argidx+1 < args.size()) { | ||||||
|  | 				size_t pos = args[argidx+1].find(':'); | ||||||
|  | 				if (pos == std::string::npos) | ||||||
|  | 					break; | ||||||
|  | 				run_from = args[++argidx].substr(0, pos); | ||||||
|  | 				run_to = args[argidx].substr(pos+1); | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-flatten") { | ||||||
|  | 				flatten = true; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-noflatten") { | ||||||
|  | 				flatten = false; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			if (args[argidx] == "-vpr") { | ||||||
|  | 				vpr = true; | ||||||
|  | 				continue; | ||||||
|  | 			} | ||||||
|  | 			break; | ||||||
|  | 		} | ||||||
|  | 		extra_args(args, argidx, design); | ||||||
|  | 
 | ||||||
|  | 		if (!design->full_selection()) | ||||||
|  | 			log_cmd_error("This command only operates on fully selected designs!\n"); | ||||||
|  | 
 | ||||||
|  | 		log_header(design, "Executing SYNTH_MACHXO2 pass.\n"); | ||||||
|  | 		log_push(); | ||||||
|  | 
 | ||||||
|  | 		run_script(design, run_from, run_to); | ||||||
|  | 
 | ||||||
|  | 		log_pop(); | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	void script() override | ||||||
|  | 	{ | ||||||
|  | 		if (check_label("begin")) | ||||||
|  | 		{ | ||||||
|  | 			run("read_verilog -lib +/machxo2/cells_sim.v"); | ||||||
|  | 			run(stringf("hierarchy -check %s", help_mode ? "-top <top>" : top_opt.c_str())); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("flatten", "(unless -noflatten)")) | ||||||
|  | 		{ | ||||||
|  | 			if (flatten) { | ||||||
|  | 				run("proc"); | ||||||
|  | 				run("flatten"); | ||||||
|  | 				run("tribuf -logic"); | ||||||
|  | 				run("deminout"); | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("coarse")) | ||||||
|  | 		{ | ||||||
|  | 			run("synth -run coarse"); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("fine")) | ||||||
|  | 		{ | ||||||
|  | 			run("memory_map"); | ||||||
|  | 			run("opt -full"); | ||||||
|  | 			run("techmap -map +/techmap.v"); | ||||||
|  | 			run("opt -fast"); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("map_ffs")) | ||||||
|  | 		{ | ||||||
|  | 			run("dfflegalize -cell $_DFF_P_ 0"); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("map_luts")) | ||||||
|  | 		{ | ||||||
|  | 			run("abc -lut 4 -dress"); | ||||||
|  | 			run("clean"); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("map_cells")) | ||||||
|  | 		{ | ||||||
|  | 			run("techmap -map +/machxo2/cells_map.v"); | ||||||
|  | 			run("clean"); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("check")) | ||||||
|  | 		{ | ||||||
|  | 			run("hierarchy -check"); | ||||||
|  | 			run("stat"); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("blif")) | ||||||
|  | 		{ | ||||||
|  | 			if (!blif_file.empty() || help_mode) { | ||||||
|  | 				if (vpr || help_mode) { | ||||||
|  | 					run(stringf("opt_clean -purge"), | ||||||
|  | 							"                                 (vpr mode)"); | ||||||
|  | 					run(stringf("write_blif -attr -cname -conn -param %s", | ||||||
|  | 							help_mode ? "<file-name>" : blif_file.c_str()), | ||||||
|  | 							" (vpr mode)"); | ||||||
|  | 				} | ||||||
|  | 				if (!vpr) | ||||||
|  | 					run(stringf("write_blif -gates -attr -param %s", | ||||||
|  | 							help_mode ? "<file-name>" : blif_file.c_str()), | ||||||
|  | 							"       (non-vpr mode)"); | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("edif")) | ||||||
|  | 		{ | ||||||
|  | 			if (!edif_file.empty() || help_mode) | ||||||
|  | 				run(stringf("write_edif %s", help_mode ? "<file-name>" : edif_file.c_str())); | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (check_label("json")) | ||||||
|  | 		{ | ||||||
|  | 			if (!json_file.empty() || help_mode) | ||||||
|  | 				run(stringf("write_json %s", help_mode ? "<file-name>" : json_file.c_str())); | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | } SynthMachXO2Pass; | ||||||
|  | 
 | ||||||
|  | PRIVATE_NAMESPACE_END | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue