예제 #1
0
def nt_gen_replay_mem_read_test(dut):
    """Test bench main function."""
    # open trace file
    trace = File("files/random.file")

    # get trace file size
    trace_size = trace.size()

    # trace file size must be a multiple of AXI data width
    if trace.size() % (AXI_BIT_WIDTH / 8) != 0:
        raise cocotb.result.TestFailure("invalid trace size")

    # calculate ring buffer sizes
    ring_buff_sizes = []
    for ring_buff_size in RING_BUFF_SIZES:
        # size of ring buffer is determined by multiplying the size factor by
        # the size of the trace
        ring_buff_size = int(ring_buff_size * trace_size)

        # make sure that the ring buffer size is multiple of AXI data width
        if ring_buff_size % (AXI_BIT_WIDTH / 8) != 0:
            ring_buff_size += AXI_BIT_WIDTH/8 - ring_buff_size % \
                             (AXI_BIT_WIDTH/8)
        ring_buff_sizes.append(ring_buff_size)

    # create a ring buffer memory (initially of size 0) and connect it to the
    # DUT
    ring_buff = Mem(0)
    ring_buff.connect(dut)

    # start the clock
    cocotb.fork(clk_gen(dut.clk, CLK_FREQ_MHZ))

    # deassert sw reset
    dut.rst_sw <= 0

    # initially module start is not triggered
    dut.ctrl_start_i <= 0

    # reset dut
    yield rstn(dut.clk, dut.rstn)

    # start the ring buffer memory main routine
    cocotb.fork(ring_buff.main())

    # wait some more clock cycles
    yield wait_n_cycles(dut.clk, 5)

    # randomly toggle fifo_prog_full input signal
    dut.fifo_prog_full_i <= 0
    cocotb.fork(toggle_signal(dut.clk, dut.fifo_prog_full_i))

    # iterate over all ring buffer sizes
    for i, ring_buff_size in enumerate(ring_buff_sizes):

        # set ring buffer size
        ring_buff.set_size(ring_buff_size)

        # iterate over all adderesses where ring buffer shall be located in
        # memory
        for j, ring_buff_addr in enumerate(RING_BUFF_ADDRS):

            # print status
            print("Test %d/%d" % (i * len(RING_BUFF_ADDRS) + j + 1,
                                  len(RING_BUFF_ADDRS) * len(RING_BUFF_SIZES)))

            # we have a total of 8 GByte of memory. Make sure the ring buffer
            # fits at the desired address
            if ring_buff_addr + ring_buff_size > 0x1FFFFFFFF:
                raise cocotb.result.TestFailure("ring buffer is too large")

            # to reduce the simulation memory footprint, provide the memory
            # module the first memory address that we actually care about
            ring_buff.set_offset(ring_buff_addr)

            # apply ring buffer memory location to dut
            dut.ctrl_mem_addr_hi_i <= ring_buff_addr >> 32
            dut.ctrl_mem_addr_lo_i <= ring_buff_addr & 0xFFFFFFFF

            # apply ring buffer address range to dut
            dut.ctrl_mem_range_i <= ring_buff_size - 1

            # apply trace size to dut
            dut.ctrl_trace_size_hi_i <= trace_size >> 32
            dut.ctrl_trace_size_lo_i <= trace_size & 0xFFFFFFFF

            # reset write address pointer
            dut.ctrl_addr_wr_i <= 0

            # start reading from the ring buffer
            dut.ctrl_start_i <= 1
            yield RisingEdge(dut.clk)
            dut.ctrl_start_i <= 0
            yield RisingEdge(dut.clk)

            # start writing the ring buffer
            cocotb.fork(ring_buff_write(dut, ring_buff, trace))

            # start checking dut output and wait until it completes
            yield cocotb.fork(check_output(dut, trace)).join()

            # clear the ring buffer contents
            ring_buff.clear()

    # close trace file
    trace.close()
예제 #2
0
def nt_gen_replay_top_test(dut):
    """Test bench main function."""
    # start the clock
    cocotb.fork(clk_gen(dut.clk, CLK_FREQ_MHZ))

    # no software reset
    dut.rst_sw <= 0

    # reset dut
    yield rstn(dut.clk, dut.rstn)

    # open trace file
    trace = File("files/random.file")

    # get trace file size
    trace_size = trace.size()

    # trace file must be a multiple of the AXI data width
    if trace.size() % (AXI_MEM_BIT_WIDTH / 8) != 0:
        raise cocotb.result.TestFailure("invalid trace size")

    # calculate ring buffer sizes
    ring_buff_sizes = []
    for ring_buff_size in RING_BUFF_SIZES:
        # size of ring buffer is determined by multiplying the size factor by
        # the size of the trace
        ring_buff_size = int(ring_buff_size * trace_size)

        # make sure that the ring buffer size is multiple of AXI data width
        if ring_buff_size % (AXI_MEM_BIT_WIDTH / 8) != 0:
            ring_buff_size += AXI_MEM_BIT_WIDTH/8 - \
                    ring_buff_size % (AXI_MEM_BIT_WIDTH/8)
        ring_buff_sizes.append(ring_buff_size)

    # create a ring buffer memory (initially of size 0) and connect it to the
    # DUT
    ring_buff = Mem(0)
    ring_buff.connect(dut, "ddr3")

    # create axi lite writer, connect and reset
    axi_lite_writer = AXI_Lite_Writer()
    axi_lite_writer.connect(dut, dut.clk, AXI_LITE_BIT_WIDTH, "ctrl")
    yield axi_lite_writer.rst()

    # create axi lite reader, connect and reset
    axi_lite_reader = AXI_Lite_Reader()
    axi_lite_reader.connect(dut, dut.clk, AXI_LITE_BIT_WIDTH, "ctrl")
    yield axi_lite_reader.rst()

    # create axi stream reader, connect and reset
    axis_reader = AXIS_Reader()
    axis_reader.connect(dut, dut.clk, AXIS_BIT_WIDTH)
    yield axis_reader.rst()

    # start the ring buffer memory main routine
    cocotb.fork(ring_buff.main())

    # toggle m_axis_tready
    cocotb.fork(toggle_signal(dut.clk, dut.m_axis_tready))

    # iterate over all ring buffer sizes
    for i, ring_buff_size in enumerate(ring_buff_sizes):

        # set ring buffer size
        ring_buff.set_size(ring_buff_size)

        # iterate over all addresses where ring buffer shall be located in
        # memory
        for j, ring_buff_addr in enumerate(RING_BUFF_ADDRS):

            # print status
            print("Test %d/%d" % (i * len(RING_BUFF_ADDRS) + j + 1,
                                  len(RING_BUFF_ADDRS) * len(RING_BUFF_SIZES)))

            print("Ring Buff Addr: 0x%x, Size: %d" %
                  (ring_buff_addr, ring_buff_size))

            # we have a total of 8 GByte of memory. Make sure the ring buffer
            # fits at the desired address
            if ring_buff_addr + ring_buff_size > 0x1FFFFFFFF:
                raise cocotb.result.TestFailure("ring buffer is too large")

            # to reduce the simulation memory footprint, provide the memory
            # module the first memory address that we acutally care about
            ring_buff.set_offset(ring_buff_addr)

            # configure ring buffer memory location
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_MEM_ADDR_HI,
                                        ring_buff_addr >> 32)
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_MEM_ADDR_LO,
                                        ring_buff_addr & 0xFFFFFFFF)

            # configure ring buffer address range
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_MEM_RANGE,
                                        ring_buff_size - 1)

            # configure trace size
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_TRACE_SIZE_HI,
                                        trace_size >> 32)
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_TRACE_SIZE_LO,
                                        trace_size & 0xFFFFFFFF)

            # reset write address pointer
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_ADDR_WR, 0x0)

            # make sure module initially is inactive
            status = yield axi_lite_reader.read(CPUREG_OFFSET_STATUS)
            if status & 0x3 != 0:
                raise cocotb.reset.TestFailure("module is active")

            # start the module
            yield axi_lite_writer.write(CPUREG_OFFSET_CTRL_START, 0x1)

            # wait a few cycles
            yield wait_n_cycles(dut.clk, 10)

            # start writing the ring buffer
            cocotb.fork(
                ring_buff_write(dut, ring_buff, trace, ring_buff_addr,
                                axi_lite_reader, axi_lite_writer))

            # start coroutine that checks dut output
            coroutine_chk_out = cocotb.fork(
                check_output(dut, trace, axis_reader))

            # wait a few cycles and make sure module is active
            yield wait_n_cycles(dut.clk, 10)
            status = yield axi_lite_reader.read(CPUREG_OFFSET_STATUS)
            if status & 0x1 == 0x0:
                raise cocotb.result.TestFailure("mem read not active")
            if status & 0x2 == 0x0:
                raise cocotb.result.TestFailure("packet assembly not active")

            # wait for output check to complete
            yield coroutine_chk_out.join()

            # wait a few cycles
            yield wait_n_cycles(dut.clk, 10)

            # make sure module is now inactive
            status = yield axi_lite_reader.read(CPUREG_OFFSET_STATUS)
            if status & 0x3 != 0x0:
                raise cocotb.result.TestFailure("module does not become " +
                                                "inactive")

            # clear the ring buffer contents
            ring_buff.clear()

    # close the trace file
    trace.close()
예제 #3
0
def nt_recv_capture_mem_write_test(dut):
    """Test bench main function."""
    # open file with random content
    try:
        f = File("files/random.file")
    except IOError:
        raise cocotb.result.TestFailure("Generate input data by calling " +
                                        "'./create_random.py' in 'files' " +
                                        "folder!")

    # file size must be a multiple of AXI data width
    if f.size() % (BIT_WIDTH_MEM_WRITE / 8) != 0:
        raise cocotb.result.TestFailure("invalid input data size")

    # create a ring buffer memory (initially of size 0) and connect it to the
    # DuT
    ring_buff = Mem(0)
    ring_buff.connect(dut)

    # start the clock
    cocotb.fork(clk_gen(dut.clk, CLK_FREQ_MHZ))

    # deassert sw reset
    dut.rst_sw <= 0

    # initially module is disabled
    dut.active_i <= 0

    # initially no FIFO flush
    dut.flush_i <= 0

    # reset DuT
    yield rstn(dut.clk, dut.rstn)

    # start the ring buffer memory main routine
    cocotb.fork(ring_buff.main())

    # wait some more clock cycles
    yield wait_n_cycles(dut.clk, 5)

    # iterate over all ring buffer sizes
    for i, ring_buff_size in enumerate(RING_BUFF_SIZES):

        # set ring buffer size
        ring_buff.set_size(ring_buff_size)

        # iterate over all adderesses where ring buffer shall be located in
        # memory
        for j, ring_buff_addr in enumerate(RING_BUFF_ADDRS):

            # print status
            print("Test %d/%d" % (i * len(RING_BUFF_ADDRS) + j + 1,
                                  len(RING_BUFF_ADDRS) * len(RING_BUFF_SIZES)))

            # we have a total of 8 GByte of memory. Make sure the ring buffer
            # fits at the desired address
            if ring_buff_addr + ring_buff_size > 0x1FFFFFFFF:
                raise cocotb.result.TestFailure("ring buffer is too large")

            # to reduce the simulation memory footprint, provide the memory
            # module the first memory address that we actually care about
            ring_buff.set_offset(ring_buff_addr)

            # apply ring buffer memory location to dut
            dut.mem_addr_hi_i <= ring_buff_addr >> 32
            dut.mem_addr_lo_i <= ring_buff_addr & 0xFFFFFFFF

            # apply ring buffer address range to dut
            dut.mem_range_i <= ring_buff_size - 1

            # reset read address pointer
            dut.addr_rd_i <= 0

            # start a couroutine that applies input data
            cocotb.fork(apply_input(dut, f))

            # wait a few clock cycles
            yield wait_n_cycles(dut.clk, 10)

            # start the ring buffer read coroutine and wait until it completes
            yield ring_buff_read(dut, ring_buff, f)

            # clear the ring buffer contents
            ring_buff.clear()

    # close file
    f.close()