A Color Vision System for Embedded Robotics Applications

Click here to return to article

Verilog FPGA RAM_SCHEDULER.V:

Changes in Blue/Bold


module ram_scheduler(
			input wire sys_clock,
			input wire force_reset,

			input wire [14:0] proc_data_w,
			input wire qual2_data,
			input wire [17:1] proc_addr,

			input wire [17:0] disp_data_get_addr,
			input wire disp_data_get_strb,			
			output reg [14:0] disp_data,

			input wire [17:0] video1_addr,
			input wire [14:0] video1_data,
			input wire video1_store_strb,

			input wire [17:0] retrieve_addr,
			output reg [14:0] retrieve_data,
			input wire retrieve_get_strb,
			output reg retrieve_data_ready_strb

			input wire disp_ping_pong,

			output reg ram_we,
			output reg ram_oe,
			output reg ram_ce,
			output reg [19:1] ram_addr,
			inout wire [14:0] ram_data_io,
			
			output reg fifo_error,
			input wire clear_fifo_error
			);

reg [10:0] store_state_var;

reg clear_display_read_pending;
reg display_read_pending;
reg ram_data_mux1;
reg ram_data_mux2;

wire [14:0] proc_fifo_dout;
wire [17:0] proc_fifo_aout;
reg p_write_fifo_re;
wire proc_write_fifo_epty;

wire [14:0] video1_fifo_dout;
wire [17:0] video1_fifo_aout;
reg video1_fifo_re;
wire video1_write_fifo_epty;

wire f1_full;

parameter[10:0]
			DISPATCH_STATE		= 11'b00000000001,
			STORE_PROC1_STATE	= 11'b00000000010,
			STORE_PROC2_STATE	= 11'b00000000100,
			GET_DISP1_STATE	= 11'b00000001000,
			GET_DISP2_STATE	= 11'b00000010000,
			STORE_VID1_STATE1	= 11'b00000100000,
			STORE_VID1_STATE2	= 11'b00001000000,
			STORE_VID1_STATE3	= 11'b00010000000,
			RETRIEVE_STATE0	= 11'b00100000000,
			RETRIEVE_STATE1	= 11'b01000000000,
			RETRIEVE_STATE2	= 11'b10000000000;

parameter[10:0]
			DISPATCH_CASE		= 11'bxxxxxxxxxx1,
			STORE_PROC1_CASE	= 11'bxxxxxxxxx1x,
			STORE_PROC2_CASE	= 11'bxxxxxxxx1xx,
			GET_DISP1_CASE		= 11'bxxxxxxX1xxx,
			GET_DISP2_CASE		= 11'bxxxxxx1xxxx,
			STORE_VID1_CASE1	= 11'bxxxxx1xxxxx,
			STORE_VID1_CASE2  = 11'bxxxx1xxxxxx,
			STORE_VID1_CASE3  = 11'bxxx1xxxxxxx,
			RETRIEVE_CASE0		= 11'bxx1xxxxxxxx,
			RETRIEVE_CASE1		= 11'bx1xxxxxxxxx,
			RETRIEVE_CASE2		= 11'b1xxxxxxxxxx;

always @(posedge sys_clock or posedge force_reset) begin : store_state_fsm
	if (force_reset)
		store_state_var[10:0] <= #1 DISPATCH_STATE;
	else begin
		casex (store_state_var[10:0]) // synopsys parallel_case full_case

			DISPATCH_CASE:
			begin
				if(display_read_pending)
					store_state_var[10:0] <= #1 GET_DISP1_STATE;		//always service display fetch first.
				else if(~video1_write_fifo_epty)
					store_state_var[10:0] <= #1 STORE_VID1_STATE1;
				else if(~proc_write_fifo_epty)
					store_state_var[10:0] <= #1 STORE_PROC1_STATE;
				else if(retrieve_get_strb)
					store_state_var[10:0] <= #1 RETRIEVE_STATE0;
				else
					store_state_var[10:0] <= #1 DISPATCH_STATE;
			end
			
			STORE_PROC1_CASE:
			begin
				store_state_var[10:0] <= #1 STORE_PROC2_STATE;
			end

			STORE_PROC2_CASE:
			begin
				store_state_var[10:0] <= #1 DISPATCH_STATE;
			end

			GET_DISP1_CASE:
			begin
				disp_data[14:0] <= #1 ram_data_io[14:0];
				store_state_var[10:0] <= #1 GET_DISP2_STATE;
			end

			GET_DISP2_CASE:
			begin
				disp_data[14:0] <= #1 ram_data_io[14:0];
				store_state_var[10:0] <= #1 DISPATCH_STATE;
			end

			STORE_VID1_CASE1:
			begin
				store_state_var[10:0] <= #1 STORE_VID1_STATE2;
			end

			STORE_VID1_CASE2:
			begin
				store_state_var[10:0] <= #1 STORE_VID1_STATE3;
			end

			STORE_VID1_CASE3:
			begin
				store_state_var[10:0] <= #1 DISPATCH_STATE;
			end
			
			
			RETRIEVE_CASE0:
			begin
				store_state_var[10:0] <= #1 RETRIEVE_STATE1;
			end
			
			RETRIEVE_CASE1:
			begin
				store_state_var[10:0] <= #1 RETRIEVE_STATE2;
				retrieve_data[14:0] <= #1 ram_data_io[14:0];
			end
		
			RETRIEVE_CASE2:
			begin
				store_state_var[10:0] <= #1 DISPATCH_STATE;
				retrieve_data[14:0] <= #1 ram_data_io[14:0];
			end
		endcase
	end
end // store_state_fsm

always @(store_state_var[10:0],disp_ping_pong,proc_fifo_aout[17:0],disp_data_get_addr[17:0],video1_fifo_aout[17:0],retrieve_addr[17:0])begin : store2_state_assn_fsm
	casex (store_state_var[10:0]) // synopsys parallel_case full_case
		DISPATCH_CASE:
		begin
			clear_display_read_pending = 0;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 0;
			ram_data_mux1 = 0;  // high impedance
			ram_data_mux2 = 0;
			ram_addr[19:1] = {~disp_ping_pong,disp_data_get_addr[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end
		
		STORE_PROC1_CASE:
		begin
			clear_display_read_pending = 0;
			ram_we = 0;
			ram_ce = 1;
			ram_oe = 1;
			ram_data_mux1 = 1;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {disp_ping_pong,proc_fifo_aout[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		STORE_PROC2_CASE:
		begin
			clear_display_read_pending = 0;
			ram_we = 0;
			ram_ce = 0;
			ram_oe = 1;
			ram_data_mux1 = 1;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {disp_ping_pong,proc_fifo_aout[17:0]};
			p_write_fifo_re = 1;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		GET_DISP1_CASE:
		begin
			clear_display_read_pending = 0;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 0;
			ram_data_mux1 = 0;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {~disp_ping_pong,disp_data_get_addr[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		GET_DISP2_CASE:
		begin
			clear_display_read_pending = 1;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 0;
			ram_data_mux1 = 0;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {~disp_ping_pong,disp_data_get_addr[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		STORE_VID1_CASE1:
		begin
			clear_display_read_pending = 0;
			ram_we = 0;
			ram_ce = 1;
			ram_oe = 1;
			ram_data_mux1 = 0;
			ram_data_mux2 = 1;
			ram_addr[19:1] = {disp_ping_pong,video1_fifo_aout[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		STORE_VID1_CASE2:
		begin
			clear_display_read_pending = 0;
			ram_we = 0;
			ram_ce = 0;
			ram_oe = 1;
			ram_data_mux1 = 0;
			ram_data_mux2 = 1;
			ram_addr[19:1] = {disp_ping_pong,video1_fifo_aout[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		STORE_VID1_CASE3:
		begin
			clear_display_read_pending = 0;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 1;
			ram_data_mux1 = 0;
			ram_data_mux2 = 1;
			ram_addr[19:1] = {disp_ping_pong,video1_fifo_aout[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 1;
			retrieve_data_ready_strb = 0;
		end

		RETRIEVE_CASE0:
		begin
			clear_display_read_pending = 0;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 0;
			ram_data_mux1 = 0;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {~disp_ping_pong,retrieve_addr[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		RETRIEVE_CASE1:
		begin
			clear_display_read_pending = 0;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 0;
			ram_data_mux1 = 0;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {~disp_ping_pong,retrieve_addr[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 0;
		end

		RETRIEVE_CASE2:
		begin
			clear_display_read_pending = 0;
			ram_we = 1;
			ram_ce = 0;
			ram_oe = 0;
			ram_data_mux1 = 0;
			ram_data_mux2 = 0;
			ram_addr[19:1] = {~disp_ping_pong,retrieve_addr[17:0]};
			p_write_fifo_re = 0;
			video1_fifo_re = 0;
			retrieve_data_ready_strb = 1;
		end
	endcase
end //store2_state_assn

always @(posedge sys_clock)
begin
	if(force_reset | clear_fifo_error)
		fifo_error <= #1 1'b0;
	else if(f1_full)
		fifo_error <= #1 1'b1;
end

fifo_33 #(33) video1_write_fifo(
			.clk(sys_clock),
			.rst(force_reset),
			.din({video1_data[14:0],video1_addr[17:0]}),	// [32:0]
			.we(video1_store_strb),
			.dout({video1_fifo_dout[14:0],video1_fifo_aout[17:0]}),	// [32:0]
			.re(video1_fifo_re),
			.full(f1_full),
			.empty(video1_write_fifo_epty)
			);

assign #1 ram_data_io[14:0] = ram_data_mux2 ? video1_fifo_dout[14:0] : 15'bZZZZZZZZZZZZZZZ;

fifo_33 #(33) proc_write_fifo(
			.clk(sys_clock),
			.rst(force_reset),
			.din({proc_data_w[14:0],1'b0,proc_addr[17:1]}),	// [32:0]
			.we(qual2_data),
			.dout({proc_fifo_dout[14:0],proc_fifo_aout[17:0]}),	// [32:0]
			.re(p_write_fifo_re),
			.full(),
			.empty(proc_write_fifo_epty)
			);

assign #1 ram_data_io[14:0] = ram_data_mux1 ? proc_fifo_dout[14:0] : 15'bZZZZZZZZZZZZZZZ;

always @(posedge sys_clock)
begin
	if(force_reset || clear_display_read_pending)
		display_read_pending <= #1 1'b0;
	else if(disp_data_get_strb)
		display_read_pending <= #1 1'b1;
end


endmodule


Click here to return to article