From e5956467fd9d9e60d27813604c8ab06723decfcc Mon Sep 17 00:00:00 2001 From: tangxifan Date: Thu, 10 Oct 2019 14:43:32 -0600 Subject: [PATCH] developing verilog writer for modules --- .../vpr/SRC/fpga_x2p/base/module_manager.cpp | 116 +++++++++++++++++- .../vpr/SRC/fpga_x2p/base/module_manager.h | 36 ++++++ .../verilog/verilog_module_writer.cpp | 85 +++++++++++++ .../fpga_x2p/verilog/verilog_module_writer.h | 15 +++ .../fpga_x2p/verilog/verilog_writer_utils.h | 1 + 5 files changed, 252 insertions(+), 1 deletion(-) create mode 100644 vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.cpp create mode 100644 vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.h diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.cpp b/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.cpp index 853ca2643..f7e7b1e6c 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.cpp +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.cpp @@ -2,6 +2,7 @@ * Memember functions for data structure ModuleManager ******************************************************************************/ #include +#include #include #include "vtr_assert.h" @@ -12,6 +13,49 @@ * Public Constructors ******************************************************************************/ +/************************************************** + * Public Accessors : Aggregates + *************************************************/ +/* Find all the modules */ +ModuleManager::module_range ModuleManager::modules() const { + return vtr::make_range(ids_.begin(), ids_.end()); +} + +/* Find all the nets belonging to a module */ +ModuleManager::module_net_range ModuleManager::module_nets(const ModuleId& module) const { + /* Validate the module_id */ + VTR_ASSERT(valid_module_id(module)); + return vtr::make_range(net_ids_[module].begin(), net_ids_[module].end()); +} + +/* Find all the child modules under a parent module */ +std::vector ModuleManager::child_modules(const ModuleId& parent_module) const { + /* Validate the module_id */ + VTR_ASSERT(valid_module_id(parent_module)); + return children_[parent_module]; +} + +/* Find all the instances under a parent module */ +std::vector ModuleManager::child_module_instances(const ModuleId& parent_module, const ModuleId& child_module) const { + /* Validate the module_id */ + VTR_ASSERT(valid_module_id(parent_module)); + /* Ensure that the child module is in the child list of parent module */ + size_t child_index = children_[parent_module].size(); + for (size_t i = 0; i < children_[parent_module].size(); ++i) { + if (child_module == children_[parent_module][i]) { + child_index = i; + break; + } + } + VTR_ASSERT(child_index != children_[parent_module].size()); + + /* Create a vector, with sequentially increasing numbers */ + std::vector instance_range(num_child_instances_[parent_module][child_index]); + std::iota(instance_range.begin(), instance_range.end(), 0); + + return instance_range; +} + /****************************************************************************** * Public Accessors ******************************************************************************/ @@ -20,6 +64,13 @@ size_t ModuleManager::num_modules() const { return ids_.size(); } +/* Return number of net of a module */ +size_t ModuleManager::num_nets(const ModuleId& module) const { + /* Validate the module_id */ + VTR_ASSERT(valid_module_id(module)); + return net_ids_[module].size(); +} + /* Find the name of a module */ std::string ModuleManager::module_name(const ModuleId& module_id) const { /* Validate the module_id */ @@ -120,7 +171,6 @@ std::string ModuleManager::port_preproc_flag(const ModuleId& module, const Modul return port_preproc_flags_[module][port]; } - /* Find a net from an instance of a module */ ModuleNetId ModuleManager::module_instance_port_net(const ModuleId& parent_module, const ModuleId& child_module, const size_t& child_instance, @@ -156,6 +206,70 @@ std::string ModuleManager::net_name(const ModuleId& module, const ModuleNetId& n return net_names_[module][net]; } +/* Find the source modules of a net */ +std::vector ModuleManager::net_source_modules(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_src_module_ids_[module][net]; +} + +/* Find the ids of source instances of a net */ +std::vector ModuleManager::net_source_instances(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_src_instance_ids_[module][net]; +} + +/* Find the source ports of a net */ +std::vector ModuleManager::net_source_ports(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_src_port_ids_[module][net]; +} + +/* Find the source pin indices of a net */ +std::vector ModuleManager::net_source_pins(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_src_pin_ids_[module][net]; +} + +/* Find the sink modules of a net */ +std::vector ModuleManager::net_sink_modules(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_sink_module_ids_[module][net]; +} + +/* Find the ids of sink instances of a net */ +std::vector ModuleManager::net_sink_instances(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_sink_instance_ids_[module][net]; +} + +/* Find the sink ports of a net */ +std::vector ModuleManager::net_sink_ports(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_sink_port_ids_[module][net]; +} + +/* Find the sink pin indices of a net */ +std::vector ModuleManager::net_sink_pins(const ModuleId& module, const ModuleNetId& net) const { + /* Validate module net */ + VTR_ASSERT(valid_module_net_id(module, net)); + + return net_sink_pin_ids_[module][net]; +} + /****************************************************************************** * Public Mutators ******************************************************************************/ diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.h b/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.h index 99858cd7a..5204f0de3 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.h +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/module_manager.h @@ -32,9 +32,29 @@ class ModuleManager { MODULE_CLOCK_PORT, NUM_MODULE_PORT_TYPES }; + public: /* Public Constructors */ + + public: /* Types and ranges */ + typedef vtr::vector::const_iterator module_iterator; + typedef vtr::vector::const_iterator module_net_iterator; + + typedef vtr::Range module_range; + typedef vtr::Range module_net_range; + + public: /* Public aggregators */ + /* Find all the modules */ + module_range modules() const; + /* Find all the nets belonging to a module */ + module_net_range module_nets(const ModuleId& module) const; + /* Find all the child modules under a parent module */ + std::vector child_modules(const ModuleId& parent_module) const; + /* Find all the instances under a parent module */ + std::vector child_module_instances(const ModuleId& parent_module, const ModuleId& child_module) const; + public: /* Public accessors */ size_t num_modules() const; + size_t num_nets(const ModuleId& module) const; std::string module_name(const ModuleId& module_id) const; std::string module_port_type_str(const enum e_module_port_type& port_type) const; std::vector module_ports_by_type(const ModuleId& module_id, const enum e_module_port_type& port_type) const; @@ -58,6 +78,22 @@ class ModuleManager { const ModulePortId& child_port, const size_t& child_pin) const; /* Find the name of net */ std::string net_name(const ModuleId& module, const ModuleNetId& net) const; + /* Find the source modules of a net */ + std::vector net_source_modules(const ModuleId& module, const ModuleNetId& net) const; + /* Find the ids of source instances of a net */ + std::vector net_source_instances(const ModuleId& module, const ModuleNetId& net) const; + /* Find the source ports of a net */ + std::vector net_source_ports(const ModuleId& module, const ModuleNetId& net) const; + /* Find the source pin indices of a net */ + std::vector net_source_pins(const ModuleId& module, const ModuleNetId& net) const; + /* Find the sink modules of a net */ + std::vector net_sink_modules(const ModuleId& module, const ModuleNetId& net) const; + /* Find the ids of sink instances of a net */ + std::vector net_sink_instances(const ModuleId& module, const ModuleNetId& net) const; + /* Find the sink ports of a net */ + std::vector net_sink_ports(const ModuleId& module, const ModuleNetId& net) const; + /* Find the sink pin indices of a net */ + std::vector net_sink_pins(const ModuleId& module, const ModuleNetId& net) const; public: /* Public mutators */ /* Add a module */ ModuleId add_module(const std::string& name); diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.cpp b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.cpp new file mode 100644 index 000000000..c54d73619 --- /dev/null +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.cpp @@ -0,0 +1,85 @@ +/******************************************************************** + * This file includes functions to write a Verilog module + * based on its definition in Module Manager + * + * Note that Verilog writer functions are just an outputter for the + * module definition. + * You should NOT modify any content of the module manager + * Please use const keyword to restrict this! + *******************************************************************/ +#include "vtr_assert.h" +#include "fpga_x2p_utils.h" +#include "verilog_writer_utils.h" +#include "verilog_module_writer.h" + +/******************************************************************** + * Collect all the nets that are going to be local wires + * And organize it in a vector of ports + * Verilog wire writter function will use the output of this function + * to write up local wire declaration in Verilog format + * + * Here is the strategy to identify local wires: + * Iterate over the nets inside the module. + * A net is a local wire if it connects between two instances, + * This is valid when all the sinks of the net are pins/ports of instances + *******************************************************************/ +static +std::vector find_verilog_module_local_wires(const ModuleManager& module_manager, + const ModuleId& module_id) { + std::vector local_wire_ports; + + /* Find local wires between instances */ + for (ModuleNetId module_net : module_manager.module_nets(module_id)) { + /* A flag to identify local wire */ + bool is_local_wire = false; + + /* Each net must only one 1 source */ + VTR_ASSERT(1 == module_manager.net_source_modules(module_id, module_net).size()); + + /* Check if source module is the module itself */ + if (module_id != module_manager.net_source_modules(module_id, module_net)[0]) { + is_local_wire = true; + } + + /* Check all the sink modules of the net */ + for (ModuleId sink_module : module_manager.net_sink_modules(module_id, module_net)) { + if (module_id == sink_module) { + is_local_wire = false; + } + } + + /* TODO: Push the Verilog port the list, try to combine the ports if we can */ + } + + return local_wire_ports; +} + +/******************************************************************** + * Write a Verilog module to a file + * This is a key function, maybe most frequently called in our Verilog writer + * Note that file stream must be valid + *******************************************************************/ +void writer_verilog_module_to_file(std::fstream& fp, + const ModuleManager& module_manager, + const ModuleId& module_id) { + /* Ensure a valid file stream */ + check_file_handler(fp); + + /* Ensure we have a valid module_id */ + VTR_ASSERT(module_manager.valid_module_id(module_id)); + + /* Print module declaration */ + print_verilog_module_declaration(fp, module_manager, module_id); + + /* TODO: Print internal wires */ + + /* TODO: Print instances */ + for (ModuleId child_module : module_manager.child_modules(module_id)) { + for (size_t instance : module_manager.child_module_instances(module_id, child_module)) { + /* Print an instance */ + } + } + + /* Print an end for the module */ + print_verilog_module_end(fp, module_manager.module_name(module_id)); +} diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.h b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.h new file mode 100644 index 000000000..bb7b401fb --- /dev/null +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_module_writer.h @@ -0,0 +1,15 @@ +/******************************************************************** + * Header file for verilog_module_writer.cpp + *******************************************************************/ + +#ifndef VERILOG_MODULE_WRITER_H +#define VERILOG_MODULE_WRITER_H + +#include +#include "module_manager.h" + +void writer_verilog_module_to_file(std::fstream& fp, + const ModuleManager& module_manager, + const ModuleId& module_id); + +#endif diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_writer_utils.h b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_writer_utils.h index 5e390ed02..1840f447f 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_writer_utils.h +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_writer_utils.h @@ -7,6 +7,7 @@ #define VERILOG_WRITER_UTILS_H #include +#include "verilog_global.h" #include "device_port.h" #include "module_manager.h"