GDay guys! I'm playing with CANOpen Slave Device in CoDeSys 3.5.11.0 and trying to achieve behaviour of any off-the-shelf CANOpen slave device (encoder, inclinometer, etc...) inside CoDeSys, particularly with SDOs. Usually then you use any CANOpen configuration software (e.g. IFM Maintenance) to change SDO parameter of any CANOpen slave, the change is either automatically retained OR you should write "SAVE" string to 0x1010h and power cycle device.
Unfortunately I could not achieve similar behaviour inside CoDeSys. Please see a picture attached.
I was trying to map SDO variable directly to persistent retain global variable list, but every time I reboot my PLC, retain variable is reinitialised with default value "10" from the object dictionary settings. These settings are also transfered to EDS file during export, so I believe that pre-setting of these values is ESSENTIAL for my end-customer, because everyone expects professionally made EDS file supplied with the end-product. Right?
I've also tried to wipe away default value and map SDO value to a volatile memory variable and then overwrite it with retained value in external program using CAA CIA 405 library as well as CANopen_Device.ObjectDictionary.WriteObjectByAddress(...) method during main program initialization. Nothing works - the value is always "0"!
Without having the application it's a little bit difficult to help.
But I would suppose that it's a problem in initialization order.
When the program starts, first of all the retains are initialized.
Then the CANopen Slave stack starts and writes the default (which you configured before in the editor) to the object dictionary.
This of course overwrites your retain value. The CANopen slave stack does not know that the object is mapped to a retain variable.
There are different possible solutions which depend on your specific use case:
1. Setting the default value in object dicitionary configurator
The CANopen Slave then awakes with this default value and it is also part of the EDS file. OR
2. Do not map a retain variable to the object and backup the value of the object to a retain variable.
So you could for example read the object in PLC_PRG and copy the value to a retain variable (the polling method).
Or you could register to the write event of the object dictionary and backup the value to a retain variable in write event (the event method).
In first PLC cycle you could copy the retain variable back to the object dictionary by using WriteObjectByAddress.
With this solution the retain variable is independent from CANopenSlave stack and will not be overwritten.
Of course the retain value is not part of the EDS file. But this is the same behaviour like for any off-shelf slave out there.
The EDS file always contains the off-shelf default values. Never the last stored value.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Hi eschwellinger! Thank you for reply, I always use method described above. I am using IFM CR710S combined Standard/Safety PLC and this code sits on Safety PLC side. I think the problem is that safe retain GVL, safe PLC_PRG, non-safe PLC_PRGs and CANOpen Slave Device stack on Safety PLC have either different starting sequences OR non-safe PRG (to which I am only allowed to map CANOpen Slave Device variables) are randomly "floating" within task time because safe data processing takes highest priority. So I decided to move communication and retain processing code from Safety PLC to Standard PLC. Will see how it will go.
π
1
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
I do not find the answer informative. I have the same problem: I would like to configure my CR711S standard side CANopen device parameters by using CANopen SDO. I can write the variables and read them. The device answers also to save commands 0x1010:1 and 3 with ack but every time I reboot the parameter (variable) is not stored.
I just need to understand how to map a "persistent" variable into the OD so that I can write it once over CAN (SDO) and the value will be stored nonvolatile
Last edit: juha-herrala 2022-09-29
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
GDay guys! I'm playing with CANOpen Slave Device in CoDeSys 3.5.11.0 and trying to achieve behaviour of any off-the-shelf CANOpen slave device (encoder, inclinometer, etc...) inside CoDeSys, particularly with SDOs. Usually then you use any CANOpen configuration software (e.g. IFM Maintenance) to change SDO parameter of any CANOpen slave, the change is either automatically retained OR you should write "SAVE" string to 0x1010h and power cycle device.
Unfortunately I could not achieve similar behaviour inside CoDeSys. Please see a picture attached.
I was trying to map SDO variable directly to persistent retain global variable list, but every time I reboot my PLC, retain variable is reinitialised with default value "10" from the object dictionary settings. These settings are also transfered to EDS file during export, so I believe that pre-setting of these values is ESSENTIAL for my end-customer, because everyone expects professionally made EDS file supplied with the end-product. Right?
I've also tried to wipe away default value and map SDO value to a volatile memory variable and then overwrite it with retained value in external program using CAA CIA 405 library as well as CANopen_Device.ObjectDictionary.WriteObjectByAddress(...) method during main program initialization. Nothing works - the value is always "0"!
Any suggestions how to fix this issue?
Last edit: Alexey 2021-02-16
more posts ...
Hi Alexey,
Without having the application it's a little bit difficult to help.
But I would suppose that it's a problem in initialization order.
When the program starts, first of all the retains are initialized.
Then the CANopen Slave stack starts and writes the default (which you configured before in the editor) to the object dictionary.
This of course overwrites your retain value. The CANopen slave stack does not know that the object is mapped to a retain variable.
There are different possible solutions which depend on your specific use case:
1. Setting the default value in object dicitionary configurator
The CANopen Slave then awakes with this default value and it is also part of the EDS file. OR
2. Do not map a retain variable to the object and backup the value of the object to a retain variable.
So you could for example read the object in PLC_PRG and copy the value to a retain variable (the polling method).
Or you could register to the write event of the object dictionary and backup the value to a retain variable in write event (the event method).
In first PLC cycle you could copy the retain variable back to the object dictionary by using WriteObjectByAddress.
With this solution the retain variable is independent from CANopenSlave stack and will not be overwritten.
Of course the retain value is not part of the EDS file. But this is the same behaviour like for any off-shelf slave out there.
The EDS file always contains the off-shelf default values. Never the last stored value.
Hi eschwellinger! Thank you for reply, I always use method described above. I am using IFM CR710S combined Standard/Safety PLC and this code sits on Safety PLC side. I think the problem is that safe retain GVL, safe PLC_PRG, non-safe PLC_PRGs and CANOpen Slave Device stack on Safety PLC have either different starting sequences OR non-safe PRG (to which I am only allowed to map CANOpen Slave Device variables) are randomly "floating" within task time because safe data processing takes highest priority. So I decided to move communication and retain processing code from Safety PLC to Standard PLC. Will see how it will go.
I do not find the answer informative. I have the same problem: I would like to configure my CR711S standard side CANopen device parameters by using CANopen SDO. I can write the variables and read them. The device answers also to save commands 0x1010:1 and 3 with ack but every time I reboot the parameter (variable) is not stored.
I just need to understand how to map a "persistent" variable into the OD so that I can write it once over CAN (SDO) and the value will be stored nonvolatile
Last edit: juha-herrala 2022-09-29