Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Activity
    jemeador
    @jemeador
    Hello! I'm experiencing a deadlock in the Lely LoopDriver on RunWrite. We invoke Deferto RunWrite on a Driver, but it seems that the loop thread is blocked indefinitely
    8 replies
    jemeador
    @jemeador
    I'm seeing a lot of Boot failure D even though the response from the slave node is perfectly fine. In debug mode, it seems this is associated with an assertion failure in the nmt.c file.
    5 replies
    Romeo Perlstein
    @RomePerl14
    Hello! Im not sure if this has been answered vefore but Im currently using LelyCANopen specifically jsut just the CAN protocol (long story). I’m having issues in two places: reading a writing commands to the bus, and being able to set Rx and Tx queue lengths. Currently my stack involves cr
    Agony I pressed enter too early
    Romeo Perlstein
    @RomePerl14
    Currently my stack involves me creating all of the necessary variables like io::Context, io::Poll, etc so that I can create a CAN channel (using io::CanChannel). Then, I just use CanChannel.write and CanChannel.read to write and read messages to the bus. I’m having issues however where I believe the Tx or Rx buffers become filled making me have ti reset the CAN bus outside of the code (im using the PCAN_USB adapter). After a little of successfully sending and receiving CAN packets Im thrown a what(): write: resource temporarily unavailable, which I assume is because the Rx queue is not being cleared. Sorry if any of this is extremely wrong, Im new to coding and especially new to CAN
    5 replies
    Tuna Ozkoc
    @tozkoc_gitlab
    Hello! I am still learning the concepts of the CANOpen and the C++. I would like to do a Block Downloadbut couldn't figure out how to do it. I need to Write/Download 200+ bytes. I have found a method in the API called AsyncBlockWrite. I've got an error when I'm trying to use it:
    unsigned char val[] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
    asyncMaster->AsyncBlockWrite<unsigned char (&)[]>(asyncMaster->get_executor(), asyncMaster->id(), idx, subidx, std::forward<unsigned char[]>(
                    reinterpret_cast<unsigned char (&)[]>(val)));
    17 replies
    image.png
    JHertig
    @JHertig
    Can someone point me to documentation on how to configure the AsyncWrite function of the NodeDriver. I have been implementing by putting a "try-catch" around it and getting an exception when a timeout occurs or other error. I get these on occassion when sending transmit SDOs to devices that usually work. Especially the first time. I would like to know the reason for the exception and if it is a timeout, if and how I can increase the timeout duration.
    2 replies
    Tuna Ozkoc
    @tozkoc_gitlab

    I am using dcfgen to dcfs. But whenever I use dcfgen to configure slaves it creates a .bin file named slave_2.bin. Then I use that file in my AsyncMaster constructor but it gives an error called:Parameter is incorrect. This was the yaml file I was using:

    # options:
    #   dcf_path: ""
    #   heartbeat_multiplier: 3.0
    
    master:
      node_id: 1
      # baudrate: 1000 # kbit/s
      # vendor_id: 0x12345678
      # product_code: 0x12345678
      # revision_number: 0x12345678
      # serial_number: 0x12345678
       heartbeat_multiplier: 3.0
       heartbeat_consumer: true
      # heartbeat_producer: 2000 # ms
      # emcy_inhibit_time: 0 # 100 us
      sync_period: 1000000 # us
      # sync_window: 0 # us
      # sync_overflow: 0
      # error_behavior: {1: 0x00}
      # nmt_inhibit_time: 0 # 100 us
      # start: true
      # start_nodes: true
      # start_all_nodes: false
      # reset_all_nodes: false
      # stop_all_nodes: false
      # boot_time: 0 # ms
    
    slave_2:
      dcf: "cpp-slave.eds"
      # dcf_path: ""
      node_id: 2
      # revision_number: 0x12345678
      # serial_number: 0x12345678
      # heartbeat_multiplier: 3.0
       heartbeat_consumer: true
       heartbeat_producer: 1000 # ms
      # error_behavior: {}
      # rpdo:
      #   1:
      #     enabled: true
      #     cob_id: auto
      #     transmission: 0x01
      #     inhibit_time: 0 # 100 us
      #     event_timer: 0 # ms
      #     mapping:
      #       - {index: 0x4000, sub_index: 0x00}
      # tpdo:
      #   1:
      #     enabled: true
      #     cob_id: auto
      #     transmission: 0x01
      #     inhibit_time: 0 # 100 us
      #     event_timer: 0 # ms
      #     sync_start: 0
      #     mapping:
      #       - {index: 0x4001, sub_index: 0x00}
      # boot: true
      # mandatory: false
      # reset_communication: true
      # software_file: "slave_v1.2.3.bin"
      # software_version: 0x00010203
      # restore_configuration: 0x00
      # sdo:
      #   - {index: 0x5000, sub_index: 0x00, value: 42}

    And this is the error:

    error: C:/Users/tuna.ozkoc/Desktop/lelyson/lely-core/python/dcf-tools/slave_2.bin: The parameter is incorrect.
    4 replies
    Tuna Ozkoc
    @tozkoc_gitlab
    Hi again! What is the proper way of the terminating a slave/master without using a signal handler? I am using Ixxat devices for the communication.
    4 replies
    IanMcCutcheon
    @IanMcCutcheon
    We have a slave eds file that defines some subindex types as REAL32 and sets the default values to non-zero values such as -10.0, 0.0034. DCFGEN is reporting that the values are invalid. Is it because the regex parser in dcfgen does not appear to be allowing the decimal point? Is there a way to have floating point values for defaults for REAL32 types?
    2 replies
    Tuna Ozkoc
    @tozkoc_gitlab
    Hello again! How can I get the nmt states of master and slave?
    2 replies
    ABog
    @abog_gitlab

    Hi,
    we are programming an STM32 slave device which needs to send data based on an internal event.
    The project was initially based on the Lely lpc17xx example so it is only c-code, no c++.
    Reading and writing SDOs is no issue, but we wanted to use a TPDO for the event based message.
    In the TPDO communication parameters (0x1800), the transmission type was set to 0xFF (also tested with 0xFE).
    (COB-ID used by TPDO was not very clear and is set to 0x00000180), and in the TPDO mapping (0x1A00), several objects were mapped.
    Most of the documentation mentioned the use of WriteEvent (or similar, but this is related to c++ code)
    and we were unable to figure out which command to use to trigger the message as defined in 0x1A00.

    We added the following line to create the TPDO
    m_tpdo1 = co_tpdo_create(m_net1, m_dev1, 1);
    --> lely-core/src/co/tpdo.c:271: debug: creating Transmit-PDO 1

    3 replies

    We have done some tests, but do not see any TPDO-related data coming in over the CAN-bus...
    co_tpdo_event(m_tpdo1); returns -1
    co_tpdo_sync(m_tpdo1, 0); returns 0
    co_dev_tpdo_event(m_dev1, 0x1800, 0x00); is a void function, so no idea what is happening...

    How can we trigger the TPDO message, or are we doing something wrong elsewhere?

    Tuna Ozkoc
    @tozkoc_gitlab
    Hi! When slave is booting, master and slave terminates for no reason. It only occurs when at least one TPDO and one RPDO in slave's OD. Could you please help me?
    2 replies
    image.png
    image.png
    Tomasz Adamczyk
    @tomasz_adamczyk_gitlab

    Hello! Is there an example how to use SubmitRead() and SubmitWrite() functions? To be precise, I cannot uderstand what arguments shall be passed to the confirmation function. Im more familiar with C than C++ (templates, references) so i have trouble deducing how it should work from the header alone.

    Im trying to use SubmitWrite() / SubmitRead() from separate thread to request SDO readas/writes and process the result. As far as i understand, this call should be asynchronous and will call the confirmation function when SDO operation completes. Does it work as i expect?

    2 replies
    Russell Bingham
    @bingham-pliant

    Hi to all, especially @jseldent_gitlab (thanks as always for your time and great code) - Question about understanding a particular Lely error message while initializing hardware.

    I have a mostly complete Lely distributed compute architecture (several Beaglebones linked via CANopen) that works very consistently over vcan. I've gotten it to work intermittently over a physical bus (Beaglebone DCAN1 specifically), but it's somewhat inconsistent and dependent on several different initializations being correct. Currently working on getting the initializations up to production quality and am hitting the same error across several systems.

    Everything seems to boot fine and throw no errors if the can1 device is set up with loopback on, but if I set up can1 with loopback off, Lely throws a "warning: error writing CAN frame: Operation canceled" (thrown after initializing the whole OD, including entering operational mode and creating PDOs). In both cases, no CAN messages seem to actually be getting through to the physical bus, because my remote nodes see no traffic (though candump does show local "traffic" when loopback is on).

    I'm not exactly sure if this is a SocketCAN initialization problem or a Lely initialization one -- SocketCAN can1 gets set up with Baudrate 1000000 throwing no errors, so I expect it's on the Lely side (though the loopback behavior makes little sense). My master .yaml file and various EDS files all match the 1000kbit baud rate, though admittedly I've done quite a bit of tinkering with configuration settings while developing and it's possible I'm missing one somewhere.

    I've gotten messages to work over wires successfully in the past, but am stumped about what I could be missing now. If anyone has seen this behavior before or could explain what this warning means at a functional level, would be much appreciated.

    2 replies
    AdrienMatricon
    @AdrienMatricon

    Hello,
    I've been using v2.3.0 of the library for a while, and I've recently come upon a strange behavior. There are currently some temporary communication issues over my CAN bus (for an external reason I've yet to identify), which result in this :

    2022-08-25 12:30:44:289 CANopen slave: 0x20: Sent EMCY message with code 0x8130 (0x81 means Communication)
    2022-08-25 12:30:44:295 CANopen master: warning: error writing CAN frame: Operation canceled
    2022-08-25 12:30:44:330 CANopen slave: 0x20: NMT: Entering pre-operational state

    with the device then staying in the pre-operational state and the master never telling it to go back to the operational state.
    It's not the first time I've seen an EMCY message with code 0x8130 (again, for reasons external to the library, or at least I think so), but usually after that the master brings the situation back to normal, so I have to assume this case is different due to the canceled write operation. Do you have any idea why this is happening? I would have assumed that the NMT message about entering the pre-operational state would have caused the master to react or something

    5 replies
    ABog
    @abog_gitlab

    Hello,
    we are running the Lely CANopen stack (v2.2.7) on a STM32F4 slave device (based on the Lely lpc17xx example).
    When requesting data from an SDO: 0x60D [ 0x40 0xFF 0x5F 0x01 0x00 0x00 0x00 0x00 ],
    we normally get the following logging: /lely-core/src/co/ssdo.c:1075: debug: SSDO: 5FFF:01: received upload request
    and we get a reply message: 0x58D [0x43 0xFF 0x5F 0x01 0x3F 0xE7 0x2F 0x00].

    After receiving the SDO can message we forward it to can_net_recv and print it,
    but we do not always get the received upload request and would like to understand what is happening.

        if (m_CAN1_enabled && peripheralInterface().m_can1->receive(receiveMessage1))
        {
            // Process received CAN frames.
            can_msg message1;
            message1.id = receiveMessage1.id;
            message1.len = receiveMessage1.dataLength;
            for (int i = 0; i < message1.len; ++i) { message1.data[i] = receiveMessage1.data[i]; }
            int result1 = can_net_recv(m_net1, &message1);
            // Print received Message (on uart)
            printf("CAN1 %03lu: Message %03lX [ ", (unsigned long)m_receiveCount1, (unsigned long)receiveMessage1.id);
            ...
    3 replies
    pitb
    @pitb:matrix.org
    [m]
    Hello,
    I have the situation that there are already some slave nodes on the bus sending heartbeats. I'm using AsyncMaster but OnHeartbeat is not reacting on theses heartbeats. Is there any possibility with AsyncMaster to react on theses incoming heartbeats and therefor detect which slaves are already online.
    1 reply
    pitb
    @pitb:matrix.org
    [m]

    I'm using AsyncMaster like shown in the tutorial. I get a debug message

       ssdo.c:958: debug: SSDO: 2012:02: received download request

    but OnRpdoWrite of the master is not called. I have overwritten this method by my own one but it's never called. How can read in the received SDOs?

    1 reply
    pitb
    @pitb:matrix.org
    [m]

    This is an excerpt from a longer candump

    <0x701> [1] 7f 
    <0x70b> [1] 7f 
    <0x70c> [1] 7f 
    <0x60b> [8] 2f 80 12 03 3d 00 00 00 
    <0x58b> [8] 60 80 12 03 00 00 00 00 
    <0x60b> [8] 2b 13 20 01 02 00 00 00 
    <0x58b> [8] 60 13 20 01 00 00 00 00 
    <0x60b> [8] 23 30 20 01 06 00 00 00 
    <0x58b> [8] 60 30 20 01 00 00 00 00 
    <0x60b> [8] 23 30 20 02 02 01 01 01 
    <0x58b> [8] 60 30 20 02 00 00 00 00 
    <0x60b> [8] 23 30 20 03 02 00 00 00 
    <0x58b> [8] 80 30 20 03 10 00 07 06 
    <0x60b> [8] 23 01 20 01 01 00 00 00 
    <0x58b> [8] 60 01 20 01 00 00 00 00 
    <0x63d> [8] 23 12 20 02 00 00 00 02 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x63d> [8] 23 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x701> [1] 7f 
    <0x70b> [1] 7f 
    <0x70c> [1] 7f

    The master has the id 0x3d. The other nodes are sending the <0x70x> [1] 7f which as I know is the heartbeat.

    OnWrite is not listed in the documentation for AsyncMaster or BasicMaster. Where can I find it?
    pitb
    @pitb:matrix.org
    [m]
    BasicSlave has OnWrite and according to my grep output also Device.
    With OnWrite from Device it is working. Thanks.
    pitb
    @pitb:matrix.org
    [m]

    :point_up: Edit: This is an excerpt from a longer candump

    <0x701> [1] 7f 
    <0x70b> [1] 7f 
    <0x70c> [1] 7f 
    <0x63d> [8] 23 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x701> [1] 7f 
    <0x70b> [1] 7f 
    <0x70c> [1] 7f

    The master has the id 0x3d. The other nodes are sending the \<0x70x> [1] 7f which as I know is the heartbeat.

    pitb
    @pitb:matrix.org
    [m]
    I'm now receiving the SDO from the slaves via OnWrite. There I only print out idx and subidx. But the response on the bus is send out twice:
    <0x63d> [8] 23 12 20 02 00 00 00 02 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x63d> [8] 23 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00 
    <0x5bd> [8] 60 12 20 02 00 00 00 00
    Nazarii Obukhovskyi
    @nazarii.obukhovskyi_gitlab
    Hello.
    Is there any particular reason why coapp: add master/slave constructors using a static device description functionality is not included in v.2.3.1 release?
    pitb
    @pitb:matrix.org
    [m]

    Hello,
    I'm using FiberDriver for my slave node. According to the documentation Wait can only be called from inside the task submitted to the executor. So I use the following from outside the task to write to the node and see if it was successful:

        auto future = m_pWP1->AsyncWrite(0x1280, 3, 4, 1000ms);
        while (!future.is_ready()) {
            usleep(10000);
        }
        auto result = future.get();
        if (result.has_error() )
            std::cout << "error on write" << std::endl;

    I think it's also possible to use SubmitWrite, but then I need a callback function. Is there a simpler way like using Wait to write e.g. from a main task to the FiberDriver node?

    1 reply
    Nick
    @Nick17059601_twitter

    Hi,
    I'm running master & slave devices with coctl on a virtual socketcan. When I try to put the slave into preop, it automatically transitions back to operational. Why is this happening?
    Master:

    nick@wlink:~$ coctl vcan0 /etc/coctl.dcf
    [1] set network 1
    [1] OK
    [2] set id 1
    [2] OK
    [3] init 3
    coctl: error: unable to set bitrate of vcan0 to 250000 bit/s
    coctl: NMT: entering reset application state
    coctl: NMT: entering reset communication state
    coctl: NMT: running as master
    coctl: NMT: entering pre-operational state
    coctl: NMT: entering operational state
    [3] OK
    [4] 20 preop
    1 20 BOOT_UP
    1 20 USER BOOT A (The CANopen device is not listed in object 1F81.)
    [4] OK

    Slave:

    nick@wlink:~$ coctl vcan0 ~/eds/rm9000.DCF
    [1] set network 1
    [1] OK
    [2] set id 20
    [2] OK
    [3] init 3
    coctl: error: unable to set bitrate of vcan0 to 250000 bit/s
    coctl: NMT: entering reset application state
    coctl: NMT: entering reset communication state
    coctl: NMT: running as slave
    coctl: NMT: entering pre-operational state
    coctl: NMT: entering operational state
    [3] OK
    [4] coctl: NMT: entering pre-operational state
    coctl: NMT: entering operational state
    2 replies
    pitb
    @pitb:matrix.org
    [m]
    Meanwhile I have a running system based on AsyncMaster. I registered a callback function for OnWrite. Sometimes this callback function is called twice when SDOs are received. I can see it when I compare my received data with the listing from candump. The method loop.run is called from inside a thread and the rest is running in another thread. What could be the reason that OnWrite is called twice when one SDO is received?
    pitb
    @pitb:matrix.org
    [m]
    Found it by myself. The entry for object 1200 in the dcf file was wrong. Now I get single messages.
    jemeador
    @jemeador
    Would it be possible to change the dcf_txt and dcf_bin path based on the SW version 0x100A read from a device? It looks like the path must be determined before the master can be created and cannot be changed. My use case is that the manufacturer updates the revision number and other fields between firmware versions, and I would like my software to be compatible with multiple versions of the firmware if there aren't substantial differences. I'd like to avoid destroying and recreating the Lely thread or AsyncMaster object if possible.
    2 replies
    Nick
    @Nick17059601_twitter
    I have a question concerning handling concurrency in the Lely stack.
    In my application I have multiple slaves (derived from BasicSlave) that I am managing. I spin up a separate thread that regularly calls update functions on each of the slaves. The update function reads/writes to slave’s object dictionaries using the Get and Set functions. It all seems to be working for now. But my question is about whether it is safe to be updating the object dictionary from another thread like this.
    I see in the ‘ev’ folder there are a bunch of modules relating to event loops, executors, fibres, etc. Should I be using the constructs provided here instead of just spinning up my own thread? So far I haven’t been able to get my head around how all this works. Is there some documentation or examples somewhere on how to use this (event loops, executors, timers, etc)?
    2 replies
    Tomasz Adamczyk
    @tomasz_adamczyk_gitlab

    I need to collect a number of samples on a embedded device store them into a local buffer (this has to be fast) and transfer them via CANopen (this can be slow).

    I can define OCTET_STRING type object in object dictionary, copy data to it using co_dev_set_val(IDX_ARRRAY, SUB_ARRAY, local_buffer, sizeof(local_buffer))
    and read it via SDO on the other end. This works as expected, but the problem is co_dev_set_val() copies data from local_buffer to internal one, allocated by malloc() inside lely-core library.

    Is it possible to write directly to the internal buffer without copying data? Slave device is a MCU with limited amount of memory.
    Getting pointer to internal buffer and its size would be enough. A function which writes data to internal buffer and checks for buffer overflow would be perfect.

    8 replies
    Nick
    @Nick17059601_twitter

    I've got a slave device running the Lely stack. I've noticed that when I try to read the slave's entire object dictionary with a tool like Kefex CoEdit I get errors. I load the slave EDS file into CoEdit, set the node ID, then hit "read all values". It then sends lots of SDO request to try read all the values from the object dictionary. I'm getting an error for every second or third subindex that it tries to read. If I ignore errors and proceed every second/third value is missing. If I read the missing values individually the load fine.

    Maybe the slave is having trouble keeping up with replying to the SDO requests when they are coming in quickly? I'm running the slave on a linux virtual machine with an IXXAT can-to-USB converter.
    The same problem occurs when I run the example slave (with cpp-slave.eds) from the tutorial, so it doesn't seem to be specific to my code.

    29 replies
    AdrienMatricon
    @AdrienMatricon

    Hello,
    What would trigger this log?

    warning: error writing CAN frame: Operation canceled

    I'm getting it from time to time since I upgraded the system I'm working with, and I'm not sure if it's because I'm using the library wrong somehow and it just started showing, or if there's a deeper issue at the driver/OS level (also if you have any advice on how to investigate this I'm all ears)

    9 replies
    Nick
    @Nick17059601_twitter
    image.png
    Nick
    @Nick17059601_twitter
    image.png
    ABog
    @abog_gitlab
    "What to do with the CANopen Vendor ID for an internal CAN network?"
    We have programmed our own CANopen master and also created multiple CANopen slaves, but these are only used internally and are not supposed to be used outside our system.
    Do you always need to buy/pay for a CiA Vendor ID? https://www.can-cia.org/services/canopen-vendor-id/
    Is it fine to default the VendorID to 0x00000000? Or should we use another number? Or buy one?
    1 reply
    Pedro Ribeiro
    @pedro-m-ribeiro
    Hello,
    I'm working a simple ROS driver using lely canopen library that is based on the master.cpp example.
    The driver was tested with a canopen device and is communicating as expected however it seems that the event loop is hogging the CPU and the CPU usage is always 100%.
    I've tried using poll_one() or poll() and the result is the same. With poll_one() I can control the rate however if I reduce it too much I start getting timeout errors.
    Is there a way to reduce the CPU usage?
    2 replies
    JHertig
    @JHertig
    Is it possible to prevent a master from resetting the bus when it starts up? Its normal for the Master node when reset to automatically send a NMI 82 command. I am tasked to prevent that in our case. Is there a way to do that?
    4 replies
    JHertig
    @JHertig
    I keep doing Google searches one Lely firmware updates for upgrading slaves but when I follow the links I come up empty. Is there any documentation on how this is done?
    2 replies
    JHertig
    @JHertig
    I'm having a problem with sending SDO's where sometimes the SDO fails with the error being written to stderr: "warning: error writing CAN frame: Operation canceled" . I need to know when this fails in my code. Currently I'm doing this:
    try {
    Wait( AsyncWrite( idx, subIdx, val, std::chrono::milliseconds( timeout ) ) );
    } catch (canopen::SdoError& e) {
    Where "val" is a std:vector<uint8_t>. But I'm not getting an exception.
    2 replies
    ProgMatFiz
    @ProgMatFiz
    Hello I want to control 6 motors (aka 6 slaves) with one master. Is it possible to implement it with just only one yml file? (setting for each slave for example tpdos, rpdos etc individually with just one master)? The motors have the same configuration, there are just minor differences in the default values in the registers (each one has a 402 profile).
    7 replies
    JacobJBeck
    @JacobJBeck
    How does remote PDO mapping work? I'm trying to control a CiA 402 servo drive with defined PDOs that are not enabled by default and have fixed mappings. If I write to the 'Communication Parameter Object' to enable some TPDO, I can see the data in candump, but OnRpdoWrite() is not called. If I define TPDOs in the devices.yaml file with enabled, cob_id, and transmission parameters (not setting mapping as this is fixed), I get this error on startup: error: SDO abort code 06090030 received while updating the configuration of node 02: Invalid value for parameter.
    Perry Hung
    @fractalbroccoli_twitter
    why does setting --disable-diag also disable generation of tools? I need dcf2c and friends, but I also want to get rid of the spew from :
    NMT: entering reset application state NMT: entering reset communication state NMT: running as master NMT: entering pre-operational state NMT: entering operational state