Commit cc8ba521 authored by Tristan Gingold's avatar Tristan Gingold

Rework plc urv memory map to improve speed.

TODO: add byte selects for data memory
parent bb956743
......@@ -34,8 +34,7 @@ use work.urv_pkg.all;
entity plc_urv is
generic(
g_IRAM_LOG_SIZE : natural := 10;
g_DRAM_LOG_SIZE : natural := 12);
g_IRAM_LOG_SIZE : natural := 10);
port(
clk_sys_i : in std_logic;
rst_n_i : in std_logic;
......@@ -61,16 +60,6 @@ architecture arch of plc_urv is
signal dm_data_select : std_logic_vector(3 downto 0);
signal dm_load, dm_store, dm_load_done, dm_store_done : std_logic;
signal reg_dm_addr, reg_dm_data_s : std_logic_vector(31 downto 0);
signal reg_dm_data_select : std_logic_vector(3 downto 0);
signal reg_dm_load, reg_dm_store : std_logic;
signal dm_cycle_in_progress, reg_dm_is_wishbone : std_logic;
signal dm_mem_rdata, dm_wb_rdata : std_logic_vector(31 downto 0);
signal dm_wb_write, dm_select_wb : std_logic;
signal reg_dm_data_write : std_logic;
signal dwb_out : t_wishbone_master_out;
begin
......@@ -111,18 +100,28 @@ begin
begin
if rising_edge(clk_sys_i) then
if rst_n_i = '0' then
reg_dm_load <= '0';
reg_dm_store <= '0';
dwb_out.cyc <= '0';
dwb_out.stb <= '0';
else
reg_dm_load <= dm_load;
reg_dm_store <= dm_store;
reg_dm_addr <= dm_addr;
reg_dm_data_s <= dm_data_s;
reg_dm_data_select <= dm_data_select;
if dm_load = '1' or dm_store = '1' then
dwb_out.cyc <= '1';
dwb_out.stb <= '1';
dwb_out.adr <= dm_addr;
dwb_out.sel <= dm_data_select;
dwb_out.we <= dm_store;
dwb_out.dat <= dm_data_s;
elsif dwb_i.ack = '1' then
dwb_out.cyc <= '0';
dwb_out.stb <= '0';
end if;
end if;
end if;
end process;
dm_data_l <= dwb_i.dat;
dm_store_done <= dwb_i.ack and dwb_out.we;
dm_load_done <= dwb_i.ack and not dwb_out.we;
p_iram: process (clk_sys_i)
is
constant IRAM_WSIZE : natural := 2 ** (g_IRAM_LOG_SIZE - 2);
......@@ -143,106 +142,6 @@ begin
ram_wb_o.rty <= '0';
ram_wb_o.stall <= '0';
-- 1st MByte of the mem is the IRAM
reg_dm_is_wishbone <= '1' when reg_dm_addr(31 downto 20) /= x"000" else '0';
reg_dm_data_write <= not reg_dm_is_wishbone and reg_dm_store;
dm_data_l <= dm_wb_rdata when dm_select_wb = '1' else dm_mem_rdata;
p_ram: process (clk_sys_i)
is
variable mem : t_ram32_type (2**(g_DRAM_LOG_SIZE - 2) - 1 downto 0);
variable addr : natural range mem'range;
begin
if rising_edge(clk_sys_i) then
addr := to_integer(unsigned(reg_dm_addr(g_DRAM_LOG_SIZE - 1 downto 2)));
dm_mem_rdata <= mem(addr);
if reg_dm_data_write = '1' then
for i in 0 to 3 loop
if reg_dm_data_select (i) = '1' then
mem(addr)(8*i + 7 downto 8*i) := reg_dm_data_s(8*i + 7 downto 8*i);
end if;
end loop;
end if;
end if;
end process;
-- Wishbone bus arbitration / internal RAM access
p_wishbone_master : process(clk_sys_i)
begin
if rising_edge(clk_sys_i) then
if rst_n_i = '0' then
dwb_out.cyc <= '0';
dwb_out.stb <= '0';
dwb_out.adr <= (others => '0');
dwb_out.sel <= x"0";
dwb_out.we <= '0';
dwb_out.dat <= (others => '0');
dm_cycle_in_progress <= '0';
dm_load_done <= '0';
dm_store_done <= '0';
dm_select_wb <= '0';
else
if dm_cycle_in_progress = '0' then
if reg_dm_is_wishbone = '0' then
-- Internal access
if reg_dm_store = '1' then
dm_load_done <= '0';
dm_store_done <= '1';
dm_select_wb <= '0';
elsif reg_dm_load = '1' then
dm_load_done <= '1';
dm_store_done <= '0';
dm_select_wb <= '0';
else
dm_store_done <= '0';
dm_load_done <= '0';
dm_select_wb <= '0';
end if;
else
-- Wishbone access
if reg_dm_load = '1' or reg_dm_store = '1' then
dwb_out.cyc <= '1';
dwb_out.stb <= '1';
dwb_out.we <= reg_dm_store;
dm_wb_write <= reg_dm_store;
dwb_out.adr <= reg_dm_addr;
dwb_out.dat <= reg_dm_data_s;
dwb_out.sel <= reg_dm_data_select;
dm_load_done <= '0';
dm_store_done <= '0';
dm_cycle_in_progress <= '1';
else
dm_store_done <= '0';
dm_load_done <= '0';
dm_cycle_in_progress <= '0';
end if;
end if;
else
-- Wishbone transfer in progress.
if dwb_i.stall = '0' then
dwb_out.stb <= '0';
end if;
if dwb_i.ack = '1' then
if dm_wb_write = '0' then
dm_wb_rdata <= dwb_i.dat;
dm_select_wb <= '1';
dm_load_done <= '1';
else
dm_store_done <= '1';
dm_select_wb <= '0';
end if;
dm_cycle_in_progress <= '0';
dwb_out.cyc <= '0';
end if;
end if;
end if;
end if;
end process p_wishbone_master;
cpu_rst <= not rst_n_i;
p_im_valid : process(clk_sys_i)
......
......@@ -5,6 +5,16 @@ memory-map:
x-hdl:
busgroup: True
children:
- memory:
name: sram
address: 0x10000
interface: sram
memsize: 8k
children:
- reg:
name: value
access: rw
width: 32
- submap:
name: mailboxes
filename: "mbox_regs.cheby"
......
-- Do not edit. Generated on Fri Feb 14 11:50:20 2020 by tgingold
-- Do not edit. Generated on Wed Feb 26 09:20:54 2020 by tgingold
-- With Cheby 1.4.dev0 and these options:
-- -i plc_urv_regs.cheby --gen-hdl plc_urv_regs.vhd
......@@ -15,6 +15,12 @@ entity plc_urv_regs is
wb_i : in t_wishbone_slave_in;
wb_o : out t_wishbone_slave_out;
-- SRAM bus sram
sram_addr_o : out std_logic_vector(12 downto 2);
sram_data_i : in std_logic_vector(31 downto 0);
sram_data_o : out std_logic_vector(31 downto 0);
sram_wr_o : out std_logic;
-- Mailbox to the fip urv
mailboxes_mboxout_o : out std_logic_vector(31 downto 0);
mailboxes_mboxout_wr_o : out std_logic;
......@@ -81,7 +87,7 @@ entity plc_urv_regs is
end plc_urv_regs;
architecture syn of plc_urv_regs is
signal adr_int : std_logic_vector(6 downto 2);
signal adr_int : std_logic_vector(16 downto 2);
signal rd_req_int : std_logic;
signal wr_req_int : std_logic;
signal rd_ack_int : std_logic;
......@@ -90,6 +96,8 @@ architecture syn of plc_urv_regs is
signal ack_int : std_logic;
signal wb_rip : std_logic;
signal wb_wip : std_logic;
signal sram_rack : std_logic;
signal sram_re : std_logic;
signal mailboxes_mboxout_wreq : std_logic;
signal relays_pins_0_reg : std_logic_vector(31 downto 0);
signal relays_pins_0_wreq : std_logic;
......@@ -118,13 +126,15 @@ architecture syn of plc_urv_regs is
signal rd_ack_d0 : std_logic;
signal rd_dat_d0 : std_logic_vector(31 downto 0);
signal wr_req_d0 : std_logic;
signal wr_adr_d0 : std_logic_vector(6 downto 2);
signal wr_adr_d0 : std_logic_vector(16 downto 2);
signal wr_dat_d0 : std_logic_vector(31 downto 0);
signal wr_sel_d0 : std_logic_vector(3 downto 0);
signal sram_wp : std_logic;
signal sram_we : std_logic;
begin
-- WB decode signals
adr_int <= wb_i.adr(6 downto 2);
adr_int <= wb_i.adr(16 downto 2);
wb_en <= wb_i.cyc and wb_i.stb;
process (clk_i) begin
......@@ -172,6 +182,35 @@ begin
end if;
end process;
-- Interface sram
process (clk_i) begin
if rising_edge(clk_i) then
if rst_n_i = '0' then
sram_rack <= '0';
else
sram_rack <= sram_re and not sram_rack;
end if;
end if;
end process;
sram_data_o <= wr_dat_d0;
process (clk_i) begin
if rising_edge(clk_i) then
if rst_n_i = '0' then
sram_wp <= '0';
else
sram_wp <= (wr_req_d0 or sram_wp) and rd_req_int;
end if;
end if;
end process;
sram_we <= (wr_req_d0 or sram_wp) and not rd_req_int;
process (adr_int, wr_adr_d0, sram_re) begin
if sram_re = '1' then
sram_addr_o <= adr_int(12 downto 2);
else
sram_addr_o <= wr_adr_d0(12 downto 2);
end if;
end process;
-- Register mailboxes_mboxout
mailboxes_mboxout_o <= wr_dat_d0;
mailboxes_mboxout_wr_o <= mailboxes_mboxout_wreq;
......@@ -327,7 +366,8 @@ begin
end process;
-- Process for write requests.
process (wr_adr_d0, wr_req_d0, relays_pins_0_wack, relays_pins_1_wack, relays_pins_2_wack, relays_pins_3_wack, relays_pins_4_wack, relays_pins_5_wack, relays_pins_6_wack, relays_pins_7_wack) begin
process (wr_adr_d0, sram_we, wr_req_d0, relays_pins_0_wack, relays_pins_1_wack, relays_pins_2_wack, relays_pins_3_wack, relays_pins_4_wack, relays_pins_5_wack, relays_pins_6_wack, relays_pins_7_wack) begin
sram_wr_o <= '0';
mailboxes_mboxout_wreq <= '0';
relays_pins_0_wreq <= '0';
relays_pins_1_wreq <= '0';
......@@ -337,170 +377,190 @@ begin
relays_pins_5_wreq <= '0';
relays_pins_6_wreq <= '0';
relays_pins_7_wreq <= '0';
case wr_adr_d0(6 downto 2) is
when "00000" =>
-- Reg mailboxes_mboxout
mailboxes_mboxout_wreq <= wr_req_d0;
wr_ack_int <= wr_req_d0;
when "00001" =>
-- Reg mailboxes_mboxin
wr_ack_int <= wr_req_d0;
when "00010" =>
-- Reg mailboxes_status
wr_ack_int <= wr_req_d0;
when "00100" =>
-- Reg presence
wr_ack_int <= wr_req_d0;
when "01000" =>
-- Reg loops_pins_0
wr_ack_int <= wr_req_d0;
when "01001" =>
-- Reg loops_pins_1
wr_ack_int <= wr_req_d0;
when "01010" =>
-- Reg loops_pins_2
wr_ack_int <= wr_req_d0;
when "01011" =>
-- Reg loops_pins_3
wr_ack_int <= wr_req_d0;
when "01100" =>
-- Reg loops_pins_4
wr_ack_int <= wr_req_d0;
when "01101" =>
-- Reg loops_pins_5
wr_ack_int <= wr_req_d0;
when "01110" =>
-- Reg loops_pins_6
wr_ack_int <= wr_req_d0;
when "01111" =>
-- Reg loops_pins_7
wr_ack_int <= wr_req_d0;
when "10000" =>
-- Reg relays_pins_0
relays_pins_0_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_0_wack;
when "10001" =>
-- Reg relays_pins_1
relays_pins_1_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_1_wack;
when "10010" =>
-- Reg relays_pins_2
relays_pins_2_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_2_wack;
when "10011" =>
-- Reg relays_pins_3
relays_pins_3_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_3_wack;
when "10100" =>
-- Reg relays_pins_4
relays_pins_4_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_4_wack;
when "10101" =>
-- Reg relays_pins_5
relays_pins_5_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_5_wack;
when "10110" =>
-- Reg relays_pins_6
relays_pins_6_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_6_wack;
when "10111" =>
-- Reg relays_pins_7
relays_pins_7_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_7_wack;
case wr_adr_d0(16 downto 13) is
when "1000" =>
-- Memory sram
sram_wr_o <= sram_we;
wr_ack_int <= sram_we;
when "1001" =>
case wr_adr_d0(12 downto 2) is
when "00000000000" =>
-- Reg mailboxes_mboxout
mailboxes_mboxout_wreq <= wr_req_d0;
wr_ack_int <= wr_req_d0;
when "00000000001" =>
-- Reg mailboxes_mboxin
wr_ack_int <= wr_req_d0;
when "00000000010" =>
-- Reg mailboxes_status
wr_ack_int <= wr_req_d0;
when "00000000100" =>
-- Reg presence
wr_ack_int <= wr_req_d0;
when "00000001000" =>
-- Reg loops_pins_0
wr_ack_int <= wr_req_d0;
when "00000001001" =>
-- Reg loops_pins_1
wr_ack_int <= wr_req_d0;
when "00000001010" =>
-- Reg loops_pins_2
wr_ack_int <= wr_req_d0;
when "00000001011" =>
-- Reg loops_pins_3
wr_ack_int <= wr_req_d0;
when "00000001100" =>
-- Reg loops_pins_4
wr_ack_int <= wr_req_d0;
when "00000001101" =>
-- Reg loops_pins_5
wr_ack_int <= wr_req_d0;
when "00000001110" =>
-- Reg loops_pins_6
wr_ack_int <= wr_req_d0;
when "00000001111" =>
-- Reg loops_pins_7
wr_ack_int <= wr_req_d0;
when "00000010000" =>
-- Reg relays_pins_0
relays_pins_0_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_0_wack;
when "00000010001" =>
-- Reg relays_pins_1
relays_pins_1_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_1_wack;
when "00000010010" =>
-- Reg relays_pins_2
relays_pins_2_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_2_wack;
when "00000010011" =>
-- Reg relays_pins_3
relays_pins_3_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_3_wack;
when "00000010100" =>
-- Reg relays_pins_4
relays_pins_4_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_4_wack;
when "00000010101" =>
-- Reg relays_pins_5
relays_pins_5_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_5_wack;
when "00000010110" =>
-- Reg relays_pins_6
relays_pins_6_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_6_wack;
when "00000010111" =>
-- Reg relays_pins_7
relays_pins_7_wreq <= wr_req_d0;
wr_ack_int <= relays_pins_7_wack;
when others =>
wr_ack_int <= wr_req_d0;
end case;
when others =>
wr_ack_int <= wr_req_d0;
end case;
end process;
-- Process for read requests.
process (adr_int, rd_req_int, mailboxes_mboxin_i, mailboxes_status_mbin_i, mailboxes_status_mbout_i, presence_en_i, loops_pins_0_i, loops_pins_1_i, loops_pins_2_i, loops_pins_3_i, loops_pins_4_i, loops_pins_5_i, loops_pins_6_i, loops_pins_7_i, relays_pins_0_reg, relays_pins_1_reg, relays_pins_2_reg, relays_pins_3_reg, relays_pins_4_reg, relays_pins_5_reg, relays_pins_6_reg, relays_pins_7_reg) begin
process (adr_int, sram_data_i, sram_rack, rd_req_int, mailboxes_mboxin_i, mailboxes_status_mbin_i, mailboxes_status_mbout_i, presence_en_i, loops_pins_0_i, loops_pins_1_i, loops_pins_2_i, loops_pins_3_i, loops_pins_4_i, loops_pins_5_i, loops_pins_6_i, loops_pins_7_i, relays_pins_0_reg, relays_pins_1_reg, relays_pins_2_reg, relays_pins_3_reg, relays_pins_4_reg, relays_pins_5_reg, relays_pins_6_reg, relays_pins_7_reg) begin
-- By default ack read requests
rd_dat_d0 <= (others => 'X');
sram_re <= '0';
mailboxes_mboxin_rd_o <= '0';
case adr_int(6 downto 2) is
when "00000" =>
-- Reg mailboxes_mboxout
rd_ack_d0 <= rd_req_int;
when "00001" =>
-- Reg mailboxes_mboxin
mailboxes_mboxin_rd_o <= rd_req_int;
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= mailboxes_mboxin_i;
when "00010" =>
-- Reg mailboxes_status
rd_ack_d0 <= rd_req_int;
rd_dat_d0(0) <= mailboxes_status_mbin_i;
rd_dat_d0(1) <= mailboxes_status_mbout_i;
rd_dat_d0(31 downto 2) <= (others => '0');
when "00100" =>
-- Reg presence
rd_ack_d0 <= rd_req_int;
rd_dat_d0(7 downto 0) <= presence_en_i;
rd_dat_d0(31 downto 8) <= (others => '0');
when "01000" =>
-- Reg loops_pins_0
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_0_i;
when "01001" =>
-- Reg loops_pins_1
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_1_i;
when "01010" =>
-- Reg loops_pins_2
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_2_i;
when "01011" =>
-- Reg loops_pins_3
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_3_i;
when "01100" =>
-- Reg loops_pins_4
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_4_i;
when "01101" =>
-- Reg loops_pins_5
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_5_i;
when "01110" =>
-- Reg loops_pins_6
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_6_i;
when "01111" =>
-- Reg loops_pins_7
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_7_i;
when "10000" =>
-- Reg relays_pins_0
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_0_reg;
when "10001" =>
-- Reg relays_pins_1
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_1_reg;
when "10010" =>
-- Reg relays_pins_2
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_2_reg;
when "10011" =>
-- Reg relays_pins_3
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_3_reg;
when "10100" =>
-- Reg relays_pins_4
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_4_reg;
when "10101" =>
-- Reg relays_pins_5
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_5_reg;
when "10110" =>
-- Reg relays_pins_6
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_6_reg;
when "10111" =>
-- Reg relays_pins_7
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_7_reg;
case adr_int(16 downto 13) is
when "1000" =>
-- Memory sram
rd_dat_d0 <= sram_data_i;
rd_ack_d0 <= sram_rack;
sram_re <= rd_req_int;
when "1001" =>
case adr_int(12 downto 2) is
when "00000000000" =>
-- Reg mailboxes_mboxout
rd_ack_d0 <= rd_req_int;
when "00000000001" =>
-- Reg mailboxes_mboxin
mailboxes_mboxin_rd_o <= rd_req_int;
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= mailboxes_mboxin_i;
when "00000000010" =>
-- Reg mailboxes_status
rd_ack_d0 <= rd_req_int;
rd_dat_d0(0) <= mailboxes_status_mbin_i;
rd_dat_d0(1) <= mailboxes_status_mbout_i;
rd_dat_d0(31 downto 2) <= (others => '0');
when "00000000100" =>
-- Reg presence
rd_ack_d0 <= rd_req_int;
rd_dat_d0(7 downto 0) <= presence_en_i;
rd_dat_d0(31 downto 8) <= (others => '0');
when "00000001000" =>
-- Reg loops_pins_0
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_0_i;
when "00000001001" =>
-- Reg loops_pins_1
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_1_i;
when "00000001010" =>
-- Reg loops_pins_2
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_2_i;
when "00000001011" =>
-- Reg loops_pins_3
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_3_i;
when "00000001100" =>
-- Reg loops_pins_4
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_4_i;
when "00000001101" =>
-- Reg loops_pins_5
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_5_i;
when "00000001110" =>
-- Reg loops_pins_6
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_6_i;
when "00000001111" =>
-- Reg loops_pins_7
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= loops_pins_7_i;
when "00000010000" =>
-- Reg relays_pins_0
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_0_reg;
when "00000010001" =>
-- Reg relays_pins_1
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_1_reg;
when "00000010010" =>
-- Reg relays_pins_2
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_2_reg;
when "00000010011" =>
-- Reg relays_pins_3
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_3_reg;
when "00000010100" =>
-- Reg relays_pins_4
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_4_reg;
when "00000010101" =>
-- Reg relays_pins_5
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_5_reg;
when "00000010110" =>
-- Reg relays_pins_6
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_6_reg;
when "00000010111" =>
-- Reg relays_pins_7
rd_ack_d0 <= rd_req_int;
rd_dat_d0 <= relays_pins_7_reg;
when others =>
rd_ack_d0 <= rd_req_int;
end case;
when others =>
rd_ack_d0 <= rd_req_int;
end case;
......
......@@ -134,21 +134,24 @@ begin
x"14", x"00", x"10", x"00",
others => x"00"),
-- Second command: load plc
1 => (x"10", x"2f", x"00", x"00",
x"00", x"20", x"10", x"00",
x"93", x"01", x"00", x"03",
1 => (x"10", x"2f", x"00", x"00", -- Load block
x"00", x"20", x"10", x"00", -- In plc RAM
x"93", x"01", x"00", x"04", -- plc_demo code
x"17", x"01", x"01", x"00",
x"13", x"01", x"c1", x"3f",
x"ef", x"00", x"c0", x"00",
x"ef", x"00", x"c0", x"01",
x"ef", x"00", x"40", x"01",
x"6f", x"f0", x"df", x"ff",
x"b7", x"57", x"34", x"12",
x"37", x"07", x"10", x"00",
x"93", x"87", x"87", x"67",
x"23", x"20", x"f7", x"00",
x"67", x"80", x"00", x"00",
x"b7", x"07", x"10", x"00",
x"23", x"a8", x"07", x"04",
x"67", x"80", x"00", x"00",
others => x"00"),
x"37", x"07", x"10", x"00",
x"83", x"27", x"07", x"03",
x"93", x"f7", x"17", x"00",
x"b3", x"07", x"f0", x"40",
x"93", x"f7", x"e7", x"ff",
x"23", x"28", x"f7", x"04",
x"6f", x"f0", x"df", x"fe"),
-- Third command: deassert plc reset
2 => (x"01", x"4b", x"00", x"00",
x"00", x"00", x"10", x"00",
......
......@@ -31,6 +31,7 @@ use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.wishbone_pkg.all;
use work.genram_pkg.all;
library proasic3e;
use proasic3e.all;
......@@ -156,6 +157,11 @@ architecture rtl of diot_urv_top is
signal wb_plc_in : t_wishbone_slave_in;
signal wb_plc_out : t_wishbone_slave_out;
signal plc_sram_addr : std_logic_vector(12 downto 2);
signal plc_sram_dato : std_logic_vector(31 downto 0);
signal plc_sram_dati : std_logic_vector(31 downto 0);
signal plc_sram_wr : std_logic;
-- MEM bus for FIP cpu to write into PLC memory.
signal wb_mem_in : t_wishbone_slave_in;
signal wb_mem_out : t_wishbone_slave_out;
......@@ -388,19 +394,25 @@ begin
cyc_o <= '0';
stb_o <= '0';
we_o <= '0';
fip_ack <= '0';
else
cyc_o <= fip_cyc;
stb_o <= fip_stb;
we_o <= fip_we;
dat_o <= fip_dato;
adr_o <= fip_adr;
fip_ack <= ack_i;
fip_dati <= dat_i;
end if;
end if;
end process;
inst_fip_ack: entity work.gc_sync
port map (
clk_i => clk_2,
rst_n_a_i => rst_n,
d_i => ack_i,
q_o => fip_ack
);
wclk_o <= clk_2;
rst_o <= not rst_n;
......@@ -417,8 +429,7 @@ begin
inst_plc_urv: entity work.plc_urv
generic map (
g_iram_log_size => 10,
g_dram_log_size => 12
g_iram_log_size => 10
)
port map (
clk_sys_i => clk,
......@@ -435,6 +446,10 @@ begin
clk_i => clk,
wb_i => wb_plc_in,
wb_o => wb_plc_out,
sram_addr_o => plc_sram_addr,
sram_data_i => plc_sram_dati,
sram_data_o => plc_sram_dato,
sram_wr_o => plc_sram_wr,
mailboxes_mboxout_o => mbox_in_dat,
mailboxes_mboxout_wr_o => mbox_in_wr,
mailboxes_mboxin_i => mbox_out_reg,
......@@ -466,30 +481,112 @@ begin
relays_pins_6_o => open,
relays_pins_7_o => open
);
p_ram: process (clk)
is
constant c_DRAM_LOG_SIZE : natural := 12;
variable mem : t_ram32_type (2**(c_DRAM_LOG_SIZE - 2) - 1 downto 0);
variable addr : natural range mem'range;
begin
if rising_edge(clk) then
addr := to_integer(unsigned(plc_sram_addr(c_DRAM_LOG_SIZE - 1 downto 2)));
plc_sram_dati <= mem(addr);
if plc_sram_wr = '1' then
for i in 0 to 3 loop
if true then -- if reg_dm_data_select (i) = '1' then
mem(addr)(8*i + 7 downto 8*i) := plc_sram_dato(8*i + 7 downto 8*i);
end if;
end loop;
end if;
end if;
end process;
-------------------------------------------------------------------------------
GEN_REAL_IO: block
begin
-- slots assignment
slots_loops(0)(15 downto 0) <= s1_p_b(15 downto 0);
slots_loops(1)(13 downto 0) <= s2_p_b(13 downto 0);
slots_loops(2)(13 downto 0) <= s3_p_b(13 downto 0);
slots_loops(3)(8 downto 0) <= s4_p_b(13 downto 6) & s4_p_b(3);
slots_loops(4)(13 downto 0) <= s5_p_b(13 downto 0);
slots_loops(5)(15 downto 0) <= s7_p_b(15 downto 0);
gen_slots_0: for i in 15 downto 0 generate
inst_sync: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s1_p_b(i),
q_o => slots_loops(0)(i)
);
end generate;
slots_loops(0)(31 downto 16) <= (others=>'0');
gen_slots_1: for i in 13 downto 0 generate
inst_sync: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s2_p_b(i),
q_o => slots_loops(1)(i)
);
end generate;
slots_loops(1)(31 downto 14) <= (others=>'0');
gen_slots_2: for i in 13 downto 0 generate
inst_sync: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s3_p_b(i),
q_o => slots_loops(2)(i)
);
end generate;
slots_loops(2)(31 downto 14) <= (others=>'0');
gen_slots_3: for i in 13 downto 6 generate
inst_sync: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s4_p_b(i),
q_o => slots_loops(3)(i)
);
end generate;
inst_slots_3_3: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s4_p_b(3),
q_o => slots_loops(3)(3)
);
slots_loops(3)(31 downto 14) <= (others=>'0');
slots_loops(3)(5 downto 4) <= (others=>'0');
slots_loops(3)(2 downto 0) <= (others=>'0');
gen_slots_4: for i in 13 downto 0 generate
inst_sync: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s5_p_b(i),
q_o => slots_loops(4)(i)
);
end generate;
slots_loops(4)(31 downto 14) <= (others=>'0');
gen_slots_5: for i in 15 downto 0 generate
inst_sync: entity work.gc_sync
port map (
clk_i => clk,
rst_n_a_i => rst_n,
d_i => s7_p_b(i),
q_o => slots_loops(5)(i)
);
end generate;
slots_loops(5)(31 downto 16) <= (others=>'0');
s1_n_b(15 downto 0) <= slots_relays(0)(15 downto 0);
s2_n_b(13 downto 0) <= slots_relays(1)(13 downto 0);
s3_n_b(13 downto 0) <= slots_relays(2)(13 downto 0);
s4_n_b(13 downto 6) <= slots_relays(3)(8 downto 1);
s4_n_b(3) <= slots_relays(3)(0);
s4_n_b(13 downto 6) <= slots_relays(3)(13 downto 6);
s4_n_b(3) <= slots_relays(3)(3);
s5_n_b(13 downto 0) <= slots_relays(4)(13 downto 0);
s7_n_b(15 downto 0) <= slots_relays(5)(15 downto 0);
-- not used loops
slots_loops(0)(31 downto 16) <= (others=>'0');
slots_loops(1)(31 downto 14) <= (others=>'0');
slots_loops(2)(31 downto 14) <= (others=>'0');
slots_loops(3)(31 downto 9) <= (others=>'0');
slots_loops(4)(31 downto 14) <= (others=>'0');
end block;
-- Leds: assign to '0' to switch on the led, 'Z' to switch off.
......
......@@ -9,7 +9,7 @@ SIZE = $(CROSS_COMPILE)size
PROG=plc_mbox
CFLAGS = -mabi=ilp32 -march=rv32im -Os -Wall
CFLAGS = -mabi=ilp32 -march=rv32im -Os -Wall -ffreestanding -fno-delete-null-pointer-checks
OBJS = crt0.o $(PROG).o
LDS = plc.ld
......
......@@ -8,7 +8,7 @@ MEMORY
LENGTH = 1024
bss :
ORIGIN = 0x00010000,
LENGTH = 2048
LENGTH = 4096
/* Sorry, but there is no initialized ram. */
empty :
......
......@@ -7,7 +7,7 @@ void
init (void)
{
volatile struct plc_urv_regs *regs =
(volatile struct plc_urv_regs *)0x100000;
(volatile struct plc_urv_regs *)0x00000;
regs->relays.SLOT = 0;
}
......@@ -16,9 +16,11 @@ void
main (void)
{
volatile struct plc_urv_regs *regs =
(volatile struct plc_urv_regs *)0x100000;
(volatile struct plc_urv_regs *)0x00000;
while (1) {
unsigned v = regs->loops.SLOT;
regs->relays.SLOT = -(v & 1) & (~1);
}
}
......@@ -2,87 +2,103 @@
#define __CHEBY__PLC_URV_REGS__H__
#include "mbox_regs.h"
#define PLC_URV_REGS_SIZE 96
#define PLC_URV_REGS_SIZE 73824
/* None */
#define PLC_URV_REGS_MAILBOXES 0x0UL
#define PLC_URV_REGS_SRAM 0x10000UL
#define PLC_URV_REGS_SRAM_SIZE 4
/* None */
#define PLC_URV_REGS_SRAM_VALUE 0x0UL
/* None */
#define PLC_URV_REGS_MAILBOXES 0x12000UL
#define PLC_URV_REGS_MAILBOXES_SIZE 16
/* presence lines for boards */
#define PLC_URV_REGS_PRESENCE 0x10UL
#define PLC_URV_REGS_PRESENCE 0x12010UL
#define PLC_URV_REGS_PRESENCE_EN_MASK 0xffUL
#define PLC_URV_REGS_PRESENCE_EN_SHIFT 0
/* None */
#define PLC_URV_REGS_LOOPS 0x20UL
#define PLC_URV_REGS_LOOPS 0x12020UL
#define PLC_URV_REGS_LOOPS_SIZE 32
/* None */
#define PLC_URV_REGS_LOOPS_PINS_0 0x20UL
#define PLC_URV_REGS_LOOPS_PINS_0 0x12020UL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_1 0x24UL
#define PLC_URV_REGS_LOOPS_PINS_1 0x12024UL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_2 0x28UL
#define PLC_URV_REGS_LOOPS_PINS_2 0x12028UL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_3 0x2cUL
#define PLC_URV_REGS_LOOPS_PINS_3 0x1202cUL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_4 0x30UL
#define PLC_URV_REGS_LOOPS_PINS_4 0x12030UL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_5 0x34UL
#define PLC_URV_REGS_LOOPS_PINS_5 0x12034UL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_6 0x38UL
#define PLC_URV_REGS_LOOPS_PINS_6 0x12038UL
/* None */
#define PLC_URV_REGS_LOOPS_PINS_7 0x3cUL
#define PLC_URV_REGS_LOOPS_PINS_7 0x1203cUL
/* None */
#define PLC_URV_REGS_RELAYS 0x40UL
#define PLC_URV_REGS_RELAYS 0x12040UL
#define PLC_URV_REGS_RELAYS_SIZE 32
/* None */
#define PLC_URV_REGS_RELAYS_PINS_0 0x40UL
#define PLC_URV_REGS_RELAYS_PINS_0 0x12040UL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_1 0x44UL
#define PLC_URV_REGS_RELAYS_PINS_1 0x12044UL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_2 0x48UL
#define PLC_URV_REGS_RELAYS_PINS_2 0x12048UL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_3 0x4cUL
#define PLC_URV_REGS_RELAYS_PINS_3 0x1204cUL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_4 0x50UL
#define PLC_URV_REGS_RELAYS_PINS_4 0x12050UL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_5 0x54UL
#define PLC_URV_REGS_RELAYS_PINS_5 0x12054UL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_6 0x58UL
#define PLC_URV_REGS_RELAYS_PINS_6 0x12058UL
/* None */
#define PLC_URV_REGS_RELAYS_PINS_7 0x5cUL
#define PLC_URV_REGS_RELAYS_PINS_7 0x1205cUL
struct plc_urv_regs {
/* [0x0]: SUBMAP (no description) */
/* padding to: 16384 words */
uint32_t __padding_0[16384];
/* [0x10000]: MEMORY (no description) */
struct sram {
/* [0x0]: REG (rw) (no description) */
uint32_t value;
} sram[2048];
/* [0x12000]: SUBMAP (no description) */
struct mbox_regs mailboxes;
/* padding to: 4 words */
uint32_t __padding_0[1];
/* padding to: 18436 words */
uint32_t __padding_1[1];
/* [0x10]: REG (ro) presence lines for boards */
/* [0x12010]: REG (ro) presence lines for boards */
uint32_t presence;
/* padding to: 8 words */
uint32_t __padding_1[3];
/* padding to: 18440 words */
uint32_t __padding_2[3];
/* [0x20]: BLOCK (no description) */
/* [0x12020]: BLOCK (no description) */
struct loops {
/* [0x0]: REG (ro) (no description) */
uint32_t pins_0;
......@@ -109,7 +125,7 @@ struct plc_urv_regs {
uint32_t pins_7;
} loops;
/* [0x40]: BLOCK (no description) */
/* [0x12040]: BLOCK (no description) */
struct relays {
/* [0x0]: REG (rw) (no description) */
uint32_t pins_0;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment