def read_route_bitstream(): global route_bitstream route_bitstream_file_dir = route_bitstream_filepath with open(route_bitstream_file_dir, 'r') as route_file: lines = route_file.readlines() for line, index in zip(lines, range(len(lines))): if index < len(lines) - 20: route_bitstream += helper.int_list_to_bitstream([int(line)], 2) else: route_bitstream += [int(line)] route_bitstream = [str(x) for x in route_bitstream] route_bitstream = route_bitstream[::-1]
async def test_cb(dut): clock = Clock(dut.scan_clk, 10000, units="ps") cocotb.fork(clock.start()) width = dut.CHANNEL_ONEWAY_WIDTH.value dut._log.info("Found CB with channel oneway width %d" % (width)) # random config generation out_config = [random.randint(0, 3) for i in range(2)] out_config_binary = int_list_to_bitstream(out_config, 2) # random input generation tracks_0 = random.randint(0, 2 ** width - 1) tracks_1 = random.randint(0, 2 ** width - 1) bitstream = out_config_binary total_scan_size = len(bitstream) print(bitstream) # scan in config dut.scan_en <= 1 for i in range(total_scan_size): # push the last value into the scan chain # scan in MSB first dut.scan_in <= bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.scan_en <= 0 dut.tracks_0 <= tracks_0 dut.tracks_1 <= tracks_1 await Timer(100, units='ps') out_0 = dut.out_0.value out_1 = dut.out_1.value # convert int to cocotb BinaryValue for easy bit select tracks_0 = BinaryValue(tracks_0, n_bits=4, bigEndian=False) tracks_1 = BinaryValue(tracks_1, n_bits=4, bigEndian=False) golden_out_0 = {0: tracks_0[0], 1: tracks_1[0], 2: tracks_0[2], 3: tracks_1[2]} golden_out_1 = {0: tracks_0[1], 1: tracks_1[1], 2: tracks_0[3], 3: tracks_1[3]} assert out_0 == golden_out_0[out_config[0]], "out_0 expecting %d, getting %d" % (golden_out_0[out_config[0]], out_0) assert out_1 == golden_out_1[out_config[1]], "out_1 expecting %d, getting %d" % (golden_out_1[out_config[1]], out_1)
async def test_tile(dut): clock = Clock(dut.scan_clk, 10000, units="ps") cocotb.fork(clock.start()) # read param channel_oneway_width = dut.CHANNEL_ONEWAY_WIDTH.value ble_num = dut.CLB_BLE_NUM.value conn_sel_width = dut.CONN_SEL_WIDTH.value dut._log.info("Found CB with COW: %d, #BLE: %d, CSW: %d" % (channel_oneway_width, ble_num, conn_sel_width)) # generate and scan in random clb config lut_binary = [random.randint(0, 1) for i in range(2**channel_oneway_width)] complete_config = [ random.randint(0, 3) for i in range(channel_oneway_width) ] # complete_config = [0, 1, 2, 3] complete_binary = int_list_to_bitstream(complete_config, 3) is_comb = [1] clb_bitstream = is_comb + complete_binary + lut_binary clb_scan_size = len(clb_bitstream) print("clb bitstream") print("length: %d" % clb_scan_size) print(clb_bitstream) dut.clb_scan_en <= 1 for i in range(clb_scan_size): dut.clb_scan_in <= clb_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.clb_scan_en <= 0 # generate and scan in conn config sb_left_select = [random.randint(0, 2) for i in range(3)] sb_left_select.append(random.randint(0, 3)) sb_right_select = [random.randint(0, 2) for i in range(3)] sb_right_select.append(random.randint(0, 3)) sb_top_select = [random.randint(0, 2) for i in range(4)] sb_bottom_select = [random.randint(0, 2) for i in range(4)] # convert to bitstream sb_left_binary = int_list_to_bitstream(sb_left_select, 2) sb_right_binary = int_list_to_bitstream(sb_right_select, 2) sb_top_binary = int_list_to_bitstream(sb_top_select, 2) sb_bottom_binary = int_list_to_bitstream(sb_bottom_select, 2) # cb config & bitstream cb_0_config = [random.randint(0, 3) for i in range(2)] cb_0_binary = int_list_to_bitstream(cb_0_config, 2) cb_1_config = [random.randint(0, 3) for i in range(2)] cb_1_binary = int_list_to_bitstream(cb_1_config, 2) conn_bitstream = sb_left_binary + sb_right_binary + sb_top_binary + sb_bottom_binary + cb_0_binary + cb_1_binary conn_scan_size = len(conn_bitstream) print("conn bitstream") print("length: %d" % conn_scan_size) print(conn_bitstream) dut.conn_scan_en <= 1 for i in range(conn_scan_size): dut.conn_scan_in <= conn_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.conn_scan_en <= 0 # random input generation left_in = random.randint(0, 2**channel_oneway_width - 1) right_in = random.randint(0, 2**channel_oneway_width - 1) top_in = random.randint(0, 2**channel_oneway_width - 1) bottom_in = random.randint(0, 2**channel_oneway_width - 1) left_clb_in = random.randint(0, 1) bottom_clb_in = random.randint(0, 1) right_sb_in = random.randint(0, 1) # input to dut dut.left_in <= left_in dut.right_in <= right_in dut.top_in <= top_in dut.bottom_in <= bottom_in dut.left_clb_in <= left_clb_in dut.bottom_clb_in <= bottom_clb_in dut.right_sb_in <= right_sb_in await Timer(100, units='ps') # verification # first check if clb out matches lut result clb_in_actual = dut.test_out_x4.value clb_in_actual.big_endian = False clb_out_actual = dut.left_clb_out.value lut_binary_actual = [ clb_in_actual[complete_config[0]], clb_in_actual[complete_config[1]], clb_in_actual[complete_config[2]], clb_in_actual[complete_config[3]] ] lut_in_actual = bin_list_to_int_little_endian(lut_binary_actual) assert clb_out_actual == lut_binary[ lut_in_actual], "clb out expecting %d, getting %d" % ( lut_binary[lut_in_actual], clb_out_actual) # check if cb and sb are working properly # convert int to cocotb BinaryValue for easy bit select left_in = BinaryValue(left_in, n_bits=4, bigEndian=False) right_in = BinaryValue(right_in, n_bits=4, bigEndian=False) top_in = BinaryValue(top_in, n_bits=4, bigEndian=False) bottom_in = BinaryValue(bottom_in, n_bits=4, bigEndian=False) # dictionary for finding golden sb out, index is arbitrary arch design left_out_dict_0 = {0: bottom_in[2], 1: top_in[1], 2: right_in[0]} left_out_dict_1 = {0: bottom_in[1], 1: top_in[2], 2: right_in[1]} left_out_dict_2 = {0: bottom_in[0], 1: top_in[3], 2: right_in[2]} left_out_dict_3 = { 0: bottom_in[3], 1: top_in[0], 2: right_in[3], 3: clb_out_actual.integer } right_out_dict_0 = {0: bottom_in[3], 1: top_in[2], 2: left_in[0]} right_out_dict_1 = {0: bottom_in[0], 1: top_in[1], 2: left_in[1]} right_out_dict_2 = {0: bottom_in[1], 1: top_in[0], 2: left_in[2]} right_out_dict_3 = { 0: bottom_in[2], 1: top_in[3], 2: left_in[3], 3: right_sb_in } top_out_dict_0 = {0: bottom_in[0], 1: right_in[2], 2: left_in[3]} top_out_dict_1 = {0: bottom_in[1], 1: right_in[1], 2: left_in[0]} top_out_dict_2 = {0: bottom_in[2], 1: right_in[0], 2: left_in[1]} top_out_dict_3 = {0: bottom_in[3], 1: right_in[3], 2: left_in[2]} bottom_out_dict_0 = {0: top_in[0], 1: right_in[1], 2: left_in[2]} bottom_out_dict_1 = {0: top_in[1], 1: right_in[2], 2: left_in[1]} bottom_out_dict_2 = {0: top_in[2], 1: right_in[3], 2: left_in[0]} bottom_out_dict_3 = {0: top_in[3], 1: right_in[0], 2: left_in[3]} # create sb golden out left_out_golden = [ left_out_dict_0[sb_left_select[0]], left_out_dict_1[sb_left_select[1]], left_out_dict_2[sb_left_select[2]], left_out_dict_3[sb_left_select[3]] ] right_out_golden = [ right_out_dict_0[sb_right_select[0]], right_out_dict_1[sb_right_select[1]], right_out_dict_2[sb_right_select[2]], right_out_dict_3[sb_right_select[3]] ] top_out_golden = [ top_out_dict_0[sb_top_select[0]], top_out_dict_1[sb_top_select[1]], top_out_dict_2[sb_top_select[2]], top_out_dict_3[sb_top_select[3]] ] bottom_out_golden = [ bottom_out_dict_0[sb_bottom_select[0]], bottom_out_dict_1[sb_bottom_select[1]], bottom_out_dict_2[sb_bottom_select[2]], bottom_out_dict_3[sb_bottom_select[3]] ] # get actual sb out in int left_out_actual = dut.left_out.value.integer right_out_actual = dut.right_out.value.integer top_out_actual = dut.top_out.value.integer bottom_out_actual = dut.bottom_out.value.integer # compare golden out and actual out assert left_out_actual == bin_list_to_int_little_endian( left_out_golden), "left out expecting %d, getting %d" % ( bin_list_to_int_little_endian(left_out_golden), left_out_actual) assert right_out_actual == bin_list_to_int_little_endian( right_out_golden), "right out expecting %d, getting %d" % ( bin_list_to_int_little_endian(right_out_golden), right_out_actual) assert top_out_actual == bin_list_to_int_little_endian( top_out_golden), "top out expecting %d, getting %d" % ( bin_list_to_int_little_endian(top_out_golden), top_out_actual) assert bottom_out_actual == bin_list_to_int_little_endian( bottom_out_golden), "bottom out expecting %d, getting %d" % ( bin_list_to_int_little_endian(bottom_out_golden), bottom_out_actual) # diectionary for finding golden cb out # cb_<cb inst id>_dict_<bit id> cb_0_dict_0 = { 0: left_out_golden[0], 1: left_in[0], 2: left_out_golden[2], 3: left_in[2] } cb_0_dict_1 = { 0: left_out_golden[1], 1: left_in[1], 2: left_out_golden[3], 3: left_in[3] } cb_1_dict_0 = { 0: bottom_in[0], 1: bottom_out_golden[0], 2: bottom_in[2], 3: bottom_out_golden[2] } cb_1_dict_1 = { 0: bottom_in[1], 1: bottom_out_golden[1], 2: bottom_in[3], 3: bottom_out_golden[3] } # cb golden out cb_0_golden = [cb_0_dict_0[cb_0_config[0]], cb_0_dict_1[cb_0_config[1]]] cb_1_golden = [cb_1_dict_0[cb_1_config[0]], cb_1_dict_1[cb_1_config[1]]] # cb_0_0 to clb_in[2] in the tile above assert dut.top_cb_out.value == cb_0_golden[ 0], "cb_0_0 expecting %d, getting %d" % (cb_0_golden[0], dut.top_cb_out.value) # cb_0_1 to clb_in[0] in this tile assert clb_in_actual[0] == cb_0_golden[ 1], "cb_0_1 expecting %d, getting %d" % (cb_0_golden[1], clb_in_actual[0]) # cb_1_0 to clb_in[1] in this tile assert clb_in_actual[1] == cb_1_golden[ 0], "cb_1_0 expecting %d, getting %d" % (cb_1_golden[0], clb_in_actual[1]) # cb_1_1 to clb_in[3] in the tile to the right assert dut.right_cb_out == cb_1_golden[ 1], "cb_1_1 expecting %d, getting %d" % (cb_1_golden[1], dut.right_cb_out)
async def test_fpga_core(dut): clock = Clock(dut.scan_clk, 10000, units="ps") cocotb.fork(clock.start()) # 2 * 2 fpga # built for primary fpga functional test because bitstream generator is pending complete # bitstream used in this testbench is hand-translated from VTR result # io info: # io_0: C, io_1: B, io_2: A, io_3: D # C = A | B, D = A & B tile_2_A_port = 0 tile_3_A_port = 0 tile_2_B_port = 2 tile_3_B_port = 2 # The Environmental Variable BITSTREAM_DIR is set in the vtr_wholeflow.sh # Loading Routing Configuration Bitstream import re f = open(os.getenv('BITSTREAM_ROUTE_PATH'), "r") routing = f.read() routing = re.split("\n", routing) routing = [int(i) for i in routing if len(i) > 0] f.close() conn_bitstream = int_list_to_bitstream(routing, 2) conn_scan_size = len(conn_bitstream) conn_bitstream_check = conn_bitstream.copy() conn_bitstream += conn_bitstream_check # Loading CLB Configuration Bitstream # The Environmental Variable BITSTREAM_DIR is set in the vtr_wholeflow.sh f = open(os.getenv('BITSTREAM_CLB_PATH'), "r") lut_bitstream = f.read() lut_bitstream = [int(i) for i in lut_bitstream] f.close() lut_scan_size = len(lut_bitstream) lut_bitstream_check = lut_bitstream.copy() lut_bitstream += lut_bitstream_check # print("lut bitstream:") # print(lut_bitstream) # print("conn bitstream:") # print(conn_bitstream) #first scan dut.clb_scan_en <= 1 for i in range(lut_scan_size): dut.clb_scan_in <= lut_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.clb_scan_en <= 0 dut.conn_scan_en <= 1 for i in range(conn_scan_size): dut.conn_scan_in <= conn_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.conn_scan_en <= 0 #repeated scan and check clb_scan_out = [] dut.clb_scan_en <= 1 for i in range(lut_scan_size): dut.clb_scan_in <= lut_bitstream.pop(-1) await RisingEdge(dut.scan_clk) clb_scan_out.append(dut.clb_scan_out.value) dut.clb_scan_en <= 0 if(lut_bitstream_check == clb_scan_out[::-1]): print('clb bitstream valid') else: print('clb bitstream invalid') conn_scan_out = [] dut.conn_scan_en <= 1 for i in range(conn_scan_size): dut.conn_scan_in <= conn_bitstream.pop(-1) await RisingEdge(dut.scan_clk) conn_scan_out.append(dut.conn_scan_out.value) dut.conn_scan_en <= 0 if(conn_bitstream_check == conn_scan_out[::-1]): print('conn bitstream valid') else: print('conn bitstream invalid') print("This is really the blink test.") print(conn_scan_size) await Timer(100, units='ps') clock = Clock(dut.clk, 10000, units="ps") cocotb.fork(clock.start()) dut.reset <= 1; dut.fpga_in[14] <= 1; await Timer(100, units='ns') dut.reset <= 0; await Timer(100, units='ns') dut.fpga_in[14] <= 0; await Timer(1000, units='ns')
async def test_sb(dut): clock = Clock(dut.scan_clk, 10000, units="ps") cocotb.fork(clock.start()) width = dut.CHANNEL_ONEWAY_WIDTH.value dut._log.info("Found SB with channel oneway width %d" % (width)) # random config generation left_select = [random.randint(0, 2) for i in range(3)] left_select.append(random.randint(0, 3)) right_select = [random.randint(0, 2) for i in range(3)] right_select.append(random.randint(0, 3)) top_select = [random.randint(0, 2) for i in range(4)] bottom_select = [random.randint(0, 2) for i in range(4)] left_binary = int_list_to_bitstream(left_select, 2) right_binary = int_list_to_bitstream(right_select, 2) top_binary = int_list_to_bitstream(top_select, 2) bottom_binary = int_list_to_bitstream(bottom_select, 2) # random input generation left_in = random.randint(0, 2**width - 1) right_in = random.randint(0, 2**width - 1) top_in = random.randint(0, 2**width - 1) bottom_in = random.randint(0, 2**width - 1) left_clb_in = random.randint(0, 1) right_clb_in = random.randint(0, 1) print(left_select + right_select + top_select + bottom_select) bitstream = left_binary + right_binary + top_binary + bottom_binary print(bitstream) total_scan_size = len(bitstream) # print(bitstream) # scan in config dut.scan_en <= 1 for i in range(total_scan_size): # push the last value into the scan chain # scan in MSB first dut.scan_in <= bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.scan_en <= 0 # input dut.left_in <= left_in dut.right_in <= right_in dut.top_in <= top_in dut.bottom_in <= bottom_in dut.left_clb_in <= left_clb_in dut.right_clb_in <= right_clb_in await Timer(100, units='ps') left_out = dut.left_out.value right_out = dut.right_out.value top_out = dut.top_out.value bottom_out = dut.bottom_out.value left_out.big_endian = False right_out.big_endian = False top_out.big_endian = False bottom_out.big_endian = False # left_out[0] => LSB # left_out.integer # convert int to cocotb BinaryValue for easy bit select left_in = BinaryValue(left_in, n_bits=4, bigEndian=False) right_in = BinaryValue(right_in, n_bits=4, bigEndian=False) top_in = BinaryValue(top_in, n_bits=4, bigEndian=False) bottom_in = BinaryValue(bottom_in, n_bits=4, bigEndian=False) # golden result left_out_dict_0 = {0: bottom_in[2], 1: top_in[1], 2: right_in[0]} left_out_dict_1 = {0: bottom_in[1], 1: top_in[2], 2: right_in[1]} left_out_dict_2 = {0: bottom_in[0], 1: top_in[3], 2: right_in[2]} left_out_dict_3 = { 0: bottom_in[3], 1: top_in[0], 2: right_in[3], 3: left_clb_in } assert left_out[0] == left_out_dict_0[ left_select[0]], "left_out[0] expecting %d, getting %d" % ( left_out_dict_0[left_select[0]], left_out[0]) assert left_out[1] == left_out_dict_1[ left_select[1]], "left_out[1] expecting %d, getting %d" % ( left_out_dict_1[left_select[1]], left_out[1]) assert left_out[2] == left_out_dict_2[ left_select[2]], "left_out[2] expecting %d, getting %d" % ( left_out_dict_2[left_select[2]], left_out[2]) assert left_out[3] == left_out_dict_3[ left_select[3]], "left_out[3] expecting %d, getting %d" % ( left_out_dict_3[left_select[3]], left_out[3]) right_out_dict_0 = {0: bottom_in[3], 1: top_in[2], 2: left_in[0]} right_out_dict_1 = {0: bottom_in[0], 1: top_in[1], 2: left_in[1]} right_out_dict_2 = {0: bottom_in[1], 1: top_in[0], 2: left_in[2]} right_out_dict_3 = { 0: bottom_in[2], 1: top_in[3], 2: left_in[3], 3: right_clb_in } assert right_out[0] == right_out_dict_0[ right_select[0]], "right_out[0] expecting %d, getting %d" % ( right_out_dict_0[right_select[0]], right_out[0]) assert right_out[1] == right_out_dict_1[ right_select[1]], "right_out[1] expecting %d, getting %d" % ( right_out_dict_1[right_select[1]], right_out[1]) assert right_out[2] == right_out_dict_2[ right_select[2]], "right_out[2] expecting %d, getting %d" % ( right_out_dict_2[right_select[2]], right_out[2]) assert right_out[3] == right_out_dict_3[ right_select[3]], "right_out[3] expecting %d, getting %d" % ( right_out_dict_3[right_select[3]], right_out[3]) top_out_dict_0 = {0: bottom_in[0], 1: right_in[2], 2: left_in[3]} top_out_dict_1 = {0: bottom_in[1], 1: right_in[1], 2: left_in[0]} top_out_dict_2 = {0: bottom_in[2], 1: right_in[0], 2: left_in[1]} top_out_dict_3 = {0: bottom_in[3], 1: right_in[3], 2: left_in[2]} assert top_out[0] == top_out_dict_0[ top_select[0]], "top_out[0] expecting %d, getting %d" % ( top_out_dict_0[top_select[0]], top_out[0]) assert top_out[1] == top_out_dict_1[ top_select[1]], "top_out[1] expecting %d, getting %d" % ( top_out_dict_1[top_select[1]], top_out[1]) assert top_out[2] == top_out_dict_2[ top_select[2]], "top_out[2] expecting %d, getting %d" % ( top_out_dict_2[top_select[2]], top_out[2]) assert top_out[3] == top_out_dict_3[ top_select[3]], "top_out[3] expecting %d, getting %d" % ( top_out_dict_3[top_select[3]], top_out[3]) bottom_out_dict_0 = {0: top_in[0], 1: right_in[1], 2: left_in[2]} bottom_out_dict_1 = {0: top_in[1], 1: right_in[2], 2: left_in[1]} bottom_out_dict_2 = {0: top_in[2], 1: right_in[3], 2: left_in[0]} bottom_out_dict_3 = {0: top_in[3], 1: right_in[0], 2: left_in[3]} assert bottom_out[0] == bottom_out_dict_0[ bottom_select[0]], "bottom_out[0] expecting %d, getting %d" % ( bottom_out_dict_0[bottom_select[0]], bottom_out[0]) assert bottom_out[1] == bottom_out_dict_1[ bottom_select[1]], "bottom_out[1] expecting %d, getting %d" % ( bottom_out_dict_1[bottom_select[1]], bottom_out[1]) assert bottom_out[2] == bottom_out_dict_2[ bottom_select[2]], "bottom_out[2] expecting %d, getting %d" % ( bottom_out_dict_2[bottom_select[2]], bottom_out[2]) assert bottom_out[3] == bottom_out_dict_3[ bottom_select[3]], "bottom_out[3] expecting %d, getting %d" % ( bottom_out_dict_3[bottom_select[3]], bottom_out[3])
async def test_fpga_core(dut): clock = Clock(dut.scan_clk, 10000, units="ps") cocotb.fork(clock.start()) # 2 * 2 fpga # built for primary fpga functional test because bitstream generator is pending complete # bitstream used in this testbench is hand-translated from VTR result # io info: # io_0: C, io_1: B, io_2: A, io_3: D # C = A | B, D = A & B tile_2_A_port = 0 tile_3_A_port = 0 tile_2_B_port = 2 tile_3_B_port = 2 # The Environmental Variable BITSTREAM_DIR is set in the vtr_wholeflow.sh # Loading Routing Configuration Bitstream import re f = open(os.getenv('BITSTREAM_DIR') + "/route.bitstream", "r") routing = f.read() routing = re.split("\n", routing) routing = [int(i) for i in routing if len(i) > 0] f.close() conn_bitstream = int_list_to_bitstream(routing, 2) conn_scan_size = len(conn_bitstream) # Loading CLB Configuration Bitstream # The Environmental Variable BITSTREAM_DIR is set in the vtr_wholeflow.sh f = open(os.getenv('BITSTREAM_DIR') + "/clb.bitstream", "r") lut_bitstream = f.read() lut_bitstream = [int(i) for i in lut_bitstream] f.close() lut_scan_size = len(lut_bitstream) # print("lut bitstream:") # print(lut_bitstream) # print("conn bitstream:") # print(conn_bitstream) dut.clb_scan_en <= 1 for i in range(lut_scan_size): dut.clb_scan_in <= lut_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.clb_scan_en <= 0 dut.conn_scan_en <= 1 for i in range(conn_scan_size): dut.conn_scan_in <= conn_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.conn_scan_en <= 0 await Timer(100, units='ps') test_in_A = random.randint(0, 1) test_in_B = random.randint(0, 1) # dut.fpga_in[0] <= 0 # B dut.fpga_in[2] <= test_in_B # A dut.fpga_in[1] <= test_in_A # dut.fpga_in[3] <= 0 await Timer(100, units='ps') result_C = dut.fpga_out[3] result_D = dut.fpga_out[0] print(dut.fpga_out.value) assert result_C == test_in_A | test_in_B, "port 0 (C) mismatch" assert result_D == test_in_A & test_in_B, "port 3 (D) mismatch"
async def test_fpga_core_2x2(dut): clock = Clock(dut.scan_clk, 10000, units="ps") cocotb.fork(clock.start()) # 2 * 2 fpga # built for primary fpga functional test because bitstream generator is pending complete # bitstream used in this testbench is hand-translated from VTR result # io info: # io_0: C, io_1: B, io_2: A, io_3: D # C = A | B, D = A & B tile_2_A_port = 0 tile_3_A_port = 0 tile_2_B_port = 2 tile_3_B_port = 2 sb_0_config_left = [1, 0, 0, 0] sb_0_config_right = [0, 0, 0, 0] sb_0_config_top = [0, 0, 0, 2] sb_0_config_bottom = [0, 0, 0, 0] sb_0_config = sb_0_config_left + sb_0_config_right + sb_0_config_top + sb_0_config_bottom sb_1_config_left = [2, 0, 1, 0] sb_1_config_right = [0, 1, 2, 0] sb_1_config_top = [2, 0, 0, 2] sb_1_config_bottom = [0, 0, 0, 0] sb_1_config = sb_1_config_left + sb_1_config_right + sb_1_config_top + sb_1_config_bottom sb_2_config_left = [0, 0, 0, 0] sb_2_config_right = [0, 0, 1, 3] sb_2_config_top = [1, 0, 0, 0] sb_2_config_bottom = [0, 0, 0, 0] sb_2_config = sb_2_config_left + sb_2_config_right + sb_2_config_top + sb_2_config_bottom sb_3_config_left = [0, 0, 0, 0] sb_3_config_right = [0, 0, 0, 3] sb_3_config_top = [0, 0, 0, 0] sb_3_config_bottom = [2, 0, 0, 0] sb_3_config = sb_3_config_left + sb_3_config_right + sb_3_config_top + sb_3_config_bottom sb_4_config_left = [0, 0, 0, 0] sb_4_config_right = [0, 0, 0, 0] sb_4_config_top = [0, 0, 0, 0] sb_4_config_bottom = [0, 0, 0, 0] sb_4_config = sb_4_config_left + sb_4_config_right + sb_4_config_top + sb_4_config_bottom cb_0_config = [0, 1] cb_1_config = [0, 0] cb_2_config = [0, 0] cb_3_config = [0, 0] # cb_0 -> top, cb_1 -> right tile_0_cb_0_config = [0, 0] tile_0_cb_1_config = [0, 0] tile_0_sb_config_left = [0, 0, 0, 0] tile_0_sb_config_right = [0, 0, 0, 0] tile_0_sb_config_top = [0, 0, 0, 0] tile_0_sb_config_bottom = [0, 1, 0, 0] tile_0_conn_config = tile_0_sb_config_left + tile_0_sb_config_right + tile_0_sb_config_top + tile_0_sb_config_bottom tile_0_conn_config += tile_0_cb_0_config + tile_0_cb_1_config tile_1_cb_0_config = [0, 0] tile_1_cb_1_config = [0, 0] tile_1_sb_config_left = [0, 0, 0, 0] tile_1_sb_config_right = [0, 0, 0, 0] tile_1_sb_config_top = [0, 0, 0, 0] tile_1_sb_config_bottom = [0, 0, 0, 0] tile_1_conn_config = tile_1_sb_config_left + tile_1_sb_config_right + tile_1_sb_config_top + tile_1_sb_config_bottom tile_1_conn_config += tile_1_cb_0_config + tile_1_cb_1_config tile_2_cb_0_config = [0, 2] tile_2_cb_1_config = [0, 0] tile_2_sb_config_left = [0, 0, 0, 0] tile_2_sb_config_right = [0, 0, 0, 0] tile_2_sb_config_top = [2, 0, 0, 0] tile_2_sb_config_bottom = [0, 2, 0, 0] tile_2_conn_config = tile_2_sb_config_left + tile_2_sb_config_right + tile_2_sb_config_top + tile_2_sb_config_bottom tile_2_conn_config += tile_2_cb_0_config + tile_2_cb_1_config tile_3_cb_0_config = [0, 2] tile_3_cb_1_config = [0, 0] tile_3_sb_config_left = [0, 0, 0, 0] tile_3_sb_config_right = [0, 0, 0, 3] tile_3_sb_config_top = [0, 0, 0, 0] tile_3_sb_config_bottom = [0, 0, 0, 2] tile_3_conn_config = tile_3_sb_config_left + tile_3_sb_config_right + tile_3_sb_config_top + tile_3_sb_config_bottom tile_3_conn_config += tile_3_cb_0_config + tile_3_cb_1_config conn_config = sb_0_config + cb_0_config + sb_1_config + cb_1_config + sb_2_config + cb_2_config conn_config += sb_3_config + cb_3_config + sb_4_config conn_config += tile_0_conn_config + tile_1_conn_config + tile_2_conn_config + tile_3_conn_config # index -> tile id is_comb = [[1], [1], [1], [1]] # [3:0] -> clb_in[3:0], 4 -> ble_out, 5 -> 1'b0 tile_0_complete_config = [5, 5, 5, 5] tile_1_complete_config = [0, 0, 0, 0] tile_2_complete_config = [0, 5, 2, 5] tile_3_complete_config = [0, 5, 2, 5] tile_0_complete_binary = int_list_to_bitstream(tile_0_complete_config, 3) tile_1_complete_binary = int_list_to_bitstream(tile_1_complete_config, 3) tile_2_complete_binary = int_list_to_bitstream(tile_2_complete_config, 3) tile_3_complete_binary = int_list_to_bitstream(tile_3_complete_config, 3) conn_bitstream = int_list_to_bitstream(conn_config, 2) conn_scan_size = len(conn_bitstream) # print(conn_bitstream) tile_0_lut_config = [0 for i in range(16)] tile_1_lut_config = [0 for i in range(16)] tile_2_lut_config = [1 for i in range(16)] tile_3_lut_config = [0 for i in range(16)] # set lut value for index, value in enumerate(tile_2_lut_config): index_binary = int_to_bin_list_little_endian(index, 4) if index_binary[tile_2_A_port] == 0 and index_binary[tile_2_B_port] == 0: tile_2_lut_config[index] = 0 for index, value in enumerate(tile_3_lut_config): index_binary = int_to_bin_list_little_endian(index, 4) if index_binary[tile_3_A_port] == 1 and index_binary[tile_3_B_port] == 1: tile_3_lut_config[index] = 1 lut_bitstream = is_comb[0] + tile_0_complete_binary + tile_0_lut_config lut_bitstream += is_comb[1] + tile_1_complete_binary + tile_1_lut_config lut_bitstream += is_comb[2] + tile_2_complete_binary + tile_2_lut_config lut_bitstream += is_comb[3] + tile_3_complete_binary + tile_3_lut_config lut_scan_size = len(lut_bitstream) print("lut bitstream:") print(lut_bitstream) print("conn bitstream:") print(conn_bitstream) dut.reset <= 1 await Timer(100, units='ps') dut.reset <= 0 dut.clb_scan_en <= 1 for i in range(lut_scan_size): dut.clb_scan_in <= lut_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.clb_scan_en <= 0 dut.conn_scan_en <= 1 for i in range(conn_scan_size): dut.conn_scan_in <= conn_bitstream.pop(-1) await RisingEdge(dut.scan_clk) dut.conn_scan_en <= 0 await Timer(100, units='ps') test_in_A = random.randint(0, 1) test_in_B = random.randint(0, 1) # dut.fpga_in[0] <= 0 # B dut.fpga_in[1] <= test_in_B # A dut.fpga_in[2] <= test_in_A # dut.fpga_in[3] <= 0 await Timer(100, units='ps') result_C = dut.fpga_out[0] result_D = dut.fpga_out[3] assert result_C == test_in_A | test_in_B, "port 0 (C) mismatch" assert result_D == test_in_A & test_in_B, "port 3 (D) mismatch"