Merge pull request #1847 from lnis-uofu/bin_format

Bin format
This commit is contained in:
tangxifan 2024-10-09 13:19:50 -07:00 committed by GitHub
commit 7c3de4c113
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
38 changed files with 708 additions and 186 deletions

View File

@ -10,3 +10,4 @@ add_subdirectory(libpcf)
add_subdirectory(libbusgroup)
add_subdirectory(libnamemanager)
add_subdirectory(libtileconfig)
add_subdirectory(libopenfpgacapnproto)

View File

@ -0,0 +1,67 @@
include(GNUInstallDirs)
if(NOT MSCV)
# These flags generate noisy but non-bug warnings when using lib kj,
# supress them.
set(WARN_FLAGS_TO_DISABLE
-Wno-undef
-Wno-non-virtual-dtor
)
foreach(flag ${WARN_FLAGS_TO_DISABLE})
CHECK_CXX_COMPILER_FLAG(${flag} CXX_COMPILER_SUPPORTS_${flag})
if(CXX_COMPILER_SUPPORTS_${flag})
#Flag supported, so enable it
add_compile_options(${flag})
endif()
endforeach()
endif()
# Create generated headers from capnp schema files
set(CAPNP_DEFS
gen/unique_blocks_uxsdcxx.capnp
)
capnp_generate_cpp(CAPNP_SRCS CAPNP_HDRS
${CAPNP_DEFS}
)
add_library(libopenfpgacapnproto STATIC
${CAPNP_SRCS}
${IC_SRCS}
)
add_dependencies(libopenfpgacapnproto
generate_unique_block_capnp
)
target_include_directories(libopenfpgacapnproto PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}
${CMAKE_CURRENT_BINARY_DIR}
${CMAKE_CURRENT_BINARY_DIR}/gen
)
target_link_libraries(libopenfpgacapnproto
libopenfpgautil
libvtrcapnproto
)
add_custom_target(
generate_unique_block_capnp
COMMAND ${CMAKE_COMMAND} -E remove_directory unique_blocks_capnproto_generate
COMMAND ${CMAKE_COMMAND} -E make_directory unique_blocks_capnproto_generate
COMMAND ${CMAKE_COMMAND} -E chdir unique_blocks_capnproto_generate git clone https://github.com/duck2/uxsdcxx
COMMAND python3 -mpip install --user -r unique_blocks_capnproto_generate/uxsdcxx/requirements.txt
COMMAND ${CMAKE_COMMAND} -E chdir unique_blocks_capnproto_generate python3 uxsdcxx/uxsdcxx.py ${CMAKE_CURRENT_SOURCE_DIR}/gen/unique_blocks.xsd
COMMAND ${CMAKE_COMMAND} -E chdir unique_blocks_capnproto_generate python3 uxsdcxx/uxsdcap.py ${CMAKE_CURRENT_SOURCE_DIR}/gen/unique_blocks.xsd
unique_blocks_capnproto_generate/unique_blocks_uxsdcxx.h
unique_blocks_capnproto_generate/unique_blocks_uxsdcxx_capnp.h
unique_blocks_capnproto_generate/unique_blocks_uxsdcxx_interface.h
${CMAKE_CURRENT_SOURCE_DIR}/gen
COMMAND ${CMAKE_COMMAND} -E copy unique_blocks_capnproto_generate/unique_blocks_uxsdcxx.capnp ${CMAKE_CURRENT_SOURCE_DIR}/gen
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/gen/unique_blocks.xsd
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
)

View File

@ -0,0 +1,74 @@
Capnproto usage in Openfpga
======================
Capnproto is a data serialization framework designed for portabliity and speed.
In Openfpga, capnproto is used to provide binary formats for internal data
structures that can be computed once, and used many times. Specific examples:
- preload unique blocks
What is capnproto?
==================
capnproto can be broken down into 3 parts:
- A schema language
- A code generator
- A library
The schema language is used to define messages. Each message must have an
explcit capnproto schema, which are stored in files suffixed with ".capnp".
The capnproto documentation for how to write these schema files can be found
here: https://capnproto.org/language.html
The schema by itself is not especially useful. In order to read and write
messages defined by the schema in a target language (e.g. C++), a code
generation step is required. Capnproto provides a cmake function for this
purpose, `capnp_generate_cpp`. This generates C++ source and header files.
These source and header files combined with the capnproto C++ library, enables
C++ code to read and write the messages matching a particular schema. The C++
library API can be found here: https://capnproto.org/cxx.html
Contents of libopenfpgacapnproto
===========================
libopenfpgacapnproto should contain two elements:
- Utilities for working capnproto messages in Openfpga
- Generate source and header files of all capnproto messages used in Openfpga
I/O Utilities
-------------
Capnproto does not provide IO support, instead it works from arrays (or file
descriptors). To avoid re-writing this code, libopenfpgacapnproto provides two
utilities that should be used whenever reading or writing capnproto message to
disk. These two files are copied :
- `serdes_utils.h` provides the writeMessageToFile function - Writes a
capnproto message to disk.
- `mmap_file.h` provides MmapFile object - Maps a capnproto message from the
disk as a flat array.
Capnproto schemas
-----------------
libopenfpgacapnproto should contain all capnproto schema definitions used within
Openfpga. To add a new schema:
1. Add the schema to git in `libs/libopenfpgacapnproto/`
2. Add the schema file name to `capnp_generate_cpp` invocation in
`libs/libopenfpgacapnproto/CMakeLists.txt`.
The schema will be available in the header file `schema filename>.h`. The
actual header file will appear in the CMake build directory
`libs/libopenfpgacapnproto` after `libopenfpgacapnproto` has been rebuilt.
Writing capnproto binary files to text
======================================
The `capnp` tool (found in the CMake build directiory
`/vtr-verilog-to-routing/libs/EXTERNAL/capnproto/c++/src/capnp`) can be used to convert from a binary
capnp message to a textual form.
Example converting UniqueBlockCompactInfo from binary to text:
```
capnp convert binary:text unique_blocks_uxsdcxx.capnp UniqueBlockCompactInfo \
< test.bin > test.txt
```

View File

@ -0,0 +1,4 @@
`unique_blocks_uxsdcxx.capnp` is generated via uxsdcxx and is checked in to
avoid requiring python3 and the uxsdcxx depedencies to build Openfpga.

View File

@ -0,0 +1,38 @@
<?xml version="1.0"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
<!-- Enumeration for BlockType -->
<xs:simpleType name="type">
<xs:restriction base="xs:string">
<xs:enumeration value="cbx"/>
<xs:enumeration value="cby"/>
<xs:enumeration value="sb"/>
</xs:restriction>
</xs:simpleType>
<!-- InstanceInfo Structure (using attributes for x and y) -->
<xs:complexType name="instance">
<xs:attribute name="x" type="xs:unsignedInt" use="required"/>
<xs:attribute name="y" type="xs:unsignedInt" use="required"/>
</xs:complexType>
<!-- BlockInfo Structure (using attributes for type, x, and y, and instances as children) -->
<xs:complexType name="block">
<xs:sequence>
<xs:element name="instance" type="instance" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
<xs:attribute name="type" type="type" use="required" />
<xs:attribute name="x" type="xs:unsignedInt" use="required" />
<xs:attribute name="y" type="xs:unsignedInt" use="required" />
</xs:complexType>
<!-- Root element definition -->
<xs:element name="unique_blocks">
<xs:complexType>
<xs:sequence>
<xs:element name="block" type="block" maxOccurs="unbounded"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>

View File

@ -0,0 +1,34 @@
# This file is generated by uxsdcap 0.1.0.
# https://github.com/duck2/uxsdcxx
# Modify only if your build process doesn't involve regenerating this file.
#
# Cmdline: uxsdcxx/uxsdcap.py /home/jrlin/add_feature/bin_format/OpenFPGA/libs/libopenfpgacapnproto/gen/unique_blocks.xsd unique_blocks_capnproto_generate/unique_blocks_uxsdcxx.h unique_blocks_capnproto_generate/unique_blocks_uxsdcxx_capnp.h unique_blocks_capnproto_generate/unique_blocks_uxsdcxx_interface.h /home/jrlin/add_feature/bin_format/OpenFPGA/libs/libopenfpgacapnproto/gen
# Input file: /home/jrlin/add_feature/bin_format/OpenFPGA/libs/libopenfpgacapnproto/gen/unique_blocks.xsd
# md5sum of input file: 1db9d740309076fa51f61413bae1e072
@0xc5f2ef95c322aac3;
using Cxx = import "/capnp/c++.capnp";
$Cxx.namespace("ucap");
enum Type {
uxsdInvalid @0;
cbx @1;
cby @2;
sb @3;
}
struct Instance {
x @0 :UInt32;
y @1 :UInt32;
}
struct Block {
type @0 :Type;
x @1 :UInt32;
y @2 :UInt32;
instances @3 :List(Instance);
}
struct UniqueBlocks {
blocks @0 :List(Block);
}

View File

@ -44,7 +44,9 @@ target_link_libraries(libopenfpga
libnamemanager
libtileconfig
libpugixml
libvpr)
libvpr
libopenfpgacapnproto
)
#Create the test executable
add_executable(openfpga ${EXEC_SOURCE})

View File

@ -116,10 +116,12 @@ std::vector<vtr::Point<size_t>> DeviceRRGSB::get_sb_unique_block_instance_coord(
sb_unique_module_id_[location_x][location_y];
if (unique_module_id_instance == unique_module_id) {
vtr::Point<size_t> instance_coord(location_x, location_y);
if (instance_coord != unique_block_coord) {
instance_map.push_back(instance_coord);
}
}
}
}
return instance_map;
}
@ -144,10 +146,12 @@ DeviceRRGSB::get_cbx_unique_block_instance_coord(
cbx_unique_module_id_[location_x][location_y];
if (unique_module_id_instance == unique_module_id) {
vtr::Point<size_t> instance_coord(location_x, location_y);
if (instance_coord != unique_block_coord) {
instance_map.push_back(instance_coord);
}
}
}
}
return instance_map;
}
@ -172,10 +176,12 @@ DeviceRRGSB::get_cby_unique_block_instance_coord(
cby_unique_module_id_[location_x][location_y];
if (unique_module_id_instance == unique_module_id) {
vtr::Point<size_t> instance_coord(location_x, location_y);
if (instance_coord != unique_block_coord) {
instance_map.push_back(instance_coord);
}
}
}
}
return instance_map;
}

View File

@ -0,0 +1,103 @@
#include <capnp/message.h>
#include <capnp/serialize.h>
#include <kj/io.h>
#include <string>
/* Headers from pugi XML library */
#include "pugixml.hpp"
#include "pugixml_util.hpp"
/* Headers from vtr util library */
#include "vtr_assert.h"
#include "vtr_log.h"
#include "vtr_time.h"
/* Headers from libarchfpga */
#include "arch_error.h"
#include "command_exit_codes.h"
#include "device_rr_gsb_utils.h"
#include "mmap_file.h"
#include "openfpga_digest.h"
#include "read_unique_blocks_bin.h"
#include "read_unique_blocks_xml.h"
#include "read_xml_util.h"
#include "rr_gsb.h"
#include "unique_blocks_uxsdcxx.capnp.h"
#include "write_xml_utils.h"
/********************************************************************
* This file includes the top-level functions of this library
* which includes:
* -- reads a bin file of unique blocks to the associated
* data structures: device_rr_gsb
*******************************************************************/
namespace openfpga {
/*read the instances' coordinate of a unique block from a bin file*/
std::vector<vtr::Point<size_t>> read_bin_unique_instance_coords(
const ucap::Block::Reader& unique_block) {
std::vector<vtr::Point<size_t>> instance_coords;
if (unique_block.hasInstances()) {
auto instance_list = unique_block.getInstances();
for (auto instance : instance_list) {
int instance_x = instance.getX();
int instance_y = instance.getY();
vtr::Point<size_t> instance_coordinate(instance_x, instance_y);
instance_coords.push_back(instance_coordinate);
}
}
return instance_coords;
}
/*read the unique block coordinate from a bin file */
vtr::Point<size_t> read_bin_unique_block_coord(
const ucap::Block::Reader& unique_block, ucap::Type& type) {
int block_x = unique_block.getX();
int block_y = unique_block.getY();
type = unique_block.getType();
vtr::Point<size_t> block_coordinate(block_x, block_y);
return block_coordinate;
}
/*top-level function to read unique blocks from bin file*/
int read_bin_unique_blocks(DeviceRRGSB& device_rr_gsb, const char* file_name,
bool verbose_output) {
/* clear unique modules & reserve memory to relavant vectors */
device_rr_gsb.clear_unique_modules();
device_rr_gsb.reserve_unique_modules();
MmapFile f(file_name);
::capnp::FlatArrayMessageReader reader(f.getData());
auto root = reader.getRoot<ucap::UniqueBlocks>();
if (root.hasBlocks()) {
auto block_list = root.getBlocks();
for (auto unique_block : block_list) {
ucap::Type type;
vtr::Point<size_t> block_coordinate = read_bin_unique_block_coord(
unique_block, type); /*get block coordinate and type*/
std::vector<vtr::Point<size_t>> instance_coords =
read_bin_unique_instance_coords(
unique_block); /* get a list of instance coordinates*/
/* get block coordinate and instance coordinate, try to setup
* device_rr_gsb */
if (type == ucap::Type::SB) {
device_rr_gsb.preload_unique_sb_module(block_coordinate,
instance_coords);
} else if (type == ucap::Type::CBY) {
device_rr_gsb.preload_unique_cby_module(block_coordinate,
instance_coords);
} else if (type == ucap::Type::CBX) {
device_rr_gsb.preload_unique_cbx_module(block_coordinate,
instance_coords);
} else if (type == ucap::Type::UXSD_INVALID) {
VTR_LOG_ERROR("Invalid block type!");
return CMD_EXEC_FATAL_ERROR;
}
}
}
device_rr_gsb.build_gsb_unique_module();
if (verbose_output) {
report_unique_module_status_read(device_rr_gsb, true);
}
return CMD_EXEC_SUCCESS;
}
} // namespace openfpga

View File

@ -0,0 +1,36 @@
#ifndef READ_XML_UNIQUE_BLOCKS_BIN_H
#define READ_XML_UNIQUE_BLOCKS_BIN_H
#include <string>
/* Headers from pugi XML library */
#include "pugixml.hpp"
#include "pugixml_util.hpp"
/* Headers from vtr util library */
#include "vtr_assert.h"
#include "vtr_log.h"
#include "vtr_time.h"
/* Headers from libarchfpga */
#include "arch_error.h"
#include "device_rr_gsb_utils.h"
#include "unique_blocks_uxsdcxx.capnp.h"
/********************************************************************
* This file includes the top-level functions of this library
* which includes:
* -- reads a bin file of unique blocks to the associated
* data structures: device_rr_gsb
*******************************************************************/
namespace openfpga {
std::vector<vtr::Point<size_t>> read_bin_unique_instance_coords(
const ucap::Block::Reader& unique_block);
vtr::Point<size_t> read_bin_unique_block_coord(
const ucap::Block::Reader& unique_block, ucap::Type& type);
int read_bin_unique_blocks(DeviceRRGSB& device_rr_gsb, const char* file_name,
bool verbose_output);
} // namespace openfpga
#endif

View File

@ -1,3 +1,4 @@
#include <string>
/* Headers from pugi XML library */
#include "pugixml.hpp"
@ -12,10 +13,12 @@
#include "arch_error.h"
#include "command_exit_codes.h"
#include "device_rr_gsb_utils.h"
#include "mmap_file.h"
#include "openfpga_digest.h"
#include "read_xml_unique_blocks.h"
#include "read_unique_blocks_xml.h"
#include "read_xml_util.h"
#include "rr_gsb.h"
#include "unique_blocks_uxsdcxx.capnp.h"
#include "write_xml_utils.h"
/********************************************************************
@ -109,7 +112,6 @@ int read_xml_unique_blocks(DeviceRRGSB& device_rr_gsb, const char* file_name,
pugi::xml_node xml_root = get_single_child(doc, "unique_blocks", loc_data);
/* clear unique modules & reserve memory to relavant vectors */
device_rr_gsb.clear_unique_modules();
// vtr::Point<size_t> grid_coord(rr_gsb_.size());
device_rr_gsb.reserve_unique_modules();
/* load unique blocks xml file and set up device_rr_gdb */

View File

@ -1,5 +1,5 @@
#ifndef READ_XML_UNIQUE_BLOCKS_H
#define READ_XML_UNIQUE_BLOCKS_H
#ifndef READ_XML_UNIQUE_BLOCKS_XML_H
#define READ_XML_UNIQUE_BLOCKS_XML_H
#include <string>
@ -15,7 +15,7 @@
/* Headers from libarchfpga */
#include "arch_error.h"
#include "device_rr_gsb_utils.h"
#include "unique_blocks_uxsdcxx.capnp.h"
/********************************************************************
* This file includes the top-level functions of this library
* which includes:
@ -36,4 +36,5 @@ void report_unique_module_status_read(const DeviceRRGSB& device_rr_gsb,
int read_xml_unique_blocks(DeviceRRGSB& device_rr_gsb, const char* file_name,
bool verbose_output);
} // namespace openfpga
#endif

View File

@ -0,0 +1,119 @@
#include <capnp/message.h>
#include <string>
/* Headers from pugi XML library */
#include "pugixml.hpp"
#include "pugixml_util.hpp"
#include "serdes_utils.h"
/* Headers from vtr util library */
#include "vtr_assert.h"
#include "vtr_log.h"
#include "vtr_time.h"
/* Headers from libarchfpga */
#include "arch_error.h"
#include "command_exit_codes.h"
#include "device_rr_gsb_utils.h"
#include "openfpga_digest.h"
#include "read_xml_util.h"
#include "rr_gsb.h"
#include "unique_blocks_uxsdcxx.capnp.h"
#include "write_unique_blocks_bin.h"
#include "write_unique_blocks_xml.h"
#include "write_xml_utils.h"
/********************************************************************
* This file includes the top-level functions of this library
* which includes:
* -- write the unique blocks' information in the associated data structures:
*device_rr_gsb to a bin file
*******************************************************************/
namespace openfpga {
/* write each unique block (including a single unique block info and its mirror
* instances' info)into capnp builder */
int write_bin_atom_block(const std::vector<vtr::Point<size_t>>& instance_map,
const vtr::Point<size_t>& unique_block_coord,
const ucap::Type type, ucap::Block::Builder& root) {
root.setX(unique_block_coord.x());
root.setY(unique_block_coord.y());
root.setType(type);
if (instance_map.size() > 0) {
auto instance_list = root.initInstances(instance_map.size());
for (size_t instance_id = 0; instance_id < instance_map.size();
instance_id++) {
auto instance = instance_list[instance_id];
instance.setX(instance_map[instance_id].x());
instance.setY(instance_map[instance_id].y());
}
}
return openfpga::CMD_EXEC_SUCCESS;
}
/* Top-level function to write bin file of unique blocks */
int write_bin_unique_blocks(const DeviceRRGSB& device_rr_gsb, const char* fname,
bool verbose_output) {
::capnp::MallocMessageBuilder builder;
auto unique_blocks = builder.initRoot<ucap::UniqueBlocks>();
int num_unique_blocks = device_rr_gsb.get_num_sb_unique_module() +
device_rr_gsb.get_num_cb_unique_module(CHANX) +
device_rr_gsb.get_num_cb_unique_module(CHANY);
auto block_list = unique_blocks.initBlocks(num_unique_blocks);
/*write switch blocks into bin file */
for (size_t id = 0; id < device_rr_gsb.get_num_sb_unique_module(); ++id) {
const auto unique_block_coord = device_rr_gsb.get_sb_unique_block_coord(id);
const std::vector<vtr::Point<size_t>> instance_map =
device_rr_gsb.get_sb_unique_block_instance_coord(unique_block_coord);
auto unique_block = block_list[id];
int status_code = write_bin_atom_block(instance_map, unique_block_coord,
ucap::Type::SB, unique_block);
if (status_code != 0) {
VTR_LOG_ERROR("write sb unique blocks into bin file failed!");
return CMD_EXEC_FATAL_ERROR;
}
}
/*write cbx blocks into bin file */
for (size_t id = 0; id < device_rr_gsb.get_num_cb_unique_module(CHANX);
++id) {
const auto unique_block_coord =
device_rr_gsb.get_cbx_unique_block_coord(id);
const std::vector<vtr::Point<size_t>> instance_map =
device_rr_gsb.get_cbx_unique_block_instance_coord(unique_block_coord);
int block_id = id + device_rr_gsb.get_num_sb_unique_module();
auto unique_block = block_list[block_id];
int status_code = write_bin_atom_block(instance_map, unique_block_coord,
ucap::Type::CBX, unique_block);
if (status_code != 0) {
VTR_LOG_ERROR("write cbx unique blocks into bin file failed!");
return CMD_EXEC_FATAL_ERROR;
}
}
/*write cby blocks into bin file */
for (size_t id = 0; id < device_rr_gsb.get_num_cb_unique_module(CHANY);
++id) {
const auto unique_block_coord =
device_rr_gsb.get_cby_unique_block_coord(id);
const std::vector<vtr::Point<size_t>> instance_map =
device_rr_gsb.get_cby_unique_block_instance_coord(unique_block_coord);
int block_id = id + device_rr_gsb.get_num_sb_unique_module() +
device_rr_gsb.get_num_cb_unique_module(CHANX);
auto unique_block = block_list[block_id];
int status_code = write_bin_atom_block(instance_map, unique_block_coord,
ucap::Type::CBY, unique_block);
if (status_code != 0) {
VTR_LOG_ERROR("write cby unique blocks into bin file failed!");
return CMD_EXEC_FATAL_ERROR;
}
}
writeMessageToFile(fname, &builder);
if (verbose_output) {
report_unique_module_status_write(device_rr_gsb, true);
}
return openfpga::CMD_EXEC_SUCCESS;
}
} // namespace openfpga

View File

@ -0,0 +1,33 @@
#ifndef WRITE_XML_UNIQUE_BLOCKS_BIN_H
#define WRITE_XML_UNIQUE_BLOCKS_BIN_H
#include <string>
/* Headers from pugi XML library */
#include "pugixml.hpp"
#include "pugixml_util.hpp"
/* Headers from vtr util library */
#include "vtr_assert.h"
#include "vtr_log.h"
#include "vtr_time.h"
/* Headers from libarchfpga */
#include "arch_error.h"
#include "device_rr_gsb_utils.h"
/********************************************************************
* This file includes the top-level functions of this library
* which includes:
* -- write the unique blocks' information in the associated data structures:
*device_rr_gsb to a bin file
*******************************************************************/
namespace openfpga {
int write_bin_unique_blocks(const DeviceRRGSB& device_rr_gsb, const char* fname,
bool verbose_output);
int write_bin_atom_block(const std::vector<vtr::Point<size_t>>& instance_map,
const vtr::Point<size_t>& unique_block_coord,
const ucap::Type type, ucap::Block::Builder& root);
} // namespace openfpga
#endif

View File

@ -1,10 +1,11 @@
#include <capnp/message.h>
#include <string>
/* Headers from pugi XML library */
#include "pugixml.hpp"
#include "pugixml_util.hpp"
#include "serdes_utils.h"
/* Headers from vtr util library */
#include "vtr_assert.h"
#include "vtr_log.h"
@ -17,7 +18,8 @@
#include "openfpga_digest.h"
#include "read_xml_util.h"
#include "rr_gsb.h"
#include "write_xml_unique_blocks.h"
#include "unique_blocks_uxsdcxx.capnp.h"
#include "write_unique_blocks_xml.h"
#include "write_xml_utils.h"
/********************************************************************
@ -48,10 +50,6 @@ int write_xml_atom_block(std::fstream& fp,
<< "\n";
for (const auto& instance_info : instance_map) {
if (instance_info.x() == unique_block_coord.x() &&
instance_info.y() == unique_block_coord.y()) {
;
} else {
openfpga::write_tab_to_file(fp, 2);
fp << "<instance";
write_xml_attribute(fp, "x", instance_info.x());
@ -60,7 +58,6 @@ int write_xml_atom_block(std::fstream& fp,
fp << "/>"
<< "\n";
}
}
openfpga::write_tab_to_file(fp, 1);
fp << "</block>"
<< "\n";

View File

@ -1,5 +1,5 @@
#ifndef WRITE_XML_UNIQUE_BLOCKS_H
#define WRITE_XML_UNIQUE_BLOCKS_H
#ifndef WRITE_XML_UNIQUE_BLOCKS_XML_H
#define WRITE_XML_UNIQUE_BLOCKS_XML_H
#include <string>

View File

@ -16,18 +16,20 @@
#include "fabric_key_writer.h"
#include "globals.h"
#include "openfpga_naming.h"
#include "read_unique_blocks_bin.h"
#include "read_unique_blocks_xml.h"
#include "read_xml_fabric_key.h"
#include "read_xml_io_name_map.h"
#include "read_xml_module_name_map.h"
#include "read_xml_tile_config.h"
#include "read_xml_unique_blocks.h"
#include "rename_modules.h"
#include "report_reference.h"
#include "vtr_log.h"
#include "vtr_time.h"
#include "write_unique_blocks_bin.h"
#include "write_unique_blocks_xml.h"
#include "write_xml_fabric_pin_physical_location.h"
#include "write_xml_module_name_map.h"
#include "write_xml_unique_blocks.h"
/* begin namespace openfpga */
namespace openfpga {
@ -500,6 +502,10 @@ int read_unique_blocks_template(T& openfpga_ctx, const Command& cmd,
return read_xml_unique_blocks(openfpga_ctx.mutable_device_rr_gsb(),
file_name.c_str(),
cmd_context.option_enable(cmd, opt_verbose));
} else if (file_type == "bin") {
return read_bin_unique_blocks(openfpga_ctx.mutable_device_rr_gsb(),
file_name.c_str(),
cmd_context.option_enable(cmd, opt_verbose));
} else {
VTR_LOG_ERROR("file type %s not supported", file_type.c_str());
return CMD_EXEC_FATAL_ERROR;
@ -528,6 +534,10 @@ int write_unique_blocks_template(T& openfpga_ctx, const Command& cmd,
return write_xml_unique_blocks(openfpga_ctx.device_rr_gsb(),
file_name.c_str(),
cmd_context.option_enable(cmd, opt_verbose));
} else if (file_type == "bin") {
return write_bin_unique_blocks(openfpga_ctx.mutable_device_rr_gsb(),
file_name.c_str(),
cmd_context.option_enable(cmd, opt_verbose));
} else {
VTR_LOG_ERROR("file type %s not supported", file_type.c_str());
return CMD_EXEC_FATAL_ERROR;

View File

@ -1,52 +0,0 @@
# Run VPR for the 'and' design
#--write_rr_graph example_rr_graph.xml
vpr ${VPR_ARCH_FILE} ${VPR_TESTBENCH_BLIF} --clock_modeling route
# Read OpenFPGA architecture definition
read_openfpga_arch -f ${OPENFPGA_ARCH_FILE}
# Read OpenFPGA simulation settings
read_openfpga_simulation_setting -f ${OPENFPGA_SIM_SETTING_FILE}
# Annotate the OpenFPGA architecture to VPR data base
# to debug use --verbose options
link_openfpga_arch --activity_file ${ACTIVITY_FILE} --sort_gsb_chan_node_in_edges
# Check and correct any naming conflicts in the BLIF netlist
check_netlist_naming_conflict --fix --report ./netlist_renaming.xml
# preload unique blocks from the provided xml file
read_unique_blocks --file ${READ_UNIQUE_BLOCKS_XML} --verbose --type xml
# Build the module graph
# - Enabled compression on routing architecture modules
# - Enable pin duplication on grid modules
build_fabric --compress_routing #--verbose
#write unique blocks xml file
write_unique_blocks --file ./write_unique_block.xml --verbose --type xml
# Write the fabric hierarchy of module graph to a file
# This is used by hierarchical PnR flows
write_fabric_hierarchy --file ./fabric_hierarchy.txt
# Write the fabric I/O attributes to a file
# This is used by pin constraint files
write_fabric_io_info --file ./fabric_io_location.xml --verbose
# Write the Verilog netlist for FPGA fabric
# - Enable the use of explicit port mapping in Verilog netlist
write_fabric_verilog --file ${OPENFPGA_VERILOG_OUTPUT_DIR}/SRC --explicit_port_mapping --include_timing --print_user_defined_template --verbose
# Write the SDC files for PnR backend
# - Turn on every options here
write_pnr_sdc --file ./SDC
# Write SDC to disable timing for configure ports
write_sdc_disable_timing_configure_ports --file ./SDC/disable_configure_ports.sdc
# Finish and exit OpenFPGA
exit
# Note :
# To run verification at the end of the flow maintain source in ./SRC directory

View File

@ -21,13 +21,13 @@ ${OPENFPGA_PB_PIN_FIXUP_COMMAND}
# Apply fix-up to Look-Up Table truth tables based on packing results
lut_truth_table_fixup
# preload unique blocks from the provided xml file
read_unique_blocks --file ${READ_UNIQUE_BLOCKS_XML} --verbose --type xml
# preload unique blocks from the provided file
read_unique_blocks --file ${READ_UNIQUE_BLOCKS} --verbose --type ${OPENFPGA_UNIQUE_BLOCK_FILE}
# Build the module graph
# - Enabled compression on routing architecture modules
# - Enable pin duplication on grid modules
build_fabric --compress_routing --group_tile ${OPENFPGA_GROUP_TILE_CONFIG_FILE} #--verbose
build_fabric --group_tile ${OPENFPGA_GROUP_TILE_CONFIG_FILE} #--verbose
# Write the fabric hierarchy of module graph to a file
# This is used by hierarchical PnR flows

View File

@ -21,16 +21,16 @@ ${OPENFPGA_PB_PIN_FIXUP_COMMAND}
# Apply fix-up to Look-Up Table truth tables based on packing results
lut_truth_table_fixup
# preload unique blocks from the provided xml file
read_unique_blocks --file ${READ_UNIQUE_BLOCKS_XML} --verbose --type xml
# preload unique blocks from the provided file
read_unique_blocks --file ${READ_UNIQUE_BLOCKS} --verbose --type ${OPENFPGA_UNIQUE_BLOCK_FILE_READ}
# Build the module graph
# - Enabled compression on routing architecture modules
# - Enable pin duplication on grid modules
build_fabric --group_tile ${OPENFPGA_GROUP_TILE_CONFIG_FILE} #--verbose
#write unique blocks to a xml format file
write_unique_blocks --file ./write_unique_block.xml --verbose --type xml
#write unique blocks to a format file
write_unique_blocks --file ./${WRITE_UNIQUE_BLOCKS} --verbose --type ${OPENFPGA_UNIQUE_BLOCK_FILE_WRITE}
# Write the fabric hierarchy of module graph to a file
# This is used by hierarchical PnR flows

View File

@ -1,49 +0,0 @@
# Run VPR for the 'and' design
#--write_rr_graph example_rr_graph.xml
vpr ${VPR_ARCH_FILE} ${VPR_TESTBENCH_BLIF} --clock_modeling route
# Read OpenFPGA architecture definition
read_openfpga_arch -f ${OPENFPGA_ARCH_FILE}
# Read OpenFPGA simulation settings
read_openfpga_simulation_setting -f ${OPENFPGA_SIM_SETTING_FILE}
# Annotate the OpenFPGA architecture to VPR data base
# to debug use --verbose options
link_openfpga_arch --activity_file ${ACTIVITY_FILE} --sort_gsb_chan_node_in_edges
# Check and correct any naming conflicts in the BLIF netlist
check_netlist_naming_conflict --fix --report ./netlist_renaming.xml
# Build the module graph
# - Enabled compression on routing architecture modules
# - Enable pin duplication on grid modules
build_fabric --compress_routing #--verbose
#write unique blocks xml file
write_unique_blocks --file ./write_unique_block.xml --verbose --type xml
# Write the fabric hierarchy of module graph to a file
# This is used by hierarchical PnR flows
write_fabric_hierarchy --file ./fabric_hierarchy.txt
# Write the fabric I/O attributes to a file
# This is used by pin constraint files
write_fabric_io_info --file ./fabric_io_location.xml --verbose
# Write the Verilog netlist for FPGA fabric
# - Enable the use of explicit port mapping in Verilog netlist
write_fabric_verilog --file ${OPENFPGA_VERILOG_OUTPUT_DIR}/SRC --explicit_port_mapping --include_timing --print_user_defined_template --verbose
# Write the SDC files for PnR backend
# - Turn on every options here
write_pnr_sdc --file ./SDC
# Write SDC to disable timing for configure ports
write_sdc_disable_timing_configure_ports --file ./SDC/disable_configure_ports.sdc
# Finish and exit OpenFPGA
exit
# Note :
# To run verification at the end of the flow maintain source in ./SRC directory

View File

@ -27,8 +27,8 @@ lut_truth_table_fixup
# - Enable pin duplication on grid modules
build_fabric --compress_routing --group_tile ${OPENFPGA_GROUP_TILE_CONFIG_FILE} #--verbose
#write unique blocks xml file
write_unique_blocks --file ./write_unique_block.xml --verbose --type xml
#write unique blocks file
write_unique_blocks --file ./${WRITE_UNIQUE_BLOCKS} --verbose --type ${OPENFPGA_UNIQUE_BLOCK_FILE}
# Write the fabric hierarchy of module graph to a file
# This is used by hierarchical PnR flows

View File

@ -19,11 +19,13 @@ run-task basic_tests/preload_rr_graph/preload_rr_graph_xml $@
run-task basic_tests/preload_rr_graph/preload_rr_graph_bin $@
echo -e "Testing preloading unique blocks"
run-task basic_tests/preload_unique_blocks/write_unique_blocks $@
run-task basic_tests/preload_unique_blocks/read_unique_blocks $@
run-task basic_tests/preload_unique_blocks/write_unique_blocks_full_flow $@
run-task basic_tests/preload_unique_blocks/read_unique_blocks_full_flow $@
run-task basic_tests/preload_unique_blocks/read_write_unique_blocks $@
run-task basic_tests/preload_unique_blocks/read_write_unique_blocks_bin $@
run-task basic_tests/preload_unique_blocks/write_bin_unique_blocks_full_flow $@
run-task basic_tests/preload_unique_blocks/read_unique_blocks_bin $@
run-task basic_tests/preload_unique_blocks/read_bin_write_xml $@
echo -e "Testing testbenches using fpga core wrapper"

View File

@ -0,0 +1,45 @@
# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
# Configuration file for running experiments
# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
# timeout_each_job : FPGA Task script splits fpga flow into multiple jobs
# Each job execute fpga_flow script on combination of architecture & benchmark
# timeout_each_job is timeout for each job
# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
[GENERAL]
run_engine=openfpga_shell
power_tech_file = ${PATH:OPENFPGA_PATH}/openfpga_flow/tech/PTM_45nm/45nm.xml
power_analysis = false
spice_output=false
verilog_output=true
timeout_each_job = 20*60
fpga_flow=yosys_vpr
[OpenFPGA_SHELL]
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/read_write_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
read_unique_blocks =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_write_unique_blocks_bin/read_unique_block.bin
openfpga_unique_block_file_read=bin
openfpga_unique_block_file_write=xml
write_unique_blocks=write_unique_block.xml
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4
openfpga_vpr_route_chan_width=20
openfpga_group_tile_config_file=${PATH:TASK_DIR}/config/tile_config.xml
openfpga_verilog_testbench_options=--explicit_port_mapping
[ARCHITECTURES]
arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_TileOrgzTl_40nm.xml
[BENCHMARKS]
bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/or2/or2.v
[SYNTHESIS_PARAM]
bench_read_verilog_options_common = -nolatches
bench0_top = or2
[SCRIPT_PARAM_MIN_ROUTE_CHAN_WIDTH]
end_flow_with_test=
vpr_fpga_verilog_formal_verification_top_netlist=

View File

@ -0,0 +1 @@
<tiles style="top_left"/>

View File

@ -1,22 +0,0 @@
<unique_blocks>
<block type="sb" x="0" y="0">
</block>
<block type="sb" x="0" y="1">
</block>
<block type="sb" x="1" y="0">
</block>
<block type="sb" x="1" y="1">
</block>
<block type="cbx" x="1" y="0">
<instance x="0" y="0"/>
<instance x="0" y="1"/>
</block>
<block type="cbx" x="1" y="1">
</block>
<block type="cby" x="0" y="1">
<instance x="0" y="0"/>
<instance x="1" y="0"/>
</block>
<block type="cby" x="1" y="1">
</block>
</unique_blocks>

View File

@ -9,27 +9,35 @@
[GENERAL]
run_engine=openfpga_shell
power_tech_file = ${PATH:OPENFPGA_PATH}/openfpga_flow/tech/PTM_45nm/45nm.xml
power_analysis = true
power_analysis = false
spice_output=false
verilog_output=true
timeout_each_job = 20*60
fpga_flow=vpr_blif
fpga_flow=yosys_vpr
[OpenFPGA_SHELL]
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_unique_blocks_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k6_frac_N10_40nm_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/read_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
read_unique_blocks =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_unique_blocks_bin/read_unique_block.bin
openfpga_unique_block_file=bin
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4
openfpga_vpr_route_chan_width=20
openfpga_group_tile_config_file=${PATH:TASK_DIR}/config/tile_config.xml
openfpga_verilog_testbench_options=--explicit_port_mapping
[ARCHITECTURES]
arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k6_frac_N10_tileable_40nm.xml
arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_TileOrgzTl_40nm.xml
[BENCHMARKS]
bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/and2/and2.blif
bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/or2/or2.v
[SYNTHESIS_PARAM]
bench0_top = and2
bench0_act = ${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/and2/and2.act
bench0_verilog = ${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/and2/and2.v
bench_read_verilog_options_common = -nolatches
bench0_top = or2
[SCRIPT_PARAM_MIN_ROUTE_CHAN_WIDTH]
end_flow_with_test=
vpr_fpga_verilog_formal_verification_top_netlist=

View File

@ -0,0 +1 @@
<tiles style="top_left"/>

View File

@ -19,7 +19,8 @@ fpga_flow=yosys_vpr
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/read_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
read_unique_blocks_xml =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_unique_blocks_full_flow/read_unique_block.xml
read_unique_blocks =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_unique_blocks_full_flow/read_unique_block.xml
openfpga_unique_block_file=xml
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4

View File

@ -19,7 +19,10 @@ fpga_flow=yosys_vpr
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/read_write_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
read_unique_blocks_xml =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_unique_blocks_full_flow/read_unique_block.xml
read_unique_blocks =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_unique_blocks_full_flow/read_unique_block.xml
openfpga_unique_block_file_read=xml
openfpga_unique_block_file_write=xml
write_unique_blocks=write_unique_block.xml
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4

View File

@ -0,0 +1,45 @@
# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
# Configuration file for running experiments
# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
# timeout_each_job : FPGA Task script splits fpga flow into multiple jobs
# Each job execute fpga_flow script on combination of architecture & benchmark
# timeout_each_job is timeout for each job
# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
[GENERAL]
run_engine=openfpga_shell
power_tech_file = ${PATH:OPENFPGA_PATH}/openfpga_flow/tech/PTM_45nm/45nm.xml
power_analysis = false
spice_output=false
verilog_output=true
timeout_each_job = 20*60
fpga_flow=yosys_vpr
[OpenFPGA_SHELL]
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/read_write_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
read_unique_blocks =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_write_unique_blocks_bin/read_unique_block.bin
openfpga_unique_block_file_read=bin
openfpga_unique_block_file_write=bin
write_unique_blocks=write_unique_block.bin
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4
openfpga_vpr_route_chan_width=20
openfpga_group_tile_config_file=${PATH:TASK_DIR}/config/tile_config.xml
openfpga_verilog_testbench_options=--explicit_port_mapping
[ARCHITECTURES]
arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_TileOrgzTl_40nm.xml
[BENCHMARKS]
bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/or2/or2.v
[SYNTHESIS_PARAM]
bench_read_verilog_options_common = -nolatches
bench0_top = or2
[SCRIPT_PARAM_MIN_ROUTE_CHAN_WIDTH]
end_flow_with_test=
vpr_fpga_verilog_formal_verification_top_netlist=

View File

@ -9,27 +9,35 @@
[GENERAL]
run_engine=openfpga_shell
power_tech_file = ${PATH:OPENFPGA_PATH}/openfpga_flow/tech/PTM_45nm/45nm.xml
power_analysis = true
power_analysis = false
spice_output=false
verilog_output=true
timeout_each_job = 20*60
fpga_flow=vpr_blif
fpga_flow=yosys_vpr
[OpenFPGA_SHELL]
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/read_unique_blocks_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k6_frac_N10_40nm_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml
read_unique_blocks_xml =${PATH:OPENFPGA_PATH}/openfpga_flow/tasks/basic_tests/preload_unique_blocks/read_unique_blocks/read_unique_block.xml
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
write_unique_blocks=write_unique_block.bin
openfpga_unique_block_file=bin
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4
openfpga_vpr_route_chan_width=20
openfpga_group_tile_config_file=${PATH:TASK_DIR}/config/tile_config.xml
openfpga_verilog_testbench_options=--explicit_port_mapping
[ARCHITECTURES]
arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k6_frac_N10_tileable_40nm.xml
arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_TileOrgzTl_40nm.xml
[BENCHMARKS]
bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/and2/and2.blif
bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/or2/or2.v
[SYNTHESIS_PARAM]
bench0_top = and2
bench0_act = ${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/and2/and2.act
bench0_verilog = ${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/and2/and2.v
bench_read_verilog_options_common = -nolatches
bench0_top = or2
[SCRIPT_PARAM_MIN_ROUTE_CHAN_WIDTH]
end_flow_with_test=
vpr_fpga_verilog_formal_verification_top_netlist=

View File

@ -19,6 +19,8 @@ fpga_flow=yosys_vpr
openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_unique_blocks_full_flow_example_script.openfpga
openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml
openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml
write_unique_blocks=write_unique_blocks.xml
openfpga_unique_block_file=xml
openfpga_vpr_extra_options=
openfpga_pb_pin_fixup_command=
openfpga_vpr_device=4x4