Skip to content

Commit 5267e9a

Browse files
committed
Add PicoSoC GateMate demo
1 parent f00a88c commit 5267e9a

File tree

6 files changed

+330
-6
lines changed

6 files changed

+330
-6
lines changed

picosoc/Makefile

+41
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,45 @@ icebreaker_fw.hex: icebreaker_fw.elf
9494
icebreaker_fw.bin: icebreaker_fw.elf
9595
$(CROSS)objcopy -O binary icebreaker_fw.elf icebreaker_fw.bin
9696

97+
# ---- GateMate Evaluation Board ----
98+
99+
gatematesim: gatemate_tb.vvp gatemate_fw.hex
100+
vvp -N $< +firmware=gatemate_fw.hex
101+
102+
gatematesynsim: gatemate_syn_tb.vvp gatemate_fw.hex
103+
vvp -N $< +firmware=gatemate_fw.hex
104+
105+
gatemate_synth.v: gatemate.v spimemio.v simpleuart.v picosoc.v ../picorv32.v
106+
yosys -ql gatemate_synth.log -p 'synth_gatemate -top gatemate -nomx8 -vlog gatemate_synth.v' $^
107+
108+
gatemate_tb.vvp: gatemate_tb.v gatemate.v spimemio.v simpleuart.v picosoc.v ../picorv32.v spiflash.v
109+
iverilog -s testbench -o $@ $^ `yosys-config --datdir/gatemate/cells_sim.v`
110+
111+
gatemate_syn_tb.vvp: gatemate_tb.v gatemate_synth.v spiflash.v
112+
iverilog -s testbench -o $@ $^ `yosys-config --datdir/gatemate/cells_sim.v`
113+
114+
gatemate_00.cfg.bit: gatemate.ccf gatemate_synth.v
115+
$(CC_TOOL)/p_r -i gatemate_synth.v -o gatemate -ccf gatemate.ccf +uCIO -cCP > gatemate_impl.log
116+
117+
gatemateflash: gatemate_00.cfg.bit gatemate_fw.bin
118+
openFPGALoader -b gatemate_evb_spi -f gatemate_00.cfg.bit
119+
openFPGALoader -b gatemate_evb_spi -f -o 1048576 gatemate_fw.bin
120+
121+
gatemateflash_fw: gatemate_fw.bin
122+
openFPGALoader -b gatemate_evb_spi -f -o 1048576 gatemate_fw.bin
123+
124+
gatemate_sections.lds: sections.lds
125+
$(CROSS)cpp -P -DGATEMATE -o $@ $^
126+
127+
gatemate_fw.elf: gatemate_sections.lds start.s firmware.c
128+
$(CROSS)gcc $(CFLAGS) -DGATEMATE -mabi=ilp32 -march=rv32ic -Wl,-Bstatic,-T,gatemate_sections.lds,--strip-debug -ffreestanding -nostdlib -o gatemate_fw.elf start.s firmware.c
129+
130+
gatemate_fw.hex: gatemate_fw.elf
131+
$(CROSS)objcopy -O verilog gatemate_fw.elf gatemate_fw.hex
132+
133+
gatemate_fw.bin: gatemate_fw.elf
134+
$(CROSS)objcopy -O binary gatemate_fw.elf gatemate_fw.bin
135+
97136
# ---- Testbench for SPI Flash Model ----
98137

99138
spiflash_tb: spiflash_tb.vvp icebreaker_fw.hex
@@ -117,7 +156,9 @@ clean:
117156
rm -f hx8kdemo_syn.v hx8kdemo_syn_tb.vvp hx8kdemo_tb.vvp
118157
rm -f icebreaker.json icebreaker.log icebreaker.asc icebreaker.rpt icebreaker.bin
119158
rm -f icebreaker_syn.v icebreaker_syn_tb.vvp icebreaker_tb.vvp
159+
rm -f *.prn *.used *.pin *.place *.cdf *.id *.pos *.pathes *.ref* *.sdf *.cfg* *.net gatemate_synth.log gatemate_impl.log *_00.v gatemate_synth.v lut*.txt
120160

121161
.PHONY: spiflash_tb clean
122162
.PHONY: hx8kprog hx8kprog_fw hx8ksim hx8ksynsim
123163
.PHONY: icebprog icebprog_fw icebsim icebsynsim
164+
.PHONY: gatemateflash gatemateflash_fw gatematesim gatematesynsim

picosoc/firmware.c

+13-5
Original file line numberDiff line numberDiff line change
@@ -22,10 +22,15 @@
2222

2323
#ifdef ICEBREAKER
2424
# define MEM_TOTAL 0x20000 /* 128 KB */
25+
# define CPU_FREQ 12000000
2526
#elif HX8KDEMO
2627
# define MEM_TOTAL 0x200 /* 2 KB */
28+
# define CPU_FREQ 12000000
29+
#elif GATEMATE
30+
# define MEM_TOTAL 0x800
31+
# define CPU_FREQ 10000000
2732
#else
28-
# error "Set -DICEBREAKER or -DHX8KDEMO when compiling firmware.c"
33+
# error "Set -DICEBREAKER or -DHX8KDEMO or -DGATEMATE when compiling firmware.c"
2934
#endif
3035

3136
// a pointer to this is a null pointer, but the compiler does not
@@ -110,7 +115,7 @@ void set_flash_mode_qddr()
110115
}
111116
#endif
112117

113-
#ifdef ICEBREAKER
118+
#if defined(ICEBREAKER) || defined(GATEMATE)
114119
void set_flash_qspi_flag()
115120
{
116121
uint8_t buffer[8];
@@ -386,7 +391,7 @@ void cmd_read_flash_regs()
386391
}
387392
#endif
388393

389-
#ifdef ICEBREAKER
394+
#if defined(ICEBREAKER) || defined(GATEMATE)
390395
uint8_t cmd_read_flash_reg(uint8_t cmd)
391396
{
392397
uint8_t buffer[2] = {cmd, 0};
@@ -610,7 +615,7 @@ void cmd_benchmark_all()
610615
}
611616
#endif
612617

613-
#ifdef ICEBREAKER
618+
#if defined(ICEBREAKER) || defined(GATEMATE)
614619
void cmd_benchmark_all()
615620
{
616621
uint32_t instns = 0;
@@ -666,7 +671,7 @@ void cmd_echo()
666671
void main()
667672
{
668673
reg_leds = 31;
669-
reg_uart_clkdiv = 104;
674+
reg_uart_clkdiv = 87; // 104; (CPU_FREQ / 115200);
670675
print("Booting..\n");
671676

672677
reg_leds = 63;
@@ -683,6 +688,9 @@ void main()
683688
print(" |_| |_|\\___\\___/____/ \\___/ \\____|\n");
684689
print("\n");
685690

691+
print("Core frequency: ");
692+
print_dec(CPU_FREQ / 1000000);
693+
print(" MHz\n");
686694
print("Total memory: ");
687695
print_dec(MEM_TOTAL / 1024);
688696
print(" KiB\n");

picosoc/gatemate.ccf

+26
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
# picosoc pin file
2+
3+
## 10 MHz clock
4+
Pin_in "clk" Loc = "IO_SB_A8" | SCHMITT_TRIGGER=true;
5+
6+
## UART
7+
Pin_out "ser_tx" Loc = "IO_NB_B5"; # Pmod B: IO D4
8+
Pin_in "ser_rx" Loc = "IO_NB_B6"; # Pmod B: IO D5
9+
10+
## Serial flash (use +uCIO to enable bank)
11+
Pin_out "flash_csb" Loc = "IO_WA_A8";
12+
Pin_out "flash_clk" Loc = "IO_WA_B8";
13+
Pin_inout "flash_io0" Loc = "IO_WA_B7";
14+
Pin_inout "flash_io1" Loc = "IO_WA_A7";
15+
Pin_inout "flash_io2" Loc = "IO_WA_B6";
16+
Pin_inout "flash_io3" Loc = "IO_WA_A6";
17+
18+
## GPIO
19+
Pin_out "led[0]" Loc = "IO_EB_B1";
20+
Pin_out "led[1]" Loc = "IO_EB_B2";
21+
Pin_out "led[2]" Loc = "IO_EB_B3";
22+
Pin_out "led[3]" Loc = "IO_EB_B4";
23+
Pin_out "led[4]" Loc = "IO_EB_B5";
24+
Pin_out "led[5]" Loc = "IO_EB_B6";
25+
Pin_out "led[6]" Loc = "IO_EB_B7";
26+
Pin_out "led[7]" Loc = "IO_EB_B8";

picosoc/gatemate.v

+134
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,134 @@
1+
/*
2+
* PicoSoC - A simple example SoC using PicoRV32
3+
*
4+
* Copyright (C) 2017 Claire Xenia Wolf <claire@yosyshq.com>
5+
* Copyright (C) 2023 Cologne Chip AG <support@colognechip.com>
6+
*
7+
* Permission to use, copy, modify, and/or distribute this software for any
8+
* purpose with or without fee is hereby granted, provided that the above
9+
* copyright notice and this permission notice appear in all copies.
10+
*
11+
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12+
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13+
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14+
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15+
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16+
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
17+
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18+
*
19+
*/
20+
21+
`ifdef PICOSOC_V
22+
`error "gatemate.v must be read before picosoc.v!"
23+
`endif
24+
25+
module gatemate (
26+
input clk,
27+
28+
output ser_tx,
29+
input ser_rx,
30+
31+
output [7:0] led,
32+
33+
output flash_csb,
34+
output flash_clk,
35+
inout flash_io0,
36+
inout flash_io1,
37+
inout flash_io2,
38+
inout flash_io3
39+
);
40+
parameter integer MEM_WORDS = 512;
41+
42+
reg [5:0] reset_cnt = 0;
43+
wire resetn = &reset_cnt;
44+
45+
always @(posedge clk) begin
46+
reset_cnt <= reset_cnt + !resetn;
47+
end
48+
49+
wire flash_io0_oe, flash_io0_do, flash_io0_di;
50+
wire flash_io1_oe, flash_io1_do, flash_io1_di;
51+
wire flash_io2_oe, flash_io2_do, flash_io2_di;
52+
wire flash_io3_oe, flash_io3_do, flash_io3_di;
53+
54+
assign flash_io3 = (flash_io3_oe) ? flash_io3_do : 1'bz;
55+
assign flash_io2 = (flash_io2_oe) ? flash_io2_do : 1'bz;
56+
assign flash_io1 = (flash_io1_oe) ? flash_io1_do : 1'bz;
57+
assign flash_io0 = (flash_io0_oe) ? flash_io0_do : 1'bz;
58+
59+
assign flash_io3_di = flash_io3;
60+
assign flash_io2_di = flash_io2;
61+
assign flash_io1_di = flash_io1;
62+
assign flash_io0_di = flash_io0;
63+
64+
wire iomem_valid;
65+
reg iomem_ready;
66+
wire [3:0] iomem_wstrb;
67+
wire [31:0] iomem_addr;
68+
wire [31:0] iomem_wdata;
69+
reg [31:0] iomem_rdata;
70+
71+
reg [31:0] gpio;
72+
assign led = gpio[7:0];
73+
74+
always @(posedge clk) begin
75+
if (!resetn) begin
76+
gpio <= 0;
77+
end else begin
78+
iomem_ready <= 0;
79+
if (iomem_valid && !iomem_ready && iomem_addr[31:24] == 8'h 03) begin
80+
iomem_ready <= 1;
81+
iomem_rdata <= gpio;
82+
if (iomem_wstrb[0]) gpio[ 7: 0] <= iomem_wdata[ 7: 0];
83+
if (iomem_wstrb[1]) gpio[15: 8] <= iomem_wdata[15: 8];
84+
if (iomem_wstrb[2]) gpio[23:16] <= iomem_wdata[23:16];
85+
if (iomem_wstrb[3]) gpio[31:24] <= iomem_wdata[31:24];
86+
end
87+
end
88+
end
89+
90+
picosoc #(
91+
.BARREL_SHIFTER(0),
92+
.ENABLE_MUL(0),
93+
.ENABLE_DIV(0),
94+
.ENABLE_FAST_MUL(0),
95+
.MEM_WORDS(MEM_WORDS),
96+
.ENABLE_COMPRESSED(1),
97+
.ENABLE_COUNTERS(1)
98+
) soc (
99+
.clk (clk ),
100+
.resetn (resetn ),
101+
102+
.ser_tx (ser_tx ),
103+
.ser_rx (ser_rx ),
104+
105+
.flash_csb (flash_csb ),
106+
.flash_clk (flash_clk ),
107+
108+
.flash_io0_oe (flash_io0_oe),
109+
.flash_io1_oe (flash_io1_oe),
110+
.flash_io2_oe (flash_io2_oe),
111+
.flash_io3_oe (flash_io3_oe),
112+
113+
.flash_io0_do (flash_io0_do),
114+
.flash_io1_do (flash_io1_do),
115+
.flash_io2_do (flash_io2_do),
116+
.flash_io3_do (flash_io3_do),
117+
118+
.flash_io0_di (flash_io0_di),
119+
.flash_io1_di (flash_io1_di),
120+
.flash_io2_di (flash_io2_di),
121+
.flash_io3_di (flash_io3_di),
122+
123+
.irq_5 (1'b0 ),
124+
.irq_6 (1'b0 ),
125+
.irq_7 (1'b0 ),
126+
127+
.iomem_valid (iomem_valid ),
128+
.iomem_ready (iomem_ready ),
129+
.iomem_wstrb (iomem_wstrb ),
130+
.iomem_addr (iomem_addr ),
131+
.iomem_wdata (iomem_wdata ),
132+
.iomem_rdata (iomem_rdata )
133+
);
134+
endmodule

picosoc/gatemate_tb.v

+113
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
/*
2+
* PicoSoC - A simple example SoC using PicoRV32
3+
*
4+
* Copyright (C) 2017 Claire Xenia Wolf <claire@yosyshq.com>
5+
*
6+
* Permission to use, copy, modify, and/or distribute this software for any
7+
* purpose with or without fee is hereby granted, provided that the above
8+
* copyright notice and this permission notice appear in all copies.
9+
*
10+
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11+
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12+
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13+
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14+
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15+
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16+
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17+
*
18+
*/
19+
20+
`timescale 1 ns / 1 ps
21+
22+
module testbench;
23+
reg clk;
24+
always #5 clk = (clk === 1'b0);
25+
26+
localparam ser_half_period = 53;
27+
event ser_sample;
28+
29+
initial begin
30+
$dumpfile("testbench.vcd");
31+
$dumpvars(0, testbench);
32+
33+
repeat (6) begin
34+
repeat (50000) @(posedge clk);
35+
$display("+50000 cycles");
36+
end
37+
$finish;
38+
end
39+
40+
integer cycle_cnt = 0;
41+
42+
always @(posedge clk) begin
43+
cycle_cnt <= cycle_cnt + 1;
44+
end
45+
46+
wire [7:0] led;
47+
48+
wire ser_rx;
49+
wire ser_tx;
50+
51+
wire flash_csb;
52+
wire flash_clk;
53+
wire flash_io0;
54+
wire flash_io1;
55+
wire flash_io2;
56+
wire flash_io3;
57+
58+
always @(leds) begin
59+
#1 $display("%b", leds);
60+
end
61+
62+
gatemate #(
63+
// We limit the amount of memory in simulation
64+
// in order to avoid reduce simulation time
65+
// required for intialization of RAM
66+
.MEM_WORDS(256)
67+
) uut (
68+
.clk (clk ),
69+
.led (led ),
70+
.ser_rx (ser_rx ),
71+
.ser_tx (ser_tx ),
72+
.flash_csb(flash_csb),
73+
.flash_clk(flash_clk),
74+
.flash_io0(flash_io0),
75+
.flash_io1(flash_io1),
76+
.flash_io2(flash_io2),
77+
.flash_io3(flash_io3)
78+
);
79+
80+
spiflash spiflash (
81+
.csb(flash_csb),
82+
.clk(flash_clk),
83+
.io0(flash_io0),
84+
.io1(flash_io1),
85+
.io2(flash_io2),
86+
.io3(flash_io3)
87+
);
88+
89+
reg [7:0] buffer;
90+
91+
always begin
92+
@(negedge ser_tx);
93+
94+
repeat (ser_half_period) @(posedge clk);
95+
-> ser_sample; // start bit
96+
97+
repeat (8) begin
98+
repeat (ser_half_period) @(posedge clk);
99+
repeat (ser_half_period) @(posedge clk);
100+
buffer = {ser_tx, buffer[7:1]};
101+
-> ser_sample; // data bit
102+
end
103+
104+
repeat (ser_half_period) @(posedge clk);
105+
repeat (ser_half_period) @(posedge clk);
106+
-> ser_sample; // stop bit
107+
108+
if (buffer < 32 || buffer >= 127)
109+
$display("Serial data: %d", buffer);
110+
else
111+
$display("Serial data: '%c'", buffer);
112+
end
113+
endmodule

0 commit comments

Comments
 (0)