vhdl: implement setting LEDs via UDP

This commit is contained in:
Xiretza 2022-06-05 21:34:31 +02:00
parent d5b0ee2cfa
commit 9121ccfdbe
2 changed files with 71 additions and 13 deletions

View file

@ -116,6 +116,16 @@ architecture a of arty_a7 is
signal pixel_sink_ready : std_logic; signal pixel_sink_ready : std_logic;
signal pixel_sink_data : std_logic_vector(31 downto 0); signal pixel_sink_data : std_logic_vector(31 downto 0);
signal pixel_source_src_ip_address : std_logic_vector(31 downto 0);
signal pixel_source_src_port : std_logic_vector(15 downto 0);
signal pixel_source_length : std_logic_vector(15 downto 0);
signal pixel_source_valid : std_logic;
signal pixel_source_last : std_logic;
signal pixel_source_last_be : std_logic_vector(3 downto 0);
signal pixel_source_ready : std_logic;
signal pixel_source_data : std_logic_vector(31 downto 0);
component PLLE2_BASE component PLLE2_BASE
generic ( generic (
CLKFBOUT_MULT : integer; CLKFBOUT_MULT : integer;
@ -232,15 +242,15 @@ begin
pixel_sink_data => pixel_sink_data, pixel_sink_data => pixel_sink_data,
-- source -- source
pixel_source_src_ip_address => open, pixel_source_src_ip_address => pixel_source_src_ip_address,
pixel_source_src_port => open, pixel_source_src_port => pixel_source_src_port,
pixel_source_length => open, pixel_source_length => pixel_source_length,
pixel_source_valid => open, pixel_source_valid => pixel_source_valid,
pixel_source_last => open, pixel_source_last => pixel_source_last,
pixel_source_last_be => open, pixel_source_last_be => pixel_source_last_be,
pixel_source_ready => '1', pixel_source_ready => pixel_source_ready,
pixel_source_data => open pixel_source_data => pixel_source_data
); );
-- 800 MHz VCO -- 800 MHz VCO
@ -323,6 +333,16 @@ begin
clk => sys_clk, clk => sys_clk,
reset => sys_reset, reset => sys_reset,
udp_src_ip_address => pixel_source_src_ip_address,
udp_src_port => pixel_source_src_port,
udp_length => pixel_source_length,
udp_valid => pixel_source_valid,
udp_last => pixel_source_last,
udp_last_be => pixel_source_last_be,
udp_ready => pixel_source_ready,
udp_data => pixel_source_data,
drivers => drivers drivers => drivers
); );
end architecture; end architecture;

View file

@ -11,16 +11,34 @@ entity splink is
clk : in std_logic; clk : in std_logic;
reset : in std_logic; reset : in std_logic;
udp_src_ip_address : in std_logic_vector(31 downto 0);
udp_src_port : in std_logic_vector(15 downto 0);
udp_length : in std_logic_vector(15 downto 0);
udp_valid : in std_logic;
udp_last : in std_logic;
udp_last_be : in std_logic_vector(3 downto 0);
udp_ready : out std_logic;
udp_data : in std_logic_vector(31 downto 0);
drivers : out std_logic_vector(NUM_STRANDS-1 downto 0) drivers : out std_logic_vector(NUM_STRANDS-1 downto 0)
); );
end entity; end entity;
architecture a of splink is architecture a of splink is
signal driver_out : std_logic; signal driver_out : std_logic;
constant BITS_PER_LED: natural := 24;
subtype color_t is std_logic_vector(BITS_PER_LED-1 downto 0);
type strand_store_t is array(0 to MAX_STRAND_LEN) of color_t;
signal strand_store: strand_store_t;
signal led_addr : std_logic_vector(7 downto 0);
signal current_color : color_t;
begin begin
ws2812_inst: entity work.ws2812 ws2812_inst: entity work.ws2812
generic map ( generic map (
NUM_LEDS => 20, NUM_LEDS => MAX_STRAND_LEN,
COLOR_ORDER => "GRB", COLOR_ORDER => "GRB",
T_CLK => 12.5 ns, T_CLK => 12.5 ns,
@ -35,15 +53,35 @@ begin
n_reset => not reset, n_reset => not reset,
clk => clk, clk => clk,
led_addr => open, led_addr => led_addr,
led_red => x"ff", led_red => current_color(7 downto 0),
led_green => x"00", led_green => current_color(15 downto 8),
led_blue => x"ff", led_blue => current_color(23 downto 16),
dout => driver_out dout => driver_out
); );
-- https://github.com/YosysHQ/yosys/issues/3360 -- https://github.com/YosysHQ/yosys/issues/3360
drivers <= (19 => driver_out, others => '0'); drivers <= (19 => driver_out, others => '0');
writer: process(clk)
variable store_counter: natural range 0 to MAX_STRAND_LEN-1;
begin
if rising_edge(clk) then
current_color <= strand_store(to_integer(unsigned(led_addr)));
if udp_valid then
strand_store(store_counter) <= udp_data(23 downto 0);
if udp_last then
store_counter := 0;
elsif store_counter /= MAX_STRAND_LEN-1 then
store_counter := store_counter + 1;
end if;
end if;
end if;
end process;
udp_ready <= '1';
end architecture; end architecture;