diff --git a/libopenfpga/libarchopenfpga/src/circuit_library.cpp b/libopenfpga/libarchopenfpga/src/circuit_library.cpp index a94b4b8a2..f9c101aff 100644 --- a/libopenfpga/libarchopenfpga/src/circuit_library.cpp +++ b/libopenfpga/libarchopenfpga/src/circuit_library.cpp @@ -235,6 +235,24 @@ CircuitModelId CircuitLibrary::pass_gate_logic_model(const CircuitModelId& model return pgl_model_id; } +/* Find the name of pass-gate circuit model + * Two cases to be considered: + * 1. this is a pass-gate circuit model, just find the data and return + * 2. this circuit model includes a pass-gate, find the link to pass-gate circuit model and go recursively + */ +std::string CircuitLibrary::pass_gate_logic_model_name(const CircuitModelId& model_id) const { + /* validate the model_id */ + VTR_ASSERT(valid_model_id(model_id)); + + /* Return the data if this is a pass-gate circuit model */ + if (CIRCUIT_MODEL_PASSGATE == model_type(model_id)) { + return model_names_[model_id]; + } + + /* Otherwise, we need to make sure this circuit model contains a pass-gate */ + return pass_gate_logic_model_names_[model_id]; +} + /* Return the type of pass gate logic module, only applicable to circuit model whose type is pass-gate logic */ enum e_circuit_model_pass_gate_logic_type CircuitLibrary::pass_gate_logic_type(const CircuitModelId& model_id) const { /* validate the model_id */ diff --git a/libopenfpga/libarchopenfpga/src/circuit_library.h b/libopenfpga/libarchopenfpga/src/circuit_library.h index 4150ceebf..130b08c4e 100644 --- a/libopenfpga/libarchopenfpga/src/circuit_library.h +++ b/libopenfpga/libarchopenfpga/src/circuit_library.h @@ -27,6 +27,15 @@ * The class CircuitLibrary is a critical data structure for OpenFPGA * It stores all the circuit-level details from XML architecture file * + * Typical usage: + * // Create an empty circuit library + * CircuitLibrary circuit_lib; + * // call your builder for circuit library + * // Build the internal links for the circuit library + * circuit_lib.build_model_links(); + * // Build the timing graph inside the circuit library + * circuit_lib.build_timing_graphs(); + * * It includes the following data: * * ------ Fundamental Information ----- @@ -197,6 +206,7 @@ class CircuitLibrary { std::string lut_intermediate_buffer_location_map(const CircuitModelId& model_id) const; /* Pass-gate-logic information */ CircuitModelId pass_gate_logic_model(const CircuitModelId& model_id) const; + std::string pass_gate_logic_model_name(const CircuitModelId& model_id) const; enum e_circuit_model_pass_gate_logic_type pass_gate_logic_type(const CircuitModelId& model_id) const; float pass_gate_logic_pmos_size(const CircuitModelId& model_id) const; float pass_gate_logic_nmos_size(const CircuitModelId& model_id) const; diff --git a/libopenfpga/libarchopenfpga/src/read_xml_openfpga_arch.cpp b/libopenfpga/libarchopenfpga/src/read_xml_openfpga_arch.cpp index 20f701028..236dac68c 100644 --- a/libopenfpga/libarchopenfpga/src/read_xml_openfpga_arch.cpp +++ b/libopenfpga/libarchopenfpga/src/read_xml_openfpga_arch.cpp @@ -41,6 +41,12 @@ OpenFPGAArch read_xml_openfpga_arch(const char* arch_file_name) { auto xml_circuit_models = get_single_child(xml_circuit_settings, "circuit_library", loc_data); openfpga_arch.circuit_lib = read_xml_circuit_library(xml_circuit_models, loc_data); + /* Build the internal links for the circuit library */ + openfpga_arch.circuit_lib.build_model_links(); + + /* Build the timing graph inside the circuit library */ + openfpga_arch.circuit_lib.build_timing_graphs(); + } catch (pugiutil::XmlError& e) { archfpga_throw(arch_file_name, e.line(), "%s", e.what()); diff --git a/libopenfpga/libarchopenfpga/src/write_xml_circuit_library.cpp b/libopenfpga/libarchopenfpga/src/write_xml_circuit_library.cpp index 60acf66d9..a162838a4 100644 --- a/libopenfpga/libarchopenfpga/src/write_xml_circuit_library.cpp +++ b/libopenfpga/libarchopenfpga/src/write_xml_circuit_library.cpp @@ -241,13 +241,64 @@ void write_xml_circuit_model(std::fstream& fp, /* Write the design technology of circuit model */ write_xml_design_technology(fp, fname, circuit_lib, model); - /* TODO: Write the input buffer information of circuit model */ - /* TODO: Write the output buffer information of circuit model */ - /* TODO: Write the lut input buffer information of circuit model */ - /* TODO: Write the lut input inverter information of circuit model */ - /* TODO: Write the lut intermediate buffer information of circuit model */ + /* Write the input buffer information of circuit model, + * only applicable when this circuit model is neither inverter nor buffer + */ + if (CIRCUIT_MODEL_INVBUF != circuit_lib.model_type(model)) { + if (true == circuit_lib.is_input_buffered(model)) { + fp << "\t\t\t" << "" << "\n"; + } + } - /* TODO: Write the pass-gate-logic information of circuit model */ + /* Write the output buffer information of circuit model */ + if (CIRCUIT_MODEL_INVBUF != circuit_lib.model_type(model)) { + if (true == circuit_lib.is_output_buffered(model)) { + fp << "\t\t\t" << "" << "\n"; + } + } + + if (CIRCUIT_MODEL_LUT == circuit_lib.model_type(model)) { + /* Write the lut input buffer information of circuit model + * This is a mandatory attribute for LUT, so it must exist + */ + fp << "\t\t\t" << "" << "\n"; + + /* Write the lut input inverter information of circuit model + * This is a mandatory attribute for LUT, so it must exist + */ + fp << "\t\t\t" << "" << "\n"; + + /* Write the lut intermediate buffer information of circuit model */ + if (true == circuit_lib.is_lut_intermediate_buffered(model)) { + fp << "\t\t\t" << "" << "\n"; + } + } + + /* Write the pass-gate-logic information of circuit model */ + if ( (CIRCUIT_MODEL_LUT == circuit_lib.model_type(model)) + || (CIRCUIT_MODEL_MUX == circuit_lib.model_type(model)) ) { + fp << "\t\t\t" << "" << "\n"; + } /* Write the ports of circuit model */ for (const CircuitPortId& port : circuit_lib.model_ports(model)) { @@ -264,6 +315,11 @@ void write_xml_circuit_model(std::fstream& fp, /******************************************************************** * A writer to output a circuit library to XML format + * Note: + * This function should be run after that the following methods of + * CircuitLibrary are executed + * 1. build_model_links(); + * 2. build_timing_graph(); *******************************************************************/ void write_xml_circuit_library(std::fstream& fp, const char* fname, diff --git a/libopenfpga/libarchopenfpga/src/write_xml_utils.cpp b/libopenfpga/libarchopenfpga/src/write_xml_utils.cpp index b7b02b272..0c782f328 100644 --- a/libopenfpga/libarchopenfpga/src/write_xml_utils.cpp +++ b/libopenfpga/libarchopenfpga/src/write_xml_utils.cpp @@ -5,6 +5,9 @@ #include #include +/* Headers from vtrutil library */ +#include "vtr_assert.h" + /* Headers from openfpgautil library */ #include "openfpga_digest.h" @@ -22,3 +25,23 @@ void write_xml_attribute(std::fstream& fp, fp << " " << attr << "=\"" << value << "\""; } + +/******************************************************************** + * A most utilized function to write an XML attribute to file + * This accepts the value as a boolean + *******************************************************************/ +void write_xml_attribute(std::fstream& fp, + const char* attr, + const bool& value) { + /* Validate the file stream */ + openfpga::valid_file_stream(fp); + + fp << " " << attr << "=\""; + if (true == value) { + fp << "true"; + } else { + VTR_ASSERT_SAFE(false == value); + fp << "false"; + } + fp << "\""; +} diff --git a/libopenfpga/libarchopenfpga/src/write_xml_utils.h b/libopenfpga/libarchopenfpga/src/write_xml_utils.h index cafea189d..adb90262a 100644 --- a/libopenfpga/libarchopenfpga/src/write_xml_utils.h +++ b/libopenfpga/libarchopenfpga/src/write_xml_utils.h @@ -14,4 +14,8 @@ void write_xml_attribute(std::fstream& fp, const char* attr, const char* value); +void write_xml_attribute(std::fstream& fp, + const char* attr, + const bool& value); + #endif diff --git a/libopenfpga/libarchopenfpga/test/main.cpp b/libopenfpga/libarchopenfpga/test/main.cpp index 624d9669f..4280f84e4 100644 --- a/libopenfpga/libarchopenfpga/test/main.cpp +++ b/libopenfpga/libarchopenfpga/test/main.cpp @@ -20,7 +20,7 @@ int main(int argc, const char** argv) { VTR_LOG("Parsed %lu circuit models from XML into circuit library.\n", openfpga_arch.circuit_lib.num_models()); - /* Check the circuit library */ + /* TODO: Check the circuit library */ /* Output the circuit library to an XML file * This is optional only used when there is a second argument