openfpga/src/fpga_sdc/sdc_mux_utils.cpp
/********************************************************************
 * Break combinational loops in FPGA fabric, which mainly come from 
 * loops of multiplexers.
 * To handle this, we disable the timing at configuration ports of routing multiplexers
 *
 * Return code:
 *   0: success
 *   1: fatal error occurred
 *******************************************************************/
Break combinational loops in FPGA fabric, which mainly come from
loops of multiplexers.
To handle this, we disable the timing at configuration ports of routing multiplexers

Return code:
0: success
1: fatal error occurred
Break combinational loops in FPGA fabric which mainly come from loops of multiplexers . To handle this we disable the timing at configuration ports of routing multiplexers Return code : 0 : success 1 : fatal error occurred
int print_sdc_disable_routing_multiplexer_configure_ports(std::fstream& fp,
                                                          const bool& flatten_names,
                                                          const MuxLibrary& mux_lib,
                                                          const CircuitLibrary& circuit_lib,
                                                          const ModuleManager& module_manager,
                                                          const ModuleId& top_module) {
  if (false == valid_file_stream(fp)) {
    return CMD_EXEC_FATAL_ERROR;
  }
  for (const MuxId& mux_id : mux_lib.muxes()) {
    const CircuitModelId& mux_model = mux_lib.mux_circuit_model(mux_id);
    if (CIRCUIT_MODEL_MUX != circuit_lib.model_type(mux_model)) {
      continue;
    }
    const MuxGraph& mux_graph = mux_lib.mux_graph(mux_id);
    std::string mux_module_name = generate_mux_subckt_name(circuit_lib, mux_model, 
                                                           find_mux_num_datapath_inputs(circuit_lib, mux_model, mux_graph.num_inputs()), 
                                                           std::string(""));
    ModuleId mux_module = module_manager.find_module(mux_module_name);
    VTR_ASSERT(true == module_manager.valid_module_id(mux_module));
    for (const CircuitPortId& mux_sram_port : find_circuit_regular_sram_ports(circuit_lib, mux_model)) {
      const std::string& mux_sram_port_name = circuit_lib.port_lib_name(mux_sram_port);
      VTR_ASSERT(true == module_manager.valid_module_port_id(mux_module, module_manager.find_module_port(mux_module, mux_sram_port_name)));
      if (CMD_EXEC_FATAL_ERROR == 
            rec_print_sdc_disable_timing_for_module_ports(fp,
                                                          flatten_names,
                                                          module_manager,
                                                          top_module,
                                                          mux_module,
                                                          format_dir_path(module_manager.module_name(top_module)),
                                                          mux_sram_port_name)) {
        return CMD_EXEC_FATAL_ERROR;
      }
      const std::string& mux_sram_inv_port_name = circuit_lib.port_lib_name(mux_sram_port) + INV_PORT_POSTFIX;
      VTR_ASSERT(true == module_manager.valid_module_port_id(mux_module, module_manager.find_module_port(mux_module, mux_sram_inv_port_name)));
      if (CMD_EXEC_FATAL_ERROR == 
            rec_print_sdc_disable_timing_for_module_ports(fp,
                                                          flatten_names,
                                                          module_manager,
                                                          top_module,
                                                          mux_module,
                                                          format_dir_path(module_manager.module_name(top_module)),
                                                          mux_sram_inv_port_name)) {
        return CMD_EXEC_FATAL_ERROR;
      }
    }
  }
  return CMD_EXEC_SUCCESS;
}
int print_sdc_disable_routing_multiplexer_configure_ports ( std :: fstream & fp , const bool & flatten_names , const MuxLibrary & mux_lib , const CircuitLibrary & circuit_lib , const ModuleManager & module_manager , const ModuleId & top_module ) { if ( false == valid_file_stream ( fp ) ) { return CMD_EXEC_FATAL_ERROR ; } for ( const MuxId & mux_id : mux_lib . muxes ( ) ) { const CircuitModelId & mux_model = mux_lib . mux_circuit_model ( mux_id ) ; if ( CIRCUIT_MODEL_MUX != circuit_lib . model_type ( mux_model ) ) { continue ; } const MuxGraph & mux_graph = mux_lib . mux_graph ( mux_id ) ; std :: string mux_module_name = generate_mux_subckt_name ( circuit_lib , mux_model , find_mux_num_datapath_inputs ( circuit_lib , mux_model , mux_graph . num_inputs ( ) ) , std :: string ( " " ) ) ; ModuleId mux_module = module_manager . find_module ( mux_module_name ) ; VTR_ASSERT ( true == module_manager . valid_module_id ( mux_module ) ) ; for ( const CircuitPortId & mux_sram_port : find_circuit_regular_sram_ports ( circuit_lib , mux_model ) ) { const std :: string & mux_sram_port_name = circuit_lib . port_lib_name ( mux_sram_port ) ; VTR_ASSERT ( true == module_manager . valid_module_port_id ( mux_module , module_manager . find_module_port ( mux_module , mux_sram_port_name ) ) ) ; if ( CMD_EXEC_FATAL_ERROR == rec_print_sdc_disable_timing_for_module_ports ( fp , flatten_names , module_manager , top_module , mux_module , format_dir_path ( module_manager . module_name ( top_module ) ) , mux_sram_port_name ) ) { return CMD_EXEC_FATAL_ERROR ; } const std :: string & mux_sram_inv_port_name = circuit_lib . port_lib_name ( mux_sram_port ) + INV_PORT_POSTFIX ; VTR_ASSERT ( true == module_manager . valid_module_port_id ( mux_module , module_manager . find_module_port ( mux_module , mux_sram_inv_port_name ) ) ) ; if ( CMD_EXEC_FATAL_ERROR == rec_print_sdc_disable_timing_for_module_ports ( fp , flatten_names , module_manager , top_module , mux_module , format_dir_path ( module_manager . module_name ( top_module ) ) , mux_sram_inv_port_name ) ) { return CMD_EXEC_FATAL_ERROR ; } } } return CMD_EXEC_SUCCESS ; }
Break combinational loops in FPGA fabric, which mainly come from
 loops of multiplexers.
Break combinational loops in FPGA fabric which mainly come from loops of multiplexers .
/* Iterate over the MUX modules */ /* Skip LUTs, we only care about multiplexers here */ /* Find the module name in module manager */ /* Go recursively in the module manager, 
     * starting from the top-level module: instance id of the top-level module is 0 by default 
     * Disable all the outputs of child modules that matches the mux_module id
     */