start developing the openfpga arch binding to vpr
This commit is contained in:
parent
46b53f20ba
commit
a6fbbce33e
|
@ -789,6 +789,22 @@ struct t_pb_type {
|
||||||
t_pin_to_pin_annotation* annotations = nullptr; /* [0..num_annotations-1] */
|
t_pin_to_pin_annotation* annotations = nullptr; /* [0..num_annotations-1] */
|
||||||
int num_annotations = 0;
|
int num_annotations = 0;
|
||||||
|
|
||||||
|
/************************************************************************
|
||||||
|
* Xifan Tang: Add useful methods for pb_type
|
||||||
|
* - A pb_type is considered to be primitive when it has zero modes
|
||||||
|
* However, this not always true. An exception is the LUT_CLASS
|
||||||
|
* VPR added two modes by default to a LUT pb_type. Therefore,
|
||||||
|
* for LUT_CLASS, it is a primitive when it is binded to a blif model
|
||||||
|
* - A pb_type is the root pb_type when it has no parent mode
|
||||||
|
************************************************************************/
|
||||||
|
bool is_primitive() const {
|
||||||
|
if (LUT_CLASS == class_type) {
|
||||||
|
return nullptr != blif_model;
|
||||||
|
}
|
||||||
|
return 0 == num_modes;
|
||||||
|
}
|
||||||
|
bool is_root() const { return parent_mode == nullptr; }
|
||||||
|
|
||||||
/* Power related members */
|
/* Power related members */
|
||||||
t_pb_type_power* pb_type_power = nullptr;
|
t_pb_type_power* pb_type_power = nullptr;
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
|
|
||||||
#include "vpr_context.h"
|
#include "vpr_context.h"
|
||||||
#include "openfpga_arch.h"
|
#include "openfpga_arch.h"
|
||||||
|
#include "vpr_pb_type_annotation.h"
|
||||||
|
|
||||||
/********************************************************************
|
/********************************************************************
|
||||||
* This file includes the declaration of the date structure
|
* This file includes the declaration of the date structure
|
||||||
|
@ -34,11 +35,15 @@
|
||||||
class OpenfpgaContext : public Context {
|
class OpenfpgaContext : public Context {
|
||||||
public: /* Public accessors */
|
public: /* Public accessors */
|
||||||
const openfpga::Arch& arch() const { return arch_; }
|
const openfpga::Arch& arch() const { return arch_; }
|
||||||
|
const openfpga::VprPbTypeAnnotation& vpr_pb_type_annotation() const { return vpr_pb_type_annotation_; }
|
||||||
public: /* Public mutators */
|
public: /* Public mutators */
|
||||||
openfpga::Arch& mutable_arch() { return arch_; }
|
openfpga::Arch& mutable_arch() { return arch_; }
|
||||||
|
openfpga::VprPbTypeAnnotation& mutable_vpr_pb_type_annotation() { return vpr_pb_type_annotation_; }
|
||||||
private: /* Internal data */
|
private: /* Internal data */
|
||||||
/* Data structure to store information from read_openfpga_arch library */
|
/* Data structure to store information from read_openfpga_arch library */
|
||||||
openfpga::Arch arch_;
|
openfpga::Arch arch_;
|
||||||
|
/* Annotation to pb_type of VPR */
|
||||||
|
openfpga::VprPbTypeAnnotation vpr_pb_type_annotation_;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -0,0 +1,86 @@
|
||||||
|
/********************************************************************
|
||||||
|
* This file includes functions to read an OpenFPGA architecture file
|
||||||
|
* which are built on the libarchopenfpga library
|
||||||
|
*******************************************************************/
|
||||||
|
/* Headers from vtrutil library */
|
||||||
|
#include "vtr_log.h"
|
||||||
|
|
||||||
|
#include "vpr_pb_type_annotation.h"
|
||||||
|
#include "openfpga_link_arch.h"
|
||||||
|
|
||||||
|
/* Include global variables of VPR */
|
||||||
|
#include "globals.h"
|
||||||
|
|
||||||
|
/* begin namespace openfpga */
|
||||||
|
namespace openfpga {
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* This function will recursively traverse pb_type graph to ensure
|
||||||
|
* 1. there is only a physical mode under each pb_type
|
||||||
|
* 2. physical mode appears only when its parent is a physical mode.
|
||||||
|
*******************************************************************/
|
||||||
|
static
|
||||||
|
void rec_check_pb_type_physical_mode(const t_pb_type& cur_pb_type) {
|
||||||
|
/* We do not check any primitive pb_type */
|
||||||
|
if (true == cur_pb_type.is_primitive()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* For non-primitive pb_type: we should iterate over each mode
|
||||||
|
* Ensure there is only one physical mode
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Traverse all the modes for identifying idle mode */
|
||||||
|
for (int imode = 0; cur_pb_type.num_modes; ++imode) {
|
||||||
|
/* Check each pb_type_child */
|
||||||
|
for (int ichild = 0; ichild < cur_pb_type.modes[imode].num_pb_type_children; ++ichild) {
|
||||||
|
rec_check_pb_type_physical_mode(cur_pb_type.modes[imode].pb_type_children[ichild]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* This function will
|
||||||
|
* - identify the physical pb_type for each multi-mode pb_type in
|
||||||
|
* VPR pb_type graph
|
||||||
|
* - identify the physical pb_type for operating pb_types in VPR
|
||||||
|
*******************************************************************/
|
||||||
|
static
|
||||||
|
void build_physical_pb_type_vpr_annotation(const DeviceContext& vpr_device_ctx,
|
||||||
|
const Arch& openfpga_arch,
|
||||||
|
VprPbTypeAnnotation& vpr_pb_type_annotation) {
|
||||||
|
/* Walk through the pb_type annotation stored in the openfpga arch */
|
||||||
|
for (const PbTypeAnnotation& pb_type_annotation : openfpga_arch.pb_type_annotations) {
|
||||||
|
/* Pb type information are located at the logic_block_types in the device context of VPR
|
||||||
|
* We iterate over the vectors and annotate the pb_type
|
||||||
|
*/
|
||||||
|
for (const t_logical_block_type& lb_type : vpr_device_ctx.logical_block_types) {
|
||||||
|
/* By pass nullptr for pb_type head */
|
||||||
|
if (nullptr == lb_type.pb_type) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* Top-level function to link openfpga architecture to VPR, including:
|
||||||
|
* - physical pb_type
|
||||||
|
* - idle pb_type
|
||||||
|
* - circuit models for pb_type, pb interconnect and routing architecture
|
||||||
|
*******************************************************************/
|
||||||
|
void link_arch(OpenfpgaContext& openfpga_context) {
|
||||||
|
|
||||||
|
/* Annotate physical pb_type in the VPR pb_type graph */
|
||||||
|
build_physical_pb_type_vpr_annotation(g_vpr_ctx.device(), openfpga_context.arch(),
|
||||||
|
openfpga_context.mutable_vpr_pb_type_annotation());
|
||||||
|
|
||||||
|
/* Annotate idle pb_type in the VPR pb_type graph */
|
||||||
|
|
||||||
|
/* Link physical pb_type to circuit model */
|
||||||
|
|
||||||
|
/* Link routing architecture to circuit model */
|
||||||
|
}
|
||||||
|
|
||||||
|
} /* end namespace openfpga */
|
||||||
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
#ifndef OPENFPGA_LINK_ARCH_COMMAND_H
|
||||||
|
#define OPENFPGA_LINK_ARCH_COMMAND_H
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* Include header files that are required by function declaration
|
||||||
|
*******************************************************************/
|
||||||
|
#include "command.h"
|
||||||
|
#include "command_context.h"
|
||||||
|
#include "openfpga_context.h"
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* Function declaration
|
||||||
|
*******************************************************************/
|
||||||
|
|
||||||
|
/* begin namespace openfpga */
|
||||||
|
namespace openfpga {
|
||||||
|
|
||||||
|
void link_arch(OpenfpgaContext& openfpga_context);
|
||||||
|
|
||||||
|
} /* end namespace openfpga */
|
||||||
|
|
||||||
|
#endif
|
|
@ -4,6 +4,7 @@
|
||||||
* - read_openfpga_arch : read OpenFPGA architecture file
|
* - read_openfpga_arch : read OpenFPGA architecture file
|
||||||
*******************************************************************/
|
*******************************************************************/
|
||||||
#include "openfpga_read_arch.h"
|
#include "openfpga_read_arch.h"
|
||||||
|
#include "openfpga_link_arch.h"
|
||||||
#include "openfpga_setup_command.h"
|
#include "openfpga_setup_command.h"
|
||||||
|
|
||||||
/* begin namespace openfpga */
|
/* begin namespace openfpga */
|
||||||
|
@ -36,8 +37,23 @@ void add_openfpga_setup_commands(openfpga::Shell<OpenfpgaContext>& shell) {
|
||||||
ShellCommandId shell_cmd_write_arch_id = shell.add_command(shell_cmd_write_arch, "write OpenFPGA architecture file");
|
ShellCommandId shell_cmd_write_arch_id = shell.add_command(shell_cmd_write_arch, "write OpenFPGA architecture file");
|
||||||
shell.set_command_class(shell_cmd_write_arch_id, openfpga_setup_cmd_class);
|
shell.set_command_class(shell_cmd_write_arch_id, openfpga_setup_cmd_class);
|
||||||
shell.set_command_const_execute_function(shell_cmd_write_arch_id, write_arch);
|
shell.set_command_const_execute_function(shell_cmd_write_arch_id, write_arch);
|
||||||
/* The 'write_openfpga_arch' command should be executed before 'read_openfpga_arch' */
|
/* The 'write_openfpga_arch' command should NOT be executed before 'read_openfpga_arch' */
|
||||||
shell.set_command_dependency(shell_cmd_write_arch_id, std::vector<ShellCommandId>(1, shell_cmd_read_arch_id));
|
shell.set_command_dependency(shell_cmd_write_arch_id, std::vector<ShellCommandId>(1, shell_cmd_read_arch_id));
|
||||||
|
|
||||||
|
/* Command 'link_openfpga_arch' */
|
||||||
|
Command shell_cmd_link_openfpga_arch("link_openfpga_arch");
|
||||||
|
|
||||||
|
/* Add command 'link_openfpga_arch' to the Shell */
|
||||||
|
ShellCommandId shell_cmd_link_openfpga_arch_id = shell.add_command(shell_cmd_link_openfpga_arch, "Bind OpenFPGA architecture to VPR");
|
||||||
|
shell.set_command_class(shell_cmd_link_openfpga_arch_id, openfpga_setup_cmd_class);
|
||||||
|
shell.set_command_execute_function(shell_cmd_link_openfpga_arch_id, link_arch);
|
||||||
|
/* The 'link_openfpga_arch' command should NOT be executed before 'read_openfpga_arch' and 'vpr' */
|
||||||
|
const ShellCommandId& shell_cmd_vpr_id = shell.command("vpr");
|
||||||
|
std::vector<ShellCommandId> cmd_dependency_link_openfpga_arch;
|
||||||
|
cmd_dependency_link_openfpga_arch.push_back(shell_cmd_read_arch_id);
|
||||||
|
cmd_dependency_link_openfpga_arch.push_back(shell_cmd_vpr_id);
|
||||||
|
shell.set_command_dependency(shell_cmd_link_openfpga_arch_id, cmd_dependency_link_openfpga_arch);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
} /* end namespace openfpga */
|
} /* end namespace openfpga */
|
||||||
|
|
|
@ -0,0 +1,18 @@
|
||||||
|
/************************************************************************
|
||||||
|
* Member functions for class VprPbTypeAnnotation
|
||||||
|
***********************************************************************/
|
||||||
|
#include "vtr_log.h"
|
||||||
|
#include "vtr_assert.h"
|
||||||
|
#include "vpr_pb_type_annotation.h"
|
||||||
|
|
||||||
|
/* namespace openfpga begins */
|
||||||
|
namespace openfpga {
|
||||||
|
|
||||||
|
/************************************************************************
|
||||||
|
* Constructors
|
||||||
|
***********************************************************************/
|
||||||
|
VprPbTypeAnnotation::VprPbTypeAnnotation() {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
} /* End namespace openfpga*/
|
|
@ -0,0 +1,39 @@
|
||||||
|
#ifndef VPR_PB_TYPE_ANNOTATION_H
|
||||||
|
#define VPR_PB_TYPE_ANNOTATION_H
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* Include header files required by the data structure definition
|
||||||
|
*******************************************************************/
|
||||||
|
#include <map>
|
||||||
|
|
||||||
|
/* Header from archfpga library */
|
||||||
|
#include "physical_types.h"
|
||||||
|
|
||||||
|
/* Header from openfpgautil library */
|
||||||
|
#include "circuit_library.h"
|
||||||
|
|
||||||
|
/* Begin namespace openfpga */
|
||||||
|
namespace openfpga {
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* This is the critical data structure to link the pb_type in VPR
|
||||||
|
* to openfpga annotations
|
||||||
|
* With a given pb_type pointer, it aims to identify:
|
||||||
|
* 1. if the pb_type is a physical pb_type or a operating pb_type
|
||||||
|
* 2. what is the circuit model id linked to a physical pb_type
|
||||||
|
* 3. what is the physical pb_type for an operating pb_type
|
||||||
|
* 4. what is the mode pointer that represents the physical mode for a pb_type
|
||||||
|
*******************************************************************/
|
||||||
|
class VprPbTypeAnnotation {
|
||||||
|
public: /* Constructor */
|
||||||
|
VprPbTypeAnnotation();
|
||||||
|
private: /* Internal data */
|
||||||
|
std::map<t_pb_type*, bool> is_physical_pb_types_;
|
||||||
|
std::map<t_pb_type*, t_pb_type*> physical_pb_types_;
|
||||||
|
std::map<t_pb_type*, t_mode*> physical_pb_modes_;
|
||||||
|
std::map<t_pb_type*, CircuitModelId> pb_type_circuit_models_;
|
||||||
|
};
|
||||||
|
|
||||||
|
} /* End namespace openfpga*/
|
||||||
|
|
||||||
|
#endif
|
Loading…
Reference in New Issue