From caef4e3753d2c76de5d7030fcc2e3a1c331c64c6 Mon Sep 17 00:00:00 2001 From: Clifford Wolf Date: Mon, 7 Aug 2017 13:38:07 +0200 Subject: Rename "spiflash" example to "picosoc" --- picosoc/picosoc.v | 111 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 111 insertions(+) create mode 100644 picosoc/picosoc.v (limited to 'picosoc/picosoc.v') diff --git a/picosoc/picosoc.v b/picosoc/picosoc.v new file mode 100644 index 0000000..d1b01dd --- /dev/null +++ b/picosoc/picosoc.v @@ -0,0 +1,111 @@ +/* + * PicoSoC - A simple example SoC using PicoRV32 + * + * Copyright (C) 2017 Clifford Wolf + * + * 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. + * + */ + +module picosoc ( + input clk, + output trap, + + input [31:0] gpio_i, + output reg [31:0] gpio_o, + + output flash_csb, + output flash_clk, + output flash_io0, + input flash_io1, + input flash_io2, + input flash_io3 +); + parameter integer MEM_WORDS = 256; + parameter [31:0] STACKADDR = (4*MEM_WORDS); // end of memory + parameter [31:0] PROGADDR_RESET = 32'h 8010_0000; // 1 MB into flash + + reg [5:0] reset_cnt = 0; + wire resetn = &reset_cnt; + + always @(posedge clk) begin + reset_cnt <= reset_cnt + !resetn; + end + + wire mem_valid; + wire mem_instr; + reg mem_ready; + wire [31:0] mem_addr; + wire [31:0] mem_wdata; + wire [3:0] mem_wstrb; + reg [31:0] mem_rdata; + + wire spimem_ready; + wire [31:0] spimem_rdata; + + picorv32 #( + .STACKADDR(STACKADDR), + .PROGADDR_RESET(PROGADDR_RESET) + ) cpu ( + .clk (clk ), + .resetn (resetn ), + .trap (trap ), + .mem_valid (mem_valid ), + .mem_instr (mem_instr ), + .mem_ready (mem_ready || spimem_ready), + .mem_addr (mem_addr ), + .mem_wdata (mem_wdata ), + .mem_wstrb (mem_wstrb ), + .mem_rdata (spimem_ready ? spimem_rdata : mem_rdata ) + ); + + spimemio spimemio ( + .clk(clk), + .resetn(resetn), + .valid (mem_valid && mem_addr[31:30] == 2'b10), + .ready (spimem_ready), + .addr (mem_addr[23:0]), + .rdata (spimem_rdata), + + .flash_csb (flash_csb), + .flash_clk (flash_clk), + .flash_io0 (flash_io0), + .flash_io1 (flash_io1), + .flash_io2 (flash_io2), + .flash_io3 (flash_io3) + ); + + reg [31:0] memory [0:MEM_WORDS-1]; + + always @(posedge clk) begin + mem_ready <= 0; + if (mem_valid && !mem_ready) begin + if (mem_addr < 4*MEM_WORDS) begin + mem_ready <= 1; + mem_rdata <= memory[mem_addr >> 2]; + if (mem_wstrb[0]) memory[mem_addr >> 2][ 7: 0] <= mem_wdata[ 7: 0]; + if (mem_wstrb[1]) memory[mem_addr >> 2][15: 8] <= mem_wdata[15: 8]; + if (mem_wstrb[2]) memory[mem_addr >> 2][23:16] <= mem_wdata[23:16]; + if (mem_wstrb[3]) memory[mem_addr >> 2][31:24] <= mem_wdata[31:24]; + end + if (mem_addr == 32'h c000_0000) begin + mem_ready <= 1; + mem_rdata <= gpio_i; + if (mem_wstrb[0]) gpio_o[ 7: 0] <= mem_wdata[ 7: 0]; + if (mem_wstrb[1]) gpio_o[15: 8] <= mem_wdata[15: 8]; + if (mem_wstrb[2]) gpio_o[23:16] <= mem_wdata[23:16]; + if (mem_wstrb[3]) gpio_o[31:24] <= mem_wdata[31:24]; + end + end + end +endmodule -- cgit