diff --git a/vpr7_x2p/libarchfpga/SRC/include/ReadLine.h b/vpr7_x2p/libarchfpga/SRC/ReadLine.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/ReadLine.h rename to vpr7_x2p/libarchfpga/SRC/ReadLine.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/arch_types.h b/vpr7_x2p/libarchfpga/SRC/arch_types.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/arch_types.h rename to vpr7_x2p/libarchfpga/SRC/arch_types.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/arch_types_mrfpga.h b/vpr7_x2p/libarchfpga/SRC/arch_types_mrfpga.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/arch_types_mrfpga.h rename to vpr7_x2p/libarchfpga/SRC/arch_types_mrfpga.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/cad_types.h b/vpr7_x2p/libarchfpga/SRC/cad_types.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/cad_types.h rename to vpr7_x2p/libarchfpga/SRC/cad_types.h diff --git a/vpr7_x2p/libarchfpga/SRC/check_circuit_library.cpp b/vpr7_x2p/libarchfpga/SRC/check_circuit_library.cpp new file mode 100644 index 000000000..0b0f8fa69 --- /dev/null +++ b/vpr7_x2p/libarchfpga/SRC/check_circuit_library.cpp @@ -0,0 +1,467 @@ +/********************************************************** + * MIT License + * + * Copyright (c) 2018 LNIS - The University of Utah + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + ***********************************************************************/ + +/************************************************************************ + * Filename: check_circuit_library.cpp + * Created by: Xifan Tang + * Change history: + * +-------------------------------------+ + * | Date | Author | Notes + * +-------------------------------------+ + * | 2019/08/12 | Xifan Tang | Created + * +-------------------------------------+ + ***********************************************************************/ + +/************************************************************************ + * Function to perform fundamental checking for the circuit library + * such as + * 1. if default circuit models are defined + * 2. if any circuit models shared the same name or prefix + * 3. if nay circuit model miss mandatory ports + ***********************************************************************/ + +/* Header files should be included in a sequence */ +/* Standard header files required go first */ +#include "vtr_assert.h" + +#include "util.h" + +#include "check_circuit_library.h" + + +/************************************************************************ + * Circuit models have unique names, return the number of errors + * If not found, we give an error + ***********************************************************************/ +static +size_t check_circuit_library_unique_names(const CircuitLibrary& circuit_lib) { + size_t num_err = 0; + + for (size_t i = 0; i < circuit_lib.num_circuit_models(); ++i) { + /* Skip for the last element, because the inner loop will access it */ + if (i == circuit_lib.num_circuit_models() - 1) { + continue; + } + /* Get the name of reference */ + const std::string& i_name = circuit_lib.circuit_model_name(CircuitModelId(i)); + for (size_t j = i + 1; j < circuit_lib.num_circuit_models(); ++j) { + /* Compare the name of candidate */ + const std::string& j_name = circuit_lib.circuit_model_name(CircuitModelId(j)); + /* Compare the name and skip for different names */ + if (0 != i_name.compare(j_name)) { + continue; + } + vpr_printf(TIO_MESSAGE_ERROR, + "Circuit model(index=%d) and (index=%d) share the same name, which is invalid!\n", + i , j, i_name.c_str()); + /* Incremental the counter for errors */ + num_err++; + } + } + + return num_err; +} + + +/************************************************************************ + * Circuit models have unique names, return the number of errors + * If not found, we give an error + ***********************************************************************/ +static +size_t check_circuit_library_unique_prefix(const CircuitLibrary& circuit_lib) { + size_t num_err = 0; + + for (size_t i = 0; i < circuit_lib.num_circuit_models(); ++i) { + /* Skip for the last element, because the inner loop will access it */ + if (i == circuit_lib.num_circuit_models() - 1) { + continue; + } + /* Get the name of reference */ + const std::string& i_prefix = circuit_lib.circuit_model_prefix(CircuitModelId(i)); + for (size_t j = i + 1; j < circuit_lib.num_circuit_models(); ++j) { + /* Compare the name of candidate */ + const std::string& j_prefix = circuit_lib.circuit_model_prefix(CircuitModelId(j)); + /* Compare the name and skip for different prefix */ + if (0 != i_prefix.compare(j_prefix)) { + continue; + } + vpr_printf(TIO_MESSAGE_ERROR, + "Circuit model(name=%s) and (name=%s) share the same prefix, which is invalid!\n", + circuit_lib.circuit_model_name(CircuitModelId(i)).c_str(), + circuit_lib.circuit_model_name(CircuitModelId(j)).c_str(), + i_prefix.c_str()); + /* Incremental the counter for errors */ + num_err++; + } + } + + return num_err; +} + +/************************************************************************ + * A generic function to check the port list of a circuit model in a given type + * If not found, we give an error + ***********************************************************************/ +static +size_t check_circuit_model_required(const CircuitLibrary& circuit_lib, + const enum e_spice_model_type& circuit_model_type_to_check) { + size_t num_err = 0; + + /* We must have an IOPAD*/ + if ( 0 == circuit_lib.circuit_models_by_type(circuit_model_type_to_check).size()) { + vpr_printf(TIO_MESSAGE_ERROR, + "At least one %s circuit model is required!\n", + CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_model_type_to_check)]); + /* Incremental the counter for errors */ + num_err++; + } + + return num_err; +} + +/************************************************************************ + * A generic function to check the port list of a circuit model in a given type + * If not found, we give an error + ***********************************************************************/ +size_t check_one_circuit_model_port_required(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const std::vector& port_types_to_check) { + size_t num_err = 0; + + for (const auto& port_type: port_types_to_check) { + if (0 == circuit_lib.ports_by_type(circuit_model, port_type).size()) { + vpr_printf(TIO_MESSAGE_ERROR, + "%s circuit model(name=%s) does not have %s port\n", + CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_lib.circuit_model_type(circuit_model))], + circuit_lib.circuit_model_name(circuit_model).c_str(), + CIRCUIT_MODEL_PORT_TYPE_STRING[size_t(port_type)]); + /* Incremental the counter for errors */ + num_err++; + } + } + + return num_err; +} + +/************************************************************************ + * A generic function to check the port size of a given circuit model + * if the port size does not match, we give an error + ***********************************************************************/ +size_t check_one_circuit_model_port_size_required(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const CircuitPortId& circuit_port, + const size_t& port_size_to_check) { + + size_t num_err = 0; + + if (port_size_to_check != circuit_lib.port_size(circuit_model, circuit_port)) { + vpr_printf(TIO_MESSAGE_ERROR, + "Port of circuit model(name=%s) does not have a port(type=%s) of size=%d.\n", + circuit_lib.circuit_model_name(circuit_model).c_str(), + CIRCUIT_MODEL_PORT_TYPE_STRING[size_t(circuit_lib.port_type(circuit_model, circuit_port))], + port_size_to_check); + /* Incremental the counter for errors */ + num_err++; + } + + return num_err; +} + +/************************************************************************ + * A generic function to check the port size of a given circuit model + * if the number of ports in the given type does not match, we give an error + * for each port, if the port size does not match, we give an error + ***********************************************************************/ +size_t check_one_circuit_model_port_type_and_size_required(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const enum e_spice_model_port_type& port_type_to_check, + const size_t& num_ports_to_check, + const size_t& port_size_to_check, + const bool& include_global_ports) { + + size_t num_err = 0; + + std::vector ports = circuit_lib.ports_by_type(circuit_model, port_type_to_check, include_global_ports); + if (num_ports_to_check != ports.size()) { + vpr_printf(TIO_MESSAGE_ERROR, + "Expect %d %s ports for a %s circuit model, but only have %d %s ports!\n", + num_ports_to_check, + CIRCUIT_MODEL_PORT_TYPE_STRING[size_t(port_type_to_check)], + CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_lib.circuit_model_type(circuit_model))], + CIRCUIT_MODEL_PORT_TYPE_STRING[size_t(port_type_to_check)], + ports.size()); + num_err++; + } + for (const auto& port : ports) { + num_err += check_one_circuit_model_port_size_required(circuit_lib, + circuit_model, + port, port_size_to_check); + } + + return num_err; +} + +/************************************************************************ + * A generic function to check the port list of circuit models in a given type + * If not found, we give an error + ***********************************************************************/ +static +size_t check_circuit_model_port_required(const CircuitLibrary& circuit_lib, + const enum e_spice_model_type& circuit_model_type_to_check, + const std::vector& port_types_to_check) { + size_t num_err = 0; + + for (const auto& id : circuit_lib.circuit_models_by_type(circuit_model_type_to_check)) { + num_err += check_one_circuit_model_port_required(circuit_lib, id, port_types_to_check); + } + + return num_err; +} + +/************************************************************************ + * A generic function to find the default circuit model with a given type + * If not found, we give an error + ***********************************************************************/ +static +size_t check_required_default_circuit_model(const CircuitLibrary& circuit_lib, + const enum e_spice_model_type& circuit_model_type) { + size_t num_err = 0; + + if (CIRCUIT_MODEL_OPEN_ID == circuit_lib.default_circuit_model(circuit_model_type)) { + vpr_printf(TIO_MESSAGE_ERROR, + "A default circuit model for the type %s! Try to define it in your architecture file!\n", + CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_model_type)]); + exit(1); + } + + return num_err; +} + +/************************************************************************ + * A function to check the port map of FF circuit model + ***********************************************************************/ +size_t check_ff_circuit_model_ports(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model) { + size_t num_err = 0; + + /* Check the type of circuit model */ + VTR_ASSERT(SPICE_MODEL_FF == circuit_lib.circuit_model_type(circuit_model)); + /* Check if we have D, Set and Reset */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_INPUT, + 3, 1, false); + /* Check if we have a clock */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_CLOCK, + 1, 1, false); + + + /* Check if we have output */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_OUTPUT, + 1, 1, false); + + return num_err; +} + +/************************************************************************ + * A function to check the port map of SCFF circuit model + ***********************************************************************/ +size_t check_scff_circuit_model_ports(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model) { + size_t num_err = 0; + + /* Check the type of circuit model */ + VTR_ASSERT(SPICE_MODEL_SCFF == circuit_lib.circuit_model_type(circuit_model)); + + /* Check if we have D, Set and Reset */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_INPUT, + 1, 1, false); + /* Check if we have a clock */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_CLOCK, + 1, 1, true); + + + /* Check if we have output */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_OUTPUT, + 2, 1, false); + + return num_err; +} + +/************************************************************************ + * A function to check the port map of SRAM circuit model + ***********************************************************************/ +size_t check_sram_circuit_model_ports(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const bool& check_blwl) { + size_t num_err = 0; + + /* Check the type of circuit model */ + VTR_ASSERT(SPICE_MODEL_SRAM == circuit_lib.circuit_model_type(circuit_model)); + + /* Check if we has 1 output with size 2 */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_OUTPUT, + 1, 2, false); + /* basic check finished here */ + if (false == check_blwl) { + return num_err; + } + + /* If bl and wl are required, check their existence */ + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_BL, + 1, 1, false); + + num_err += check_one_circuit_model_port_type_and_size_required(circuit_lib, circuit_model, + SPICE_MODEL_PORT_WL, + 1, 1, false); + + return num_err; +} + + +/************************************************************************ + * Check points to make sure we have a valid circuit library + * Detailed checkpoints: + * 1. Circuit models have unique names + * 2. Circuit models have unique prefix + * 3. Check IOPADs have input and output ports + * 4. Check MUXes has been defined and has input and output ports + * 5. We must have at least one SRAM or SCFF + * 6. SRAM must have at least an input and an output ports + * 7. SCFF must have at least a clock, an input and an output ports + * 8. FF must have at least a clock, an input and an output ports + * 9. LUT must have at least an input, an output and a SRAM ports + * 10. We must have default circuit models for these types: MUX, channel wires and wires + ***********************************************************************/ +void check_circuit_library(const CircuitLibrary& circuit_lib) { + size_t num_err = 0; + + vpr_printf(TIO_MESSAGE_INFO, "Checking circuit models...\n"); + + /* 1. Circuit models have unique names + * For each circuit model, we always make sure it does not share any name with any circuit model locating after it + */ + num_err += check_circuit_library_unique_names(circuit_lib); + + /* 2. Circuit models have unique prefix + * For each circuit model, we always make sure it does not share any prefix with any circuit model locating after it + */ + num_err += check_circuit_library_unique_prefix(circuit_lib); + + /* 3. Check io has been defined and has input and output ports + * [a] We must have an IOPAD! + * [b] For each IOPAD, we must have at least an input, an output, an INOUT and an SRAM port + */ + num_err += check_circuit_model_required(circuit_lib, SPICE_MODEL_IOPAD); + + std::vector iopad_port_types_required; + iopad_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); + iopad_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); + iopad_port_types_required.push_back(SPICE_MODEL_PORT_INOUT); + iopad_port_types_required.push_back(SPICE_MODEL_PORT_SRAM); + + num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_IOPAD, iopad_port_types_required); + + /* 4. Check mux has been defined and has input and output ports + * [a] We must have a MUX! + * [b] For each MUX, we must have at least an input, an output, and an SRAM port + */ + num_err += check_circuit_model_required(circuit_lib, SPICE_MODEL_MUX); + + std::vector mux_port_types_required; + mux_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); + mux_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); + mux_port_types_required.push_back(SPICE_MODEL_PORT_SRAM); + + num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_MUX, mux_port_types_required); + + /* 5. We must have at least one SRAM or SCFF */ + if ( ( 0 == circuit_lib.circuit_models_by_type(SPICE_MODEL_SRAM).size()) + && ( 0 == circuit_lib.circuit_models_by_type(SPICE_MODEL_SCFF).size()) ) { + vpr_printf(TIO_MESSAGE_ERROR, + "At least one %s or %s circuit model is required!\n", + CIRCUIT_MODEL_TYPE_STRING[size_t(SPICE_MODEL_SRAM)], + CIRCUIT_MODEL_TYPE_STRING[size_t(SPICE_MODEL_SCFF)]); + /* Incremental the counter for errors */ + num_err++; + } + + /* 6. SRAM must have at least an input and an output ports*/ + std::vector sram_port_types_required; + sram_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); + sram_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); + + num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_SRAM, sram_port_types_required); + + /* 7. SCFF must have at least a clock, an input and an output ports*/ + std::vector scff_port_types_required; + scff_port_types_required.push_back(SPICE_MODEL_PORT_CLOCK); + scff_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); + scff_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); + + num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_SCFF, scff_port_types_required); + + /* 8. FF must have at least a clock, an input and an output ports*/ + std::vector ff_port_types_required; + ff_port_types_required.push_back(SPICE_MODEL_PORT_CLOCK); + ff_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); + ff_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); + + num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_FF, ff_port_types_required); + + /* 9. LUT must have at least an input, an output and a SRAM ports*/ + std::vector lut_port_types_required; + lut_port_types_required.push_back(SPICE_MODEL_PORT_SRAM); + lut_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); + lut_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); + + num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_LUT, lut_port_types_required); + + /* 10. We must have default circuit models for these types: MUX, channel wires and wires */ + num_err += check_required_default_circuit_model(circuit_lib, SPICE_MODEL_MUX); + num_err += check_required_default_circuit_model(circuit_lib, SPICE_MODEL_CHAN_WIRE); + num_err += check_required_default_circuit_model(circuit_lib, SPICE_MODEL_WIRE); + + /* If we have any errors, exit */ + vpr_printf(TIO_MESSAGE_INFO, + "Finished checking circuit library with %d errors!\n", + num_err); + + if (0 < num_err) { + exit(1); + } + + return; +} + +/************************************************************************ + * End of file : check_circuit_library.cpp + ***********************************************************************/ + diff --git a/vpr7_x2p/libarchfpga/SRC/check_circuit_library.h b/vpr7_x2p/libarchfpga/SRC/check_circuit_library.h new file mode 100644 index 000000000..f70133697 --- /dev/null +++ b/vpr7_x2p/libarchfpga/SRC/check_circuit_library.h @@ -0,0 +1,86 @@ +/********************************************************** + * MIT License + * + * Copyright (c) 2018 LNIS - The University of Utah + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + ***********************************************************************/ + +/************************************************************************ + * Filename: check_circuit_library.h + * Created by: Xifan Tang + * Change history: + * +-------------------------------------+ + * | Date | Author | Notes + * +-------------------------------------+ + * | 2019/08/12 | Xifan Tang | Created + * +-------------------------------------+ + ***********************************************************************/ + +/* IMPORTANT: + * The following preprocessing flags are added to + * avoid compilation error when this headers are included in more than 1 times + */ +#ifndef CHECK_CIRCUIT_LIBRARY_H +#define CHECK_CIRCUIT_LIBRARY_H + +/* + * Notes in include header files in a head file + * Only include the neccessary header files + * that is required by the data types in the function/class declarations! + */ +/* Header files should be included in a sequence */ +/* Standard header files required go first */ +#include "circuit_library.h" + +/* Check points to make sure we have a valid circuit library */ +size_t check_one_circuit_model_port_required(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const std::vector& port_types_to_check); + +size_t check_one_circuit_model_port_size_required(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const CircuitPortId& circuit_port, + const size_t& port_size_to_check); + +size_t check_one_circuit_model_port_type_and_size_required(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const enum e_spice_model_port_type& port_type_to_check, + const size_t& num_ports_to_check, + const size_t& port_size_to_check, + const bool& include_global_ports); + +size_t check_ff_circuit_model_ports(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model); + +size_t check_scff_circuit_model_ports(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model); + +size_t check_sram_circuit_model_ports(const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const bool& check_blwl); + +void check_circuit_library(const CircuitLibrary& circuit_lib); + +#endif + +/************************************************************************ + * End of file : check_circuit_library.h + ***********************************************************************/ + diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_library.cpp b/vpr7_x2p/libarchfpga/SRC/circuit_library.cpp similarity index 83% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_library.cpp rename to vpr7_x2p/libarchfpga/SRC/circuit_library.cpp index e8487bdff..4da76e417 100644 --- a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_library.cpp +++ b/vpr7_x2p/libarchfpga/SRC/circuit_library.cpp @@ -48,6 +48,9 @@ /************************************************************************ * Constructors ***********************************************************************/ +CircuitLibrary::CircuitLibrary() { + return; +} /************************************************************************ * Public Accessors : aggregates @@ -88,6 +91,29 @@ std::vector CircuitLibrary::ports_by_type(const CircuitModelId& c return port_ids; } +/* Find the ports of a circuit model by a given type, return a list of qualified ports + * with an option to include/exclude global ports + */ +std::vector CircuitLibrary::ports_by_type(const CircuitModelId& circuit_model_id, + const enum e_spice_model_port_type& type, + const bool& include_global_port) const { + std::vector port_ids; + for (const auto& port_id : ports(circuit_model_id)) { + /* We skip unmatched ports */ + if ( type != port_type(circuit_model_id, port_id) ) { + continue; + } + /* We skip global ports if specified */ + if ( (false == include_global_port) + && (true == port_is_global(circuit_model_id, port_id)) ) { + continue; + } + port_ids.push_back(port_id); + } + return port_ids; +} + + /* Create a vector for all the ports whose directionality is input * This includes all the ports other than whose types are OUPUT or INOUT */ @@ -140,96 +166,106 @@ size_t CircuitLibrary::num_circuit_models() const { /* Access the type of a circuit model */ enum e_spice_model_type CircuitLibrary::circuit_model_type(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return circuit_model_types_[circuit_model_id]; } /* Access the name of a circuit model */ std::string CircuitLibrary::circuit_model_name(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return circuit_model_names_[circuit_model_id]; } /* Access the prefix of a circuit model */ std::string CircuitLibrary::circuit_model_prefix(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return circuit_model_prefix_[circuit_model_id]; } /* Access the path + file of user-defined verilog netlist of a circuit model */ std::string CircuitLibrary::circuit_model_verilog_netlist(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return circuit_model_verilog_netlists_[circuit_model_id]; } /* Access the path + file of user-defined spice netlist of a circuit model */ std::string CircuitLibrary::circuit_model_spice_netlist(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return circuit_model_spice_netlists_[circuit_model_id]; } /* Access the is_default flag (check if this is the default circuit model in the type) of a circuit model */ bool CircuitLibrary::circuit_model_is_default(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return circuit_model_is_default_[circuit_model_id]; } /* Access the dump_structural_verilog flag of a circuit model */ bool CircuitLibrary::dump_structural_verilog(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return dump_structural_verilog_[circuit_model_id]; } /* Access the dump_explicit_port_map flag of a circuit model */ bool CircuitLibrary::dump_explicit_port_map(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return dump_explicit_port_map_[circuit_model_id]; } /* Access the design technology type of a circuit model */ enum e_spice_model_design_tech CircuitLibrary::design_tech_type(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return design_tech_types_[circuit_model_id]; } /* Access the is_power_gated flag of a circuit model */ bool CircuitLibrary::is_power_gated(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return is_power_gated_[circuit_model_id]; } /* Return a flag showing if inputs are buffered for a circuit model */ bool CircuitLibrary::is_input_buffered(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return buffer_existence_[circuit_model_id][INPUT]; } /* Return a flag showing if outputs are buffered for a circuit model */ bool CircuitLibrary::is_output_buffered(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return buffer_existence_[circuit_model_id][OUTPUT]; } /* Return a flag showing if intermediate stages of a LUT are buffered for a circuit model */ bool CircuitLibrary::is_lut_intermediate_buffered(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate the circuit model type is LUT */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); return buffer_existence_[circuit_model_id][LUT_INTER_BUFFER]; } +/* Return the multiplex structure of a circuit model */ +enum e_spice_model_structure CircuitLibrary::mux_structure(const CircuitModelId& circuit_model_id) const { + /* validate the circuit_model_id */ + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + /* validate the circuit model type is MUX */ + VTR_ASSERT( (SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)) ); + return mux_structure_[circuit_model_id]; +} + /************************************************************************ * Public Accessors : Basic data query on Circuit Porst ***********************************************************************/ @@ -237,7 +273,7 @@ bool CircuitLibrary::is_lut_intermediate_buffered(const CircuitModelId& circuit_ /* identify if this port is an input port */ bool CircuitLibrary::is_input_port(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_model_id and circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); /* Only SPICE_MODEL_OUTPUT AND INOUT are considered as outputs */ return ( (SPICE_MODEL_PORT_OUTPUT != port_type(circuit_model_id, circuit_port_id)) && (SPICE_MODEL_PORT_INOUT != port_type(circuit_model_id, circuit_port_id)) ); @@ -246,7 +282,7 @@ bool CircuitLibrary::is_input_port(const CircuitModelId& circuit_model_id, const /* identify if this port is an output port */ bool CircuitLibrary::is_output_port(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_model_id and circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); /* Only SPICE_MODEL_OUTPUT AND INOUT are considered as outputs */ return ( (SPICE_MODEL_PORT_OUTPUT == port_type(circuit_model_id, circuit_port_id)) || (SPICE_MODEL_PORT_INOUT == port_type(circuit_model_id, circuit_port_id)) ); @@ -255,7 +291,7 @@ bool CircuitLibrary::is_output_port(const CircuitModelId& circuit_model_id, cons /* Given a name and return the port id */ CircuitPortId CircuitLibrary::port(const CircuitModelId& circuit_model_id, const std::string& name) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Walk through the ports and try to find a matched name */ CircuitPortId ret = CIRCUIT_PORT_OPEN_ID; size_t num_found = 0; @@ -267,22 +303,34 @@ CircuitPortId CircuitLibrary::port(const CircuitModelId& circuit_model_id, const num_found++; } /* Make sure we will not find two ports with the same name */ - VTR_ASSERT_SAFE( (0 == num_found) || (1 == num_found) ); + VTR_ASSERT( (0 == num_found) || (1 == num_found) ); return ret; } /* Access the type of a port of a circuit model */ size_t CircuitLibrary::num_ports(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return port_ids_[circuit_model_id].size(); } +/* Access the type of a port of a circuit model + * with an option to include/exclude global ports + * when counting + */ +size_t CircuitLibrary::num_ports_by_type(const CircuitModelId& circuit_model_id, + const enum e_spice_model_port_type& port_type, + const bool& include_global_port) const { + /* validate the circuit_model_id */ + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + return ports_by_type(circuit_model_id, port_type, include_global_port).size(); +} + /* Access the type of a port of a circuit model */ enum e_spice_model_port_type CircuitLibrary::port_type(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_types_[circuit_model_id][circuit_port_id]; } @@ -290,7 +338,7 @@ enum e_spice_model_port_type CircuitLibrary::port_type(const CircuitModelId& cir size_t CircuitLibrary::port_size(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_sizes_[circuit_model_id][circuit_port_id]; } @@ -298,7 +346,7 @@ size_t CircuitLibrary::port_size(const CircuitModelId& circuit_model_id, std::string CircuitLibrary::port_prefix(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_prefix_[circuit_model_id][circuit_port_id]; } @@ -306,7 +354,7 @@ std::string CircuitLibrary::port_prefix(const CircuitModelId& circuit_model_id, std::string CircuitLibrary::port_lib_name(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_lib_names_[circuit_model_id][circuit_port_id]; } @@ -314,7 +362,7 @@ std::string CircuitLibrary::port_lib_name(const CircuitModelId& circuit_model_id std::string CircuitLibrary::port_inv_prefix(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_inv_prefix_[circuit_model_id][circuit_port_id]; } @@ -322,7 +370,7 @@ std::string CircuitLibrary::port_inv_prefix(const CircuitModelId& circuit_model_ size_t CircuitLibrary::port_default_value(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_default_values_[circuit_model_id][circuit_port_id]; } @@ -331,7 +379,7 @@ size_t CircuitLibrary::port_default_value(const CircuitModelId& circuit_model_id bool CircuitLibrary::port_is_mode_select(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_is_mode_select_[circuit_model_id][circuit_port_id]; } @@ -339,7 +387,7 @@ bool CircuitLibrary::port_is_mode_select(const CircuitModelId& circuit_model_id, bool CircuitLibrary::port_is_global(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_is_global_[circuit_model_id][circuit_port_id]; } @@ -347,7 +395,7 @@ bool CircuitLibrary::port_is_global(const CircuitModelId& circuit_model_id, bool CircuitLibrary::port_is_reset(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_is_reset_[circuit_model_id][circuit_port_id]; } @@ -355,7 +403,7 @@ bool CircuitLibrary::port_is_reset(const CircuitModelId& circuit_model_id, bool CircuitLibrary::port_is_set(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_is_set_[circuit_model_id][circuit_port_id]; } @@ -363,7 +411,7 @@ bool CircuitLibrary::port_is_set(const CircuitModelId& circuit_model_id, bool CircuitLibrary::port_is_config_enable(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_is_config_enable_[circuit_model_id][circuit_port_id]; } @@ -371,7 +419,7 @@ bool CircuitLibrary::port_is_config_enable(const CircuitModelId& circuit_model_i bool CircuitLibrary::port_is_prog(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return port_is_prog_[circuit_model_id][circuit_port_id]; } @@ -379,6 +427,12 @@ bool CircuitLibrary::port_is_prog(const CircuitModelId& circuit_model_id, /************************************************************************ * Public Accessors : Methods to find circuit model ***********************************************************************/ +/* Find a circuit model by a given name and return its id */ +CircuitModelId CircuitLibrary::circuit_model(const char* name) const { + std::string name_str(name); + return circuit_model(name_str); +} + /* Find a circuit model by a given name and return its id */ CircuitModelId CircuitLibrary::circuit_model(const std::string& name) const { CircuitModelId ret = CIRCUIT_MODEL_OPEN_ID; @@ -403,7 +457,9 @@ CircuitModelId CircuitLibrary::circuit_model(const std::string& name) const { /* Get the CircuitModelId of a default circuit model with a given type */ CircuitModelId CircuitLibrary::default_circuit_model(const enum e_spice_model_type& type) const { /* Default circuit model id is the first element by type in the fast look-up */ - return circuit_model_lookup_[size_t(type)].front(); + CircuitModelId default_id = circuit_model_lookup_[size_t(type)].front(); + VTR_ASSERT(true == circuit_model_is_default(default_id)); + return default_id; } /************************************************************************ @@ -414,8 +470,8 @@ CircuitEdgeId CircuitLibrary::edge(const CircuitModelId& circuit_model_id, const CircuitPortId& from_port, const size_t from_pin, const CircuitPortId& to_port, const size_t to_pin) { /* validate the circuit_pin_id */ - VTR_ASSERT_SAFE(valid_circuit_pin_id(circuit_model_id, from_port, from_pin)); - VTR_ASSERT_SAFE(valid_circuit_pin_id(circuit_model_id, to_port, to_pin)); + VTR_ASSERT(valid_circuit_pin_id(circuit_model_id, from_port, from_pin)); + VTR_ASSERT(valid_circuit_pin_id(circuit_model_id, to_port, to_pin)); /* Walk through the edge list until we find the one */ for (auto edge : edge_ids_[circuit_model_id]) { if ( (from_port == edge_src_port_ids_[circuit_model_id][edge]) @@ -551,7 +607,7 @@ CircuitModelId CircuitLibrary::add_circuit_model() { void CircuitLibrary::set_circuit_model_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_type& type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_types_[circuit_model_id] = type; /* Build the fast look-up for circuit models */ build_circuit_model_lookup(); @@ -561,7 +617,7 @@ void CircuitLibrary::set_circuit_model_type(const CircuitModelId& circuit_model_ /* Set the name of a Circuit Model */ void CircuitLibrary::set_circuit_model_name(const CircuitModelId& circuit_model_id, const std::string& name) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_names_[circuit_model_id] = name; return; } @@ -569,7 +625,7 @@ void CircuitLibrary::set_circuit_model_name(const CircuitModelId& circuit_model_ /* Set the prefix of a Circuit Model */ void CircuitLibrary::set_circuit_model_prefix(const CircuitModelId& circuit_model_id, const std::string& prefix) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_prefix_[circuit_model_id] = prefix; return; } @@ -577,7 +633,7 @@ void CircuitLibrary::set_circuit_model_prefix(const CircuitModelId& circuit_mode /* Set the verilog_netlist of a Circuit Model */ void CircuitLibrary::set_circuit_model_verilog_netlist(const CircuitModelId& circuit_model_id, const std::string& verilog_netlist) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_verilog_netlists_[circuit_model_id] = verilog_netlist; return; } @@ -585,7 +641,7 @@ void CircuitLibrary::set_circuit_model_verilog_netlist(const CircuitModelId& cir /* Set the spice_netlist of a Circuit Model */ void CircuitLibrary::set_circuit_model_spice_netlist(const CircuitModelId& circuit_model_id, const std::string& spice_netlist) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_spice_netlists_[circuit_model_id] = spice_netlist; return; } @@ -593,7 +649,7 @@ void CircuitLibrary::set_circuit_model_spice_netlist(const CircuitModelId& circu /* Set the is_default of a Circuit Model */ void CircuitLibrary::set_circuit_model_is_default(const CircuitModelId& circuit_model_id, const bool& is_default) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_is_default_[circuit_model_id] = is_default; return; } @@ -601,7 +657,7 @@ void CircuitLibrary::set_circuit_model_is_default(const CircuitModelId& circuit_ /* Set the dump_structural_verilog of a Circuit Model */ void CircuitLibrary::set_circuit_model_dump_structural_verilog(const CircuitModelId& circuit_model_id, const bool& dump_structural_verilog) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); dump_structural_verilog_[circuit_model_id] = dump_structural_verilog; return; } @@ -609,7 +665,7 @@ void CircuitLibrary::set_circuit_model_dump_structural_verilog(const CircuitMode /* Set the dump_explicit_port_map of a Circuit Model */ void CircuitLibrary::set_circuit_model_dump_explicit_port_map(const CircuitModelId& circuit_model_id, const bool& dump_explicit_port_map) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); dump_explicit_port_map_[circuit_model_id] = dump_explicit_port_map; return; } @@ -617,7 +673,7 @@ void CircuitLibrary::set_circuit_model_dump_explicit_port_map(const CircuitModel /* Set the type of design technology of a Circuit Model */ void CircuitLibrary::set_circuit_model_design_tech_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_design_tech& design_tech_type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); design_tech_types_[circuit_model_id] = design_tech_type; return; } @@ -625,7 +681,7 @@ void CircuitLibrary::set_circuit_model_design_tech_type(const CircuitModelId& ci /* Set the power-gated flag of a Circuit Model */ void CircuitLibrary::set_circuit_model_is_power_gated(const CircuitModelId& circuit_model_id, const bool& is_power_gated) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); is_power_gated_[circuit_model_id] = is_power_gated; return; } @@ -650,9 +706,9 @@ void CircuitLibrary::set_circuit_model_output_buffer(const CircuitModelId& circu void CircuitLibrary::set_circuit_model_lut_input_buffer(const CircuitModelId& circuit_model_id, const bool& existence, const std::string& circuit_model_name) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Make sure the circuit model is a LUT! */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_types_[circuit_model_id]); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_types_[circuit_model_id]); /* Just call the base function and give the proper type */ set_circuit_model_buffer(circuit_model_id, LUT_INPUT_BUFFER, existence, circuit_model_name); return; @@ -662,9 +718,9 @@ void CircuitLibrary::set_circuit_model_lut_input_buffer(const CircuitModelId& ci void CircuitLibrary::set_circuit_model_lut_input_inverter(const CircuitModelId& circuit_model_id, const bool& existence, const std::string& circuit_model_name) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Make sure the circuit model is a LUT! */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_types_[circuit_model_id]); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_types_[circuit_model_id]); /* Just call the base function and give the proper type */ set_circuit_model_buffer(circuit_model_id, LUT_INPUT_INVERTER, existence, circuit_model_name); return; @@ -674,9 +730,9 @@ void CircuitLibrary::set_circuit_model_lut_input_inverter(const CircuitModelId& void CircuitLibrary::set_circuit_model_lut_intermediate_buffer(const CircuitModelId& circuit_model_id, const bool& existence, const std::string& circuit_model_name) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Make sure the circuit model is a LUT! */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_types_[circuit_model_id]); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_types_[circuit_model_id]); /* Just call the base function and give the proper type */ set_circuit_model_buffer(circuit_model_id, LUT_INTER_BUFFER, existence, circuit_model_name); return; @@ -685,7 +741,7 @@ void CircuitLibrary::set_circuit_model_lut_intermediate_buffer(const CircuitMode void CircuitLibrary::set_circuit_model_lut_intermediate_buffer_location_map(const CircuitModelId& circuit_model_id, const std::string& location_map) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); buffer_location_maps_[circuit_model_id][LUT_INTER_BUFFER] = location_map; return; } @@ -694,7 +750,7 @@ void CircuitLibrary::set_circuit_model_lut_intermediate_buffer_location_map(cons /* Set pass-gate logic information of a circuit model */ void CircuitLibrary::set_circuit_model_pass_gate_logic(const CircuitModelId& circuit_model_id, const std::string& circuit_model_name) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); pass_gate_logic_circuit_model_names_[circuit_model_id] = circuit_model_name; return; } @@ -702,7 +758,7 @@ void CircuitLibrary::set_circuit_model_pass_gate_logic(const CircuitModelId& cir /* Add a port to a circuit model */ CircuitPortId CircuitLibrary::add_circuit_model_port(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Create a port id */ CircuitPortId circuit_port_id = CircuitPortId(port_ids_[circuit_model_id].size()); /* Update the id list */ @@ -742,7 +798,7 @@ void CircuitLibrary::set_port_type(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const enum e_spice_model_port_type& port_type) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_types_[circuit_model_id][circuit_port_id] = port_type; /* Build the fast look-up for circuit model ports */ build_circuit_model_port_lookup(circuit_model_id); @@ -754,7 +810,7 @@ void CircuitLibrary::set_port_size(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const size_t& port_size) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_sizes_[circuit_model_id][circuit_port_id] = port_size; return; } @@ -764,7 +820,7 @@ void CircuitLibrary::set_port_prefix(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const std::string& port_prefix) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_prefix_[circuit_model_id][circuit_port_id] = port_prefix; return; } @@ -774,7 +830,7 @@ void CircuitLibrary::set_port_lib_name(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const std::string& lib_name) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_lib_names_[circuit_model_id][circuit_port_id] = lib_name; return; } @@ -784,7 +840,7 @@ void CircuitLibrary::set_port_inv_prefix(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const std::string& inv_prefix) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_inv_prefix_[circuit_model_id][circuit_port_id] = inv_prefix; return; } @@ -794,7 +850,7 @@ void CircuitLibrary::set_port_default_value(const CircuitModelId& circuit_model_ const CircuitPortId& circuit_port_id, const size_t& default_value) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_default_values_[circuit_model_id][circuit_port_id] = default_value; return; } @@ -804,7 +860,7 @@ void CircuitLibrary::set_port_is_mode_select(const CircuitModelId& circuit_model const CircuitPortId& circuit_port_id, const bool& is_mode_select) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_is_mode_select_[circuit_model_id][circuit_port_id] = is_mode_select; return; } @@ -814,7 +870,7 @@ void CircuitLibrary::set_port_is_global(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const bool& is_global) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_is_global_[circuit_model_id][circuit_port_id] = is_global; return; } @@ -824,7 +880,7 @@ void CircuitLibrary::set_port_is_reset(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const bool& is_reset) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_is_reset_[circuit_model_id][circuit_port_id] = is_reset; return; } @@ -834,7 +890,7 @@ void CircuitLibrary::set_port_is_set(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const bool& is_set) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_is_set_[circuit_model_id][circuit_port_id] = is_set; return; } @@ -844,7 +900,7 @@ void CircuitLibrary::set_port_is_config_enable(const CircuitModelId& circuit_mod const CircuitPortId& circuit_port_id, const bool& is_config_enable) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_is_config_enable_[circuit_model_id][circuit_port_id] = is_config_enable; return; } @@ -854,7 +910,7 @@ void CircuitLibrary::set_port_is_prog(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const bool& is_prog) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_is_prog_[circuit_model_id][circuit_port_id] = is_prog; return; } @@ -864,7 +920,7 @@ void CircuitLibrary::set_port_circuit_model_name(const CircuitModelId& circuit_m const CircuitPortId& circuit_port_id, const std::string& circuit_model_name) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_circuit_model_names_[circuit_model_id][circuit_port_id] = circuit_model_name; return; } @@ -874,7 +930,7 @@ void CircuitLibrary::set_port_circuit_model_id(const CircuitModelId& circuit_mod const CircuitPortId& circuit_port_id, const CircuitModelId& port_circuit_model_id) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_circuit_model_ids_[circuit_model_id][circuit_port_id] = port_circuit_model_id; return; } @@ -884,7 +940,7 @@ void CircuitLibrary::set_port_inv_circuit_model_name(const CircuitModelId& circu const CircuitPortId& circuit_port_id, const std::string& inv_circuit_model_name) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_inv_circuit_model_names_[circuit_model_id][circuit_port_id] = inv_circuit_model_name; return; } @@ -894,7 +950,7 @@ void CircuitLibrary::set_port_inv_circuit_model_id(const CircuitModelId& circuit const CircuitPortId& circuit_port_id, const CircuitModelId& inv_circuit_model_id) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_inv_circuit_model_ids_[circuit_model_id][circuit_port_id] = inv_circuit_model_id; return; } @@ -904,7 +960,7 @@ void CircuitLibrary::set_port_tri_state_map(const CircuitModelId& circuit_model_ const CircuitPortId& circuit_port_id, const std::string& tri_state_map) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); port_tri_state_maps_[circuit_model_id][circuit_port_id] = tri_state_map; return; } @@ -914,9 +970,9 @@ void CircuitLibrary::set_port_lut_frac_level(const CircuitModelId& circuit_model const CircuitPortId& circuit_port_id, const size_t& lut_frac_level) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); /* Make sure this is a LUT */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); port_lut_frac_level_[circuit_model_id][circuit_port_id] = lut_frac_level; return; } @@ -926,9 +982,9 @@ void CircuitLibrary::set_port_lut_output_mask(const CircuitModelId& circuit_mode const CircuitPortId& circuit_port_id, const std::vector& lut_output_masks) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); /* Make sure this is a LUT */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); port_lut_output_masks_[circuit_model_id][circuit_port_id] = lut_output_masks; return; } @@ -938,9 +994,9 @@ void CircuitLibrary::set_port_sram_orgz(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const enum e_sram_orgz& sram_orgz) { /* validate the circuit_port_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); /* Make sure this is a SRAM port */ - VTR_ASSERT_SAFE(SPICE_MODEL_PORT_SRAM == port_type(circuit_model_id, circuit_port_id)); + VTR_ASSERT(SPICE_MODEL_PORT_SRAM == port_type(circuit_model_id, circuit_port_id)); port_sram_orgz_[circuit_model_id][circuit_port_id] = sram_orgz; return; } @@ -954,7 +1010,7 @@ void CircuitLibrary::set_port_sram_orgz(const CircuitModelId& circuit_model_id, void CircuitLibrary::add_delay_info(const CircuitModelId& circuit_model_id, const enum spice_model_delay_type& delay_type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Check the range of vector */ if (size_t(delay_type) >= delay_types_[circuit_model_id].size()) { /* Resize */ @@ -971,9 +1027,9 @@ void CircuitLibrary::set_delay_in_port_names(const CircuitModelId& circuit_model const enum spice_model_delay_type& delay_type, const std::string& in_port_names) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Validate delay_type */ - VTR_ASSERT_SAFE(valid_delay_type(circuit_model_id, delay_type)); + VTR_ASSERT(valid_delay_type(circuit_model_id, delay_type)); delay_in_port_names_[circuit_model_id][size_t(delay_type)] = in_port_names; return; } @@ -982,9 +1038,9 @@ void CircuitLibrary::set_delay_out_port_names(const CircuitModelId& circuit_mode const enum spice_model_delay_type& delay_type, const std::string& out_port_names) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Validate delay_type */ - VTR_ASSERT_SAFE(valid_delay_type(circuit_model_id, delay_type)); + VTR_ASSERT(valid_delay_type(circuit_model_id, delay_type)); delay_out_port_names_[circuit_model_id][size_t(delay_type)] = out_port_names; return; } @@ -993,9 +1049,9 @@ void CircuitLibrary::set_delay_values(const CircuitModelId& circuit_model_id, const enum spice_model_delay_type& delay_type, const std::string& delay_values) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Validate delay_type */ - VTR_ASSERT_SAFE(valid_delay_type(circuit_model_id, delay_type)); + VTR_ASSERT(valid_delay_type(circuit_model_id, delay_type)); delay_values_[circuit_model_id][size_t(delay_type)] = delay_values; return; } @@ -1004,9 +1060,9 @@ void CircuitLibrary::set_delay_values(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_buffer_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_buffer_type& buffer_type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); buffer_types_[circuit_model_id] = buffer_type; return; } @@ -1014,9 +1070,9 @@ void CircuitLibrary::set_buffer_type(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_buffer_size(const CircuitModelId& circuit_model_id, const float& buffer_size) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); buffer_sizes_[circuit_model_id] = buffer_size; return; } @@ -1024,9 +1080,9 @@ void CircuitLibrary::set_buffer_size(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_buffer_num_levels(const CircuitModelId& circuit_model_id, const size_t& num_levels) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); buffer_num_levels_[circuit_model_id] = num_levels; return; } @@ -1034,9 +1090,9 @@ void CircuitLibrary::set_buffer_num_levels(const CircuitModelId& circuit_model_i void CircuitLibrary::set_buffer_f_per_stage(const CircuitModelId& circuit_model_id, const size_t& f_per_stage) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_INVBUF == circuit_model_type(circuit_model_id)); buffer_f_per_stage_[circuit_model_id] = f_per_stage; return; } @@ -1045,9 +1101,9 @@ void CircuitLibrary::set_buffer_f_per_stage(const CircuitModelId& circuit_model_ void CircuitLibrary::set_pass_gate_logic_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_pass_gate_logic_type& pass_gate_logic_type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_PASSGATE == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_PASSGATE == circuit_model_type(circuit_model_id)); pass_gate_logic_types_[circuit_model_id] = pass_gate_logic_type; return; } @@ -1055,9 +1111,9 @@ void CircuitLibrary::set_pass_gate_logic_type(const CircuitModelId& circuit_mode void CircuitLibrary::set_pass_gate_logic_nmos_size(const CircuitModelId& circuit_model_id, const float& nmos_size) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_PASSGATE == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_PASSGATE == circuit_model_type(circuit_model_id)); pass_gate_logic_sizes_[circuit_model_id].set_x(nmos_size); return; } @@ -1065,9 +1121,9 @@ void CircuitLibrary::set_pass_gate_logic_nmos_size(const CircuitModelId& circuit void CircuitLibrary::set_pass_gate_logic_pmos_size(const CircuitModelId& circuit_model_id, const float& pmos_size) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be BUFFER or INVERTER */ - VTR_ASSERT_SAFE(SPICE_MODEL_PASSGATE == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_PASSGATE == circuit_model_type(circuit_model_id)); pass_gate_logic_sizes_[circuit_model_id].set_y(pmos_size); return; } @@ -1076,9 +1132,10 @@ void CircuitLibrary::set_pass_gate_logic_pmos_size(const CircuitModelId& circuit void CircuitLibrary::set_mux_structure(const CircuitModelId& circuit_model_id, const enum e_spice_model_structure& mux_structure) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); - /* validate that the type of this circuit_model should be MUX */ - VTR_ASSERT_SAFE(SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + /* validate that the type of this circuit_model should be MUX or LUT */ + VTR_ASSERT( (SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)) ); mux_structure_[circuit_model_id] = mux_structure; return; } @@ -1086,9 +1143,10 @@ void CircuitLibrary::set_mux_structure(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_mux_num_levels(const CircuitModelId& circuit_model_id, const size_t& num_levels) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); - /* validate that the type of this circuit_model should be MUX */ - VTR_ASSERT_SAFE(SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + /* validate that the type of this circuit_model should be MUX or LUT */ + VTR_ASSERT( (SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)) ); mux_num_levels_[circuit_model_id] = num_levels; return; } @@ -1096,9 +1154,10 @@ void CircuitLibrary::set_mux_num_levels(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_mux_const_input_value(const CircuitModelId& circuit_model_id, const size_t& const_input_value) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); - /* validate that the type of this circuit_model should be MUX */ - VTR_ASSERT_SAFE(SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + /* validate that the type of this circuit_model should be MUX or LUT */ + VTR_ASSERT( (SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)) ); mux_const_input_values_[circuit_model_id] = const_input_value; return; } @@ -1106,9 +1165,10 @@ void CircuitLibrary::set_mux_const_input_value(const CircuitModelId& circuit_mod void CircuitLibrary::set_mux_use_local_encoder(const CircuitModelId& circuit_model_id, const bool& use_local_encoder) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); - /* validate that the type of this circuit_model should be MUX */ - VTR_ASSERT_SAFE(SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + /* validate that the type of this circuit_model should be MUX or LUT */ + VTR_ASSERT( (SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)) ); mux_use_local_encoder_[circuit_model_id] = use_local_encoder; return; } @@ -1116,9 +1176,10 @@ void CircuitLibrary::set_mux_use_local_encoder(const CircuitModelId& circuit_mod void CircuitLibrary::set_mux_use_advanced_rram_design(const CircuitModelId& circuit_model_id, const bool& use_advanced_rram_design) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); - /* validate that the type of this circuit_model should be MUX */ - VTR_ASSERT_SAFE(SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); + /* validate that the type of this circuit_model should be MUX or LUT */ + VTR_ASSERT( (SPICE_MODEL_MUX == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)) ); mux_use_advanced_rram_design_[circuit_model_id] = use_advanced_rram_design; return; } @@ -1127,9 +1188,9 @@ void CircuitLibrary::set_mux_use_advanced_rram_design(const CircuitModelId& circ void CircuitLibrary::set_lut_is_fracturable(const CircuitModelId& circuit_model_id, const bool& is_fracturable) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be LUT */ - VTR_ASSERT_SAFE(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_LUT == circuit_model_type(circuit_model_id)); lut_is_fracturable_[circuit_model_id] = is_fracturable; return; } @@ -1138,9 +1199,9 @@ void CircuitLibrary::set_lut_is_fracturable(const CircuitModelId& circuit_model_ void CircuitLibrary::set_gate_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_gate_type& gate_type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be GATE */ - VTR_ASSERT_SAFE(SPICE_MODEL_GATE == circuit_model_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_GATE == circuit_model_type(circuit_model_id)); gate_types_[circuit_model_id] = gate_type; return; } @@ -1150,9 +1211,9 @@ void CircuitLibrary::set_gate_type(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_rram_rlrs(const CircuitModelId& circuit_model_id, const float& rlrs) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the design_tech of this circuit_model should be RRAM */ - VTR_ASSERT_SAFE(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); rram_res_[circuit_model_id].set_x(rlrs); return; } @@ -1160,9 +1221,9 @@ void CircuitLibrary::set_rram_rlrs(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_rram_rhrs(const CircuitModelId& circuit_model_id, const float& rhrs) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the design_tech of this circuit_model should be RRAM */ - VTR_ASSERT_SAFE(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); rram_res_[circuit_model_id].set_y(rhrs); return; } @@ -1170,9 +1231,9 @@ void CircuitLibrary::set_rram_rhrs(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_rram_wprog_set_nmos(const CircuitModelId& circuit_model_id, const float& wprog_set_nmos) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the design_tech of this circuit_model should be RRAM */ - VTR_ASSERT_SAFE(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); wprog_set_[circuit_model_id].set_x(wprog_set_nmos); return; } @@ -1180,9 +1241,9 @@ void CircuitLibrary::set_rram_wprog_set_nmos(const CircuitModelId& circuit_model void CircuitLibrary::set_rram_wprog_set_pmos(const CircuitModelId& circuit_model_id, const float& wprog_set_pmos) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the design_tech of this circuit_model should be RRAM */ - VTR_ASSERT_SAFE(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); wprog_set_[circuit_model_id].set_y(wprog_set_pmos); return; } @@ -1190,9 +1251,9 @@ void CircuitLibrary::set_rram_wprog_set_pmos(const CircuitModelId& circuit_model void CircuitLibrary::set_rram_wprog_reset_nmos(const CircuitModelId& circuit_model_id, const float& wprog_reset_nmos) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the design_tech of this circuit_model should be RRAM */ - VTR_ASSERT_SAFE(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); wprog_reset_[circuit_model_id].set_x(wprog_reset_nmos); return; } @@ -1200,9 +1261,9 @@ void CircuitLibrary::set_rram_wprog_reset_nmos(const CircuitModelId& circuit_mod void CircuitLibrary::set_rram_wprog_reset_pmos(const CircuitModelId& circuit_model_id, const float& wprog_reset_pmos) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the design_tech of this circuit_model should be RRAM */ - VTR_ASSERT_SAFE(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); + VTR_ASSERT(SPICE_MODEL_DESIGN_RRAM == design_tech_type(circuit_model_id)); wprog_reset_[circuit_model_id].set_y(wprog_reset_pmos); return; } @@ -1211,10 +1272,10 @@ void CircuitLibrary::set_rram_wprog_reset_pmos(const CircuitModelId& circuit_mod void CircuitLibrary::set_wire_type(const CircuitModelId& circuit_model_id, const enum e_wire_model_type& wire_type) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be WIRE or CHAN_WIRE */ - VTR_ASSERT_SAFE( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) - || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); + VTR_ASSERT( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); wire_types_[circuit_model_id] = wire_type; return; } @@ -1222,10 +1283,10 @@ void CircuitLibrary::set_wire_type(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_wire_r(const CircuitModelId& circuit_model_id, const float& r_val) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be WIRE or CHAN_WIRE */ - VTR_ASSERT_SAFE( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) - || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); + VTR_ASSERT( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); wire_rc_[circuit_model_id].set_x(r_val); return; } @@ -1233,10 +1294,10 @@ void CircuitLibrary::set_wire_r(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_wire_c(const CircuitModelId& circuit_model_id, const float& c_val) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be WIRE or CHAN_WIRE */ - VTR_ASSERT_SAFE( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) - || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); + VTR_ASSERT( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); wire_rc_[circuit_model_id].set_y(c_val); return; } @@ -1244,10 +1305,10 @@ void CircuitLibrary::set_wire_c(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_wire_num_levels(const CircuitModelId& circuit_model_id, const size_t& num_level) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* validate that the type of this circuit_model should be WIRE or CHAN_WIRE */ - VTR_ASSERT_SAFE( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) - || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); + VTR_ASSERT( (SPICE_MODEL_WIRE == circuit_model_type(circuit_model_id)) + || (SPICE_MODEL_CHAN_WIRE == circuit_model_type(circuit_model_id)) ); wire_num_levels_[circuit_model_id] = num_level; return; } @@ -1263,7 +1324,7 @@ void CircuitLibrary::set_wire_num_levels(const CircuitModelId& circuit_model_id, void CircuitLibrary::set_circuit_model_buffer(const CircuitModelId& circuit_model_id, const enum e_buffer_type buffer_type, const bool& existence, const std::string& circuit_model_name) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Check the range of vector */ if (size_t(buffer_type) >= buffer_existence_[circuit_model_id].size()) { /* Resize and assign values */ @@ -1285,7 +1346,7 @@ void CircuitLibrary::set_circuit_model_buffer(const CircuitModelId& circuit_mode */ void CircuitLibrary::link_port_circuit_model(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Walk through each ports, get the port id and find the circuit model id by name */ for (auto& port_id : ports(circuit_model_id)) { /* Bypass empty name */ @@ -1303,7 +1364,7 @@ void CircuitLibrary::link_port_circuit_model(const CircuitModelId& circuit_model */ void CircuitLibrary::link_port_inv_circuit_model(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Walk through each ports, get the port id and find the circuit model id by name */ for (auto& port_id : ports(circuit_model_id)) { /* Bypass empty name */ @@ -1328,7 +1389,7 @@ void CircuitLibrary::link_port_circuit_models(const CircuitModelId& circuit_mode */ void CircuitLibrary::link_buffer_circuit_model(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Get the circuit model id by name, skip those with empty names*/ for (size_t buffer_id = 0; buffer_id < buffer_circuit_model_names_[circuit_model_id].size(); ++buffer_id) { if (true == buffer_circuit_model_names_[circuit_model_id][buffer_id].empty()) { @@ -1345,7 +1406,7 @@ void CircuitLibrary::link_buffer_circuit_model(const CircuitModelId& circuit_mod */ void CircuitLibrary::link_pass_gate_logic_circuit_model(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Get the circuit model id by name, skip those with empty names*/ if (true == pass_gate_logic_circuit_model_names_[circuit_model_id].empty()) { return; @@ -1412,7 +1473,7 @@ void CircuitLibrary::add_edge(const CircuitModelId& circuit_model_id, const CircuitPortId& from_port, const size_t& from_pin, const CircuitPortId& to_port, const size_t& to_pin) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Create an edge in the edge id list */ CircuitEdgeId edge_id = CircuitEdgeId(edge_ids_[circuit_model_id].size()); @@ -1455,8 +1516,8 @@ void CircuitLibrary::set_edge_delay(const CircuitModelId& circuit_model_id, const enum spice_model_delay_type& delay_type, const float& delay_value) { /* validate the circuit_edge_id */ - VTR_ASSERT_SAFE(valid_circuit_edge_id(circuit_model_id, circuit_edge_id)); - VTR_ASSERT_SAFE(valid_delay_type(circuit_model_id, delay_type)); + VTR_ASSERT(valid_circuit_edge_id(circuit_model_id, circuit_edge_id)); + VTR_ASSERT(valid_delay_type(circuit_model_id, delay_type)); edge_timing_info_[circuit_model_id][circuit_edge_id][size_t(delay_type)] = delay_value; return; @@ -1465,7 +1526,7 @@ void CircuitLibrary::set_edge_delay(const CircuitModelId& circuit_model_id, /* Annotate delay values on a timing graph */ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); /* Go one delay_info by another */ for (const auto& delay_type : delay_types_[circuit_model_id]) { /* Parse the input port names and output names. @@ -1484,7 +1545,7 @@ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model /* Try to find a port by the given name */ CircuitPortId port_id = port(circuit_model_id, port_info.get_name()); /* We must have a valid port and Port width must be 1! */ - VTR_ASSERT_SAFE(CIRCUIT_PORT_OPEN_ID != port_id); + VTR_ASSERT(CIRCUIT_PORT_OPEN_ID != port_id); if (0 == port_info.get_width()) { /* we need to configure the port width if it is zero. * This means that parser find some compact port defintion such as @@ -1492,12 +1553,12 @@ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model size_t port_width = port_size(circuit_model_id, port_id); port_info.set_width(port_width); } else { - VTR_ASSERT_SAFE(1 == port_info.get_width()); + VTR_ASSERT(1 == port_info.get_width()); } /* The pin id should be valid! */ - VTR_ASSERT_SAFE(true == valid_circuit_pin_id(circuit_model_id, port_id, port_info.get_lsb())); + VTR_ASSERT(true == valid_circuit_pin_id(circuit_model_id, port_id, port_info.get_lsb())); /* This must be an input port! */ - VTR_ASSERT_SAFE(true == is_input_port(circuit_model_id, port_id)); + VTR_ASSERT(true == is_input_port(circuit_model_id, port_id)); /* Push to */ input_port_ids.push_back(port_id); input_pin_ids.push_back(port_info.get_lsb()); @@ -1513,7 +1574,7 @@ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model /* Try to find a port by the given name */ CircuitPortId port_id = port(circuit_model_id, port_info.get_name()); /* We must have a valid port and Port width must be 1! */ - VTR_ASSERT_SAFE(CIRCUIT_PORT_OPEN_ID != port_id); + VTR_ASSERT(CIRCUIT_PORT_OPEN_ID != port_id); if (0 == port_info.get_width()) { /* we need to configure the port width if it is zero. * This means that parser find some compact port defintion such as @@ -1521,12 +1582,12 @@ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model size_t port_width = port_size(circuit_model_id, port_id); port_info.set_width(port_width); } else { - VTR_ASSERT_SAFE(1 == port_info.get_width()); + VTR_ASSERT(1 == port_info.get_width()); } /* The pin id should be valid! */ - VTR_ASSERT_SAFE(true == valid_circuit_pin_id(circuit_model_id, port_id, port_info.get_lsb())); + VTR_ASSERT(true == valid_circuit_pin_id(circuit_model_id, port_id, port_info.get_lsb())); /* This must be an output port! */ - VTR_ASSERT_SAFE(true == is_output_port(circuit_model_id, port_id)); + VTR_ASSERT(true == is_output_port(circuit_model_id, port_id)); /* Push to */ output_port_ids.push_back(port_id); output_pin_ids.push_back(port_info.get_lsb()); @@ -1536,10 +1597,10 @@ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model PortDelayParser port_delay_parser(delay_values_[circuit_model_id][size_t(delay_type)]); /* Make sure the delay matrix size matches */ - VTR_ASSERT_SAFE(port_delay_parser.height() == output_port_ids.size()); - VTR_ASSERT_SAFE(port_delay_parser.height() == output_pin_ids.size()); - VTR_ASSERT_SAFE(port_delay_parser.width() == input_port_ids.size()); - VTR_ASSERT_SAFE(port_delay_parser.width() == input_pin_ids.size()); + VTR_ASSERT(port_delay_parser.height() == output_port_ids.size()); + VTR_ASSERT(port_delay_parser.height() == output_pin_ids.size()); + VTR_ASSERT(port_delay_parser.width() == input_port_ids.size()); + VTR_ASSERT(port_delay_parser.width() == input_pin_ids.size()); /* Configure timing graph */ for (size_t i = 0; i < port_delay_parser.height(); ++i) { @@ -1549,7 +1610,7 @@ void CircuitLibrary::set_timing_graph_delays(const CircuitModelId& circuit_model input_port_ids[j], input_pin_ids[j], output_port_ids[i], output_pin_ids[i]); /* make sure we have an valid edge_id */ - VTR_ASSERT_SAFE(true == valid_circuit_edge_id(circuit_model_id, edge_id)); + VTR_ASSERT(true == valid_circuit_edge_id(circuit_model_id, edge_id)); set_edge_delay(circuit_model_id, edge_id, delay_type, delay_value); } @@ -1617,25 +1678,25 @@ bool CircuitLibrary::valid_circuit_model_id(const CircuitModelId& circuit_model_ bool CircuitLibrary::valid_circuit_port_id(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return ( size_t(circuit_port_id) < port_ids_[circuit_model_id].size() ) && ( circuit_port_id == port_ids_[circuit_model_id][circuit_port_id] ); } bool CircuitLibrary::valid_circuit_pin_id(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id, const size_t& pin_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_port_id(circuit_model_id, circuit_port_id)); + VTR_ASSERT(valid_circuit_port_id(circuit_model_id, circuit_port_id)); return ( size_t(pin_id) < port_size(circuit_model_id, circuit_port_id) ); } bool CircuitLibrary::valid_delay_type(const CircuitModelId& circuit_model_id, const enum spice_model_delay_type& delay_type) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return ( size_t(delay_type) < delay_types_[circuit_model_id].size() ) && ( delay_type == delay_types_[circuit_model_id][size_t(delay_type)] ); } bool CircuitLibrary::valid_circuit_edge_id(const CircuitModelId& circuit_model_id, const CircuitEdgeId& circuit_edge_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); return ( size_t(circuit_edge_id) < edge_ids_[circuit_model_id].size() ) && ( circuit_edge_id == edge_ids_[circuit_model_id][circuit_edge_id] ); } @@ -1649,7 +1710,7 @@ void CircuitLibrary::invalidate_circuit_model_lookup() const { /* Empty fast lookup for circuit ports for a circuit_model */ void CircuitLibrary::invalidate_circuit_model_port_lookup(const CircuitModelId& circuit_model_id) const { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); circuit_model_port_lookup_[size_t(circuit_model_id)].clear(); return; } @@ -1657,7 +1718,7 @@ void CircuitLibrary::invalidate_circuit_model_port_lookup(const CircuitModelId& /* Clear all the data structure related to the timing graph */ void CircuitLibrary::invalidate_circuit_model_timing_graph(const CircuitModelId& circuit_model_id) { /* validate the circuit_model_id */ - VTR_ASSERT_SAFE(valid_circuit_model_id(circuit_model_id)); + VTR_ASSERT(valid_circuit_model_id(circuit_model_id)); edge_ids_[circuit_model_id].clear(); for (const auto& port_id : ports(circuit_model_id)) { diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_library.h b/vpr7_x2p/libarchfpga/SRC/circuit_library.h similarity index 98% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_library.h rename to vpr7_x2p/libarchfpga/SRC/circuit_library.h index b655730d0..1717bb60f 100644 --- a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_library.h +++ b/vpr7_x2p/libarchfpga/SRC/circuit_library.h @@ -216,11 +216,13 @@ class CircuitLibrary { INPUT = 0, OUTPUT, LUT_INPUT_BUFFER, LUT_INPUT_INVERTER, LUT_INTER_BUFFER, NUM_BUFFER_TYPE /* Last one is a counter */ }; public: /* Constructors */ + CircuitLibrary(); public: /* Accessors: aggregates */ circuit_model_range circuit_models() const; circuit_port_range ports(const CircuitModelId& circuit_model_id) const; std::vector circuit_models_by_type(const enum e_spice_model_type& type) const; std::vector ports_by_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_port_type& port_type) const; + std::vector ports_by_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_port_type& port_type, const bool& include_global_port) const; std::vector input_ports(const CircuitModelId& circuit_model_id) const; std::vector output_ports(const CircuitModelId& circuit_model_id) const; std::vector pins(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; @@ -239,11 +241,13 @@ class CircuitLibrary { bool is_input_buffered(const CircuitModelId& circuit_model_id) const; bool is_output_buffered(const CircuitModelId& circuit_model_id) const; bool is_lut_intermediate_buffered(const CircuitModelId& circuit_model_id) const; + enum e_spice_model_structure mux_structure(const CircuitModelId& circuit_model_id) const; public: /* Public Accessors: Basic data query on Circuit Ports*/ bool is_input_port(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; bool is_output_port(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; CircuitPortId port(const CircuitModelId& circuit_model_id, const std::string& name) const; size_t num_ports(const CircuitModelId& circuit_model_id) const; + size_t num_ports_by_type(const CircuitModelId& circuit_model_id, const enum e_spice_model_port_type& port_type, const bool& include_global_port) const; enum e_spice_model_port_type port_type(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; size_t port_size(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; std::string port_prefix(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; @@ -257,6 +261,7 @@ class CircuitLibrary { bool port_is_config_enable(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; bool port_is_prog(const CircuitModelId& circuit_model_id, const CircuitPortId& circuit_port_id) const; public: /* Public Accessors: Methods to find circuit model */ + CircuitModelId circuit_model(const char* name) const; CircuitModelId circuit_model(const std::string& name) const; CircuitModelId default_circuit_model(const enum e_spice_model_type& type) const; public: /* Public Accessors: Timing graph */ diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_types.h b/vpr7_x2p/libarchfpga/SRC/circuit_types.h similarity index 92% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_types.h rename to vpr7_x2p/libarchfpga/SRC/circuit_types.h index 0ad9790dd..a2b86f38f 100644 --- a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/circuit_types.h +++ b/vpr7_x2p/libarchfpga/SRC/circuit_types.h @@ -89,6 +89,8 @@ enum e_spice_model_structure { SPICE_MODEL_STRUCTURE_CROSSBAR, NUM_CIRCUIT_MODEL_STRUCTURE_TYPES }; +/* Strings correspond to each type of mux structure */ +constexpr std::array CIRCUIT_MODEL_STRUCTURE_TYPE_STRING = {{"TREE-LIKE", "ONE-LEVEL", "MULTI-LEVEL", "CROSSBAR"}}; enum e_spice_model_buffer_type { SPICE_MODEL_BUF_INV, @@ -112,7 +114,7 @@ enum e_spice_model_gate_type { enum e_wire_model_type { WIRE_MODEL_PIE, WIRE_MODEL_T, - NUM_WIRE_MODEL_TYPES, + NUM_WIRE_MODEL_TYPES }; enum e_spice_model_port_type { @@ -138,6 +140,7 @@ enum e_sram_orgz { SPICE_SRAM_LOCAL_ENCODER, /* SRAMs are organized and accessed by a local encoder */ NUM_CIRCUIT_MODEL_SRAM_ORGZ_TYPES }; +constexpr std::array CIRCUIT_MODEL_SRAM_ORGZ_TYPE_STRING = {{"STANDALONE", "SCAN-CHAIN", "MEMORY_BANK", "LOCAL_ENCODER"}}; #endif diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/device_port.cpp b/vpr7_x2p/libarchfpga/SRC/device_port.cpp similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/device_port.cpp rename to vpr7_x2p/libarchfpga/SRC/device_port.cpp diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/device_port.h b/vpr7_x2p/libarchfpga/SRC/device_port.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/device_port.h rename to vpr7_x2p/libarchfpga/SRC/device_port.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/ezxml.h b/vpr7_x2p/libarchfpga/SRC/ezxml.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/ezxml.h rename to vpr7_x2p/libarchfpga/SRC/ezxml.h diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/check_circuit_library.cpp b/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/check_circuit_library.cpp deleted file mode 100644 index f136dba4c..000000000 --- a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/check_circuit_library.cpp +++ /dev/null @@ -1,254 +0,0 @@ -/********************************************************** - * MIT License - * - * Copyright (c) 2018 LNIS - The University of Utah - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - ***********************************************************************/ - -/************************************************************************ - * Filename: check_circuit_library.cpp - * Created by: Xifan Tang - * Change history: - * +-------------------------------------+ - * | Date | Author | Notes - * +-------------------------------------+ - * | 2019/08/12 | Xifan Tang | Created - * +-------------------------------------+ - ***********************************************************************/ - -/* Header files should be included in a sequence */ -/* Standard header files required go first */ -#include "util.h" -#include "check_circuit_library.h" - - -/* 1. Circuit models have unique names, return the number of errors */ -static -size_t check_circuit_library_unique_names(const CircuitLibrary& circuit_lib) { - size_t num_err = 0; - - for (size_t i = 0; i < circuit_lib.num_circuit_models(); ++i) { - /* Skip for the last element, because the inner loop will access it */ - if (i == circuit_lib.num_circuit_models() - 1) { - continue; - } - /* Get the name of reference */ - const std::string& i_name = circuit_lib.circuit_model_name(CircuitModelId(i)); - for (size_t j = i + 1; j < circuit_lib.num_circuit_models(); ++j) { - /* Compare the name of candidate */ - const std::string& j_name = circuit_lib.circuit_model_name(CircuitModelId(j)); - /* Compare the name and skip for different names */ - if (0 != i_name.compare(j_name)) { - continue; - } - vpr_printf(TIO_MESSAGE_ERROR, - "Circuit model(index=%d) and (index=%d) share the same name, which is invalid!\n", - i , j, i_name.c_str()); - /* Incremental the counter for errors */ - num_err++; - } - } - - return num_err; -} - - -/* 1. Circuit models have unique names, return the number of errors */ -static -size_t check_circuit_library_unique_prefix(const CircuitLibrary& circuit_lib) { - size_t num_err = 0; - - for (size_t i = 0; i < circuit_lib.num_circuit_models(); ++i) { - /* Skip for the last element, because the inner loop will access it */ - if (i == circuit_lib.num_circuit_models() - 1) { - continue; - } - /* Get the name of reference */ - const std::string& i_prefix = circuit_lib.circuit_model_prefix(CircuitModelId(i)); - for (size_t j = i + 1; j < circuit_lib.num_circuit_models(); ++j) { - /* Compare the name of candidate */ - const std::string& j_prefix = circuit_lib.circuit_model_prefix(CircuitModelId(j)); - /* Compare the name and skip for different prefix */ - if (0 != i_prefix.compare(j_prefix)) { - continue; - } - vpr_printf(TIO_MESSAGE_ERROR, - "Circuit model(name=%s) and (name=%s) share the same prefix, which is invalid!\n", - circuit_lib.circuit_model_name(CircuitModelId(i)).c_str(), - circuit_lib.circuit_model_name(CircuitModelId(j)).c_str(), - i_prefix.c_str()); - /* Incremental the counter for errors */ - num_err++; - } - } - - return num_err; -} - -/* A generic function to check the port list of a circuit model in a given type */ -static -size_t check_circuit_model_required(const CircuitLibrary& circuit_lib, - const enum e_spice_model_type& circuit_model_type_to_check) { - size_t num_err = 0; - - /* We must have an IOPAD*/ - if ( 0 == circuit_lib.circuit_models_by_type(circuit_model_type_to_check).size()) { - vpr_printf(TIO_MESSAGE_ERROR, - "At least one %s circuit model is required!\n", - CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_model_type_to_check)]); - /* Incremental the counter for errors */ - num_err++; - } - - return num_err; -} - -/* A generic function to check the port list of a circuit model in a given type */ -static -size_t check_circuit_model_port_required(const CircuitLibrary& circuit_lib, - const enum e_spice_model_type& circuit_model_type_to_check, - const std::vector& port_types_to_check) { - size_t num_err = 0; - - for (const auto& id : circuit_lib.circuit_models_by_type(circuit_model_type_to_check)) { - for (const auto& port_type: port_types_to_check) { - if (0 == circuit_lib.ports_by_type(id, port_type).size()) { - vpr_printf(TIO_MESSAGE_ERROR, - "%s circuit model(name=%s) does not have %s port\n", - CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_model_type_to_check)], - circuit_lib.circuit_model_name(id).c_str(), - CIRCUIT_MODEL_PORT_TYPE_STRING[size_t(port_type)]); - /* Incremental the counter for errors */ - num_err++; - } - } - } - - return num_err; -} - -/************************************************************************ - * Check points to make sure we have a valid circuit library - * Detailed checkpoints: - * 1. Circuit models have unique names - * 2. Circuit models have unique prefix - * 3. Check IOPADs have input and output ports - * 4. Check MUXes has been defined and has input and output ports - ***********************************************************************/ -void check_circuit_library(const CircuitLibrary& circuit_lib) { - size_t num_err = 0; - - vpr_printf(TIO_MESSAGE_INFO, "Checking circuit models...\n"); - - /* 1. Circuit models have unique names - * For each circuit model, we always make sure it does not share any name with any circuit model locating after it - */ - num_err += check_circuit_library_unique_names(circuit_lib); - - /* 2. Circuit models have unique prefix - * For each circuit model, we always make sure it does not share any prefix with any circuit model locating after it - */ - num_err += check_circuit_library_unique_prefix(circuit_lib); - - /* 3. Check io has been defined and has input and output ports - * [a] We must have an IOPAD! - * [b] For each IOPAD, we must have at least an input, an output, an INOUT and an SRAM port - */ - num_err += check_circuit_model_required(circuit_lib, SPICE_MODEL_IOPAD); - - std::vector iopad_port_types_required; - iopad_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); - iopad_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); - iopad_port_types_required.push_back(SPICE_MODEL_PORT_INOUT); - iopad_port_types_required.push_back(SPICE_MODEL_PORT_SRAM); - - num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_IOPAD, iopad_port_types_required); - - /* 4. Check mux has been defined and has input and output ports - * [a] We must have a MUX! - * [b] For each MUX, we must have at least an input, an output, and an SRAM port - */ - num_err += check_circuit_model_required(circuit_lib, SPICE_MODEL_MUX); - - std::vector mux_port_types_required; - mux_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); - mux_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); - mux_port_types_required.push_back(SPICE_MODEL_PORT_SRAM); - - num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_MUX, mux_port_types_required); - - /* 5. We must have at least one SRAM or SCFF */ - if ( ( 0 == circuit_lib.circuit_models_by_type(SPICE_MODEL_SRAM).size()) - && ( 0 == circuit_lib.circuit_models_by_type(SPICE_MODEL_SCFF).size()) ) { - vpr_printf(TIO_MESSAGE_ERROR, - "At least one %s or %s circuit model is required!\n", - CIRCUIT_MODEL_TYPE_STRING[size_t(SPICE_MODEL_SRAM)], - CIRCUIT_MODEL_TYPE_STRING[size_t(SPICE_MODEL_SCFF)]); - /* Incremental the counter for errors */ - num_err++; - } - - /* 6. SRAM must have at least an input and an output ports*/ - std::vector sram_port_types_required; - sram_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); - sram_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); - - num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_SRAM, sram_port_types_required); - - /* 7. SCFF must have at least an input and an output ports*/ - std::vector scff_port_types_required; - scff_port_types_required.push_back(SPICE_MODEL_PORT_CLOCK); - scff_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); - scff_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); - - num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_SCFF, scff_port_types_required); - - /* 8. FF must have at least an input and an output ports*/ - std::vector ff_port_types_required; - ff_port_types_required.push_back(SPICE_MODEL_PORT_CLOCK); - ff_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); - ff_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); - - num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_FF, ff_port_types_required); - - /* 9. LUY must have at least an input, an output and a SRAM ports*/ - std::vector lut_port_types_required; - lut_port_types_required.push_back(SPICE_MODEL_PORT_SRAM); - lut_port_types_required.push_back(SPICE_MODEL_PORT_INPUT); - lut_port_types_required.push_back(SPICE_MODEL_PORT_OUTPUT); - - num_err += check_circuit_model_port_required(circuit_lib, SPICE_MODEL_LUT, lut_port_types_required); - - /* If we have any errors, exit */ - vpr_printf(TIO_MESSAGE_ERROR, - "Finished checking circuit library with %d errors!\n", - num_err); - - if (0 < num_err) { - exit(1); - } - - return; -} - -/************************************************************************ - * End of file : check_circuit_library.cpp - ***********************************************************************/ - diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/linkedlist.h b/vpr7_x2p/libarchfpga/SRC/linkedlist.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/linkedlist.h rename to vpr7_x2p/libarchfpga/SRC/linkedlist.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/logic_types.h b/vpr7_x2p/libarchfpga/SRC/logic_types.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/logic_types.h rename to vpr7_x2p/libarchfpga/SRC/logic_types.h diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/my_free_fwd.h b/vpr7_x2p/libarchfpga/SRC/my_free_fwd.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/my_free_fwd.h rename to vpr7_x2p/libarchfpga/SRC/my_free_fwd.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/physical_types.h b/vpr7_x2p/libarchfpga/SRC/physical_types.h similarity index 99% rename from vpr7_x2p/libarchfpga/SRC/include/physical_types.h rename to vpr7_x2p/libarchfpga/SRC/physical_types.h index 24dee9ea8..81de09866 100644 --- a/vpr7_x2p/libarchfpga/SRC/include/physical_types.h +++ b/vpr7_x2p/libarchfpga/SRC/physical_types.h @@ -265,6 +265,7 @@ struct s_port { /* FPGA_SPICE_model support: * mapped SPICE model port */ t_spice_model_port* spice_model_port; + CircuitPortId circuit_model_port; char* physical_mode_pin; int physical_mode_pin_rotate_offset; /* The pin number will rotate by an offset unit when mapping to physical modes */ int phy_mode_pin_rotate_offset_acc; /* The pin number will rotate by an offset unit when mapping to physical modes */ @@ -341,6 +342,7 @@ struct s_interconnect { /* Xifan TANG: SPICE Support*/ char* spice_model_name; t_spice_model* spice_model; + CircuitModelId circuit_model; int fan_in; int fan_out; int num_mux; @@ -658,6 +660,7 @@ struct s_pb_type { char* physical_mode_name; char* spice_model_name; t_spice_model* spice_model; + CircuitModelId circuit_model; char* mode_bits; /* Mode bits to select */ int spice_model_sram_offset; char* physical_pb_type_name; @@ -846,6 +849,7 @@ typedef struct s_segment_inf { /* Xifan TANG: SPICE model support*/ char* spice_model_name; t_spice_model* spice_model; + CircuitModelId circuit_model; /* mrFPGA: Xifan TANG */ short seg_switch; /* end */ @@ -879,6 +883,7 @@ typedef struct s_switch_inf { /* Xifan TANG: spice support*/ char* spice_model_name; t_spice_model* spice_model; + CircuitModelId circuit_model; /* Xifan TANG: switch structure */ enum e_spice_model_structure structure; int switch_num_level; @@ -922,6 +927,7 @@ typedef struct s_direct_inf { /* Xifan Tang: FPGA-SPICE support */ char* spice_model_name; t_spice_model* spice_model; + CircuitModelId circuit_model; } t_direct_inf; diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/port_parser.cpp b/vpr7_x2p/libarchfpga/SRC/port_parser.cpp similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/port_parser.cpp rename to vpr7_x2p/libarchfpga/SRC/port_parser.cpp diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/port_parser.h b/vpr7_x2p/libarchfpga/SRC/port_parser.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/port_parser.h rename to vpr7_x2p/libarchfpga/SRC/port_parser.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/read_xml_arch_file.h b/vpr7_x2p/libarchfpga/SRC/read_xml_arch_file.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/read_xml_arch_file.h rename to vpr7_x2p/libarchfpga/SRC/read_xml_arch_file.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/read_xml_mrfpga.h b/vpr7_x2p/libarchfpga/SRC/read_xml_mrfpga.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/read_xml_mrfpga.h rename to vpr7_x2p/libarchfpga/SRC/read_xml_mrfpga.h diff --git a/vpr7_x2p/libarchfpga/SRC/read_xml_spice.c b/vpr7_x2p/libarchfpga/SRC/read_xml_spice.c index ac0892cf8..17ebb718a 100644 --- a/vpr7_x2p/libarchfpga/SRC/read_xml_spice.c +++ b/vpr7_x2p/libarchfpga/SRC/read_xml_spice.c @@ -1023,10 +1023,11 @@ static void ProcessSpiceModel(ezxml_t Parent, spice_model->design_tech_info.mux_info->structure = SPICE_MODEL_STRUCTURE_TREE; spice_model->design_tech_info.mux_info->add_const_input = FALSE; spice_model->design_tech_info.mux_info->const_input_val = 0; + spice_model->design_tech_info.mux_info->advanced_rram_design = FALSE; + spice_model->design_tech_info.mux_info->local_encoder = FALSE; } ezxml_set_attr(Node, "fracturable_lut", NULL); - spice_model->design_tech_info.gate_info = NULL; if (SPICE_MODEL_GATE == spice_model->type) { /* Malloc */ @@ -1071,13 +1072,15 @@ static void ProcessSpiceModel(ezxml_t Parent, /* LUT intermediate buffers */ Node = ezxml_child(Parent, "lut_intermediate_buffer"); - spice_model->lut_intermediate_buffer = (t_spice_model_buffer*)my_calloc(1, sizeof(t_spice_model_buffer)); + spice_model->lut_intermediate_buffer = NULL; if (Node) { + spice_model->lut_intermediate_buffer = (t_spice_model_buffer*)my_calloc(1, sizeof(t_spice_model_buffer)); /* Malloc the lut_input_buffer */ ProcessSpiceModelBuffer(Node,spice_model->lut_intermediate_buffer); FreeNode(Node); } else if ((SPICE_MODEL_LUT == spice_model->type) || (SPICE_MODEL_MUX == spice_model->type)) { + spice_model->lut_intermediate_buffer = (t_spice_model_buffer*)my_calloc(1, sizeof(t_spice_model_buffer)); /* Assign default values */ spice_model->lut_intermediate_buffer->exist = 0; spice_model->lut_intermediate_buffer->spice_model = NULL; @@ -1632,7 +1635,8 @@ CircuitLibrary build_circuit_library(int num_spice_model, t_spice_model* spice_m } circuit_lib.set_circuit_model_lut_input_inverter(model_id, 0 != spice_models[imodel].lut_input_inverter->exist, model_name); } - if (NULL != spice_models[imodel].lut_intermediate_buffer) { + if ( (NULL != spice_models[imodel].lut_intermediate_buffer) + && (1 == spice_models[imodel].lut_intermediate_buffer->exist) ) { std::string model_name; if (NULL != spice_models[imodel].lut_intermediate_buffer->spice_model_name) { model_name = spice_models[imodel].lut_intermediate_buffer->spice_model_name; diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/read_xml_spice.h b/vpr7_x2p/libarchfpga/SRC/read_xml_spice.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/read_xml_spice.h rename to vpr7_x2p/libarchfpga/SRC/read_xml_spice.h diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/read_xml_spice_util.h b/vpr7_x2p/libarchfpga/SRC/read_xml_spice_util.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/read_xml_spice_util.h rename to vpr7_x2p/libarchfpga/SRC/read_xml_spice_util.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/read_xml_util.h b/vpr7_x2p/libarchfpga/SRC/read_xml_util.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/read_xml_util.h rename to vpr7_x2p/libarchfpga/SRC/read_xml_util.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/sides.h b/vpr7_x2p/libarchfpga/SRC/sides.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/sides.h rename to vpr7_x2p/libarchfpga/SRC/sides.h diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/spice_types.h b/vpr7_x2p/libarchfpga/SRC/spice_types.h similarity index 99% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/spice_types.h rename to vpr7_x2p/libarchfpga/SRC/spice_types.h index 1c333eb70..42ecbb3f2 100644 --- a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/spice_types.h +++ b/vpr7_x2p/libarchfpga/SRC/spice_types.h @@ -396,6 +396,7 @@ struct s_spice_mux_model { struct s_sram_inf_orgz { char* spice_model_name; // Xifan TANG: Spice Support t_spice_model* spice_model; // Xifan TANG: Spice Support + CircuitModelId circuit_model; enum e_sram_orgz type; }; diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/string_token.cpp b/vpr7_x2p/libarchfpga/SRC/string_token.cpp similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/string_token.cpp rename to vpr7_x2p/libarchfpga/SRC/string_token.cpp diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/string_token.h b/vpr7_x2p/libarchfpga/SRC/string_token.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/string_token.h rename to vpr7_x2p/libarchfpga/SRC/string_token.h diff --git a/vpr7_x2p/libarchfpga/SRC/include/util.h b/vpr7_x2p/libarchfpga/SRC/util.h similarity index 100% rename from vpr7_x2p/libarchfpga/SRC/include/util.h rename to vpr7_x2p/libarchfpga/SRC/util.h diff --git a/vpr7_x2p/vpr/SRC/base/SetupVPR.c b/vpr7_x2p/vpr/SRC/base/SetupVPR.c index 7a78d6d97..5b0e90004 100644 --- a/vpr7_x2p/vpr/SRC/base/SetupVPR.c +++ b/vpr7_x2p/vpr/SRC/base/SetupVPR.c @@ -1186,7 +1186,7 @@ static void SetupSynVerilogOpts(t_options Options, /* SynVerilog needs the input from spice modeling */ if (FALSE == arch->read_xml_spice) { arch->read_xml_spice = syn_verilog_opts->dump_syn_verilog; - arch->spice = (t_spice*)my_malloc(sizeof(t_spice)); + arch->spice = (t_spice*)my_calloc(1, sizeof(t_spice)); } return; diff --git a/vpr7_x2p/vpr/SRC/base/read_blif.c b/vpr7_x2p/vpr/SRC/base/read_blif.c index 8e982725d..75008fc3f 100644 --- a/vpr7_x2p/vpr/SRC/base/read_blif.c +++ b/vpr7_x2p/vpr/SRC/base/read_blif.c @@ -524,7 +524,7 @@ static void add_latch(int doall, INP t_model *latch_model) { /* Store the initial value */ logical_block[num_logical_blocks - 1].init_val = my_atoi(saved_names[4]); /* Add clock identification */ - logical_block[logical_block[num_logical_blocks - 1].clock_net].is_clock = TRUE; + logical_block[vpack_net[logical_block[num_logical_blocks - 1].clock_net].node_block[0]].is_clock = TRUE; /*END*/ num_latches++; @@ -722,6 +722,9 @@ static void add_subckt(int doall, t_model *user_models) { add_vpack_net(circuit_signal_name[i], RECEIVER, num_logical_blocks - 1, port->index, my_atoi(pin_number), TRUE, doall); + + /* Add clock identification */ + logical_block[vpack_net[logical_block[num_logical_blocks - 1].clock_net].node_block[0]].is_clock = TRUE; } else { logical_block[num_logical_blocks - 1].input_nets[port->index][my_atoi( pin_number)] = add_vpack_net( diff --git a/vpr7_x2p/vpr/SRC/base/vpr_types.h b/vpr7_x2p/vpr/SRC/base/vpr_types.h index 561362e1d..4b039d5c8 100755 --- a/vpr7_x2p/vpr/SRC/base/vpr_types.h +++ b/vpr7_x2p/vpr/SRC/base/vpr_types.h @@ -1128,6 +1128,7 @@ typedef struct s_clb_to_clb_directs { int y_offset; int z_offset; t_spice_model* spice_model; + CircuitModelId circuit_model; char* name; } t_clb_to_clb_directs; diff --git a/vpr7_x2p/vpr/SRC/ctags_vpr_src.sh b/vpr7_x2p/vpr/SRC/ctags_vpr_src.sh index 5a37c337a..95bff29de 100755 --- a/vpr7_x2p/vpr/SRC/ctags_vpr_src.sh +++ b/vpr7_x2p/vpr/SRC/ctags_vpr_src.sh @@ -1,2 +1,2 @@ rm tags -ctags -R shell_main.c main.c ./* ../../libarchfpga/SRC/include/*.[ch] ../../libarchfpga/SRC/fpga_spice_include/*.[ch] ../../libarchfpga/SRC/*.[ch] ../../pcre/SRC/*.[ch] +ctags -R shell_main.c main.c ./* ../../libarchfpga/SRC/* ../../pcre/SRC/*.[ch] diff --git a/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.cpp b/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.cpp index 6752def9e..167d6d161 100644 --- a/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.cpp +++ b/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.cpp @@ -341,6 +341,33 @@ void add_edges_for_two_rr_nodes(const t_rr_graph* rr_graph, } +/************************************************************************ + * Get the track_id of a routing track w.r.t its coordinator + * In tileable routing architecture, the track_id changes SB by SB. + * Therefore the track_ids are stored in a vector, indexed by the relative coordinator + * based on the starting point of the track + * For routing tracks in INC_DIRECTION + * (xlow, ylow) should be the starting point + * + * (xlow, ylow) (xhigh, yhigh) + * track_id[0] -------------------------------> track_id[xhigh - xlow + yhigh - ylow] + * + * For routing tracks in DEC_DIRECTION + * (xhigh, yhigh) should be the starting point + * + * (xlow, ylow) (xhigh, yhigh) + * track_id[0] <------------------------------- track_id[xhigh - xlow + yhigh - ylow] + * + * + ***********************************************************************/ +short get_rr_node_actual_track_id(const t_rr_node* track_rr_node, + const DeviceCoordinator& coord) { + DeviceCoordinator low_coord(track_rr_node->xlow, track_rr_node->ylow); + size_t offset = (int)abs((int)coord.get_x() - (int)low_coord.get_x() + (int)coord.get_y() - (int)low_coord.get_y()); + return track_rr_node->track_ids[offset]; +} + + /************************************************************************ * Get the coordinator of a starting point of a routing track * For routing tracks in INC_DIRECTION diff --git a/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.h b/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.h index c213546d5..5ef5382f3 100644 --- a/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.h +++ b/vpr7_x2p/vpr/SRC/device/rr_graph/rr_graph_builder_utils.h @@ -35,6 +35,9 @@ void add_edges_for_two_rr_nodes(const t_rr_graph* rr_graph, const std::vector des_rr_node, const std::vector driver_switches); +short get_rr_node_actual_track_id(const t_rr_node* track_rr_node, + const DeviceCoordinator& coord); + DeviceCoordinator get_track_rr_node_start_coordinator(const t_rr_node* track_rr_node); DeviceCoordinator get_track_rr_node_end_coordinator(const t_rr_node* track_rr_node); diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.c b/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.c index 748e62ef5..9da08d95b 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.c +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.c @@ -1005,8 +1005,7 @@ int rec_count_num_conf_bits_pb_type_physical_mode(t_pb_type* cur_pb_type, cur_pb_type->physical_mode_num_conf_bits = 0; /* Recursively finish all the child pb_types*/ - if ((NULL == cur_pb_type->spice_model_name) - && (NULL == cur_pb_type->physical_pb_type_name)) { + if ( FALSE == is_primitive_pb_type(cur_pb_type)) { /* Find the mode that define_idle_mode*/ mode_index = find_pb_type_physical_mode_index((*cur_pb_type)); for (ipb = 0; ipb < cur_pb_type->modes[mode_index].num_pb_type_children; ipb++) { @@ -1017,14 +1016,14 @@ int rec_count_num_conf_bits_pb_type_physical_mode(t_pb_type* cur_pb_type, } /* Check if this has defined a spice_model*/ - if ((NULL != cur_pb_type->spice_model_name) - || (NULL != cur_pb_type->physical_pb_type_name)) { + if ( TRUE == is_primitive_pb_type(cur_pb_type)) { sum_num_conf_bits = count_num_conf_bits_one_spice_model(cur_pb_type->phy_pb_type->spice_model, cur_sram_orgz_info->type, 0); cur_pb_type->physical_mode_num_conf_bits = sum_num_conf_bits; /* calculate the number of reserved configuration bits */ cur_pb_type->physical_mode_num_reserved_conf_bits = count_num_reserved_conf_bits_one_spice_model(cur_pb_type->phy_pb_type->spice_model, cur_sram_orgz_info->type, 0); + } else { /* Count the sum of configuration bits of all the children pb_types */ /* Find the mode that define_idle_mode*/ mode_index = find_pb_type_physical_mode_index((*cur_pb_type)); @@ -1234,6 +1233,28 @@ void init_grids_num_conf_bits(t_sram_orgz_info* cur_sram_orgz_info) { return; } +/******************************************************************** + * Initialize the number of configuration bits for each pb_type + * in the list of type descriptors + *******************************************************************/ +void init_pb_types_num_conf_bits(t_sram_orgz_info* cur_sram_orgz_info) { + for (int itype = 0; itype < num_types; ++itype) { + /* bypass EMPTY_TYPES */ + if (EMPTY_TYPE == &(type_descriptors[itype])) { + continue; + } + int capacity= type_descriptors[itype].capacity; + assert(0 < capacity); + + /* check capacity and if this has been mapped */ + for (int iz = 0; iz < capacity; iz++) { + /* Check in all the blocks(clustered logic block), there is a match x,y,z*/ + rec_count_num_conf_bits_pb_type_physical_mode(type_descriptors[itype].pb_type, cur_sram_orgz_info); + } + } + return; +} + /* With given spice_model_port, find the pb_type port with same name and type*/ t_port* find_pb_type_port_match_spice_model_port(t_pb_type* pb_type, t_spice_model_port* spice_model_port) { @@ -1301,6 +1322,7 @@ t_port* find_pb_type_port_match_spice_model_port(t_pb_type* pb_type, return ret; } + t_port** find_pb_type_ports_match_spice_model_port_type(t_pb_type* pb_type, enum e_spice_model_port_type port_type, int* port_num) { @@ -1794,6 +1816,29 @@ void init_grids_num_iopads() { return; } +/******************************************************************** + * Initialize the number of configuration bits for each pb_type + * in the list of type descriptors + *******************************************************************/ +void init_pb_types_num_iopads() { + for (int itype = 0; itype < num_types; ++itype) { + /* bypass EMPTY_TYPES */ + if (EMPTY_TYPE == &(type_descriptors[itype])) { + continue; + } + + int capacity= type_descriptors[itype].capacity; + assert(0 < capacity); + + /* check capacity and if this has been mapped */ + for (int iz = 0; iz < capacity; iz++) { + /* Check in all the blocks(clustered logic block), there is a match x,y,z*/ + rec_count_num_iopads_pb_type_physical_mode(type_descriptors[itype].pb_type); + } + } + return; +} + /* Count the number of mode configuration bits of a grid (type_descriptor) in default mode */ void rec_count_num_mode_bits_pb_type_default_mode(t_pb_type* cur_pb_type) { int mode_index, ipb, jpb; diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.h b/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.h index 34063fc95..8a85329c0 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.h +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_pbtypes_utils.h @@ -93,6 +93,8 @@ void init_one_grid_num_conf_bits(int ix, int iy, void init_grids_num_conf_bits(t_sram_orgz_info* cur_sram_orgz_info); +void init_pb_types_num_conf_bits(t_sram_orgz_info* cur_sram_orgz_info); + void map_clb_pins_to_pb_graph_pins(); t_port* find_pb_type_port_match_spice_model_port(t_pb_type* pb_type, @@ -102,7 +104,6 @@ t_port** find_pb_type_ports_match_spice_model_port_type(t_pb_type* pb_type, enum e_spice_model_port_type port_type, int* port_num); - enum e_interconnect find_pb_graph_pin_in_edges_interc_type(t_pb_graph_pin pb_graph_pin); t_spice_model* find_pb_graph_pin_in_edges_interc_spice_model(t_pb_graph_pin pb_graph_pin); @@ -136,6 +137,8 @@ void init_one_grid_num_iopads(int ix, int iy); void init_grids_num_iopads(); +void init_pb_types_num_iopads(); + void rec_count_num_mode_bits_pb_type_default_mode(t_pb_type* cur_pb_type); void rec_count_num_mode_bits_pb(t_pb* cur_pb); diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_setup.c b/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_setup.c index 011eca31a..fc36ffff6 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_setup.c +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/fpga_x2p_setup.c @@ -33,6 +33,7 @@ #include "verilog_api.h" #include "fpga_x2p_unique_routing.h" +#include "link_arch_circuit_lib.h" #include "fpga_x2p_setup.h" /***** Subroutines Declarations *****/ @@ -1322,10 +1323,14 @@ void fpga_x2p_setup(t_vpr_setup vpr_setup, /* Start time count */ t_start = clock(); - vpr_printf(TIO_MESSAGE_INFO, "\nFPGA-SPICE Tool suites Initilization begins...\n"); + vpr_printf(TIO_MESSAGE_INFO, "\nFPGA-X2P Tool suites Initilization begins...\n"); - /* Initialize Arch SPICE MODELS*/ + /* FIXME: this function is going to be removed when new linking function is working + * Initialize Arch SPICE MODELS + */ init_check_arch_spice_models(Arch, &(vpr_setup.RoutingArch)); + /* Link circuit models to architecture */ + link_circuit_library_to_arch(Arch, &(vpr_setup.RoutingArch)); /* Initialize idle mode and physical mode of each pb_type and pb_graph_node */ init_check_arch_pb_type_idle_and_phy_mode(); diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/base/link_arch_circuit_lib.cpp b/vpr7_x2p/vpr/SRC/fpga_x2p/base/link_arch_circuit_lib.cpp new file mode 100644 index 000000000..3cdd35eb1 --- /dev/null +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/link_arch_circuit_lib.cpp @@ -0,0 +1,592 @@ +/********************************************************** + * MIT License + * + * Copyright (c) 2018 LNIS - The University of Utah + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + ***********************************************************************/ + +/************************************************************************ + * Filename: link_arch_circuit_lib.cpp + * Created by: Xifan Tang + * Change history: + * +-------------------------------------+ + * | Date | Author | Notes + * +-------------------------------------+ + * | 2019/08/12 | Xifan Tang | Created + * +-------------------------------------+ + ***********************************************************************/ +/************************************************************************ + * This file includes key functions to link circuit models to the architecture modules + ***********************************************************************/ +#include +#include +#include +#include +#include +#include +#include +#include + +/* Include vpr structs*/ +#include "util.h" +#include "physical_types.h" +#include "vpr_types.h" +#include "globals.h" +#include "rr_graph.h" +#include "vpr_utils.h" +#include "path_delay.h" +#include "stats.h" +#include "route_common.h" + +/* Include vtr libraries */ +#include "vtr_assert.h" + +/* Include spice support headers*/ +#include "linkedlist.h" +#include "fpga_x2p_types.h" +#include "fpga_x2p_globals.h" +#include "fpga_x2p_utils.h" +#include "fpga_x2p_timing_utils.h" +#include "fpga_x2p_backannotate_utils.h" +#include "fpga_x2p_pbtypes_utils.h" +#include "verilog_api.h" + +#include "check_circuit_library.h" +#include "link_arch_circuit_lib.h" + +/************************************************************************ + * Find a circuit model with a given name + * Case 1: if the circuit_model_name is not defined, + * we find a default circuit model and check its type + * Case 2: if the circuit_model_name is defined, + * we find a matched circuit model and check its type + ***********************************************************************/ +CircuitModelId link_circuit_model_by_name_and_type(const char* circuit_model_name, + const CircuitLibrary& circuit_lib, + const enum e_spice_model_type& model_type) { + CircuitModelId circuit_model = CIRCUIT_MODEL_OPEN_ID; + /* If the circuit_model_name is not defined, we use the default*/ + if (NULL == circuit_model_name) { + circuit_model = circuit_lib.default_circuit_model(model_type); + } else { + circuit_model = circuit_lib.circuit_model(circuit_model_name); + } + + /* Check the circuit model, we should have one! */ + if (CIRCUIT_MODEL_OPEN_ID == circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Fail to find a defined circuit model called %s!\n", + __FILE__, __LINE__, + circuit_lib.circuit_model_name(circuit_model).c_str()); + return circuit_model; /* Return here, no need to check the model_type */ + } + + /* Check the type of circuit model, make sure it is the one we want */ + if (model_type != circuit_lib.circuit_model_type(circuit_model)) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Invalid type when trying to find circuit model called %s! Expect %s but found %s!\n", + __FILE__, __LINE__, + circuit_model_name, + CIRCUIT_MODEL_TYPE_STRING[size_t(model_type)], + CIRCUIT_MODEL_TYPE_STRING[size_t(circuit_lib.circuit_model_type(circuit_model))]); + } + + return circuit_model; +} + +/************************************************************************ + * Link circuit model to the SRAM organization + * Case 1: standalone organization required a SRAM circuit model + * Case 1: scan-chain organization required a SCFF circuit model + * Case 1: memory-bank organization required a SRAM circuit model + ***********************************************************************/ +static +void link_one_sram_inf_orgz(t_sram_inf_orgz* cur_sram_inf_orgz, + const CircuitLibrary& circuit_lib) { + /* If cur_sram_inf_orgz is not initialized, do nothing */ + if (NULL == cur_sram_inf_orgz) { + return; + } + + /* Check the type of SRAM_Ciruit_MODEL required by different sram organization */ + /* check SRAM ports + * Checker for circuit models used by the SRAM organization + * either SRAMs or SCFFs + * 1. It will check the basic port required for SRAMs and SCFFs + * 2. It will check any special ports required for SRAMs and SCFFs + */ + switch (cur_sram_inf_orgz->type) { + case SPICE_SRAM_STANDALONE: + cur_sram_inf_orgz->circuit_model = link_circuit_model_by_name_and_type(cur_sram_inf_orgz->spice_model_name, circuit_lib, SPICE_MODEL_SRAM); + /* check SRAM ports */ + check_sram_circuit_model_ports(circuit_lib, cur_sram_inf_orgz->circuit_model, false); + break; + case SPICE_SRAM_MEMORY_BANK: + cur_sram_inf_orgz->circuit_model = link_circuit_model_by_name_and_type(cur_sram_inf_orgz->spice_model_name, circuit_lib, SPICE_MODEL_SRAM); + /* check if this one has bit lines and word lines */ + check_sram_circuit_model_ports(circuit_lib, cur_sram_inf_orgz->circuit_model, true); + break; + case SPICE_SRAM_SCAN_CHAIN: + /* check Scan-chain Flip-flop ports */ + cur_sram_inf_orgz->circuit_model = link_circuit_model_by_name_and_type(cur_sram_inf_orgz->spice_model_name, circuit_lib, SPICE_MODEL_SCFF); + check_scff_circuit_model_ports(circuit_lib, cur_sram_inf_orgz->circuit_model); + break; + case SPICE_SRAM_LOCAL_ENCODER: + /* Wipe out LOCAL ENCODER, it is not supported here ! */ + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Local encoder SRAM organization is not supported!\n", + __FILE__, __LINE__); + exit(1); + break; + default: + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Invalid SRAM organization!\n", + __FILE__, __LINE__); + exit(1); + } + + /* RRAM Scan-chain is not supported yet. Now just forbidden this option */ + if ( (SPICE_SRAM_SCAN_CHAIN == cur_sram_inf_orgz->type) + && (SPICE_MODEL_DESIGN_RRAM == circuit_lib.design_tech_type(cur_sram_inf_orgz->circuit_model)) ) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) RRAM-based Scan-chain Flip-flop has not been supported yet!\n", + __FILE__, __LINE__); + exit(1); + } + + return; +} + +static +void link_sram_inf(t_sram_inf* cur_sram_inf, + const CircuitLibrary& circuit_lib) { + /* We have two branches: + * 1. SPICE SRAM organization information + * 2. Verilog SRAM organization information + */ + link_one_sram_inf_orgz(cur_sram_inf->spice_sram_inf_orgz, + circuit_lib); + + link_one_sram_inf_orgz(cur_sram_inf->verilog_sram_inf_orgz, + circuit_lib); + + return; +} + + +/************************************************************************** + * With given circuit port, find the pb_type port with same name and type + **************************************************************************/ +t_port* find_pb_type_port_match_circuit_model_port(const t_pb_type* pb_type, + const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const CircuitPortId& circuit_port) { + t_port* ret = NULL; + size_t num_found = 0; + + /* Search ports */ + for (int iport = 0; iport < pb_type->num_ports; iport++) { + /* Match the name and port size*/ + if ( (0 == circuit_lib.port_prefix(circuit_model, circuit_port).compare(pb_type->ports[iport].name)) + && (size_t(pb_type->ports[iport].num_pins) == circuit_lib.port_size(circuit_model, circuit_port))) { + /* Match the type*/ + switch (circuit_lib.port_type(circuit_model, circuit_port)) { + case SPICE_MODEL_PORT_INPUT: + if ((IN_PORT == pb_type->ports[iport].type) + &&(0 == pb_type->ports[iport].is_clock)) { + ret = &(pb_type->ports[iport]); + num_found++; + } + break; + case SPICE_MODEL_PORT_OUTPUT: + if (OUT_PORT == pb_type->ports[iport].type) { + ret = &(pb_type->ports[iport]); + } + break; + case SPICE_MODEL_PORT_CLOCK: + if ((IN_PORT == pb_type->ports[iport].type)&&(1 == pb_type->ports[iport].is_clock)) { + ret = &(pb_type->ports[iport]); + num_found++; + } + break; + case SPICE_MODEL_PORT_INOUT : + if ((INOUT_PORT == pb_type->ports[iport].type)&&(0 == pb_type->ports[iport].is_clock)) { + ret = &(pb_type->ports[iport]); + num_found++; + } + break; + case SPICE_MODEL_PORT_SRAM: + break; + default: + vpr_printf(TIO_MESSAGE_ERROR,"(File:%s, [LINE%d])Invalid type for circuit model port(%s)!\n", + __FILE__, __LINE__, circuit_lib.port_prefix(circuit_model, circuit_port)); + exit(1); + } + } + } + + /* We should find only 1 match */ + if (1 < num_found) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s, [LINE%d])More than 1 pb_type(%s) port match spice_model_port(%s)!\n", + __FILE__, __LINE__, pb_type->name, circuit_lib.port_prefix(circuit_model, circuit_port).c_str()); + exit(1); + } + + return ret; +} + + +/************************************************************************ + * Map (synchronize) pb_type ports to circuit model ports + ***********************************************************************/ +static +int link_pb_type_port_to_circuit_model_ports(const t_pb_type* cur_pb_type, + const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model) { + + /* Check */ + assert(NULL != cur_pb_type); + + /* Initialize each port */ + for (int iport = 0; iport < cur_pb_type->num_ports; iport++) { + cur_pb_type->ports[iport].circuit_model_port = CIRCUIT_PORT_OPEN_ID; + } + + /* Return if SPICE_MODEL is NULL */ + if (CIRCUIT_MODEL_OPEN_ID == circuit_model) { + return 0; + } + + /* For each port, find a SPICE model port, which has the same name and port size */ + for (auto& port : circuit_lib.ports(circuit_model)) { + t_port* cur_pb_type_port = find_pb_type_port_match_circuit_model_port(cur_pb_type, circuit_lib, circuit_model, port); + /* Not every spice_model_port can find a mapped pb_type_port. + * Since a pb_type only includes necessary ports in technology mapping. + * ports for physical designs may be ignored ! + */ + if (NULL != cur_pb_type_port) { + cur_pb_type_port->circuit_model_port = port; + } + } + /* Although some spice_model_port may not have a corresponding pb_type_port + * but each pb_type_port should be mapped to a spice_model_port + */ + for (int iport = 0; iport < cur_pb_type->num_ports; iport++) { + if (CIRCUIT_PORT_OPEN_ID == cur_pb_type->ports[iport].circuit_model_port) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s, [LINE%d])Pb_type(%s) Port(%s) cannot find a corresponding port in SPICE model(%s)\n", + __FILE__, __LINE__, cur_pb_type->name, cur_pb_type->ports[iport].name, + circuit_lib.circuit_model_name(circuit_model).c_str()); + exit(1); + } + } + + return cur_pb_type->num_ports; +} + +/************************************************************************ + * Find a circuit model for an interconnect in pb_type + * Case 1: if the circuit_model_name is not defined, + * we find a default circuit model and check its type + * Case 2: if the circuit_model_name is defined, + * we find a matched circuit model and check its type + ***********************************************************************/ +static +void link_pb_type_interc_circuit_model_by_type(t_interconnect* cur_interc, + const CircuitLibrary& circuit_lib, + const enum e_spice_model_type& model_type) { + + /* If the circuit_model_name is not defined, we use the default*/ + cur_interc->circuit_model = link_circuit_model_by_name_and_type(cur_interc->spice_model_name, + circuit_lib, + model_type); + /* Check the circuit model, we should have one! */ + if (CIRCUIT_MODEL_OPEN_ID == cur_interc->circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Error in linking circuit model for interconnect(name %s)! Check [LINE%d] in architecture file)!\n", + __FILE__, __LINE__, + cur_interc->name, + cur_interc->line_num); + exit(1); + } + + /* Special check for MUXes: + * If the multiplexers do not have any input buffers, the loop breaker cannot be disabled + */ + if (SPICE_MODEL_MUX == model_type) { + if (NULL != cur_interc->loop_breaker_string) { + if (false == circuit_lib.is_input_buffered(cur_interc->circuit_model)) { + vpr_printf(TIO_MESSAGE_INFO, + "Line[%d] Cannot disable an interconnect without input buffering.\n", + cur_interc->line_num); + } + } + } + + return; +} + +/************************************************************************ + * Find a circuit model for an interconnect in pb_type + * Case 1: if this is a DIRECT interconnection, + * we will try to find a circuit model whose type is WIRE + * Case 2: if this is a COMPLETE interconnection, we should evaluate + * the number of multiplexer required. + * when it does require multiplexers + * we will try to find a circuit model whose type is MUX + * otherwise, + * we will try to find a circuit model whose type is WIRE + * Case 3: if this is a MUX interconnection, + * we will try to find a circuit model whose type is WIRE + ***********************************************************************/ +static +void link_pb_type_interc_circuit_model(t_interconnect* cur_interc, + const CircuitLibrary& circuit_lib) { + switch (cur_interc->type) { + case DIRECT_INTERC: + link_pb_type_interc_circuit_model_by_type(cur_interc, circuit_lib, SPICE_MODEL_WIRE); + break; + case COMPLETE_INTERC: + /* Special for Completer Interconnection: + * 1. The input number is 1, this infers a direct interconnection. + * 2. The input number is larger than 1, this infers multplexers + * according to interconnect[j].num_mux identify the number of input at this level + */ + if (0 == cur_interc->num_mux) { + link_pb_type_interc_circuit_model_by_type(cur_interc, circuit_lib, SPICE_MODEL_WIRE); + } else { + link_pb_type_interc_circuit_model_by_type(cur_interc, circuit_lib, SPICE_MODEL_MUX); + } + break; + case MUX_INTERC: + link_pb_type_interc_circuit_model_by_type(cur_interc, circuit_lib, SPICE_MODEL_MUX); + break; + default: + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Unknown type of interconnection (name=%s) defined in architecture file(LINE%d)!\n", + __FILE__, __LINE__, cur_interc->name, cur_interc->line_num); + exit(1); + } + return; +} + +/************************************************************************ + * Walk through the pb_types in a recursive way + * Find circuit_model_name definition in pb_types + * Try to match the name with defined spice_models + ***********************************************************************/ +static +void link_pb_types_circuit_model_rec(t_pb_type* cur_pb_type, + const CircuitLibrary& circuit_lib) { + if (NULL == cur_pb_type) { + vpr_printf(TIO_MESSAGE_WARNING, + "(File:%s,LINE[%d])cur_pb_type is null pointor!\n", + __FILE__, __LINE__); + return; + } + + /* If there is a circuit_model_name or physical_pb_type_name referring to a physical pb type, + * this is a leaf node! + */ + if ( TRUE == is_primitive_pb_type(cur_pb_type) ) { + /* What annoys me is VPR create a sub pb_type for each lut which suppose to be a leaf node + * This may bring software convience but ruins SPICE modeling + */ + if (NULL != cur_pb_type->physical_pb_type_name) { + /* if this is not a physical pb_type, we do not care its circuit_model_name*/ + return; + } + /* Let's find a matched circuit model!*/ + cur_pb_type->circuit_model = circuit_lib.circuit_model(cur_pb_type->spice_model_name); + if (CIRCUIT_MODEL_OPEN_ID == cur_pb_type->circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,LINE[%d]) Fail to find a defined circuit model called %s, in pb_type(%s)!\n", + __FILE__, __LINE__, cur_pb_type->spice_model_name, cur_pb_type->name); + exit(1); + } + /* Map pb_type ports to SPICE model ports*/ + link_pb_type_port_to_circuit_model_ports(cur_pb_type, circuit_lib, cur_pb_type->circuit_model); + return; + } + + /* Otherwise, initialize it to be OPEN node */ + cur_pb_type->circuit_model = CIRCUIT_MODEL_OPEN_ID; + + /* Traversal the hierarchy*/ + for (int imode = 0; imode < cur_pb_type->num_modes; imode++) { + /* Task 1: Find the interconnections and match the spice_model */ + for (int jinterc = 0; jinterc < cur_pb_type->modes[imode].num_interconnect; jinterc++) { + /* Initialize it to be OPEN node */ + cur_pb_type->modes[imode].interconnect[jinterc].circuit_model = CIRCUIT_MODEL_OPEN_ID; + link_pb_type_interc_circuit_model(&(cur_pb_type->modes[imode].interconnect[jinterc]), + circuit_lib); + } + /* Task 2: Find the child pb_type, do matching recursively */ + for (int ipb = 0; ipb < cur_pb_type->modes[imode].num_pb_type_children; ipb++) { + link_pb_types_circuit_model_rec(&(cur_pb_type->modes[imode].pb_type_children[ipb]), circuit_lib); + } + } + return; +} + +/* Check if the spice model structure is the same with the switch_inf structure */ +static +size_t check_circuit_model_structure_match_switch_inf(const t_switch_inf& target_switch_inf, + const CircuitLibrary& circuit_lib) { + size_t num_err = 0; + + VTR_ASSERT_SAFE(CIRCUIT_MODEL_OPEN_ID != target_switch_inf.circuit_model); + if (target_switch_inf.structure != circuit_lib.mux_structure(target_switch_inf.circuit_model)) { + vpr_printf(TIO_MESSAGE_ERROR, + "(File:%s,[LINE%d]) Mismatch in MUX structure between circuit model(%s, %s) and switch_inf(%s, %s)!\n", + __FILE__, __LINE__, + circuit_lib.circuit_model_name(target_switch_inf.circuit_model).c_str(), + CIRCUIT_MODEL_STRUCTURE_TYPE_STRING[size_t(circuit_lib.mux_structure(target_switch_inf.circuit_model))], + target_switch_inf.name, + CIRCUIT_MODEL_STRUCTURE_TYPE_STRING[size_t(target_switch_inf.structure)]); + num_err++; + } + return num_err; +} + + +/************************************************************************ + * Initialize and check circuit models defined in architecture + * Tasks: + * 1. Link the circuit model defined in pb_types and routing switches + * 2. Add default circuit model for any inexplicit definition + ***********************************************************************/ +void link_circuit_library_to_arch(t_arch* arch, + t_det_routing_arch* routing_arch) { + + vpr_printf(TIO_MESSAGE_INFO, "Linking circuit models to modules in FPGA architecture...\n"); + + /* Check Circuit models first*/ + VTR_ASSERT_SAFE( (NULL != arch) && (NULL != arch->spice) ); + + /* 1. Link the spice model defined in pb_types and routing switches */ + /* Step A: Check routing switches, connection blocks*/ + if (0 >= arch->num_cb_switch) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d]) Define Switches for Connection Blocks is mandatory in FPGA X2P support! Miss this part in architecture file.\n", + __FILE__,__LINE__); + exit(1); + } + + for (int i = 0; i < arch->num_cb_switch; i++) { + arch->cb_switches[i].circuit_model = link_circuit_model_by_name_and_type(arch->cb_switches[i].spice_model_name, + arch->spice->circuit_lib, SPICE_MODEL_MUX); + if (CIRCUIT_MODEL_OPEN_ID == arch->cb_switches[i].circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d])Invalid circuit model name(%s) of Switch(%s) is undefined in circuit models!\n", + __FILE__, __LINE__, arch->cb_switches[i].spice_model_name, arch->cb_switches[i].name); + exit(1); + } + /* Check the spice model structure is matched with the structure in switch_inf */ + if (0 < check_circuit_model_structure_match_switch_inf(arch->cb_switches[i], arch->spice->circuit_lib)) { + exit(1); + } + } + + /* Step B: Check switch list: Switch Box*/ + if (0 >= arch->num_switches) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d]) Define Switches for Switch Boxes is mandatory in FPGA X2P support! Miss this part in architecture file.\n", + __FILE__, __LINE__); + exit(1); + } + + for (int i = 0; i < arch->num_switches; i++) { + arch->Switches[i].circuit_model = link_circuit_model_by_name_and_type(arch->Switches[i].spice_model_name, + arch->spice->circuit_lib, SPICE_MODEL_MUX); + if (CIRCUIT_MODEL_OPEN_ID == arch->Switches[i].circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d])Invalid circuit model name(%s) of Switch(%s) is undefined in circuit models!\n", + __FILE__, __LINE__, arch->Switches[i].spice_model_name, arch->Switches[i].name); + exit(1); + } + /* Check the spice model structure is matched with the structure in switch_inf */ + if (0 < check_circuit_model_structure_match_switch_inf(arch->Switches[i], arch->spice->circuit_lib)) { + exit(1); + } + } + + /* Update the switches in detailed routing architecture settings*/ + for (int i = 0; i < routing_arch->num_switch; i++) { + switch_inf[i].circuit_model = link_circuit_model_by_name_and_type(switch_inf[i].spice_model_name, + arch->spice->circuit_lib, SPICE_MODEL_MUX); + if (CIRCUIT_MODEL_OPEN_ID == switch_inf[i].circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d])Invalid circuit model name(%s) of Switch(%s) is undefined in circuit models!\n", + __FILE__, __LINE__, switch_inf[i].spice_model_name, switch_inf[i].name); + exit(1); + } + } + + /* Step C: Find SRAM Model*/ + link_sram_inf(&(arch->sram_inf), arch->spice->circuit_lib); + + /* Step D: Find the segment spice_model*/ + for (int i = 0; i < arch->num_segments; i++) { + arch->Segments[i].circuit_model = link_circuit_model_by_name_and_type(arch->Segments[i].spice_model_name, + arch->spice->circuit_lib, SPICE_MODEL_CHAN_WIRE); + if (CIRCUIT_MODEL_OPEN_ID == arch->Segments[i].circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d])Invalid circuit model name(%s) of Segment(Length:%d) is undefined in circuit models!\n", + __FILE__ ,__LINE__, + arch->Segments[i].spice_model_name, + arch->Segments[i].length); + exit(1); + } + } + + /* Step E: Direct connections between CLBs */ + for (int i = 0; i < arch->num_directs; i++) { + arch->Directs[i].circuit_model = link_circuit_model_by_name_and_type(arch->Directs[i].spice_model_name, + arch->spice->circuit_lib, SPICE_MODEL_WIRE); + /* Check SPICE model type */ + if (CIRCUIT_MODEL_OPEN_ID == arch->Directs[i].circuit_model) { + vpr_printf(TIO_MESSAGE_ERROR, + "(FILE:%s, LINE[%d])Invalid circuit model name(%s) of CLB to CLB Direct Connection (name=%s) is undefined in circuit models!\n", + __FILE__ ,__LINE__, + arch->Directs[i].spice_model_name, + arch->Directs[i].name); + exit(1); + } + /* Copy it to clb2clb_directs */ + clb2clb_direct[i].circuit_model = arch->Directs[i].circuit_model; + } + + /* 2. Search Complex Blocks (Pb_Types), Link spice_model according to the spice_model_name*/ + for (int i = 0; i < num_types; i++) { + if (NULL != type_descriptors[i].pb_type) { + link_pb_types_circuit_model_rec(type_descriptors[i].pb_type, arch->spice->circuit_lib); + } + } + + vpr_printf(TIO_MESSAGE_INFO, "Linking circuit models to modules in FPGA architecture...Completed\n"); + + return; +} + +/************************************************************************ + * End of file : link_arch_circuit_lib.cpp + ***********************************************************************/ diff --git a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/check_circuit_library.h b/vpr7_x2p/vpr/SRC/fpga_x2p/base/link_arch_circuit_lib.h similarity index 72% rename from vpr7_x2p/libarchfpga/SRC/fpga_spice_include/check_circuit_library.h rename to vpr7_x2p/vpr/SRC/fpga_x2p/base/link_arch_circuit_lib.h index 4dd9d1307..1b134a78d 100644 --- a/vpr7_x2p/libarchfpga/SRC/fpga_spice_include/check_circuit_library.h +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/base/link_arch_circuit_lib.h @@ -23,7 +23,7 @@ ***********************************************************************/ /************************************************************************ - * Filename: check_circuit_library.h + * Filename: link_arch_circuit_lib.h * Created by: Xifan Tang * Change history: * +-------------------------------------+ @@ -37,8 +37,8 @@ * The following preprocessing flags are added to * avoid compilation error when this headers are included in more than 1 times */ -#ifndef CHECK_CIRCUIT_LIBRARY_H -#define CHECK_CIRCUIT_LIBRARY_H +#ifndef LINK_ARCH_CIRCUIT_LIB_H +#define LINK_ARCH_CIRCUIT_LIB_H /* * Notes in include header files in a head file @@ -47,14 +47,22 @@ */ /* Header files should be included in a sequence */ /* Standard header files required go first */ -#include "circuit_library.h" -/* Check points to make sure we have a valid circuit library */ -void check_circuit_library(const CircuitLibrary& circuit_lib); +CircuitModelId link_circuit_model_by_name_and_type(const char* circuit_model_name, + const CircuitLibrary& circuit_lib, + const enum e_spice_model_type& model_type); + +t_port* find_pb_type_port_match_circuit_model_port(const t_pb_type* pb_type, + const CircuitLibrary& circuit_lib, + const CircuitModelId& circuit_model, + const CircuitPortId& circuit_port); + +void link_circuit_library_to_arch(t_arch* arch, + t_det_routing_arch* routing_arch); #endif /************************************************************************ - * End of file : check_circuit_library.h + * End of file : link_arch_circuit_lib.h ***********************************************************************/ diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_api.c b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_api.c index 41b2c634c..5c4d1f132 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_api.c +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_api.c @@ -242,8 +242,10 @@ void vpr_fpga_verilog(t_vpr_setup vpr_setup, /* Initialize the number of configuration bits of all the grids */ vpr_printf(TIO_MESSAGE_INFO, "Count the number of configuration bits, IO pads in each logic block...\n"); /* init_grids_num_conf_bits(sram_verilog_orgz_type); */ - init_grids_num_conf_bits(sram_verilog_orgz_info); - init_grids_num_iopads(); + //init_grids_num_conf_bits(sram_verilog_orgz_info); + init_pb_types_num_conf_bits(sram_verilog_orgz_info); + //init_grids_num_iopads(); + init_pb_types_num_iopads(); /* init_grids_num_mode_bits(); */ dump_verilog_defines_preproc(src_dir_path, diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_pbtypes.c b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_pbtypes.c index 5db74a44f..f87ff45a7 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_pbtypes.c +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_pbtypes.c @@ -1751,6 +1751,7 @@ void dump_verilog_phy_pb_graph_node_rec(t_sram_orgz_info* cur_sram_orgz_info, /* update stamped sram counter */ stamped_sram_cnt += cur_pb_type->physical_mode_num_conf_bits; /* Check */ + if (stamped_sram_cnt != get_sram_orgz_info_num_mem_bit(cur_sram_orgz_info)) assert(stamped_sram_cnt == get_sram_orgz_info_num_mem_bit(cur_sram_orgz_info)); assert(stamped_iopad_cnt == iopad_verilog_model->cnt); /* Finish for primitive node, return */ diff --git a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_routing.c b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_routing.c index eb736e27e..76bf438d0 100644 --- a/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_routing.c +++ b/vpr7_x2p/vpr/SRC/fpga_x2p/verilog/verilog_routing.c @@ -2350,7 +2350,7 @@ void dump_verilog_routing_switch_box_unique_subckt(t_sram_orgz_info* cur_sram_or dump_verilog_formal_verification_sram_ports(fp, cur_sram_orgz_info, rr_gsb.get_sb_conf_bits_lsb(), rr_gsb.get_sb_conf_bits_msb(), - VERILOG_PORT_OUTPUT, is_explicit_mapping); + VERILOG_PORT_INPUT, is_explicit_mapping); fprintf(fp, "\n"); fprintf(fp, "`endif\n"); } @@ -3967,7 +3967,7 @@ void dump_verilog_routing_resources(t_sram_orgz_info* cur_sram_orgz_info, /* Create a snapshot on sram_orgz_info */ t_sram_orgz_info* stamped_sram_orgz_info = snapshot_sram_orgz_info(cur_sram_orgz_info); - /* Output unique side modules */ + /* Output unique side modules for (size_t side = 0; side < device_rr_gsb.get_max_num_sides(); ++side) { Side side_manager(side); for (size_t iseg = 0; iseg < device_rr_gsb.get_num_segments(); ++iseg) { @@ -3978,12 +3978,17 @@ void dump_verilog_routing_resources(t_sram_orgz_info* cur_sram_orgz_info, } } } + */ /* Output unique modules */ for (size_t isb = 0; isb < device_rr_gsb.get_num_sb_unique_module(); ++isb) { const RRGSB& unique_mirror = device_rr_gsb.get_sb_unique_module(isb); + /* dump_verilog_routing_switch_box_unique_module(cur_sram_orgz_info, verilog_dir, subckt_dir, unique_mirror, explicit_port_mapping); + */ + dump_verilog_routing_switch_box_unique_subckt(cur_sram_orgz_info, verilog_dir, + subckt_dir, unique_mirror, explicit_port_mapping); } /* Restore sram_orgz_info to the base */ diff --git a/vpr7_x2p/vpr/SRC/route/route_common.c b/vpr7_x2p/vpr/SRC/route/route_common.c index ad8f2d8eb..83b7c8070 100755 --- a/vpr7_x2p/vpr/SRC/route/route_common.c +++ b/vpr7_x2p/vpr/SRC/route/route_common.c @@ -20,6 +20,8 @@ #include "buffer_insertion.h" /* end */ +#include "rr_graph_builder_utils.h" + /* Xifan TANG: useful functions for pb_pin_eq_auto_detect */ void reassign_rr_node_net_num_from_scratch(); @@ -1214,7 +1216,18 @@ void print_route(char *route_file) { break; } - fprintf(fp, "%d ", rr_node[inode].ptc_num); + /* A kind of dirty fix for tileable routing, + * the track_ids is allocated by tileable routing. + * If the vector is not empty, it means tileable routing is enabled + * we need another function to get the track_id rather than ptc_num + */ + if (0 == rr_node[inode].track_ids.size()) { + fprintf(fp, "%d ", rr_node[inode].ptc_num); + } else { + /* Xifan Tang: for routing tracks, get the actual track ids */ + DeviceCoordinator cur_coord(ilow, jlow); + fprintf(fp, "%d ", get_rr_node_actual_track_id(&(rr_node[inode]), cur_coord)); + } /* Uncomment line below if you're debugging and want to see the switch types * * used in the routing. */