@@ -114,9 +114,11 @@ AnalyticalSolver::AnalyticalSolver(const APNetlist& netlist,
114114                                   float  ap_timing_tradeoff,
115115                                   int  log_verbosity)
116116    : netlist_(netlist)
117+     , atom_netlist_(atom_netlist)
117118    , blk_id_to_row_id_(netlist.blocks().size(), APRowId::INVALID())
118119    , row_id_to_blk_id_(netlist.blocks().size(), APBlockId::INVALID())
119120    , net_weights_(netlist.nets().size(), 1.0f)
121+     , ap_timing_tradeoff_(ap_timing_tradeoff)
120122    , log_verbosity_(log_verbosity) {
121123    //  Get the number of moveable blocks in the netlist and create a unique
122124    //  row ID from [0, num_moveable_blocks) for each moveable block in the
@@ -136,19 +138,38 @@ AnalyticalSolver::AnalyticalSolver(const APNetlist& netlist,
136138        num_moveable_blocks_++;
137139    }
138140
139-     if  (pre_cluster_timing_manager.is_valid ()) {
140-         for  (APNetId net_id : netlist.nets ()) {
141-             //  Get the atom net associated with the given AP net. When
142-             //  constructing the AP netlist, we happen to set the name of each
143-             //  AP net to the same name as the atom net that generated them!
144-             //  TODO: Create a proper lookup structure to go from the AP Netlist
145-             //        back to the Atom Netlist.
146-             AtomNetId atom_net_id = atom_netlist.find_net (netlist.net_name (net_id));
147-             VTR_ASSERT (atom_net_id.is_valid ());
148-             float  crit = pre_cluster_timing_manager.calc_net_setup_criticality (atom_net_id, atom_netlist);
149- 
150-             net_weights_[net_id] = ap_timing_tradeoff * crit + (1 .0f  - ap_timing_tradeoff);
151-         }
141+     update_net_weights (pre_cluster_timing_manager);
142+ }
143+ 
144+ void  AnalyticalSolver::update_net_weights (const  PreClusterTimingManager& pre_cluster_timing_manager) {
145+     //  If the pre-cluster timing manager has not been initialized (i.e. timing
146+     //  analysis is off), no need to update.
147+     if  (!pre_cluster_timing_manager.is_valid ())
148+         return ;
149+ 
150+     //  For each of the nets, update the net weights.
151+     for  (APNetId net_id : netlist_.nets ()) {
152+         //  Note: To save time, we do not compute the weights of nets that we
153+         //        do not care about for AP. This leaves their weights at 1.0 just
154+         //        in case they are accidentally used.
155+         if  (netlist_.net_is_ignored (net_id))
156+             continue ;
157+ 
158+         AtomNetId atom_net_id = netlist_.net_atom_net (net_id);
159+         VTR_ASSERT_SAFE (atom_net_id.is_valid ());
160+ 
161+         float  crit = pre_cluster_timing_manager.calc_net_setup_criticality (atom_net_id, atom_netlist_);
162+ 
163+         //  When optimizing for WL, the net weights are just set to 1 (meaning
164+         //  that we want to minimize the WL of nets).
165+         //  When optimizing for timing, the net weights are set to the timing
166+         //  criticality, which is based on the lowest slack of any edge belonging
167+         //  to this net.
168+         //  The intuition is that we care more about shrinking the wirelength of
169+         //  more critical connections than less critical ones.
170+         //  Use the AP timing trade-off term to linearly interpolate between these
171+         //  weighting terms.
172+         net_weights_[net_id] = ap_timing_tradeoff_ * crit + (1 .0f  - ap_timing_tradeoff_);
152173    }
153174}
154175
@@ -225,7 +246,11 @@ static inline void add_connection_to_system(size_t src_row_id,
225246void  QPHybridSolver::init_linear_system () {
226247    //  Count the number of star nodes that the netlist will have.
227248    size_t  num_star_nodes = 0 ;
249+     unsigned  num_nets = 0 ;
228250    for  (APNetId net_id : netlist_.nets ()) {
251+         if  (netlist_.net_is_ignored (net_id))
252+             continue ;
253+         num_nets++;
229254        if  (netlist_.net_pins (net_id).size () > star_num_pins_threshold)
230255            num_star_nodes++;
231256    }
@@ -248,13 +273,14 @@ void QPHybridSolver::init_linear_system() {
248273    //  TODO: This can be made more space-efficient by getting the average fanout
249274    //        of all nets in the APNetlist. Ideally this should be not enough
250275    //        space, but be within a constant factor.
251-     size_t  num_nets = netlist_.nets ().size ();
252276    tripletList.reserve (num_nets);
253277
254278    //  Create the connections using a hybrid connection model of the star and
255279    //  clique connnection models.
256280    size_t  star_node_offset = 0 ;
257281    for  (APNetId net_id : netlist_.nets ()) {
282+         if  (netlist_.net_is_ignored (net_id))
283+             continue ;
258284        size_t  num_pins = netlist_.net_pins (net_id).size ();
259285        VTR_ASSERT_DEBUG (num_pins > 1 );
260286
@@ -772,6 +798,8 @@ void B2BSolver::init_linear_system(PartialPlacement& p_placement) {
772798    triplet_list_y.reserve (num_nets);
773799
774800    for  (APNetId net_id : netlist_.nets ()) {
801+         if  (netlist_.net_is_ignored (net_id))
802+             continue ;
775803        size_t  num_pins = netlist_.net_pins (net_id).size ();
776804        VTR_ASSERT_SAFE_MSG (num_pins > 1 , " net must have at least 2 pins"  );
777805
0 commit comments