def main():
    parser = argparse.ArgumentParser()
    parser.add_argument('--schema_dir', required=True)
    parser.add_argument('--output_dir', required=True)
    parser.add_argument('--device', required=True)
    parser.add_argument('--device_config', required=True)

    args = parser.parse_args()
    interchange = Interchange(args.schema_dir)

    with open(args.device, 'rb') as f:
        device = interchange.read_device_resources(f)

    with open(args.device_config, 'r') as f:
        device_config = yaml.safe_load(f.read())

    const_ids = Enumerator()

    # ID = 0 is always the empty string!
    assert const_ids.get_index('') == 0

    if 'global_buffers' in device_config:
        global_buffers = device_config['global_buffers']
    else:
        global_buffers = []

    chip_info = populate_chip_info(device, const_ids, global_buffers,
                                   device_config['buckets'])

    with open(os.path.join(args.output_dir, 'chipdb.bba'), 'w') as f:
        bba = BbaWriter(f, const_ids)
        bba.pre("#include \"nextpnr.h\"")
        bba.pre("NEXTPNR_NAMESPACE_BEGIN")
        bba.post("NEXTPNR_NAMESPACE_END")
        bba.push("chipdb_blob")

        root_prefix = 'chip_info'
        bba.ref(root_prefix, root_prefix)
        chip_info.append_bba(bba, root_prefix)

        bba.label(chip_info.strings_label(root_prefix), 'strings_slice')
        bba.ref('strings_data')
        bba.u32(len(const_ids.values) - 1)

        bba.label('strings_data', 'strings')
        for s in const_ids.values[1:]:
            bba.str(s)

        bba.pop()

    bba.check_labels()

    with open(os.path.join(args.output_dir, 'constids.txt'), 'w') as f:
        for s in const_ids.values[1:]:
            print('X({})'.format(s), file=f)
Esempio n. 2
0
    def setUp(self):
        schema = get_schema(os.environ['INTERCHANGE_SCHEMA_PATH'], 'device',
                            'Device.Constraints')
        path = os.path.join(__dir__, 'data', 'series7_constraints.yaml')
        with open(path, 'rb') as f:
            constraints = read_format(schema, 'yaml', f)

        self.model = Constraints()
        self.model.read_constraints(constraints)

        interchange = Interchange(
            schema_directory=os.environ['INTERCHANGE_SCHEMA_PATH'])
        phys_netlist = example_physical_netlist()
        with open(
                os.path.join(os.environ['DEVICE_RESOURCE_PATH'],
                             phys_netlist.part + '.device'), 'rb') as f:
            device = interchange.read_device_resources(f)

        self.placement_oracle = PlacementOracle()
        self.placement_oracle.add_sites_from_device(device)
    def test_check_routing_tree_and_stitch_segments(self):
        phys_netlist = example_physical_netlist()

        interchange = Interchange(
            schema_directory=os.environ['INTERCHANGE_SCHEMA_PATH'])

        with open(
                os.path.join(os.environ['DEVICE_RESOURCE_PATH'],
                             phys_netlist.part + '.device'), 'rb') as f:
            device_resources = interchange.read_device_resources(f)

        phys_netlist.check_physical_nets(device_resources)
        before_stitch = phys_netlist.get_normalized_tuple_tree(
            device_resources)
        phys_netlist.stitch_physical_nets(device_resources)
        after_stitch = phys_netlist.get_normalized_tuple_tree(device_resources)
        phys_netlist.stitch_physical_nets(device_resources, flatten=True)
        after_stitch_from_flat = phys_netlist.get_normalized_tuple_tree(
            device_resources)

        self.assertEqual(len(before_stitch), len(after_stitch))
        self.assertEqual(len(before_stitch), len(after_stitch_from_flat))

        bad_nets = set()
        for net in before_stitch:
            if before_stitch[net] != after_stitch[net]:
                bad_nets.add(net)
                print(net)
                pprint.pprint(before_stitch[net])
                pprint.pprint(after_stitch[net])

            if before_stitch[net] != after_stitch_from_flat[net]:
                bad_nets.add(net)
                print(net)
                pprint.pprint(before_stitch[net])
                pprint.pprint(after_stitch_from_flat[net])

        self.assertEqual(set(), bad_nets)
Esempio n. 4
0
def main():
    parser = argparse.ArgumentParser(description=__doc__)

    parser.add_argument('--schema_dir', required=True)
    parser.add_argument('--device', required=True)
    parser.add_argument('--top', required=True)
    parser.add_argument('--verbose', action='store_true')
    parser.add_argument(
        '--library',
        default='work',
        help='Library to put non-primitive elements')
    parser.add_argument('yosys_json')
    parser.add_argument('netlist')

    args = parser.parse_args()

    with open(args.yosys_json) as f:
        yosys_json = json.load(f)

    assert 'modules' in yosys_json, yosys_json.keys()

    if args.top not in yosys_json['modules']:
        raise RuntimeError(
            'Could not find top module in yosys modules: {}'.format(', '.join(
                yosys_json['modules'].keys())))

    interchange = Interchange(args.schema_dir)

    with open(args.device, 'rb') as f:
        device = interchange.read_device_resources(f)

    netlist = convert_yosys_json(device, yosys_json, args.top, args.library,
                                 args.verbose)
    netlist_capnp = netlist.convert_to_capnp(interchange)

    with open(args.netlist, 'wb') as f:
        write_capnp_file(netlist_capnp, f)
Esempio n. 5
0
def main():
    parser = argparse.ArgumentParser(
        description="Run FPGA constraints placement engine.")
    parser.add_argument('--schema_dir', required=True)
    parser.add_argument('--assumptions',
                        help='Comma seperated list of assumptions to hold')
    parser.add_argument('--verbose', action='store_true')
    parser.add_argument('--allowed_sites', required=True)
    parser.add_argument('--filtered_cells')
    parser.add_argument('device')
    parser.add_argument('netlist')

    args = parser.parse_args()

    interchange = Interchange(args.schema_dir)

    with open(args.device, 'rb') as f:
        device = interchange.read_device_resources(f)

    with open(args.netlist, 'rb') as f:
        netlist = interchange.read_logical_netlist(f)

    allowed_sites = set(args.allowed_sites.split(','))
    filtered_cells = set()
    if args.filtered_cells is not None:
        filtered_cells = set(cell for cell in args.filtered_cells.split(','))

    model, placement_oracle, placements = make_problem_from_device(
        device, allowed_sites)
    cells = create_constraint_cells_from_netlist(netlist, filtered_cells)

    solver = model.build_sat(placements, cells, placement_oracle)

    if args.verbose:
        print()
        print("Preparing solver")
        print()
    clauses = solver.prepare_for_sat()

    if args.verbose:
        print()
        print("Variable names ({} total):".format(len(solver.variable_names)))
        print()
        for variable in solver.variable_names:
            print(variable)

        print()
        print("Clauses:")
        print()
        for clause in solver.abstract_clauses:
            print(clause)

    assumptions = []

    if args.assumptions:
        for assumption in args.assumptions.split(','):
            assumptions.append(solver.get_variable(assumption))

    with Solver() as sat:
        for clause in clauses:
            if args.verbose:
                print(clause)
            sat.add_clause(clause)

        if args.verbose:
            print()
            print("Running SAT:")
            print()
            print("Assumptions:")
            print(assumptions)

        solved = sat.solve(assumptions=assumptions)
        if args.verbose:
            print(sat.time())

        if solved:
            model = sat.get_model()
        else:
            core = sat.get_core()

    if solved:
        if args.verbose:
            print()
            print("Raw Solution:")
            print()
            print(model)

        print("Solution:")
        state_groups_vars, other_vars = solver.decode_solution_model(model)
        assert len(other_vars) == 0

        pprint.pprint(state_groups_vars)
    else:
        print("Unsatifiable!")
        if core is not None:
            print("Core:")
            print(core)
            print("Core variables:")
            for core_index in core:
                print(solver.variable_names[core_index])
        sys.exit(1)
Esempio n. 6
0
def main():
    parser = argparse.ArgumentParser()
    parser.add_argument('--schema_dir', required=True)
    parser.add_argument('--output_dir', required=True)
    parser.add_argument('--device', required=True)
    parser.add_argument('--device_config', required=True)
    parser.add_argument(
        '--suffix',
        type=str,
        default=None,
        help="An optional suffix to append to output file names")

    args = parser.parse_args()
    interchange = Interchange(args.schema_dir)

    with open(args.device, 'rb') as f:
        device = interchange.read_device_resources(f)

    with open(args.device_config, 'r') as f:
        device_config = yaml.safe_load(f.read())

    const_ids = Enumerator()

    # ID = 0 is always the empty string!
    assert const_ids.get_index('') == 0

    chip_info = populate_chip_info(device, const_ids, device_config)

    if args.suffix:
        fname = 'chipdb-{}.bba'.format(args.suffix)
    else:
        fname = 'chipdb.bba'

    with open(os.path.join(args.output_dir, fname), 'w') as f:
        bba = BbaWriter(f, const_ids)
        bba.pre("#include \"nextpnr.h\"")
        bba.pre("NEXTPNR_NAMESPACE_BEGIN")
        bba.post("NEXTPNR_NAMESPACE_END")
        bba.push("chipdb_blob")

        root_prefix = 'chip_info'
        bba.ref(root_prefix, root_prefix)
        chip_info.append_bba(bba, root_prefix)

        bba.label(chip_info.strings_label(root_prefix), 'strings_slice')
        bba.ref('strings_data')
        bba.u32(len(const_ids.values) - 1)

        bba.label('strings_data', 'strings')
        for s in const_ids.values[1:]:
            bba.str(s)

        bba.pop()

    bba.check_labels()

    if args.suffix:
        fname = 'constids-{}.txt'.format(args.suffix)
    else:
        fname = 'constids.txt'

    with open(os.path.join(args.output_dir, fname), 'w') as f:
        for s in const_ids.values[1:]:
            print('X({})'.format(s), file=f)