Commit ad0351ef authored by Andrey Filippov's avatar Andrey Filippov

re-organized top structure

parent f35bb39d
......@@ -2,41 +2,50 @@
// TODO: Fix VDT - without IVERILOG defined, closure does not include modules needed for Icarus
`define IVERILOG 1
`undef DEBUG_FIFO
`define USE_CMD_ENCOD_TILED_32_RD 1
// It can be used to check different `ifdef branches
//`define XIL_TIMING //Simprim
`define den4096Mb 1
// `define IVERILOG
// defines for memory channels
// chn 0 is read from memory
// chn 0 is read from memory and write to memory
`define def_enable_mem_chn0
`define def_read_mem_chn0
`define def_write_mem_chn0
`undef def_scanline_chn0
`undef def_tiled_chn0
// chn 1 is write to memory
// chn 1 is scanline r+w
`define def_enable_mem_chn1
`undef def_read_mem_chn1
`undef def_scanline_chn1
`define def_read_mem_chn1
`define def_write_mem_chn1
`define def_scanline_chn1
`undef def_tiled_chn1
// chn 2 is read from memory
// chn 2 is tiled r+w
`define def_enable_mem_chn2
`define def_read_mem_chn2
`define def_scanline_chn2
`define def_write_mem_chn2
`undef def_scanline_chn2
`define def_tiled_chn2
// chn 3 is write to memory
// chn 3 is scanline r+w (reuse later)
`define def_enable_mem_chn3
`undef def_read_mem_chn3
`define def_read_mem_chn3
`define def_write_mem_chn3
`define def_scanline_chn3
`undef def_tiled_chn3
// chn 4 is enabled
// chn 4 is tiled r+w (reuse later)
`define def_enable_mem_chn4
`define def_read_mem_chn4
`define def_write_mem_chn4
`undef def_scanline_chn4
`define def_tiled_chn4
// chn 5 is enabled
`define def_enable_mem_chn5
`undef def_read_mem_chn5
`define def_tiled_chn5
// chn 5 is disabled
`undef def_enable_mem_chn5
// chn 6 is disabled
`undef def_enable_mem_chn6
......
......@@ -142,9 +142,10 @@
parameter MCONTR_PHY_STATUS_REG_ADDR= 'h0,//8 or less bits: status register address to use for memory controller phy
parameter MCONTR_TOP_STATUS_REG_ADDR= 'h1,//8 or less bits: status register address to use for memory controller
parameter MCNTRL_PS_STATUS_REG_ADDR= 'h2
parameter MCNTRL_SCANLINE_STATUS_REG_CHN2_ADDR='h4,
parameter MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR='h5,
parameter MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h6,
parameter MCNTRL_SCANLINE_STATUS_REG_CHN1_ADDR='h4,
parameter MCNTRL_TILED_STATUS_REG_CHN2_ADDR= 'h5,
parameter MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR='h6,
parameter MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h7,
parameter MCNTRL_TEST01_STATUS_REG_CHN2_ADDR= 'h3c, // status/readback register for channel 2
parameter MCNTRL_TEST01_STATUS_REG_CHN3_ADDR= 'h3d, // status/readback register for channel 3
parameter MCNTRL_TEST01_STATUS_REG_CHN4_ADDR= 'h3e // status/readback register for channel 4
......
......@@ -20,6 +20,7 @@
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
//`define DEBUG_FIFO 1
`undef DEBUG_FIFO
module axibram_write #(
parameter ADDRESS_BITS = 10 // number of memory address bits
)(
......
......@@ -23,11 +23,20 @@
parameter MCONTR_CMD_WR_ADDR = 'h0000, // AXI write to command sequence memory
parameter MCONTR_BUF0_RD_ADDR = 'h0400, // AXI read address from buffer 0 (PS sequence, memory read)
parameter MCONTR_BUF1_WR_ADDR = 'h0400, // AXI write address to buffer 1 (PS sequence, memory write)
parameter MCONTR_BUF2_RD_ADDR = 'h0800, // AXI read address from buffer 2 (PL sequence, scanline, memory read)
parameter MCONTR_BUF0_WR_ADDR = 'h0400, // AXI write address to buffer 0 (PS sequence, memory write)
// parameter MCONTR_BUF0_WR_ADDR = 'h0400, // AXI write address to buffer 1 (PS sequence, memory write)
// parameter MCONTR_BUF2_RD_ADDR = 'h0800, // AXI read address from buffer 2 (PL sequence, scanline, memory read)
// parameter MCONTR_BUF3_WR_ADDR = 'h0800, // AXI write address to buffer 3 (PL sequence, scanline, memory write)
// parameter MCONTR_BUF4_RD_ADDR = 'h0c00, // AXI read address from buffer 4 (PL sequence, tiles, memory read)
// parameter MCONTR_BUF5_WR_ADDR = 'h0c00, // AXI write address to buffer 5 (PL sequence, scanline, memory write)
parameter MCONTR_BUF1_RD_ADDR = 'h0800, // AXI read address from buffer 1 (PL sequence, scanline, memory read)
parameter MCONTR_BUF1_WR_ADDR = 'h0800, // AXI write address to buffer 1 (PL sequence, scanline, memory write)
parameter MCONTR_BUF2_RD_ADDR = 'h0c00, // AXI read address from buffer 2 (PL sequence, tiles, memory read)
parameter MCONTR_BUF2_WR_ADDR = 'h0c00, // AXI write address to buffer 2 (PL sequence, tiles, memory write)
parameter MCONTR_BUF3_RD_ADDR = 'h0800, // AXI read address from buffer 3 (PL sequence, scanline, memory read)
parameter MCONTR_BUF3_WR_ADDR = 'h0800, // AXI write address to buffer 3 (PL sequence, scanline, memory write)
parameter MCONTR_BUF4_RD_ADDR = 'h0c00, // AXI read address from buffer 4 (PL sequence, tiles, memory read)
parameter MCONTR_BUF5_WR_ADDR = 'h0c00, // AXI write address to buffer 5 (PL sequence, scanline, memory write)
parameter MCONTR_BUF4_WR_ADDR = 'h0c00, // AXI write address to buffer 4 (PL sequence, tiles, memory write)
//command interface parameters
parameter DLY_LD = 'h080, // address to generate delay load
parameter DLY_LD_MASK = 'h380, // address mask to generate delay load
......@@ -181,7 +190,7 @@
parameter NUM_XFER_BITS= 6, // number of bits to specify transfer length
parameter FRAME_WIDTH_BITS= 13, // Maximal frame width - 8-word (16 bytes) bursts
parameter FRAME_HEIGHT_BITS= 16, // Maximal frame height
parameter MCNTRL_SCANLINE_CHN2_ADDR= 'h120,
parameter MCNTRL_SCANLINE_CHN1_ADDR= 'h120,
parameter MCNTRL_SCANLINE_CHN3_ADDR= 'h130,
parameter MCNTRL_SCANLINE_MASK= 'h3f0, // both channels 0 and 1
parameter MCNTRL_SCANLINE_MODE= 'h0, // set mode register: {extra_pages[1:0],enable,!reset}
......@@ -194,17 +203,18 @@
// Start XY can be used when read command to start from the middle
// TODO: Add number of blocks to R/W? (blocks can be different) - total length?
// Read back current address (for debugging)?
parameter MCNTRL_SCANLINE_STATUS_REG_CHN2_ADDR= 'h4,
parameter MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR= 'h5,
parameter MCNTRL_SCANLINE_STATUS_REG_CHN1_ADDR= 'h4,
parameter MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR= 'h6,
parameter MCNTRL_SCANLINE_PENDING_CNTR_BITS= 2, // Number of bits to count pending trasfers, currently 2 is enough, but may increase
// if memory controller will allow programming several sequences in advance to
// spread long-programming (tiled) over fast-programming (linear) requests.
// But that should not be too big to maintain 2-level priorities
parameter MCNTRL_SCANLINE_FRAME_PAGE_RESET =1'b0, // reset internal page number to zero at the frame start (false - only when hard/soft reset)
parameter MAX_TILE_WIDTH= 6, // number of bits to specify maximal tile (width-1) (6 -> 64)
parameter MAX_TILE_HEIGHT= 6, // number of bits to specify maximal tile (height-1) (6 -> 64)
parameter MCNTRL_TILED_CHN2_ADDR= 'h140,
parameter MCNTRL_TILED_CHN4_ADDR= 'h140,
parameter MCNTRL_TILED_CHN5_ADDR= 'h150,
parameter MCNTRL_TILED_MASK= 'h3f0, // both channels 0 and 1
parameter MCNTRL_TILED_MODE= 'h0, // set mode register: {extra_pages[1:0],write_mode,enable,!reset}
parameter MCNTRL_TILED_STATUS_CNTRL= 'h1, // control status reporting
......@@ -217,7 +227,8 @@
// TODO: Add number of blocks to R/W? (blocks can be different) - total length?
// Read back current address (for debugging)?
parameter MCNTRL_TILED_TILE_WHS= 'h7, // low word - 6-bit tile width in 8-bursts, high - tile height (0 - > 64)
parameter MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h6,
parameter MCNTRL_TILED_STATUS_REG_CHN2_ADDR= 'h5,
parameter MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h7,
parameter MCNTRL_TILED_PENDING_CNTR_BITS=2, // Number of bits to count pending trasfers, currently 2 is enough, but may increase
// if memory controller will allow programming several sequences in advance to
// spread long-programming (tiled) over fast-programming (linear) requests.
......@@ -228,16 +239,16 @@
// Channel test module parameters
parameter MCNTRL_TEST01_ADDR= 'h0f0,
parameter MCNTRL_TEST01_MASK= 'h3f0,
parameter MCNTRL_TEST01_CHN1_MODE= 'h2, // set mode register for channel 5
parameter MCNTRL_TEST01_CHN1_STATUS_CNTRL= 'h3, // control status reporting for channel 5
parameter MCNTRL_TEST01_CHN2_MODE= 'h4, // set mode register for channel 2
parameter MCNTRL_TEST01_CHN2_STATUS_CNTRL= 'h5, // control status reporting for channel 2
parameter MCNTRL_TEST01_CHN3_MODE= 'h6, // set mode register for channel 3
parameter MCNTRL_TEST01_CHN3_STATUS_CNTRL= 'h7, // control status reporting for channel 3
parameter MCNTRL_TEST01_CHN4_MODE= 'h8, // set mode register for channel 4
parameter MCNTRL_TEST01_CHN4_STATUS_CNTRL= 'h9, // control status reporting for channel 4
parameter MCNTRL_TEST01_CHN5_MODE= 'ha, // set mode register for channel 5
parameter MCNTRL_TEST01_CHN5_STATUS_CNTRL= 'hb, // control status reporting for channel 5
parameter MCNTRL_TEST01_STATUS_REG_CHN2_ADDR= 'h3c, // status/readback register for channel 2
parameter MCNTRL_TEST01_STATUS_REG_CHN3_ADDR= 'h3d, // status/readback register for channel 3
parameter MCNTRL_TEST01_STATUS_REG_CHN4_ADDR= 'h3e, // status/readback register for channel 4
parameter MCNTRL_TEST01_STATUS_REG_CHN5_ADDR= 'h3f // status/readback register for channel 4
parameter MCNTRL_TEST01_STATUS_REG_CHN1_ADDR= 'h3c, // status/readback register for channel 2
parameter MCNTRL_TEST01_STATUS_REG_CHN2_ADDR= 'h3d, // status/readback register for channel 3
parameter MCNTRL_TEST01_STATUS_REG_CHN3_ADDR= 'h3e, // status/readback register for channel 4
parameter MCNTRL_TEST01_STATUS_REG_CHN4_ADDR= 'h3f // status/readback register for channel 4
\ No newline at end of file
......@@ -20,8 +20,10 @@
*******************************************************************************/
// Low-level tasks
// alternative way to check for empty read queue (without a separate counter)
task write_contol_register;
input [29:0] reg_addr;
// input integer reg_addr;
input [31:0] data;
begin
axi_write_single_w(CONTROL_ADDR+reg_addr, data);
......
......@@ -31,11 +31,11 @@ task write_block_scanline_chn; // S uppressThisWarning VEditor : may be unused
begin
$display("====== write_block_scanline_chn:%d page: %x X=0x%x Y=0x%x num=%d @%t", chn, page, startX, startY,num_words, $time);
case (chn)
1: start_addr=MCONTR_BUF1_WR_ADDR + (page << 8);
1: start_addr=MCONTR_BUF0_WR_ADDR + (page << 8);
3: start_addr=MCONTR_BUF3_WR_ADDR + (page << 8);
default: begin
$display("**** ERROR: Invalid channel for write_block_scanline_chn = %d @%t", chn, $time);
start_addr = MCONTR_BUF1_WR_ADDR+ (page << 8);
start_addr = MCONTR_BUF0_WR_ADDR+ (page << 8);
end
endcase
// write_block_incremtal (start_addr, num_words, (startX<<2) + (startY<<16)); // 1 of startX is 8x16 bit, 16 bytes or 4 32-bit words
......@@ -84,12 +84,14 @@ task write_block_buf_chn; // S uppressThisWarning VEditor : may be unused
reg [29:0] start_addr;
begin
case (chn)
0: start_addr=MCONTR_BUF0_WR_ADDR + (page << 8);
1: start_addr=MCONTR_BUF1_WR_ADDR + (page << 8);
2: start_addr=MCONTR_BUF2_WR_ADDR + (page << 8);
3: start_addr=MCONTR_BUF3_WR_ADDR + (page << 8);
5: start_addr=MCONTR_BUF5_WR_ADDR + (page << 8);
4: start_addr=MCONTR_BUF4_WR_ADDR + (page << 8);
default: begin
$display("**** ERROR: Invalid channel for write buffer = %d @%t", chn, $time);
start_addr = MCONTR_BUF1_WR_ADDR+ (page << 8);
start_addr = MCONTR_BUF0_WR_ADDR+ (page << 8);
end
endcase
write_block_buf (start_addr, num_words);
......@@ -106,7 +108,7 @@ task write_block_buf;
axi_write_addr_data(
i, // id
{start_word_address,2'b0}+( i << 2),
// (MCONTR_BUF1_WR_ADDR + (page <<8)+ i) << 2, // addr
// (MCONTR_BUF0_WR_ADDR + (page <<8)+ i) << 2, // addr
i | (((i + 7) & 'hff) << 8) | (((i + 23) & 'hff) << 16) | (((i + 31) & 'hff) << 24),
4'hf, // len
1, // burst type - increment
......@@ -131,7 +133,8 @@ endtask
// read memory
task read_block_buf_chn; // S uppressThisWarning VEditor : may be unused
input integer chn; // buffer channel
// input integer chn; // buffer channel
input [3:0] chn; // buffer channel
input [1:0] page;
input integer num_read; // number of words to read (will be rounded up to multiple of 16)
input wait_done;
......@@ -139,7 +142,9 @@ task read_block_buf_chn; // S uppressThisWarning VEditor : may be unused
begin
case (chn)
0: start_addr=MCONTR_BUF0_RD_ADDR + (page << 8);
1: start_addr=MCONTR_BUF1_RD_ADDR + (page << 8);
2: start_addr=MCONTR_BUF2_RD_ADDR + (page << 8);
3: start_addr=MCONTR_BUF3_RD_ADDR + (page << 8);
4: start_addr=MCONTR_BUF4_RD_ADDR + (page << 8);
default: begin
$display("**** ERROR: Invalid channel for read buffer = %d @%t", chn, $time);
......
......@@ -57,10 +57,25 @@ endtask
task enable_memcntrl_channels;
input [15:0] chnen; // bit-per-channel, 1 - enable;
begin
ENABLED_CHANNELS = chnen; // currently enabled memory channels
write_contol_register(MCONTR_TOP_16BIT_ADDR + MCONTR_TOP_16BIT_CHN_EN, {16'b0,chnen});
end
endtask
task enable_memcntrl_en_dis;
input [3:0] chn;
input en;
begin
if (en) begin
ENABLED_CHANNELS = ENABLED_CHANNELS | (1<<chn);
end else begin
ENABLED_CHANNELS = ENABLED_CHANNELS & ~(1<<chn);
end
write_contol_register(MCONTR_TOP_16BIT_ADDR + MCONTR_TOP_16BIT_CHN_EN, {16'b0,ENABLED_CHANNELS});
end
endtask
task configure_channel_priority;
input [ 3:0] chn;
input [15:0] priority; // (higher is more important)
......
......@@ -60,13 +60,14 @@ endtask
read_and_wait_status (MCONTR_PHY_STATUS_REG_ADDR);
read_and_wait_status (MCONTR_TOP_STATUS_REG_ADDR);
read_and_wait_status (MCNTRL_PS_STATUS_REG_ADDR);
read_and_wait_status (MCNTRL_SCANLINE_STATUS_REG_CHN2_ADDR);
read_and_wait_status (MCNTRL_SCANLINE_STATUS_REG_CHN1_ADDR);
read_and_wait_status (MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR);
read_and_wait_status (MCNTRL_TILED_STATUS_REG_CHN2_ADDR);
read_and_wait_status (MCNTRL_TILED_STATUS_REG_CHN4_ADDR);
read_and_wait_status (MCNTRL_TEST01_STATUS_REG_CHN1_ADDR);
read_and_wait_status (MCNTRL_TEST01_STATUS_REG_CHN2_ADDR);
read_and_wait_status (MCNTRL_TEST01_STATUS_REG_CHN3_ADDR);
read_and_wait_status (MCNTRL_TEST01_STATUS_REG_CHN4_ADDR);
read_and_wait_status (MCNTRL_TEST01_STATUS_REG_CHN5_ADDR);
end
endtask
......@@ -86,14 +87,14 @@ endtask
program_status (MCONTR_PHY_16BIT_ADDR, MCONTR_PHY_STATUS_CNTRL, mode,seq_num); //MCONTR_PHY_STATUS_REG_ADDR= 'h0,
program_status (MCONTR_TOP_16BIT_ADDR, MCONTR_TOP_16BIT_STATUS_CNTRL, mode,seq_num); //MCONTR_TOP_STATUS_REG_ADDR= 'h1,
program_status (MCNTRL_PS_ADDR, MCNTRL_PS_STATUS_CNTRL, mode,seq_num); //MCNTRL_PS_STATUS_REG_ADDR= 'h2,
program_status (MCNTRL_SCANLINE_CHN2_ADDR, MCNTRL_SCANLINE_STATUS_CNTRL, mode,seq_num); //MCNTRL_SCANLINE_STATUS_REG_CHN2_ADDR='h4,
program_status (MCNTRL_SCANLINE_CHN1_ADDR, MCNTRL_SCANLINE_STATUS_CNTRL, mode,seq_num); //MCNTRL_SCANLINE_STATUS_REG_CHN2_ADDR='h4,
program_status (MCNTRL_SCANLINE_CHN3_ADDR, MCNTRL_SCANLINE_STATUS_CNTRL, mode,seq_num); //MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR='h5,
program_status (MCNTRL_TILED_CHN2_ADDR, MCNTRL_TILED_STATUS_CNTRL, mode,seq_num); //MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h6,
program_status (MCNTRL_TILED_CHN4_ADDR, MCNTRL_TILED_STATUS_CNTRL, mode,seq_num); //MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h6,
program_status (MCNTRL_TILED_CHN5_ADDR, MCNTRL_TILED_STATUS_CNTRL, mode,seq_num); //MCNTRL_TILED_STATUS_REG_CHN4_ADDR= 'h6,
program_status (MCNTRL_TEST01_ADDR, MCNTRL_TEST01_CHN1_STATUS_CNTRL,mode,seq_num); //MCNTRL_TEST01_STATUS_REG_CHN2_ADDR= 'h3c,
program_status (MCNTRL_TEST01_ADDR, MCNTRL_TEST01_CHN2_STATUS_CNTRL,mode,seq_num); //MCNTRL_TEST01_STATUS_REG_CHN2_ADDR= 'h3c,
program_status (MCNTRL_TEST01_ADDR, MCNTRL_TEST01_CHN3_STATUS_CNTRL,mode,seq_num); //MCNTRL_TEST01_STATUS_REG_CHN3_ADDR= 'h3d,
program_status (MCNTRL_TEST01_ADDR, MCNTRL_TEST01_CHN4_STATUS_CNTRL,mode,seq_num); //MCNTRL_TEST01_STATUS_REG_CHN4_ADDR= 'h3e,
program_status (MCNTRL_TEST01_ADDR, MCNTRL_TEST01_CHN5_STATUS_CNTRL,mode,seq_num); //MCNTRL_TEST01_STATUS_REG_CHN5_ADDR= 'h3f,
end
endtask
......
/*******************************************************************************
* Module: cmd_encod_4mux
* Date:2015-02-21
* Author: andrey
* Description: 4-to-1 mux to cmbine memory sequences sources
*
* Copyright (c) 2015 <set up in Preferences-Verilog/VHDL Editor-Templates> .
* cmd_encod_4mux.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* cmd_encod_4mux.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module cmd_encod_4mux(
input rst,
input clk,
input start0, // this channel was started
input [31:0] enc_cmd0, // encoded commnad
input enc_wr0, // write encoded command
input enc_done0, // encoding finished
input start1, // this channel was started
input [31:0] enc_cmd1, // encoded commnad
input enc_wr1, // write encoded command
input enc_done1, // encoding finished
input start2, // this channel was started
input [31:0] enc_cmd2, // encoded commnad
input enc_wr2, // write encoded command
input enc_done2, // encoding finished
input start3, // this channel was started
input [31:0] enc_cmd3, // encoded commnad
input enc_wr3, // write encoded command
input enc_done3, // encoding finished
output reg start, // combined output was started (1 clk from |start*)
output reg [31:0] enc_cmd, // encoded commnad
output reg enc_wr, // write encoded command
output reg enc_done // encoding finished
);
reg [3:0] select;
wire start_w= start0 | start1 |start2 | start3;
always @ (posedge rst or posedge clk) begin
if (rst) start <= 0;
else start <= start_w;
if (rst) select <= 0;
else if (start_w) select <={ // normally should be no simultaneous starts, so priority is not needed
start3 & ~start2 & ~start1 & ~start0,
start2 & ~start1 & ~start0,
start1 & ~start0,
start0};
end
always @(posedge clk) begin
enc_cmd <= ({32{select[0]}} & enc_cmd0) |
({32{select[1]}} & enc_cmd1) |
({32{select[2]}} & enc_cmd2) |
({32{select[3]}} & enc_cmd3);
enc_wr <= (select[0] & enc_wr0) |
(select[1] & enc_wr1) |
(select[2] & enc_wr2) |
(select[3] & enc_wr3);
enc_done <= (select[0] & enc_done0) |
(select[1] & enc_done1) |
(select[2] & enc_done2) |
(select[3] & enc_done3);
end
endmodule
This diff is collapsed.
/*******************************************************************************
* Module: cmd_encod_linear_rw
* Date:2015-02-21
* Author: andrey
* Description: Combining 2 modules:cmd_encod_linear_rd and cmd_encod_linear_wr
*
* Copyright (c) 2015 <set up in Preferences-Verilog/VHDL Editor-Templates> .
* cmd_encod_linear_rw.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* cmd_encod_linear_rw.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module cmd_encod_linear_rw#(
// parameter BASEADDR = 0,
parameter ADDRESS_NUMBER= 15,
parameter COLADDR_NUMBER= 10,
parameter NUM_XFER_BITS= 6, // number of bits to specify transfer length
parameter CMD_PAUSE_BITS= 10,
parameter CMD_DONE_BIT= 10 // VDT BUG: CMD_DONE_BIT is used in a function call parameter!
) (
input rst,
input clk,
// programming interface
// input [7:0] cmd_ad, // byte-serial command address/data (up to 6 bytes: AL-AH-D0-D1-D2-D3
// input cmd_stb, // strobe (with first byte) for the command a/d
input [2:0] bank_in, // bank address
input [ADDRESS_NUMBER-1:0] row_in, // memory row
input [COLADDR_NUMBER-4:0] start_col, // start memory column in 8-bursts
input [NUM_XFER_BITS-1:0] num128_in, // number of 128-bit words to transfer (8*16 bits) - full bursts of 8 ( 0 - maximal length, 64)
input skip_next_page_in, // do not reset external buffer (continue)
input start_rd, // start generating commands by cmd_encod_linear_rd
input start_wr, // start generating commands by cmd_encod_linear_wr
output reg start, // this channel was started (1 clk from start_rd || start_wr
output reg [31:0] enc_cmd, // encoded commnad
output reg enc_wr, // write encoded command
output reg enc_done // encoding finished
);
wire [31:0] enc_cmd_rd; // encoded commnad
wire enc_wr_rd; // write encoded command
wire enc_done_rd; // encoding finished
wire [31:0] enc_cmd_wr; // encoded commnad
wire enc_wr_wr; // write encoded command
wire enc_done_wr; // encoding finished
reg select_wr;
cmd_encod_linear_rd #(
.ADDRESS_NUMBER (ADDRESS_NUMBER),
.COLADDR_NUMBER (COLADDR_NUMBER),
.NUM_XFER_BITS (NUM_XFER_BITS),
.CMD_PAUSE_BITS (CMD_PAUSE_BITS),
.CMD_DONE_BIT (CMD_DONE_BIT)
) cmd_encod_linear_rd_i (
.rst (rst), // input
.clk (clk), // input
.bank_in (bank_in), // input[2:0]
.row_in (row_in), // input[14:0]
.start_col (start_col), // input[6:0]
.num128_in (num128_in), // input[5:0]
.skip_next_page_in (skip_next_page_in), // input
.start (start_rd), // input
.enc_cmd (enc_cmd_rd), // output[31:0] reg
.enc_wr (enc_wr_rd), // output reg
.enc_done (enc_done_rd) // output reg
);
cmd_encod_linear_wr #(
.ADDRESS_NUMBER (ADDRESS_NUMBER),
.COLADDR_NUMBER (COLADDR_NUMBER),
.NUM_XFER_BITS (NUM_XFER_BITS),
.CMD_PAUSE_BITS (CMD_PAUSE_BITS),
.CMD_DONE_BIT (CMD_DONE_BIT)
) cmd_encod_linear_wr_i (
.rst (rst), // input
.clk (clk), // input
.bank_in (bank_in), // input[2:0]
.row_in (row_in), // input[14:0]
.start_col (start_col), // input[6:0]
.num128_in (num128_in), // input[5:0]
.skip_next_page_in (skip_next_page_in), // input
.start (start_wr), // input
.enc_cmd (enc_cmd_wr), // output[31:0] reg
.enc_wr (enc_wr_wr), // output reg
.enc_done (enc_done_wr) // output reg
);
always @(posedge rst or posedge clk) begin
if (rst) start <= 0;
else start <= start_rd || start_wr;
if (rst) select_wr <= 0;
else if (start_rd) select_wr <= 0;
else if (start_wr) select_wr <= 1;
end
always @(posedge clk) begin
enc_cmd <= select_wr? enc_cmd_wr: enc_cmd_rd;
enc_wr <= select_wr? enc_wr_wr: enc_wr_rd;
enc_done <= select_wr? enc_done_wr: enc_done_rd;
end
endmodule
/*******************************************************************************
* Module: cmd_encod_tiled_32_rw
* Date:2015-02-21
* Author: andrey
* Description: Combines cmd_encod_tiled_32_rd and cmd_encod_tiled_32_wr modules
*
* Copyright (c) 2015 <set up in Preferences-Verilog/VHDL Editor-Templates> .
* cmd_encod_tiled_32_rw.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* cmd_encod_tiled_32_rw.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module cmd_encod_tiled_32_rw #(
parameter ADDRESS_NUMBER= 15,
parameter COLADDR_NUMBER= 10,
parameter CMD_PAUSE_BITS= 10,
parameter CMD_DONE_BIT= 10, // VDT BUG: CMD_DONE_BIT is used in a function call parameter!
parameter FRAME_WIDTH_BITS= 13 // Maximal frame width - 8-word (16 bytes) bursts
) (
input rst,
input clk,
// programming interface
input [2:0] start_bank, // bank address
input [ADDRESS_NUMBER-1:0] start_row, // memory row
input [COLADDR_NUMBER-4:0] start_col, // start memory column in 8-bit bursts
input [FRAME_WIDTH_BITS:0] rowcol_inc_in, // increment {row.col} when bank rolls over, removed 3 LSBs (in 8-bursts)
input [5:0] num_rows_in_m1, // number of rows to read minus 1
input [5:0] num_cols_in_m1, // number of 16-pixel columns to read (rows first, then columns) - 1
input keep_open_in, // keep banks open (for <=8 banks only
input skip_next_page_in, // do not reset external buffer (continue)
input start_rd, // start generating commands by cmd_encod_linear_rd
input start_wr, // start generating commands by cmd_encod_linear_wr
output reg start, // this channel was started (1 clk from start_rd || start_wr
output reg [31:0] enc_cmd, // encoded commnad
output reg enc_wr, // write encoded command
output reg enc_done // encoding finished
);
wire [31:0] enc_cmd_rd; // encoded commnad
wire enc_wr_rd; // write encoded command
wire enc_done_rd; // encoding finished
wire [31:0] enc_cmd_wr; // encoded commnad
wire enc_wr_wr; // write encoded command
wire enc_done_wr; // encoding finished
reg select_wr;
cmd_encod_tiled_32_rd #(
.ADDRESS_NUMBER (ADDRESS_NUMBER),
.COLADDR_NUMBER (COLADDR_NUMBER),
.CMD_PAUSE_BITS (CMD_PAUSE_BITS),
.CMD_DONE_BIT (CMD_DONE_BIT)
) cmd_encod_tiled_rd_i (
.rst (rst), // input
.clk (clk), // input
.start_bank (start_bank), // input[2:0]
.start_row (start_row), // input[14:0]
.start_col (start_col), // input[6:0]
.rowcol_inc_in (rowcol_inc_in), // input[13:0] // [21:0]
.num_rows_in_m1 (num_rows_in_m1), // input[5:0]
.num_cols_in_m1 (num_cols_in_m1), // input[5:0]
.keep_open_in (keep_open_in), // input
.skip_next_page_in (skip_next_page_in), // input
.start (start_rd), // input
.enc_cmd (enc_cmd_rd), // output[31:0] reg
.enc_wr (enc_wr_rd), // output reg
.enc_done (enc_done_rd) // output reg
);
cmd_encod_tiled_32_wr #(
.ADDRESS_NUMBER (ADDRESS_NUMBER),
.COLADDR_NUMBER (COLADDR_NUMBER),
.CMD_PAUSE_BITS (CMD_PAUSE_BITS),
.CMD_DONE_BIT (CMD_DONE_BIT)
) cmd_encod_tiled_wr_i (
.rst (rst), // input
.clk (clk), // input
.start_bank (start_bank), // input[2:0]
.start_row (start_row), // input[14:0]
.start_col (start_col), // input[6:0]
.rowcol_inc_in (rowcol_inc_in), // input[13:0] // [21:0]
.num_rows_in_m1 (num_rows_in_m1), // input[5:0]
.num_cols_in_m1 (num_cols_in_m1), // input[5:0]
.keep_open_in (keep_open_in), // input
.skip_next_page_in (skip_next_page_in), // input
.start (start_wr), // input
.enc_cmd (enc_cmd_wr), // output[31:0] reg
.enc_wr (enc_wr_wr), // output reg
.enc_done (enc_done_wr) // output reg
);
always @(posedge rst or posedge clk) begin
if (rst) start <= 0;
else start <= start_rd || start_wr;
if (rst) select_wr <= 0;
else if (start_rd) select_wr <= 0;
else if (start_wr) select_wr <= 1;
end
always @(posedge clk) begin
enc_cmd <= select_wr? enc_cmd_wr: enc_cmd_rd;
enc_wr <= select_wr? enc_wr_wr: enc_wr_rd;
enc_done <= select_wr? enc_done_wr: enc_done_rd;
end
endmodule
This diff is collapsed.
/*******************************************************************************
* Module: cmd_encod_tiled_rw
* Date:2015-02-21
* Author: andrey
* Description: Combines cmd_encod_tiled_rd and cmd_encod_tiled_wr modules
*
* Copyright (c) 2015 <set up in Preferences-Verilog/VHDL Editor-Templates> .
* cmd_encod_tiled_rw.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* cmd_encod_tiled_rw.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module cmd_encod_tiled_rw #(
parameter ADDRESS_NUMBER= 15,
parameter COLADDR_NUMBER= 10,
parameter CMD_PAUSE_BITS= 10,
parameter CMD_DONE_BIT= 10, // VDT BUG: CMD_DONE_BIT is used in a function call parameter!
parameter FRAME_WIDTH_BITS= 13 // Maximal frame width - 8-word (16 bytes) bursts
) (
input rst,
input clk,
// programming interface
input [2:0] start_bank, // bank address
input [ADDRESS_NUMBER-1:0] start_row, // memory row
input [COLADDR_NUMBER-4:0] start_col, // start memory column in 8-bit bursts
input [FRAME_WIDTH_BITS:0] rowcol_inc_in, // increment {row.col} when bank rolls over, removed 3 LSBs (in 8-bursts)
input [5:0] num_rows_in_m1, // number of rows to read minus 1
input [5:0] num_cols_in_m1, // number of 16-pixel columns to read (rows first, then columns) - 1
input keep_open_in, // keep banks open (for <=8 banks only
input skip_next_page_in, // do not reset external buffer (continue)
input start_rd, // start generating commands by cmd_encod_linear_rd
input start_wr, // start generating commands by cmd_encod_linear_wr
output reg start, // this channel was started (1 clk from start_rd || start_wr
output reg [31:0] enc_cmd, // encoded commnad
output reg enc_wr, // write encoded command
output reg enc_done // encoding finished
);
wire [31:0] enc_cmd_rd; // encoded commnad
wire enc_wr_rd; // write encoded command
wire enc_done_rd; // encoding finished
wire [31:0] enc_cmd_wr; // encoded commnad
wire enc_wr_wr; // write encoded command
wire enc_done_wr; // encoding finished
reg select_wr;
cmd_encod_tiled_rd #(
.ADDRESS_NUMBER (ADDRESS_NUMBER),
.COLADDR_NUMBER (COLADDR_NUMBER),
.CMD_PAUSE_BITS (CMD_PAUSE_BITS),
.CMD_DONE_BIT (CMD_DONE_BIT)
) cmd_encod_tiled_rd_i (
.rst (rst), // input
.clk (clk), // input
.start_bank (start_bank), // input[2:0]
.start_row (start_row), // input[14:0]
.start_col (start_col), // input[6:0]
.rowcol_inc_in (rowcol_inc_in), // input[13:0] // [21:0]
.num_rows_in_m1 (num_rows_in_m1), // input[5:0]
.num_cols_in_m1 (num_cols_in_m1), // input[5:0]
.keep_open_in (keep_open_in), // input
.skip_next_page_in (skip_next_page_in), // input
.start (start_rd), // input
.enc_cmd (enc_cmd_rd), // output[31:0] reg
.enc_wr (enc_wr_rd), // output reg
.enc_done (enc_done_rd) // output reg
);
cmd_encod_tiled_wr #(
.ADDRESS_NUMBER (ADDRESS_NUMBER),
.COLADDR_NUMBER (COLADDR_NUMBER),
.CMD_PAUSE_BITS (CMD_PAUSE_BITS),
.CMD_DONE_BIT (CMD_DONE_BIT)
) cmd_encod_tiled_wr_i (
.rst (rst), // input
.clk (clk), // input
.start_bank (start_bank), // input[2:0]
.start_row (start_row), // input[14:0]
.start_col (start_col), // input[6:0]
.rowcol_inc_in (rowcol_inc_in), // input[13:0] // [21:0]
.num_rows_in_m1 (num_rows_in_m1), // input[5:0]
.num_cols_in_m1 (num_cols_in_m1), // input[5:0]
.keep_open_in (keep_open_in), // input
.skip_next_page_in (skip_next_page_in), // input
.start (start_wr), // input
.enc_cmd (enc_cmd_wr), // output[31:0] reg
.enc_wr (enc_wr_wr), // output reg
.enc_done (enc_done_wr) // output reg
);
always @(posedge rst or posedge clk) begin
if (rst) start <= 0;
else start <= start_rd || start_wr;
if (rst) select_wr <= 0;
else if (start_rd) select_wr <= 0;
else if (start_wr) select_wr <= 1;
end
always @(posedge clk) begin
enc_cmd <= select_wr? enc_cmd_wr: enc_cmd_rd;
enc_wr <= select_wr? enc_wr_wr: enc_wr_rd;
enc_done <= select_wr? enc_done_wr: enc_done_rd;
end
endmodule
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
......@@ -53,33 +53,27 @@ module mcntrl_ps_pio#(
input [31:0] port1_data,
// memory controller interface
// read port 0
output reg want_rq0,
output reg need_rq0,
input channel_pgm_en0,
output [9:0] seq_data0, // only address
output seq_set0,
input seq_done0,
input buf_wr_chn0,
input buf_wpage_nxt_chn0,
input buf_run0, // @ negedge, use to force page nimber in the buffer (use fifo)
input [63:0] buf_wdata_chn0,
// write port 1
output reg want_rq1,
output reg need_rq1,
input channel_pgm_en1,
input seq_done1,
input rpage_nxt_chn1,
input buf_run1, // @ posedge, use to force page nimber in the buffer (use fifo)
input buf_rd_chn1,
output [63:0] buf_rdata_chn1
output reg want_rq,
output reg need_rq,
input channel_pgm_en,
output [9:0] seq_data, // only address
output seq_set,
input seq_done,
input buf_wr,
input buf_wpage_nxt,
input buf_run, // @ posedge, use to force page nimber in the buffer (use fifo)
input buf_wrun, // @ negedge, use to force page nimber in the buffer (use fifo)
input [63:0] buf_wdata,
input buf_rpage_nxt,
input buf_rd, //buf_rd_chn1,
output [63:0] buf_rdata // buf_rdata_chn1
);
localparam CMD_WIDTH=15;
localparam CMD_FIFO_DEPTH=4;
localparam PAGE_FIFO_DEPTH = 4;// fifo depth to hold page numbers for channels (2 bits should be OK now)
localparam PAGE_CNTR_BITS = 4;
wire channel_pgm_en=channel_pgm_en0 || channel_pgm_en1;
wire seq_done= seq_done0 || seq_done1;
reg [PAGE_CNTR_BITS-1:0] pending_pages;
......@@ -104,31 +98,38 @@ module mcntrl_ps_pio#(
wire short_busy; // does not include memory transaction
wire start;
//reg [1:0] page;
reg [1:0] page_neg;
reg [1:0] cmd_set_d;
// command bit fields
wire [9:0] cmd_seq_a= cmd_out[9:0];
wire [1:0] cmd_page= cmd_out[11:10];
wire cmd_need= cmd_out[12];
wire cmd_chn= cmd_out[13];
wire cmd_wr= cmd_out[13]; // chn= cmd_out[13]; command write, not read
wire cmd_wait= cmd_out[14]; // wait cmd finished before proceeding
reg cmd_set;
reg cmd_wait_r;
reg channel_pgm_en0_neg;
wire [1:0] page_out_chn0;
wire [1:0] page_out_chn1;
wire [1:0] page_out;
reg nreset_page_fifo;
reg nreset_page_fifo_neg;
// wire page_fifo0_nempty_neg;
// wire page_fifo1_nempty;
// reg page_fifo0_nempty;
assign short_busy= want_rq0 || need_rq0 ||want_rq1 || need_rq1 || cmd_set; // cmd_set - advance FIFO
wire cmd_wr_out;
reg [1:0] page_out_r;
reg [1:0] page_out_r_negedge;
reg page_r_set;
reg page_w_set_early;
reg page_w_set_early_negedge;
reg en_page_w_set;
reg page_w_set_negedge;
// assign short_busy= want_rq || need_rq ||want_rq1 || need_rq1 || cmd_set; // cmd_set - advance FIFO
assign short_busy= want_rq || need_rq || cmd_set; // cmd_set - advance FIFO
assign busy= short_busy || (pending_pages != 0); // mem_run;
assign start= chn_en && !short_busy && cmd_nempty && ((pending_pages == 0) || !cmd_wait_r); //(!mem_run || !cmd_wait_r); // do not wait memory transaction if wait
assign seq_data0= cmd_seq_a;
assign seq_set0=cmd_set;
assign seq_data= cmd_seq_a;
assign seq_set=cmd_set;
assign status_data= {cmd_half_full,cmd_nempty | busy};
assign set_cmd_w = cmd_we && (cmd_a== MCNTRL_PS_CMD);
assign set_status_w = cmd_we && (cmd_a== MCNTRL_PS_STATUS_CNTRL);
......@@ -149,25 +150,16 @@ module mcntrl_ps_pio#(
else if (set_en_rst) en_reset <= cmd_data[1:0];
if (rst) begin
want_rq0 <= 0;
need_rq0 <= 0;
want_rq1 <= 0;
need_rq1 <= 0;
want_rq <= 0;
need_rq <= 0;
end else if (chn_rst || channel_pgm_en) begin
want_rq0 <= 0;
need_rq0 <= 0;
want_rq1 <= 0;
need_rq1 <= 0;
want_rq <= 0;
need_rq <= 0;
end else if (start) begin
want_rq0 <= !cmd_chn;
need_rq0 <= !cmd_chn && cmd_need;
want_rq1 <= cmd_chn;
need_rq1 <= cmd_chn && cmd_need;
want_rq <= 1; // !cmd_chn;
need_rq <= cmd_need; // !cmd_chn && cmd_need;
end
// if (rst) mem_run <=0;
// else if (chn_rst || seq_done) mem_run <=0;
// else if (channel_pgm_en) mem_run <=1;
if (rst) cmd_set <= 0;
else if (chn_rst) cmd_set <= 0;
......@@ -175,19 +167,10 @@ module mcntrl_ps_pio#(
if (rst) cmd_set_d <= 0;
else cmd_set_d <= {cmd_set_d[0],cmd_set& ~cmd_chn}; // only for channel0 (memory read)
// if (rst) page_fifo0_nempty <= 0;
// else page_fifo0_nempty <=page_fifo0_nempty_neg;
// else cmd_set_d <= {cmd_set_d[0],cmd_set& ~cmd_chn}; // only for channel0 (memory read)
else cmd_set_d <= {cmd_set_d[0],cmd_set & ~cmd_wr}; // only for channel0 (memory read)
end
always @ (negedge mclk) begin
page_neg <= cmd_page; // page;
// wpage_set_chn0_neg <= cmd_set_d[1];
nreset_page_fifo_neg <= nreset_page_fifo;
channel_pgm_en0_neg <= channel_pgm_en0;
end
cmd_deser #(
.ADDR (MCNTRL_PS_ADDR),
......@@ -251,12 +234,12 @@ fifo_same_clock #(
.ext_regen (port0_regen), // input
.ext_data_out (port0_data), // output[31:0]
.wclk (!mclk), // input
.wpage_in (page_out_chn0), // page_neg), // input[1:0]
.wpage_set (buf_run0), //wpage_set_chn0_neg), // input
.page_next (buf_wpage_nxt_chn0), // input
.wpage_in (page_out_r_negedge), // page_neg), // input[1:0]
.wpage_set (page_w_set_negedge), //wpage_set_chn0_neg), // input
.page_next (buf_wpage_nxt), // input
.page (), // output[1:0]
.we (buf_wr_chn0), // input
.data_in (buf_wdata_chn0) // input[63:0]
.we (buf_wr), // input
.data_in (buf_wdata) // input[63:0]
);
// Port 1 (write DDR from AXI) buffer
......@@ -264,45 +247,51 @@ fifo_same_clock #(
.ext_clk (port1_clk), // input
.ext_waddr (port1_addr), // input[9:0]
.ext_we (port1_we), // input
.ext_data_in (port1_data), // input[31:0] buf_wdata - from AXI
.ext_data_in (port1_data), // input[31:0]
.rclk (mclk), // input
.rpage_in (page_out_chn1), //page), // input[1:0]
.rpage_set (buf_run1), // rpage_set_chn1), // input
.page_next (rpage_nxt_chn1), // input
.rpage_in (page_out_r), //page), // input[1:0]
.rpage_set (page_r_set), // rpage_set_chn1), // input
.page_next (buf_rpage_nxt), // input
.page (), // output[1:0]
.rd (buf_rd_chn1), // input
.data_out (buf_rdata_chn1) // output[63:0]
);
fifo_same_clock #(
.DATA_WIDTH(2),
.DATA_DEPTH(PAGE_FIFO_DEPTH)
) page_fifo0_i (
.rst (rst),
.clk (!mclk), // negedge
.sync_rst (!nreset_page_fifo_neg), // synchronously reset fifo;
.we (channel_pgm_en0_neg),
.re (buf_run0),
.data_in (page_neg),
.data_out (page_out_chn0),
.nempty (), //page_fifo0_nempty_neg),
.half_full ()
.rd (buf_rd), // input
.data_out (buf_rdata) // output[63:0]
);
fifo_same_clock #(
.DATA_WIDTH(2),
.DATA_WIDTH(3),
.DATA_DEPTH(PAGE_FIFO_DEPTH)
) page_fifo1_i (
.rst (rst),
.clk (mclk), // posedge
.sync_rst (!nreset_page_fifo), // synchronously reset fifo;
.we (channel_pgm_en1),
.re (buf_run1),
.data_in (cmd_page), //page),
.data_out (page_out_chn1),
.we (channel_pgm_en),
.re (buf_run),
.data_in ({cmd_wr,cmd_page}), //page),
.data_out ({cmd_wr_out,page_out}),
.nempty (), //page_fifo1_nempty),
.half_full ()
);
always @ (posedge rst or posedge mclk) begin
if (rst) page_out_r <= 0;
else if (buf_run) page_out_r <= page_out;
end
always @ (posedge mclk) begin
page_r_set <= cmd_wr_out && buf_run; // page_out_r, page_r_set - output to buffer
page_w_set_early <= !cmd_wr_out && buf_run;
end
always @ (negedge mclk) begin
nreset_page_fifo_neg <= nreset_page_fifo;
page_w_set_early_negedge <= page_w_set_early;
page_out_r_negedge <= page_out_r;
if (!nreset_page_fifo_neg || buf_wrun) en_page_w_set <= 0;
else if (page_w_set_early_negedge) en_page_w_set <= 1;
page_w_set_negedge <= en_page_w_set && buf_wrun;
end
endmodule
This diff is collapsed.
This diff is collapsed.
......@@ -143,6 +143,7 @@ module mcontr_sequencer #(
// Interface to write-to-memory buffers (up to 16)
// There will be =1 cycle external latency in address/re and 1 cycle latency in read data (should match sequence programs)
// Address data is sync to posedge mclk
output ext_buf_page_nxt, // Generated for both reads and writes, @posedge mclk
output ext_buf_rd,
output ext_buf_rpage_nxt, // increment external buffer read address to next page start
// output [6:0] ext_buf_raddr, // valid with ext_buf_rd, 2 page MSB to be generated externally
......@@ -217,7 +218,8 @@ module mcontr_sequencer #(
wire [31:0] phy_cmd_word; // selected output from either cmd0 buffer or cmd1 buffer
wire [31:0] phy_cmd0_word; // cmd0 buffer output
wire [31:0] phy_cmd1_word; // cmd1 buffer output
wire buf_raddr_reset;
reg buf_raddr_reset;
reg buf_addr_reset; // generated regardless of read/write
// reg [ 6:0] buf_raddr;
reg buf_waddr_reset_negedge;
// reg [ 6:0] buf_waddr_negedge;
......@@ -260,6 +262,7 @@ module mcontr_sequencer #(
reg run_w_d_negedge;
reg run_seq_d;
reg mem_read_mode; // last was buf_wr, not buf_rd
wire [7:0] tmp_debug_a;
assign tmp_debug[11:0] =
......@@ -284,9 +287,10 @@ module mcontr_sequencer #(
// External buffers buffer related signals
assign buf_raddr_reset= buf_rst; // run_seq_d;
// assign buf_raddr_reset= buf_rst & ~mem_read_mode; // run_seq_d;
assign ext_buf_rd= buf_rd;
assign ext_buf_rpage_nxt=buf_raddr_reset;
assign ext_buf_page_nxt= buf_addr_reset;
// assign ext_buf_raddr= buf_raddr;
assign ext_buf_rchn= run_chn_d;
assign ext_buf_rrefresh= run_refresh_d;
......@@ -469,6 +473,18 @@ module mcontr_sequencer #(
if (rst) run_seq_d <= 0;
else run_seq_d <= run_seq;
if (rst) buf_raddr_reset <= 0;
else buf_raddr_reset<= buf_rst & ~mem_read_mode;
if (rst) buf_addr_reset <= 0;
else buf_addr_reset<= buf_rst;
end
always @ (posedge mclk) begin
if (buf_wr) mem_read_mode <= 1; // last was buf_wr, not buf_rd
else if (buf_rd) mem_read_mode <= 0;
end
// re-register buffer write address to match DDR3 data
always @ (negedge mclk) begin
......@@ -613,7 +629,7 @@ module mcontr_sequencer #(
.clk(mclk), // input
.rst(1'b0), // input
.dly(wbuf_delay[3:0]), // input[3:0]
.din({buf_rst,buf_wr_ndly}), // input
.din({mem_read_mode & buf_rst,buf_wr_ndly}), // input
.dout({buf_rst_d, buf_wr}) // output reg
);
assign wbuf_delay_m1=wbuf_delay-1;
......
......@@ -27,10 +27,12 @@ module mcont_common_chnbuf_reg #(
input clk,
input [3:0] ext_buf_rchn, // ==run_chn_d valid 1 cycle ahead of ext_buf_rd!, maybe not needed - will be generated externally
input ext_buf_rrefresh,
input ext_buf_rpage_nxt,
input ext_buf_page_nxt,
input seq_done, // sequence done
input ext_buf_run,
output reg buf_done, // sequence done for the specified channel
output reg rpage_nxt
output reg page_nxt,
output reg buf_run
);
reg buf_chn_sel;
always @ (posedge rst or posedge clk) begin
......@@ -40,7 +42,10 @@ module mcont_common_chnbuf_reg #(
if (rst) buf_done <= 0;
else buf_done <= buf_chn_sel && seq_done;
if (rst) buf_run <= 0;
else buf_run <= (ext_buf_rchn==CHN_NUMBER) && !ext_buf_rrefresh && ext_buf_run;
end
always @ (posedge clk) rpage_nxt <= ext_buf_rpage_nxt && (ext_buf_rchn==CHN_NUMBER) && !ext_buf_rrefresh;
always @ (posedge clk) page_nxt <= ext_buf_page_nxt && (ext_buf_rchn==CHN_NUMBER) && !ext_buf_rrefresh;
endmodule
......@@ -29,10 +29,12 @@ module mcont_from_chnbuf_reg #(
input ext_buf_rd,
input [3:0] ext_buf_rchn, // ==run_chn_d valid 1 cycle ahead opf ext_buf_rd!, maybe not needed - will be generated externally
input ext_buf_rrefresh,
input ext_buf_rrun,
// input ext_buf_rrun,
input ext_buf_rpage_nxt,
output reg [63:0] ext_buf_rdata, // Latency of ram_1kx32w_512x64r plus 2
output reg buf_rd_chn,
output reg buf_run,
// output reg buf_run,
output reg rpage_nxt,
input [63:0] buf_rdata_chn
);
reg buf_chn_sel;
......@@ -44,8 +46,8 @@ module mcont_from_chnbuf_reg #(
if (rst) buf_rd_chn <= 0;
else buf_rd_chn <= buf_chn_sel && ext_buf_rd;
if (rst) buf_run <= 0;
else buf_run <= (ext_buf_rchn==CHN_NUMBER) && !ext_buf_rrefresh && ext_buf_rrun;
// if (rst) buf_run <= 0;
// else buf_run <= (ext_buf_rchn==CHN_NUMBER) && !ext_buf_rrefresh && ext_buf_rrun;
if (rst) latency_reg<= 0;
// else latency_reg <= buf_rd_chn | (latency_reg << 1);
......@@ -57,5 +59,7 @@ module mcont_from_chnbuf_reg #(
// always @ (posedge clk) buf_raddr_rst_chn <= ext_buf_raddr_rst && (ext_buf_rchn==CHN_NUMBER);
// always @ (posedge clk) if (buf_chn_sel && ext_buf_rd) buf_raddr_chn <= ext_buf_raddr;
always @ (posedge clk) if (latency_reg[CHN_LATENCY]) ext_buf_rdata <= buf_rdata_chn;
always @ (posedge clk) rpage_nxt <= ext_buf_rpage_nxt && (ext_buf_rchn==CHN_NUMBER) && !ext_buf_rrefresh;
endmodule
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
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