diff --git a/Makefile b/Makefile index 2f191fd..2723cff 100644 --- a/Makefile +++ b/Makefile @@ -68,8 +68,8 @@ OPENOCD_DEVICE_CONFIG=openocd/LFE5UM5G-85F.cfg synth: chiselwatt.bit -chiselwatt.json: $(verilog_files) insns.hex pll_ecp5_evn.v toplevel.v - $(YOSYS) -p "read_verilog -sv pll_ecp5_evn.v toplevel.v Core.v MemoryBlackBox.v; synth_ecp5 -json $@ -top toplevel" +chiselwatt.json: $(verilog_files) insns.hex pll/pll_ehxplll.v toplevel.v + $(YOSYS) -p "read_verilog -sv pll/pll_ehxplll.v toplevel.v Core.v MemoryBlackBox.v; synth_ecp5 -json $@ -top toplevel" chiselwatt_out.config: chiselwatt.json $(LPF) $(NEXTPNR) --json $< --lpf $(LPF) --textcfg $@ $(NEXTPNR_FLAGS) --package $(PACKAGE) diff --git a/chiselwatt.core b/chiselwatt.core new file mode 100644 index 0000000..edcafb3 --- /dev/null +++ b/chiselwatt.core @@ -0,0 +1,45 @@ +CAPI=2: + +name : ::chiselwatt:0 + +filesets: + core: + files: + - Core.v + - MemoryBlackBox.v + - toplevel.v + - insns.hex : {copyto : insns.hex, file_type : user} + file_type : verilogSource + + cmod_a7-35: + files: + - constraints/cmod_a7-35.xdc : {file_type : xdc} + - pll/pll_mmcme2.v : {file_type : verilogSource} + + ecp5-evn: + files: + - constraints/ecp5-evn.lpf : {file_type : LPF} + - pll/pll_ehxplll.v : {file_type : verilogSource} + +targets: + cmod_a7-35: + default_tool: vivado + filesets: [core, cmod_a7-35] + parameters : + - RESET_LOW=false + tools: + vivado: {part : xc7a35tcpg236-1} + toplevel : toplevel + + ecp5-evn: + default_tool: diamond + filesets: [core, ecp5-evn] + tools: + diamond: {part: LFE5U-85F-8BG381I} + toplevel : toplevel + +parameters: + RESET_LOW: + datatype : bool + description : External reset button polarity + paramtype : generic diff --git a/constraints/cmod_a7-35.xdc b/constraints/cmod_a7-35.xdc new file mode 100644 index 0000000..1048145 --- /dev/null +++ b/constraints/cmod_a7-35.xdc @@ -0,0 +1,20 @@ +## Clock signal 12 MHz +set_property -dict { PACKAGE_PIN L17 IOSTANDARD LVCMOS33 } [get_ports { clock }]; +create_clock -add -name sys_clk_pin -period 83.33 -waveform {0 41.66} [get_ports {clock}]; + +set_property -dict { PACKAGE_PIN J18 IOSTANDARD LVCMOS33 } [get_ports { io_tx }]; +set_property -dict { PACKAGE_PIN J17 IOSTANDARD LVCMOS33 } [get_ports { io_rx }]; + +set_property -dict { PACKAGE_PIN A18 IOSTANDARD LVCMOS33 } [get_ports { reset }]; + +set_property -dict { PACKAGE_PIN A17 IOSTANDARD LVCMOS33 } [get_ports { io_terminate }]; + +set_property -dict { PACKAGE_PIN C16 IOSTANDARD LVCMOS33 } [get_ports { io_ledB }]; +set_property -dict { PACKAGE_PIN B17 IOSTANDARD LVCMOS33 } [get_ports { io_ledC }]; + +set_property CONFIG_VOLTAGE 3.3 [current_design] +set_property CFGBVS VCCO [current_design] + +set_property BITSTREAM.GENERAL.COMPRESS TRUE [current_design] +set_property BITSTREAM.CONFIG.CONFIGRATE 33 [current_design] +set_property CONFIG_MODE SPIx4 [current_design] diff --git a/pll/pll_bypass.v b/pll/pll_bypass.v new file mode 100644 index 0000000..30bff07 --- /dev/null +++ b/pll/pll_bypass.v @@ -0,0 +1,12 @@ +module pll( + input clki, + output clko, + output lock +); + + always @* begin + lock <= 1; + clko <= clki; + end + +endmodule diff --git a/pll/pll_ehxplll.v b/pll/pll_ehxplll.v new file mode 100644 index 0000000..0398fe2 --- /dev/null +++ b/pll/pll_ehxplll.v @@ -0,0 +1,36 @@ +module pll( + input clki, + output clko, + output lock +); + (* ICP_CURRENT="12" *) (* LPF_RESISTOR="8" *) (* MFG_ENABLE_FILTEROPAMP="1" *) (* MFG_GMCREF_SEL="2" *) + + EHXPLLL #( + .PLLRST_ENA("DISABLED"), + .INTFB_WAKE("DISABLED"), + .STDBY_ENABLE("DISABLED"), + .DPHASE_SOURCE("DISABLED"), + .CLKOP_FPHASE(0), + .CLKOP_CPHASE(11), + .OUTDIVIDER_MUXA("DIVA"), + .CLKOP_ENABLE("ENABLED"), + .CLKOP_DIV(12), + .CLKFB_DIV(25), + .CLKI_DIV(6), + .FEEDBK_PATH("CLKOP") + ) pll_i ( + .CLKI(clki), + .CLKFB(clko), + .CLKOP(clko), + .LOCK(lock), + .RST(1'b0), + .STDBY(1'b0), + .PHASESEL0(1'b0), + .PHASESEL1(1'b0), + .PHASEDIR(1'b0), + .PHASESTEP(1'b0), + .PLLWAKESYNC(1'b0), + .ENCLKOP(1'b0) + ); + +endmodule diff --git a/pll/pll_mmcme2.v b/pll/pll_mmcme2.v new file mode 100644 index 0000000..3b188de --- /dev/null +++ b/pll/pll_mmcme2.v @@ -0,0 +1,26 @@ +module pll( + input clki, + output clko, + output lock +); + + wire clkfb; + + MMCME2_BASE #( + .BANDWIDTH("OPTIMIZED"), + .CLKFBOUT_MULT_F(50.0), + .CLKIN1_PERIOD(83.33), + .CLKOUT0_DIVIDE_F(12.0), + .DIVCLK_DIVIDE(1), + .STARTUP_WAIT("FALSE") + ) MMCME2_BASE_inst ( + .CLKOUT0(clko), + .CLKFBOUT(clkfb), + .LOCKED(lock), + .CLKIN1(clki), + .PWRDWN(1'b0), + .RST(1'b0), + .CLKFBIN(clkfb) + ); + +endmodule diff --git a/pll_ecp5_evn.v b/pll_ecp5_evn.v deleted file mode 100644 index bc032ba..0000000 --- a/pll_ecp5_evn.v +++ /dev/null @@ -1,30 +0,0 @@ -module pll_ecp5_evn(input clki, output clko, output lock); - (* ICP_CURRENT="12" *) (* LPF_RESISTOR="8" *) (* MFG_ENABLE_FILTEROPAMP="1" *) (* MFG_GMCREF_SEL="2" *) - EHXPLLL #( - .PLLRST_ENA("DISABLED"), - .INTFB_WAKE("DISABLED"), - .STDBY_ENABLE("DISABLED"), - .DPHASE_SOURCE("DISABLED"), - .CLKOP_FPHASE(0), - .CLKOP_CPHASE(11), - .OUTDIVIDER_MUXA("DIVA"), - .CLKOP_ENABLE("ENABLED"), - .CLKOP_DIV(12), - .CLKFB_DIV(25), - .CLKI_DIV(6), - .FEEDBK_PATH("CLKOP") - ) pll_i ( - .CLKI(clki), - .CLKFB(clko), - .CLKOP(clko), - .LOCK(lock), - .RST(1'b0), - .STDBY(1'b0), - .PHASESEL0(1'b0), - .PHASESEL1(1'b0), - .PHASEDIR(1'b0), - .PHASESTEP(1'b0), - .PLLWAKESYNC(1'b0), - .ENCLKOP(1'b0) - ); -endmodule diff --git a/toplevel.v b/toplevel.v index f3738f9..f567bb2 100644 --- a/toplevel.v +++ b/toplevel.v @@ -1,47 +1,45 @@ -module toplevel( - input clock, - input reset, - output io_tx, - input io_rx, - output io_terminate, - output io_ledB, - output io_ledC +module toplevel #( + parameter RESET_LOW = 1 +) ( + input clock, + input reset, + output io_tx, + input io_rx, + output io_terminate, + output io_ledB, + output io_ledC ); -wire clock_out; -reg reset_out; -wire lock; + wire clock_out; + reg reset_out; + wire lock; -pll_ecp5_evn pll( - .clki(clock), - .clko(clock_out), - .lock(lock) -); + pll chiselwatt_pll( + .clki(clock), + .clko(clock_out), + .lock(lock) + ); -Core core( - .clock(clock_out), - .reset(reset_out), - .io_tx(io_tx), - .io_rx(io_rx), - .io_terminate(io_terminate), - .io_ledB(io_ledB), - .io_ledC(io_ledC) -); + Core core( + .clock(clock_out), + .reset(reset_out), + .io_tx(io_tx), + .io_rx(io_rx), + .io_terminate(io_terminate), + .io_ledB(io_ledB), + .io_ledC(io_ledC) + ); -reg [21:0] cnt = ~0; + reg [21:0] cnt = ~0; -always@(posedge clock) -begin - if (~lock || ~reset) - begin - cnt <= ~0; - end - else if (cnt != 0) - begin - cnt <= cnt - 1; - end + always@(posedge clock) begin + if (~lock || (reset ^ RESET_LOW)) begin + cnt <= ~0; + end else if (cnt != 0) begin + cnt <= cnt - 1; + end - reset_out <= |cnt; -end + reset_out <= |cnt; + end endmodule