URL
https://opencores.org/ocsvn/potato/potato/trunk
Subversion Repositories potato
Compare Revisions
- This comparison shows the changes necessary to convert path
/potato/trunk
- from Rev 60 to Rev 61
- ↔ Reverse comparison
Rev 60 → Rev 61
/soc/pp_seg7dec.vhd
0,0 → 1,57
-- The Potato Processor - A simple processor for FPGAs |
-- (c) Kristian Klomsten Skordal 2015 <kristian.skordal@wafflemail.net> |
-- Report bugs and issues on <http://opencores.org/project,potato,bugtracker> |
|
library ieee; |
use ieee.std_logic_1164.all; |
|
-- @brief 7-Segment Display Decoder |
entity pp_seg7dec is |
port( |
input : in std_logic_vector(3 downto 0); |
output : out std_logic_vector(6 downto 0) |
); |
end entity pp_seg7dec; |
|
architecture behaviour of pp_seg7dec is |
begin |
|
decoder: process(input) |
begin |
case input is |
when x"0" => |
output <= b"1000000"; |
when x"1" => |
output <= b"1111001"; |
when x"2" => |
output <= b"0100100"; |
when x"3" => |
output <= b"0110000"; |
when x"4" => |
output <= b"0011001"; |
when x"5" => |
output <= b"0010010"; |
when x"6" => |
output <= b"0000010"; |
when x"7" => |
output <= b"1111000"; |
when x"8" => |
output <= b"1111111"; |
when x"9" => |
output <= b"0011000"; |
when x"a" => |
output <= b"0001000"; |
when x"b" => |
output <= b"0000011"; |
when x"c" => |
output <= b"1000110"; |
when x"d" => |
output <= b"0100001"; |
when x"e" => |
output <= b"0000110"; |
when x"f" => |
output <= b"0001110"; |
end case; |
end process decoder; |
|
end architecture behaviour; |
/soc/pp_soc_7seg.vhd
0,0 → 1,135
-- The Potato Processor - A simple processor for FPGAs |
-- (c) Kristian Klomsten Skordal 2015 <kristian.skordal@wafflemail.net> |
-- Report bugs and issues on <http://opencores.org/project,potato,bugtracker> |
|
library ieee; |
use ieee.std_logic_1164.all; |
use ieee.numeric_std.all; |
|
entity pp_soc_7seg is |
generic( |
NUM_DISPLAYS : natural := 8; -- Number of 7-segment displays connected to the module. |
SWITCH_COUNT : natural; -- How many ticks of the input clock to count before switching displays. |
CATHODE_ENABLE_VALUE : std_logic := '0'; -- Value of the cathode output when enabled. |
ANODE_ENABLE_VALUE : std_logic := '0' -- Value of the anode output when enabled. |
); |
port( |
clk : in std_logic; |
reset : in std_logic; |
|
-- Connections to the displays: |
seg7_anode : out std_logic_vector(NUM_DISPLAYS - 1 downto 0); -- One for each display |
seg7_cathode : out std_logic_vector(6 downto 0); |
|
-- Wishbone interface: |
wb_adr_in : in std_logic_vector( 0 downto 0); |
wb_dat_in : in std_logic_vector(31 downto 0); |
wb_dat_out : out std_logic_vector(31 downto 0); |
wb_cyc_in : in std_logic; |
wb_stb_in : in std_logic; |
wb_we_in : in std_logic; |
wb_ack_out : out std_logic |
); |
end entity pp_soc_7seg; |
|
architecture behaviour of pp_soc_7seg is |
signal ctrl_value : std_logic_vector(NUM_DISPLAYS * 4 - 1 downto 0); |
signal ctrl_enable : std_logic_vector(NUM_DISPLAYS - 1 downto 0); |
|
type seg7_array is array (0 to NUM_DISPLAYS - 1) of std_logic_vector(6 downto 0); |
signal output_array : seg7_array; |
|
subtype display_counter_type is natural range 0 to NUM_DISPLAYS - 1; |
signal active_display : display_counter_type := 0; |
|
constant ANODE_DISABLE_VALUE : std_logic := not ANODE_ENABLE_VALUE; |
|
subtype switch_counter_type is natural range 0 to SWITCH_COUNT - 1; |
signal switch_counter : switch_counter_type := 0; |
|
signal anodes : std_logic_vector(NUM_DISPLAYS - 1 downto 0); |
|
-- Wishbone controller acknowledge signal: |
signal ack : std_logic; |
begin |
|
assert NUM_DISPLAYS <= 8 and NUM_DISPLAYS > 0 |
report "Only 1 - 8 displays are supported by the 7-seg module!" |
severity FAILURE; |
|
-- Connect display outputs: |
seg7_cathode <= output_array(active_display) when CATHODE_ENABLE_VALUE = '0' else not output_array(active_display); |
seg7_anode <= anodes; |
|
-- Create one decoder for each display: |
generate_decoders: for i in 0 to NUM_DISPLAYS - 1 |
generate |
decoder: entity work.pp_seg7dec |
port map( |
input => ctrl_value(i * 4 + 3 downto i * 4), |
output => output_array(i) |
); |
end generate; |
|
-- Switch between the displays: |
switch_displays: process(clk) |
begin |
if rising_edge(clk) then |
if reset = '1' then |
anodes <= (0 => ANODE_ENABLE_VALUE, others => ANODE_DISABLE_VALUE); |
active_display <= 0; |
else |
if switch_counter = SWITCH_COUNT - 1 then |
anodes <= std_logic_vector(rotate_left(unsigned(anodes), 1)); |
switch_counter <= 0; |
if active_display = NUM_DISPLAYS - 1 then |
active_display <= 0; |
else |
active_display <= active_display + 1; |
end if; |
else |
switch_counter <= switch_counter + 1; |
end if; |
end if; |
end if; |
end process switch_displays; |
|
----- Wishbone controller: ----- |
wb_ack_out <= ack and wb_cyc_in and wb_stb_in; |
wishbone: process(clk) |
begin |
if rising_edge(clk) then |
if reset = '1' then |
ctrl_value <= (others => '0'); |
ctrl_enable <= (others => '1'); |
wb_dat_out <= (others => '0'); |
ack <= '0'; |
else |
if wb_cyc_in = '1' and wb_stb_in = '1' and ack = '0' then |
if wb_we_in = '1' then |
case wb_adr_in is |
when b"0" => |
ctrl_enable <= wb_dat_in(NUM_DISPLAYS - 1 downto 0); |
when b"1" => |
ctrl_value <= wb_dat_in(NUM_DISPLAYS * 4 - 1 downto 0); |
when others => |
end case; |
ack <= '1'; |
else |
case wb_adr_in is |
when b"0" => |
wb_dat_out <= std_logic_vector(resize(unsigned(ctrl_enable), wb_dat_out'length)); |
when b"1" => |
wb_dat_out <= std_logic_vector(resize(unsigned(ctrl_value), wb_dat_out'length)); |
when others => |
end case; |
ack <= '1'; |
end if; |
elsif wb_stb_in = '0' then |
ack <= '0'; |
end if; |
end if; |
end if; |
end process wishbone; |
|
end architecture behaviour; |
/example/toplevel.vhd
7,7 → 7,7
|
entity toplevel is |
port( |
clk : in std_logic; -- System clock, 100 MHz |
clk : in std_logic; -- External clock input, 100 MHz |
reset_n : in std_logic; -- CPU reset signal, active low |
|
-- External interrupt input: |
17,9 → 17,13
switches : inout std_logic_vector(15 downto 0); |
leds : inout std_logic_vector(15 downto 0); |
|
-- UART1 (host) pins: |
-- UART pins: |
uart_txd : out std_logic; |
uart_rxd : in std_logic |
uart_rxd : in std_logic; |
|
-- 7-Segment display pins: |
seg7_anode : out std_logic_vector(7 downto 0); |
seg7_cathode : out std_logic_vector(6 downto 0) |
); |
end entity toplevel; |
|
60,7 → 64,7
signal dmem_ack_out : std_logic; |
|
-- GPIO module I (switches) wishbone interface: |
signal gpio1_adr_in : std_logic_vector(1 downto 0); |
signal gpio1_adr_in : std_logic_vector( 1 downto 0); |
signal gpio1_dat_in : std_logic_vector(31 downto 0); |
signal gpio1_dat_out : std_logic_vector(31 downto 0); |
signal gpio1_we_in : std_logic; |
68,7 → 72,7
signal gpio1_ack_out : std_logic; |
|
-- GPIO module II (LEDs) wishbone interface: |
signal gpio2_adr_in : std_logic_vector(1 downto 0); |
signal gpio2_adr_in : std_logic_vector( 1 downto 0); |
signal gpio2_dat_in : std_logic_vector(31 downto 0); |
signal gpio2_dat_out : std_logic_vector(31 downto 0); |
signal gpio2_we_in : std_logic; |
84,7 → 88,7
signal uart_ack_out : std_logic; |
|
-- Timer module wishbone interface: |
signal timer_adr_in : std_logic_vector(1 downto 0); |
signal timer_adr_in : std_logic_vector( 1 downto 0); |
signal timer_dat_in : std_logic_vector(31 downto 0); |
signal timer_dat_out : std_logic_vector(31 downto 0); |
signal timer_we_in : std_logic; |
91,6 → 95,14
signal timer_cyc_in, timer_stb_in : std_logic; |
signal timer_ack_out : std_logic; |
|
-- 7-Segment module wishbone interface: |
signal seg7_adr_in : std_logic_vector( 0 downto 0); |
signal seg7_dat_in : std_logic_vector(31 downto 0); |
signal seg7_dat_out : std_logic_vector(31 downto 0); |
signal seg7_we_in : std_logic; |
signal seg7_cyc_in, seg7_stb_in : std_logic; |
signal seg7_ack_out : std_logic; |
|
-- Dummy module interface: |
signal dummy_dat_in : std_logic_vector(31 downto 0); |
signal dummy_dat_out : std_logic_vector(31 downto 0); |
107,6 → 119,7
MODULE_GPIO1, MODULE_GPIO2, -- GPIO modules |
MODULE_UART, -- UART module |
MODULE_TIMER, -- Timer module |
MODULE_7SEG, -- 7-Segment module |
MODULE_DUMMY, -- Dummy module, used for invalid addresses |
MODULE_NONE -- Boring no-module mode |
); |
242,6 → 255,23
wb_ack_out => timer_ack_out |
); |
|
seg7_1: entity work.pp_soc_7seg |
generic map( |
SWITCH_COUNT => 50000 -- For 50 MHz |
) port map( |
clk => system_clk, |
reset => reset, |
seg7_anode => seg7_anode, |
seg7_cathode => seg7_cathode, |
wb_adr_in => seg7_adr_in, |
wb_dat_in => seg7_dat_in, |
wb_dat_out => seg7_dat_out, |
wb_cyc_in => seg7_cyc_in, |
wb_stb_in => seg7_stb_in, |
wb_we_in => seg7_we_in, |
wb_ack_out => seg7_ack_out |
); |
|
dummy: entity work.pp_soc_dummy |
port map( |
clk => system_clk, |
260,6 → 290,7
gpio2_cyc_in <= p_cyc_out when active_module = MODULE_GPIO2 else '0'; |
uart_cyc_in <= p_cyc_out when active_module = MODULE_UART else '0'; |
timer_cyc_in <= p_cyc_out when active_module = MODULE_TIMER else '0'; |
seg7_cyc_in <= p_cyc_out when active_module = MODULE_7SEG else '0'; |
dummy_cyc_in <= p_cyc_out when active_module = MODULE_DUMMY else '0'; |
|
imem_stb_in <= p_stb_out when active_module = MODULE_IMEM else '0'; |
268,6 → 299,7
gpio2_stb_in <= p_stb_out when active_module = MODULE_GPIO2 else '0'; |
uart_stb_in <= p_stb_out when active_module = MODULE_UART else '0'; |
timer_stb_in <= p_stb_out when active_module = MODULE_TIMER else '0'; |
seg7_stb_in <= p_stb_out when active_module = MODULE_7SEG else '0'; |
dummy_stb_in <= p_stb_out when active_module = MODULE_DUMMY else '0'; |
|
imem_adr_in <= p_adr_out(12 downto 0); |
276,6 → 308,7
gpio2_adr_in <= p_adr_out(3 downto 2); |
uart_adr_in <= p_adr_out(3 downto 2); |
timer_adr_in <= p_adr_out(3 downto 2); |
seg7_adr_in <= p_adr_out(2 downto 2); |
|
dmem_dat_in <= p_dat_out; |
gpio1_dat_in <= p_dat_out; |
282,6 → 315,7
gpio2_dat_in <= p_dat_out; |
uart_dat_in <= p_dat_out(7 downto 0); |
timer_dat_in <= p_dat_out; |
seg7_dat_in <= p_dat_out; |
dummy_dat_in <= p_dat_out; |
|
dmem_sel_in <= p_sel_out; |
291,6 → 325,7
dmem_we_in <= p_we_out; |
uart_we_in <= p_we_out; |
timer_we_in <= p_we_out; |
seg7_we_in <= p_we_out; |
dummy_we_in <= p_we_out; |
|
address_decoder: process(system_clk) |
321,6 → 356,9
elsif p_adr_out(31 downto 11) = b"000000000000000001011" then -- 0x5800 |
active_module <= MODULE_TIMER; |
ad_state <= BUSY; |
elsif p_adr_out(31 downto 11) = b"000000000000000001100" then -- 0x6000 |
active_module <= MODULE_7SEG; |
ad_state <= BUSY; |
else |
active_module <= MODULE_DUMMY; |
ad_state <= BUSY; |
361,6 → 399,9
when MODULE_TIMER => |
p_ack_in <= timer_ack_out; |
p_dat_in <= timer_dat_out; |
when MODULE_7SEG => |
p_ack_in <= seg7_ack_out; |
p_dat_in <= seg7_dat_out; |
when MODULE_DUMMY => |
p_ack_in <= dummy_ack_out; |
p_dat_in <= dummy_dat_out; |
/example/nexys4_constraints.xdc
19,7 → 19,7
set_property PACKAGE_PIN E16 [get_ports external_interrupt] |
set_property IOSTANDARD LVCMOS33 [get_ports external_interrupt] |
|
# UART (to host) lines: |
# UART lines: |
set_property PACKAGE_PIN C4 [get_ports uart_rxd] |
set_property IOSTANDARD LVCMOS33 [get_ports uart_rxd] |
set_property PACKAGE_PIN D4 [get_ports uart_txd] |
92,3 → 92,36
set_property IOSTANDARD LVCMOS33 [get_ports {leds[14]}] |
set_property PACKAGE_PIN P2 [get_ports {leds[15]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {leds[15]}] |
|
## 7-Segment displays: |
set_property PACKAGE_PIN L3 [get_ports {seg7_cathode[0]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[0]}] |
set_property PACKAGE_PIN N1 [get_ports {seg7_cathode[1]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[1]}] |
set_property PACKAGE_PIN L5 [get_ports {seg7_cathode[2]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[2]}] |
set_property PACKAGE_PIN L4 [get_ports {seg7_cathode[3]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[3]}] |
set_property PACKAGE_PIN K3 [get_ports {seg7_cathode[4]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[4]}] |
set_property PACKAGE_PIN M2 [get_ports {seg7_cathode[5]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[5]}] |
set_property PACKAGE_PIN L6 [get_ports {seg7_cathode[6]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_cathode[6]}] |
|
set_property PACKAGE_PIN N6 [get_ports {seg7_anode[0]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[0]}] |
set_property PACKAGE_PIN M6 [get_ports {seg7_anode[1]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[1]}] |
set_property PACKAGE_PIN M3 [get_ports {seg7_anode[2]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[2]}] |
set_property PACKAGE_PIN N5 [get_ports {seg7_anode[3]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[3]}] |
set_property PACKAGE_PIN N2 [get_ports {seg7_anode[4]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[4]}] |
set_property PACKAGE_PIN N4 [get_ports {seg7_anode[5]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[5]}] |
set_property PACKAGE_PIN L1 [get_ports {seg7_anode[6]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[6]}] |
set_property PACKAGE_PIN M1 [get_ports {seg7_anode[7]}] |
set_property IOSTANDARD LVCMOS33 [get_ports {seg7_anode[7]}] |
/benchmarks/sha256/main.c
9,6 → 9,7
#include "potato.h" |
|
#include "gpio.h" |
#include "seg7.h" |
#include "sha256.h" |
#include "timer.h" |
#include "uart.h" |
29,6 → 30,7
uart_puts(IO_ADDRESS(UART_BASE), "Hashes per second: "); |
uart_puth(IO_ADDRESS(UART_BASE), hashes_per_second); |
uart_puts(IO_ADDRESS(UART_BASE), "\n\r"); |
seg7_set_value(IO_ADDRESS(SEG7_BASE), hashes_per_second); |
|
if(led_status == 0) |
{ |
60,6 → 62,10
gpio_set_direction(IO_ADDRESS(GPIO1_BASE), 0x0000); // Switches |
gpio_set_direction(IO_ADDRESS(GPIO2_BASE), 0xffff); // LEDs |
|
// Configure the 7-segment displays: |
seg7_set_enabled_displays(IO_ADDRESS(SEG7_BASE), 0xff); |
seg7_set_value(IO_ADDRESS(SEG7_BASE), 0); |
|
// Set up the timer: |
timer_set(IO_ADDRESS(TIMER_BASE), SYSTEM_CLK_FREQ); |
|
/benchmarks/sha256/seg7.c
0,0 → 1,18
// The Potato Processor Benchmark Applications |
// (c) Kristian Klomsten Skordal 2015 <kristian.skordal@wafflemail.net> |
// Report bugs and issues on <http://opencores.org/project,potato,bugtracker> |
|
#include "seg7.h" |
#include "platform.h" |
|
void seg7_set_enabled_displays(volatile uint32_t * base, uint8_t mask) |
{ |
base[SEG7_ENABLE >> 2] = (uint32_t) mask; |
} |
|
void seg7_set_value(volatile uint32_t * base, uint32_t value) |
{ |
base[SEG7_VALUE >> 2] = value; |
} |
|
|
/benchmarks/sha256/seg7.h
0,0 → 1,16
// The Potato Processor Benchmark Applications |
// (c) Kristian Klomsten Skordal 2015 <kristian.skordal@wafflemail.net> |
// Report bugs and issues on <http://opencores.org/project,potato,bugtracker> |
|
#ifndef SEG7_H |
#define SEG7_H |
|
#include <stdint.h> |
|
// Sets which 7-segment displays are enabled: |
void seg7_set_enabled_displays(volatile uint32_t * base, uint8_t mask); |
// Sets the value to be displayed on the displays: |
void seg7_set_value(volatile uint32_t * base, uint32_t value); |
|
#endif |
|
/benchmarks/sha256/Makefile
12,10 → 12,11
HEXDUMP ?= hexdump |
|
TARGET_CFLAGS += -m32 -march=RV32I -Wall -Os -fomit-frame-pointer \ |
-ffreestanding -fno-builtin -I.. -std=gnu99 |
-ffreestanding -fno-builtin -I.. -std=gnu99 \ |
-Wall -Werror=implicit-function-declaration |
TARGET_LDFLAGS += -m elf32lriscv -T../benchmark.ld |
|
OBJECTS := gpio.o main.o sha256.o start.o timer.o uart.o utilities.o |
OBJECTS := gpio.o main.o seg7.o sha256.o start.o timer.o uart.o utilities.o |
|
all: sha256.coe |
|
42,9 → 43,12
gpio.o: gpio.c gpio.h ../platform.h |
$(TARGET_CC) -c -o $@ $(TARGET_CFLAGS) $< |
|
main.o: main.c gpio.h timer.h sha256.h ../platform.h ../potato.h |
main.o: main.c gpio.h timer.h seg7.h sha256.h ../platform.h ../potato.h |
$(TARGET_CC) -c -o $@ $(TARGET_CFLAGS) $< |
|
seg7.o: seg7.c seg7.h ../platform.h |
$(TARGET_CC) -c -o $@ $(TARGET_CFLAGS) $< |
|
sha256.o: sha256.c sha256.h |
$(TARGET_CC) -c -o $@ $(TARGET_CFLAGS) $< |
|
/benchmarks/platform.h
21,6 → 21,7
#define GPIO2_BASE 0x00004800 |
#define UART_BASE 0x00005000 |
#define TIMER_BASE 0x00005800 |
#define SEG7_BASE 0x00006000 |
|
// IRQs: |
#define EXTERNAL_IRQ 0 |
45,5 → 46,9
#define TIMER_CTRL_RUN 0 |
#define TIMER_CTRL_CLEAR 1 |
|
// 7-Segment register offsets: |
#define SEG7_ENABLE 0 |
#define SEG7_VALUE 4 |
|
#endif |
|