@@ -1336,33 +1336,7 @@ controller_interface::return_type ControllerManager::configure_controller(
1336
1336
return controller_interface::return_type::ERROR;
1337
1337
}
1338
1338
1339
- for (const auto & cmd_itf : cmd_itfs)
1340
- {
1341
- controller_manager::ControllersListIterator ctrl_it;
1342
- if (is_interface_a_chained_interface (cmd_itf, controllers, ctrl_it))
1343
- {
1344
- ros2_control::add_item (
1345
- controller_chain_spec_[controller_name].following_controllers , ctrl_it->info .name );
1346
- ros2_control::add_item (
1347
- controller_chain_spec_[ctrl_it->info .name ].preceding_controllers , controller_name);
1348
- ros2_control::add_item (
1349
- controller_chained_reference_interfaces_cache_[ctrl_it->info .name ], controller_name);
1350
- }
1351
- }
1352
- // This is needed when we start exporting the state interfaces from the controllers
1353
- for (const auto & state_itf : state_itfs)
1354
- {
1355
- controller_manager::ControllersListIterator ctrl_it;
1356
- if (is_interface_a_chained_interface (state_itf, controllers, ctrl_it))
1357
- {
1358
- ros2_control::add_item (
1359
- controller_chain_spec_[controller_name].preceding_controllers , ctrl_it->info .name );
1360
- ros2_control::add_item (
1361
- controller_chain_spec_[ctrl_it->info .name ].following_controllers , controller_name);
1362
- ros2_control::add_item (
1363
- controller_chained_state_interfaces_cache_[ctrl_it->info .name ], controller_name);
1364
- }
1365
- }
1339
+ build_controllers_topology_info (controllers);
1366
1340
1367
1341
// Now let's reorder the controllers
1368
1342
// lock controllers
@@ -4314,6 +4288,81 @@ void ControllerManager::update_list_with_controller_chain(
4314
4288
}
4315
4289
}
4316
4290
4291
+ void ControllerManager::build_controllers_topology_info (
4292
+ const std::vector<ControllerSpec> & controllers)
4293
+ {
4294
+ std::for_each (
4295
+ controller_chain_spec_.begin (), controller_chain_spec_.end (),
4296
+ [](auto & pair)
4297
+ {
4298
+ pair.second .following_controllers .clear ();
4299
+ pair.second .preceding_controllers .clear ();
4300
+ });
4301
+ std::for_each (
4302
+ controller_chained_reference_interfaces_cache_.begin (),
4303
+ controller_chained_reference_interfaces_cache_.end (), [](auto & pair) { pair.second .clear (); });
4304
+ std::for_each (
4305
+ controller_chained_state_interfaces_cache_.begin (),
4306
+ controller_chained_state_interfaces_cache_.end (), [](auto & pair) { pair.second .clear (); });
4307
+ for (const auto & controller : controllers)
4308
+ {
4309
+ if (is_controller_unconfigured (*controller.c ))
4310
+ {
4311
+ RCLCPP_DEBUG (
4312
+ get_logger (), " Controller '%s' is unconfigured, skipping chain building." ,
4313
+ controller.info .name .c_str ());
4314
+ continue ;
4315
+ }
4316
+ const auto cmd_itfs = controller.c ->command_interface_configuration ().names ;
4317
+ const auto state_itfs = controller.c ->state_interface_configuration ().names ;
4318
+
4319
+ for (const auto & cmd_itf : cmd_itfs)
4320
+ {
4321
+ controller_manager::ControllersListIterator ctrl_it;
4322
+ if (is_interface_a_chained_interface (cmd_itf, controllers, ctrl_it))
4323
+ {
4324
+ ros2_control::add_item (
4325
+ controller_chain_spec_[controller.info .name ].following_controllers , ctrl_it->info .name );
4326
+ ros2_control::add_item (
4327
+ controller_chain_spec_[ctrl_it->info .name ].preceding_controllers , controller.info .name );
4328
+ ros2_control::add_item (
4329
+ controller_chained_reference_interfaces_cache_[ctrl_it->info .name ], controller.info .name );
4330
+ }
4331
+ }
4332
+ // This is needed when we start exporting the state interfaces from the controllers
4333
+ for (const auto & state_itf : state_itfs)
4334
+ {
4335
+ controller_manager::ControllersListIterator ctrl_it;
4336
+ if (is_interface_a_chained_interface (state_itf, controllers, ctrl_it))
4337
+ {
4338
+ ros2_control::add_item (
4339
+ controller_chain_spec_[controller.info .name ].preceding_controllers , ctrl_it->info .name );
4340
+ ros2_control::add_item (
4341
+ controller_chain_spec_[ctrl_it->info .name ].following_controllers , controller.info .name );
4342
+ ros2_control::add_item (
4343
+ controller_chained_state_interfaces_cache_[ctrl_it->info .name ], controller.info .name );
4344
+ }
4345
+ }
4346
+ }
4347
+ for (const auto & [controller_name, controller_chain] : controller_chain_spec_)
4348
+ {
4349
+ RCLCPP_INFO (
4350
+ get_logger (), " Controller '%s' has %ld following controllers and %ld preceding controllers." ,
4351
+ controller_name.c_str (), controller_chain.following_controllers .size (),
4352
+ controller_chain.preceding_controllers .size ());
4353
+ RCLCPP_INFO_EXPRESSION (
4354
+ get_logger (), !controller_chain.following_controllers .empty (),
4355
+ fmt::format (
4356
+ " \t Following controllers are : {}" , fmt::join (controller_chain.following_controllers , " , " ))
4357
+ .c_str ());
4358
+ RCLCPP_INFO_EXPRESSION (
4359
+ get_logger (), !controller_chain.preceding_controllers .empty (),
4360
+ fmt::format (
4361
+ " \t Preceding controllers are : {}" , fmt::join (controller_chain.preceding_controllers , " , " ))
4362
+ .c_str ());
4363
+ }
4364
+ }
4365
+
4317
4366
rclcpp::NodeOptions ControllerManager::determine_controller_node_options (
4318
4367
const ControllerSpec & controller) const
4319
4368
{
0 commit comments