diff --git a/Makefile b/Makefile index 68431d2..be12ae0 100644 --- a/Makefile +++ b/Makefile @@ -11,7 +11,7 @@ lint: sim: bit_fifo_tb bridge_rx_tb bridge_tx_tb fifo_tb lut_ram_tb uart_tx_tb logic_analyzer_tb: - iverilog -g2012 -o sim.out test/logic_analyzer_tb.sv src/manta/logic_analyzer.v src/manta/fifo.v src/manta/trigger.v src/manta/xilinx_true_dual_port_read_first_2_clock_ram.v + iverilog -g2012 -o sim.out test/logic_analyzer_tb.sv src/manta/logic_analyzer.v src/manta/la_fsm.v src/manta/trigger_block.v src/manta/trigger.v src/manta/sample_mem.v src/manta/xilinx_true_dual_port_read_first_2_clock_ram.v vvp sim.out rm sim.out diff --git a/src/manta/fifo.v b/src/manta/fifo.v index 3385d70..1675ae1 100644 --- a/src/manta/fifo.v +++ b/src/manta/fifo.v @@ -24,6 +24,11 @@ module fifo ( reg [AW:0] write_pointer; reg [AW:0] read_pointer; + initial begin + write_pointer = 0; + read_pointer = 0; + end + reg empty_int; assign empty_int = (write_pointer[AW] == read_pointer[AW]); diff --git a/src/manta/la_fsm.v b/src/manta/la_fsm.v new file mode 100644 index 0000000..12549b7 --- /dev/null +++ b/src/manta/la_fsm.v @@ -0,0 +1,117 @@ +`default_nettype none +`timescale 1ns/1ps + +module la_fsm( + input wire clk, + + input wire trig, + input wire [$clog2(SAMPLE_DEPTH):0] fifo_size, + output reg fifo_acquire, + output reg fifo_pop, + + // input port + input wire [15:0] addr_i, + input wire [15:0] wdata_i, + input wire [15:0] rdata_i, + input wire rw_i, + input wire valid_i, + + // output port + output reg [15:0] addr_o, + output reg [15:0] wdata_o, + output reg [15:0] rdata_o, + output reg rw_o, + output reg valid_o); + + parameter BASE_ADDR = 0; + parameter SAMPLE_DEPTH = 0; + + // state machine + localparam IDLE = 0; + localparam MOVE_TO_POSITION = 1; + localparam IN_POSITION = 2; + localparam FILLING_BUFFER = 3; + localparam FILLED = 4; + + reg [3:0] state; + reg signed [15:0] trigger_loc; + reg signed [15:0] present_loc; + + initial state = IDLE; + initial trigger_loc = 0; + initial present_loc = 0; + + // perform register operations + always @(posedge clk) begin + addr_o <= addr_i; + wdata_o <= wdata_i; + rdata_o <= rdata_i; + rw_o <= rw_i; + valid_o <= valid_i; + + // check if address is valid + if( (valid_i) && (addr_i >= BASE_ADDR) && (addr_i <= BASE_ADDR + 2)) begin + + if(!rw_i) begin // reads + case (addr_i) + BASE_ADDR + 0: rdata_o <= state; + BASE_ADDR + 1: rdata_o <= trigger_loc; + BASE_ADDR + 2: rdata_o <= present_loc; + endcase + end + + else begin // writes + case (addr_i) + BASE_ADDR + 0: state <= wdata_i; + BASE_ADDR + 1: trigger_loc <= wdata_i; + BASE_ADDR + 2: present_loc <= wdata_i; + endcase + end + end + end + + // run state machine + always @(posedge clk) begin + if(state == IDLE) begin + present_loc <= (trigger_loc < 0) ? trigger_loc : 0; + end + + else if(state == MOVE_TO_POSITION) begin + // if trigger location is negative or zero, + // then we're already in position + if(trigger_loc <= 0) state <= IN_POSITION; + + // otherwise we'll need to wait a little, + // but we'll need to buffer along the way + else begin + present_loc <= present_loc + 1; + // add code to add samples to word FIFO + fifo_acquire <= 1; + if (present_loc == trigger_loc) state <= IN_POSITION; + end + end + + else if(state == IN_POSITION) begin + // pop stuff out of the word FIFO in addition to pulling it in + fifo_acquire <= 1; + fifo_pop <= 1; + + if(trig) state <= FILLING_BUFFER; + end + + else if(state == FILLING_BUFFER) begin + fifo_acquire <= 1; + fifo_pop <= 0; + if(fifo_size == SAMPLE_DEPTH) state <= FILLED; + end + + else if(state == FILLED) begin + // don't automatically go back to IDLE, the host will move + // the state to MOVE_TO_POSITION + + present_loc <= (trigger_loc < 0) ? trigger_loc : 0; + end + end +endmodule + +`default_nettype wire \ No newline at end of file diff --git a/src/manta/logic_analyzer.v b/src/manta/logic_analyzer.v index 21f3479..2e80aeb 100644 --- a/src/manta/logic_analyzer.v +++ b/src/manta/logic_analyzer.v @@ -26,201 +26,98 @@ module logic_analyzer( ); parameter BASE_ADDR = 0; - parameter SAMPLE_DEPTH = 4096; + parameter SAMPLE_DEPTH = 0; - // trigger configuration registers - // - each probe gets an operation and a compare register - // - at the end we AND them all together. along with any custom probes the user specs - - reg [3:0] larry_trigger_op; - reg larry_trigger_arg; - reg larry_trig; - trigger #(.INPUT_WIDTH(1)) larry_trigger( + // fsm + la_fsm #(.BASE_ADDR(BASE_ADDR), .SAMPLE_DEPTH(SAMPLE_DEPTH)) fsm ( .clk(clk), - .probe(larry), - .op(larry_trigger_op), - .arg(larry_trigger_arg), - .trig(larry_trig)); + .trig(trig), + .fifo_size(fifo_size), + .fifo_acquire(fifo_acquire), + .fifo_pop(fifo_pop), - reg [3:0] curly_trigger_op; - reg curly_trigger_arg; - reg curly_trig; - trigger #(.INPUT_WIDTH(1)) curly_trigger( - .clk(clk), + .addr_i(addr_i), + .wdata_i(wdata_i), + .rdata_i(rdata_i), + .rw_i(rw_i), + .valid_i(valid_i), - .probe(curly), - .op(curly_trigger_op), - .arg(curly_trigger_arg), - .trig(curly_trig)); - - - reg [3:0] moe_trigger_op; - reg moe_trigger_arg; - reg moe_trig; - trigger #(.INPUT_WIDTH(1)) moe_trigger( - .clk(clk), - - .probe(moe), - .op(moe_trigger_op), - .arg(moe_trigger_arg), - .trig(moe_trig)); - - reg [3:0] shemp_trigger_op; - reg [3:0] shemp_trigger_arg; - reg shemp_trig; - trigger #(.INPUT_WIDTH(4)) shemp_trigger( - .clk(clk), - - .probe(shemp), - .op(shemp_trigger_op), - .arg(shemp_trigger_arg), - .trig(shemp_trig)); - - reg triggered; - assign triggered = larry_trig || curly_trig || moe_trig || shemp_trig; - - reg [6:0] concatenated; - assign concatenated = {larry, curly, moe, shemp}; + .addr_o(fsm_trig_blk_addr), + .wdata_o(fsm_trig_blk_wdata), + .rdata_o(fsm_trig_blk_rdata), + .rw_o(fsm_trig_blk_rw), + .valid_o(fsm_trig_blk_valid)); - // word-wise fifo - fifo #(.WIDTH(FIFO_WIDTH), .DEPTH(SAMPLE_DEPTH)) wfifo( + reg [15:0] fsm_trig_blk_addr; + reg [15:0] fsm_trig_blk_wdata; + reg [15:0] fsm_trig_blk_rdata; + reg fsm_trig_blk_rw; + reg fsm_trig_blk_valid; + + reg trig; + reg [$clog2(SAMPLE_DEPTH):0] fifo_size; + reg fifo_acquire; + reg fifo_pop; + + + // trigger block + trigger_block #(.BASE_ADDR(BASE_ADDR + 2)) trig_blk( .clk(clk), - .bram_rst(1'b0), - - .in(concatenated), - .in_valid(wfifo_in_valid), - - .out(wfifo_out), - .out_req(wfifo_out_req), - .out_valid(wfifo_out_valid), - .size(wfifo_size), - .empty(), - .full()); + .larry(larry), + .curly(curly), + .moe(moe), + .shemp(shemp), - reg wfifo_in_valid; - localparam FIFO_WIDTH = 7; - reg [FIFO_WIDTH-1:0] wfifo_out; - reg wfifo_out_req; - reg wfifo_out_valid; + .trig(trig), + + .addr_i(fsm_trig_blk_addr), + .wdata_i(fsm_trig_blk_wdata), + .rdata_i(fsm_trig_blk_rdata), + .rw_i(fsm_trig_blk_rw), + .valid_i(fsm_trig_blk_valid), - reg [$clog2(SAMPLE_DEPTH):0] wfifo_size; + .addr_o(trig_blk_sample_mem_addr), + .wdata_o(trig_blk_sample_mem_wdata), + .rdata_o(trig_blk_sample_mem_rdata), + .rw_o(trig_blk_sample_mem_rw), + .valid_o(trig_blk_sample_mem_valid)); - - // state machine - localparam IDLE = 0; - localparam START = 1; - localparam MOVE_TO_POSITION = 2; - localparam IN_POSITION = 3; - localparam FILLING_BUFFER = 4; - localparam FILLED = 5; + reg [15:0] trig_blk_sample_mem_addr; + reg [15:0] trig_blk_sample_mem_wdata; + reg [15:0] trig_blk_sample_mem_rdata; + reg trig_blk_sample_mem_rw; + reg trig_blk_sample_mem_valid; - reg [3:0] state; - initial state = IDLE; + // sample memory + sample_mem #(.BASE_ADDR(BASE_ADDR + 10), .SAMPLE_DEPTH(SAMPLE_DEPTH)) sample_mem( + .clk(clk), - reg signed [15:0] trigger_loc; - initial trigger_loc = 0; + // fifo + .acquire(fifo_acquire), + .pop(fifo_pop), + .size(fifo_size), - reg signed [15:0] present_loc; - initial present_loc = 0; + // probes + .larry(larry), + .curly(curly), + .moe(moe), + .shemp(shemp), - always @(posedge clk) begin - if(state == IDLE) begin - present_loc <= (trigger_loc < 0) ? trigger_loc : 0; - end + // input port + .addr_i(trig_blk_sample_mem_addr), + .wdata_i(trig_blk_sample_mem_wdata), + .rdata_i(trig_blk_sample_mem_rdata), + .rw_i(trig_blk_sample_mem_rw), + .valid_i(trig_blk_sample_mem_valid), - else if(state == MOVE_TO_POSITION) begin - // if trigger location is negative or zero, - // then we're already in position - if(trigger_loc <= 0) state <= IN_POSITION; - - // otherwise we'll need to wait a little, - // but we'll need to buffer along the way - else begin - present_loc <= present_loc + 1; - // add code to add samples to word FIFO - wfifo_in_valid <= 1; - if (present_loc == trigger_loc) state <= IN_POSITION; - end - end - - else if(state == IN_POSITION) begin - // pop stuff out of the word FIFO in addition to pulling it in - wfifo_in_valid <= 1; - wfifo_out_req <= 1; - - if(triggered) state <= FILLING_BUFFER; - end - - else if(state == FILLING_BUFFER) begin - if(wfifo_size == SAMPLE_DEPTH) state <= FILLED; - end - - else if(state == FILLED) begin - // don't automatically go back to IDLE, the host will move - // the state to MOVE_TO_POSITION - - present_loc <= (trigger_loc < 0) ? trigger_loc : 0; - end - end - - - - // memory servicing - // - TODO: add support for comparision values > 16 bits, - // we'll have to concat them somwehere up here - - always @(posedge clk) begin - - addr_o <= addr_i; - wdata_o <= wdata_i; - rdata_o <= rdata_i; - rw_o <= rw_i; - valid_o <= valid_i; - - // operations to configuration registers - if( (addr_i >= BASE_ADDR) && (addr_i <= BASE_ADDR + 9) ) begin - - // reads - if(valid_i && !rw_i) begin - case (addr_i) - BASE_ADDR + 0: rdata_o <= state; - BASE_ADDR + 1: rdata_o <= trigger_loc; - BASE_ADDR + 2: rdata_o <= larry_trigger_op; - BASE_ADDR + 3: rdata_o <= larry_trigger_arg; - BASE_ADDR + 4: rdata_o <= curly_trigger_op; - BASE_ADDR + 5: rdata_o <= curly_trigger_arg; - BASE_ADDR + 6: rdata_o <= moe_trigger_op; - BASE_ADDR + 7: rdata_o <= moe_trigger_arg; - BASE_ADDR + 8: rdata_o <= shemp_trigger_op; - BASE_ADDR + 9: rdata_o <= shemp_trigger_arg; - default: rdata_o <= rdata_i; - endcase - end - - // writes - else if(valid_i && rw_i) begin - case (addr_i) - BASE_ADDR + 0: state <= wdata_i; - BASE_ADDR + 1: trigger_loc <= wdata_i; - BASE_ADDR + 2: larry_trigger_op <= wdata_i; - BASE_ADDR + 3: larry_trigger_arg <= wdata_i; - BASE_ADDR + 4: curly_trigger_op <= wdata_i; - BASE_ADDR + 5: curly_trigger_arg <= wdata_i; - BASE_ADDR + 6: moe_trigger_op <= wdata_i; - BASE_ADDR + 7: moe_trigger_arg <= wdata_i; - BASE_ADDR + 8: shemp_trigger_op <= wdata_i; - BASE_ADDR + 9: shemp_trigger_arg <= wdata_i; - default: wdata_o <= wdata_i; - endcase - end - end - - // operations to BRAM - else if( (addr_i >= BASE_ADDR + 10) && (addr_i <= BASE_ADDR + 10 + SAMPLE_DEPTH) ) begin - end - end + // output port + .addr_o(addr_o), + .wdata_o(wdata_o), + .rdata_o(rdata_o), + .rw_o(rw_o), + .valid_o(valid_o)); endmodule `default_nettype wire \ No newline at end of file diff --git a/src/manta/sample_mem.v b/src/manta/sample_mem.v new file mode 100644 index 0000000..51a1ec9 --- /dev/null +++ b/src/manta/sample_mem.v @@ -0,0 +1,124 @@ +`default_nettype none +`timescale 1ns/1ps + +module sample_mem( + input wire clk, + + // fifo + input wire acquire, + input wire pop, + output wire [AW:0] size, + + // probes + input wire larry, + input wire curly, + input wire moe, + input wire [3:0] shemp, + + // input port + input wire [15:0] addr_i, + input wire [15:0] wdata_i, + input wire [15:0] rdata_i, + input wire rw_i, + input wire valid_i, + + // output port + output reg [15:0] addr_o, + output reg [15:0] wdata_o, + output reg [15:0] rdata_o, + output reg rw_o, + output reg valid_o); + + parameter BASE_ADDR = 0; + parameter SAMPLE_DEPTH = 0; + + // bus controller + reg [$clog2(SAMPLE_DEPTH):0] bram_read_addr; + reg [15:0] bram_read_data; + + always @(*) begin + // if address is valid + if ( (addr_i >= BASE_ADDR) && (addr_i <= BASE_ADDR + SAMPLE_DEPTH) ) begin + + // figure out proper place to read from + // want to read from the read pointer, and then loop back around + if(read_pointer + (addr_i - BASE_ADDR) > SAMPLE_DEPTH) + bram_read_addr <= read_pointer + (addr_i - BASE_ADDR) - SAMPLE_DEPTH; + + else + bram_read_addr = read_pointer + (addr_i - BASE_ADDR); + end + + else bram_read_addr <= 0; + end + + + // pipeline bus to compensate for 2-cycles of delay in BRAM + reg [15:0] addr_pip; + reg [15:0] wdata_pip; + reg [15:0] rdata_pip; + reg rw_pip; + reg valid_pip; + + always @(posedge clk) begin + addr_pip <= addr_i; + wdata_pip <= wdata_i; + rdata_pip <= rdata_i; + rw_pip <= rw_i; + valid_pip <= valid_i; + + addr_o <= addr_pip; + wdata_o <= wdata_pip; + rdata_o <= rdata_pip; + rw_o <= rw_pip; + valid_o <= valid_pip; + + if( valid_pip && !rw_pip && (addr_pip >= BASE_ADDR) && (addr_pip <= BASE_ADDR + SAMPLE_DEPTH) ) + rdata_o <= bram_read_data; + end + + + // bram + xilinx_true_dual_port_read_first_2_clock_ram #( + .RAM_WIDTH(16), + .RAM_DEPTH(SAMPLE_DEPTH), + .RAM_PERFORMANCE("HIGH_PERFORMANCE") + + ) bram ( + + // read port (controlled by bus) + .clka(clk), + .rsta(1'b0), + .ena(1'b1), + .addra(bram_read_addr), + .dina(), + .wea(1'b0), + .regcea(1'b1), + .douta(bram_read_data), + + // write port (controlled by FIFO) + .clkb(clk), + .rstb(1'b0), + .enb(1'b1), + .addrb(write_pointer), + .dinb({larry, curly, moe, shemp}), + .web(acquire), + .regceb(1'b1), + .doutb()); + + + // fifo + localparam AW = $clog2(SAMPLE_DEPTH); + + reg [AW:0] write_pointer = 0; + reg [AW:0] read_pointer = 0; + + assign size = write_pointer - read_pointer; + + always @(posedge clk) begin + if (acquire) write_pointer <= write_pointer + 1'd1; + if (pop) read_pointer <= read_pointer + 1'd1; + end +endmodule + +`default_nettype wire \ No newline at end of file diff --git a/src/manta/trigger_block.v b/src/manta/trigger_block.v new file mode 100644 index 0000000..3efaefe --- /dev/null +++ b/src/manta/trigger_block.v @@ -0,0 +1,126 @@ +`default_nettype none +`timescale 1ns/1ps + +module trigger_block( + input wire clk, + + // probes + input wire larry, + input wire curly, + input wire moe, + input wire [3:0] shemp, + + // trigger + output reg trig, + + // input port + input wire [15:0] addr_i, + input wire [15:0] wdata_i, + input wire [15:0] rdata_i, + input wire rw_i, + input wire valid_i, + + // output port + output reg [15:0] addr_o, + output reg [15:0] wdata_o, + output reg [15:0] rdata_o, + output reg rw_o, + output reg valid_o); + + parameter BASE_ADDR = 0; + + // trigger configuration registers + // - each probe gets an operation and a compare register + // - at the end we OR them all together. along with any custom probes the user specs + + reg [3:0] larry_trigger_op; + reg larry_trigger_arg; + reg larry_trig; + trigger #(.INPUT_WIDTH(1)) larry_trigger( + .clk(clk), + + .probe(larry), + .op(larry_trigger_op), + .arg(larry_trigger_arg), + .trig(larry_trig)); + + reg [3:0] curly_trigger_op; + reg curly_trigger_arg; + reg curly_trig; + trigger #(.INPUT_WIDTH(1)) curly_trigger( + .clk(clk), + + .probe(curly), + .op(curly_trigger_op), + .arg(curly_trigger_arg), + .trig(curly_trig)); + + + reg [3:0] moe_trigger_op; + reg moe_trigger_arg; + reg moe_trig; + trigger #(.INPUT_WIDTH(1)) moe_trigger( + .clk(clk), + + .probe(moe), + .op(moe_trigger_op), + .arg(moe_trigger_arg), + .trig(moe_trig)); + + reg [3:0] shemp_trigger_op; + reg [3:0] shemp_trigger_arg; + reg shemp_trig; + trigger #(.INPUT_WIDTH(4)) shemp_trigger( + .clk(clk), + + .probe(shemp), + .op(shemp_trigger_op), + .arg(shemp_trigger_arg), + .trig(shemp_trig)); + + reg triggered; + assign triggered = larry_trig || curly_trig || moe_trig || shemp_trig; + + // perform register operations + always @(posedge clk) begin + addr_o <= addr_i; + wdata_o <= wdata_i; + rdata_o <= rdata_i; + rw_o <= rw_i; + valid_o <= valid_i; + rdata_o <= rdata_i; + + if( (addr_i >= BASE_ADDR) && (addr_i <= BASE_ADDR + 9) ) begin + + // reads + if(valid_i && !rw_i) begin + case (addr_i) + BASE_ADDR + 0: rdata_o <= larry_trigger_op; + BASE_ADDR + 1: rdata_o <= larry_trigger_arg; + BASE_ADDR + 2: rdata_o <= curly_trigger_op; + BASE_ADDR + 3: rdata_o <= curly_trigger_arg; + BASE_ADDR + 4: rdata_o <= moe_trigger_op; + BASE_ADDR + 5: rdata_o <= moe_trigger_arg; + BASE_ADDR + 6: rdata_o <= shemp_trigger_op; + BASE_ADDR + 7: rdata_o <= shemp_trigger_arg; + endcase + end + + // writes + else if(valid_i && rw_i) begin + case (addr_i) + BASE_ADDR + 0: larry_trigger_op <= wdata_i; + BASE_ADDR + 1: larry_trigger_arg <= wdata_i; + BASE_ADDR + 2: curly_trigger_op <= wdata_i; + BASE_ADDR + 3: curly_trigger_arg <= wdata_i; + BASE_ADDR + 4: moe_trigger_op <= wdata_i; + BASE_ADDR + 5: moe_trigger_arg <= wdata_i; + BASE_ADDR + 6: shemp_trigger_op <= wdata_i; + BASE_ADDR + 7: shemp_trigger_arg <= wdata_i; + endcase + end + end + end +endmodule + +`default_nettype wire \ No newline at end of file diff --git a/test/fifo_tb.sv b/test/fifo_tb.sv index cf52258..83b6ff3 100644 --- a/test/fifo_tb.sv +++ b/test/fifo_tb.sv @@ -5,11 +5,11 @@ module fifo_tb(); logic clk; logic rst; - logic [7:0] data_in; - logic input_ready; + logic [7:0] in; + logic in_valid; - logic request_output; - logic [7:0] data_out; + logic out_req; + logic [7:0] out; logic [11:0] size; logic empty; @@ -17,13 +17,13 @@ module fifo_tb(); fifo uut ( .clk(clk), - .rst(rst), + .bram_rst(rst), - .data_in(data_in), - .input_ready(input_ready), + .in(in), + .in_valid(in_valid), - .request_output(request_output), - .data_out(data_out), + .out_req(out_req), + .out(out), .size(size), .empty(empty), @@ -39,27 +39,27 @@ module fifo_tb(); $dumpvars(0, fifo_tb); clk = 0; rst = 1; - data_in = 0; - input_ready = 0; - request_output = 0; + in = 0; + in_valid = 0; + out_req = 0; #10; rst = 0; #10; // try and load some data, make sure counter increases - input_ready = 1; + in_valid = 1; for(int i=0; i < 4097; i++) begin - data_in = i; + in = i; #10; end - input_ready = 0; + in_valid = 0; // try and read out said data - request_output = 1; + out_req = 1; for(int i=0; i < 4097; i++) begin - $display("%h", data_out); + $display("%h", out); #10; end diff --git a/test/logic_analyzer_tb.sv b/test/logic_analyzer_tb.sv index d151a70..70ed79d 100644 --- a/test/logic_analyzer_tb.sv +++ b/test/logic_analyzer_tb.sv @@ -30,7 +30,7 @@ module logic_analyzer_tb; logic la_tb_valid; - logic_analyzer la( + logic_analyzer #(.BASE_ADDR(0), .SAMPLE_DEPTH(128)) la( .clk(clk), // probes @@ -107,7 +107,7 @@ module logic_analyzer_tb; tb_la_wdata = 5; #`CP tb_la_valid = 0; - #`CP + while (!la_tb_valid) #`CP; $display(" -> wrote 0x0005 to state reg (addr 0x0000)"); // read @@ -118,6 +118,24 @@ module logic_analyzer_tb; while (!la_tb_valid) #`CP; $display(" -> read 0x%h from state reg (addr 0x0000)", la_tb_rdata); + // write + tb_la_addr = 0; + tb_la_valid = 1; + tb_la_rw = 1; + tb_la_wdata = 0; + #`CP + tb_la_valid = 0; + while (!la_tb_valid) #`CP; + $display(" -> wrote 0x0000 to state reg (addr 0x0000)"); + + // read + tb_la_valid = 1; + tb_la_rw = 0; + #`CP + tb_la_valid = 0; + while (!la_tb_valid) #`CP; + $display(" -> read 0x%h from state reg (addr 0x0000)", la_tb_rdata); + #(10*`CP); /* ==== Test 2 End ==== */ @@ -135,7 +153,7 @@ module logic_analyzer_tb; tb_la_wdata = -16'sd69; #`CP tb_la_valid = 0; - #`CP + while (!la_tb_valid) #`CP; $display(" -> wrote -0d69 to trigger_loc reg (addr 0x0001)"); // read @@ -146,6 +164,24 @@ module logic_analyzer_tb; while (!la_tb_valid) #`CP; $display(" -> read 0d%d from trigger_loc reg (addr 0x0001)", $signed(la_tb_rdata)); + // write + tb_la_addr = 1; + tb_la_valid = 1; + tb_la_rw = 1; + tb_la_wdata = 0; + #`CP + tb_la_valid = 0; + while (!la_tb_valid) #`CP; + $display(" -> wrote 0x0000 to trigger_loc reg (addr 0x0001)"); + + // read + tb_la_valid = 1; + tb_la_rw = 0; + #`CP + tb_la_valid = 0; + while (!la_tb_valid) #`CP; + $display(" -> read 0x%h from trigger_loc reg (addr 0x0001)", $signed(la_tb_rdata)); + #(10*`CP); /* ==== Test 3 End ==== */ @@ -163,7 +199,7 @@ module logic_analyzer_tb; tb_la_wdata = 8; #`CP tb_la_valid = 0; - #`CP + while (!la_tb_valid) #`CP; $display(" -> wrote 0x0008 to larry_op reg (addr 0x0002)"); // read @@ -191,7 +227,7 @@ module logic_analyzer_tb; tb_la_wdata = 1; #`CP tb_la_valid = 0; - #`CP + while (!la_tb_valid) #`CP; $display(" -> wrote 0x0001 to larry_arg reg (addr 0x0003)"); // read @@ -212,18 +248,52 @@ module logic_analyzer_tb; $display("\n=== test 6: set larry = 1, verify core does not trigger ==="); test_num = 6; - larry = 1; $display(" -> set larry = 1"); + larry = 1; // read - $display(" -> la core is in state 0x%h", la.state); + $display(" -> la core is in state 0x%h", la.fsm.state); + $display(" -> wait a clock cycle"); #`CP - $display(" -> la core is in state 0x%h", la.state); + $display(" -> la core is in state 0x%h", la.fsm.state); + $display(" -> set larry = 0"); + larry = 0; #(10*`CP); /* ==== Test 6 End ==== */ + + + /* ==== Test 7 Begin ==== */ + $display("\n=== test 7: set larry = 1, verify core does trigger ==="); + test_num = 7; + + // write + tb_la_addr = 0; + tb_la_valid = 1; + tb_la_rw = 1; + tb_la_wdata = 1; + #`CP + tb_la_valid = 0; + #`CP + $display(" -> wrote 0x0001 to state reg (addr 0x0000)"); + + #`CP + + $display(" -> set larry = 1"); + larry = 1; + + // read + $display(" -> la core is in state 0x%h", la.fsm.state); + $display(" -> wait a clock cycle"); + #`CP + $display(" -> la core is in state 0x%h", la.fsm.state); + + + #(200*`CP); + /* ==== Test 7 End ==== */ + $finish(); end endmodule