ros-industrial / ros2_canopen

CANopen driver framework for ROS2
https://ros-industrial.github.io/ros2_canopen/manual/rolling/
143 stars 63 forks source link

cogen_dcf vs generate_dcf #193

Closed jclinton830 closed 1 year ago

jclinton830 commented 1 year ago

Question

What is the difference between cogen_dcf vs generate_dcf? In the CMakeLists.txt within canopen_tests package these two are used to generate the dcf for different types of configs. No explanation is found in the documentation as to what is the deciding factor for the use of geenrate_dcf vs cogen_dcf.

Can someone shed some light here?

hellantos commented 1 year ago

cogen_dcf parses config files that are similar to ros_canopen. The goal is basically a compatability layer. Though at the moment it is not 100%. It also has other advantages such as setting a default config for all slaves. If you have many equal devices on the bus this can shorten the config considerably. Under the hood it uses generate_dcf.

generate_dcf is directly using configuration files based on lely_core library with our additional parameters. It leads to very long bus.yaml with more complex systems.

Basically, cogen_dcf is a newer development which should make configuration files shorter and more readable.

jclinton830 commented 1 year ago

@ipa-cmh thanks for that in depth answer.

gsalinas commented 11 months ago

@ipa-cmh I wanted to follow up on this: as you mentioned, cogen allows the use of a defaults dict for all slave devices. Is that all that it does? Does the defaults dictionary afford any advantage over using yaml's &, *, << syntax, e.g:

options:
  dcf_path: "@BUS_CONFIG_PATH@"

master:
  node_id: 1
  driver: "ros2_canopen::MasterDriver"
  package: "canopen_master_driver"
  sync_period: 10000

cia402_device_1: &cia402_device
  node_id: 2
  dcf: "cia402_slave.eds"
  driver: "ros2_canopen::Cia402Driver"
  package: "canopen_402_driver"
  period: 10
  revision_number: 0
  sdo:
    - {index: 0x60C2, sub_index: 1, value: 50} # Set interpolation time for cyclic modes to 50 ms
    - {index: 0x60C2, sub_index: 2, value: -3} # Set base 10-3s
    - {index: 0x6081, sub_index: 0, value: 1000}
    - {index: 0x6083, sub_index: 0, value: 2000}
  tpdo: # TPDO needed statusword, actual velocity, actual position, mode of operation
    1:
      enabled: true
      cob_id: "auto"
      transmission: 0x01
      mapping:
        - {index: 0x6041, sub_index: 0} # status word
        - {index: 0x6061, sub_index: 0} # mode of operation display
    2:
      enabled: true
      cob_id: "auto"
      transmission: 0x01
      mapping:
        - {index: 0x6064, sub_index: 0} # position actual value
        - {index: 0x606c, sub_index: 0} # velocity actual position
    3:
      enabled: false
    4:
      enabled: false
  rpdo: # RPDO needed controlword, target position, target velocity, mode of operation
    1:
      enabled: true
      cob_id: "auto"
      mapping:
      - {index: 0x6040, sub_index: 0} # controlword
      - {index: 0x6060, sub_index: 0} # mode of operation
    2:
      enabled: true
      cob_id: "auto"
      mapping:
      - {index: 0x607A, sub_index: 0} # target position
      - {index: 0x60FF, sub_index: 0} # target velocity

cia402_device_2:
  node_id: 3
  <<: *cia402_device
cia402_device_3:
  node_id: 4
  <<: *cia402_device
cia402_device_4:
  node_id: 5
  <<: *cia402_device
cia402_device_5:
  node_id: 6
  <<: *cia402_device
cia402_device_6:
  node_id: 7
  <<: *cia402_device

This would mean you don't need to distinguish between generate_dcf and cogen_dcf anymore, and as an added benefit if you have a CAN bus with multiple repeated actuators - for example, an arm whose joints are all alike on a wheeled platform whose wheels are all the same, but the wheels and arms are different, cogen defaults doesn't really support this well but native YAML syntax can. As far as I can tell this already just works if you write your bus.yml in this way and use generate_dcf; what advantages does cogen give you?

gsalinas commented 10 months ago

It seems I spoke too soon - I'd had a chance to try compiling but not running - and the answer appears to be that << is a proposed part of the YAML spec available in many implementations but not officially in YAML 1.2 and, crucially, not implemented by yaml-cpp, so this doesn't work without at least some further effort.