We are interested in creating the following object (check the picture). The object is from the simple type gxData (ID = 1) but it is value should be an octet-string[12] (date-time format).
We are facing problem with the initialization of the gxData value, should it be initialized as GX_OCTECT_STRING or as GX_DATETIME?
Can you please show us how to create this type of object? while and after creating it how are we supposed to fill it with real date-time values?
NB: we tried to create this object as GX_DATETIME and we tried to read it and it is causing a crashing issue, after following the error we are supposing that the type datetime is not handled well.
Sorry but we did not get what do you mean and what are we supposed to do. Can you please write for us an example code in order to understand how to create this object?
When we tried to create this object using GX_DATETIME and we tried to capture a profile generic having one of his columns equal to this object, it is crashing. There is a problem in the function dlms_setData() used in the getProfileGenericBufferColumnSizes() function.
Get the latest version. It's now released and there is support for PLC. We'll start to make an example server tomorrow. There is also support for the bit-string array, etc. Let me know if you have any problems. There is also a fixed one issue for date-time that might be the reason for your problem.
We will start checking and testing the new release. We will be waiting for the server example so we can test more easily and efficiently the new features.
We downloaded the latest version and when we tried to run it, it showed a lot of errors related to the ws2def.h and winsock2.h files (check the picture).
Any idea what is the problem and what we should do?
We downloaded the latest release and it worked. We were able to run it and connect with the client.
If you remember we did have a problem with the event notification (it is looping forever in the GXDLMSDirector until it is crashing). We tested it with the new release and the problem is still here.
To repeat the problem, these are the steps:
1- In the svr_preaction add sendEventNotification when triggering the disconnect control:
updateState(GURUX_EVENT_CODES_OUTPUT_RELAY_STATE);
line 2616 -> sendEventNotification2(settings); <-
2- Then connect with the client and try to trigger the reconnect method of the disconnect control object
3- The issue should appear. We are supposing that the problem is from the client side because we did visualize the message sent from the server, it is sending only one message not multiple one.
If you can please check it and tell us the origin of the problem if it is our code or from the server or from the client.
You are welcome if you need more information to repeat the problem feel free to ask.
We have three questions till now concerning the new release:
1 - When downloading the latest release we noticed that in the preread() function you replaced DLMS_DATA_TYPE_DATETIME by DLMS_DATA_TYPE_OCTET_STRING when reading the clock1 object
Is there a clear reason or explanation for this change? because we tested with the both type and the result is the same in the both cases
2 - If we create an object of type octet-string but we want to see it in the GXDLMSDirector as format date-time we wrote the same code of the clock1 object. But surprisingly in the client side, when we read this object, it has a format of octet-string but a meaning of date-time (check the picture).
What are we supposed to do to see it as date-time format also? If you know another way to do it please share like creating it as date-time format from the start (but we are finding difficulties to initialize this type)?
3 - When we create an object of type octet--string this way:
char* dt = "012345678901";
GX_OCTECT_STRING(passiveEndOfBillingPeriod1Contract1.value, dt, strlen(dt));
and we try to restart the meter it is crashing when loading the settings files more specifically in the function getOctetString() (dlms.c file) it is returning DLMS_ERROR_CODE_OUTOFMEMORY because value->capacity(4) < len (12). Why is this happening?
But when we replaced the above by this:
static char dt[12] = "012345678901";
GX_OCTECT_STRING(passiveEndOfBillingPeriod1Contract1.value, dt, sizeof(dt));
The problem was solved and the load of the settings worked fine but we didn't understand why it is working for one not for the other way. Is it a bug or a normal thing? if you please can clear this idea
Correct data type is DLMS_DATA_TYPE_OCTET_STRING and not DLMS_DATA_TYPE_DATETIME.
It doesn't affect in any way for the result and the memory is clear correctly. It's was changed only for clarification.
Your data is not static. It's destroyed after you leave the function. You have also allocated space for the pointer and the compiler doesn't know the size of the allocated memory.
You are seeing byte string and not date-time because this is a custom identifier for Spain. The client doesn't know that this should be shown as a date-time. We can add support for Spain OBIS codes for GXDLMSDirector if you sent the list of OBIS codes and descriptions to me.
Thank you for these precious information. Yes sure we will filter the objects needed as date-time format and share it with you through email.
Let me now highlight a possible bug that we found in the new release:
- After connected the client-server for the first time, we read the action schedule disconnect control object then we added 2 execution time.
- Then when we restarted the code it is failing to load settings file
- So we followed the failure to know the reason, we noticed in the ser_loadObjects() -> ser_loadObject() -> ser_loadActionSchedule(), the hlp_getObjectCount2(serializer, &count) function is giving count = 2 like expected BUT the size of the executionTime is equal to 0 not 2 so when we are looping the function ret = arr_getByIndex(&object->executionTime, pos, (void**)&tm, sizeof(gxtime)) is returning
DLMS_ERROR_CODE_OUTOFMEMORY because index(0) >= arr->size(0 instead of 2)
We are supposing that there is a problem when saving the execution time in the postWrite more specifically in the ser_saveActionSchedule() function.
If you can check it and if you need more information feel free to ask.
Let me kindly add another bug we think it is important to correct.
We noticed that in the saveSecurity() function, we are saving the blockCipherKey, authenticationKey, kek, invocationCounter and minimumInvocationCounter but we were not saving the security policy level.
So when we activated the security policy from none to authenticatedEncrypted and then restarted the code and loading the security information, it was back to none instead of being authenticatedEncrypted like expected so we think you should save also the security policy level.
Security policy level is saved in the Security Setup object. The reason for this is that there might be several security setup objects for different associations. Correct security setup is updated in svr_isTarget. Let me know if you have any doubts about this.
Note! You need to press the "Activate" button in GXDLMSDirector to activate the security suite. Just selecting a different policy is not activate the new security policy level.
We want to highlight a problem that we faced. We uncommented the DLMS_IGNORE_PLC in the gxignore.h file for testing purposes. A lot of errors appeared (check the picture).
If you please can solve this problem by repeating it.
Yes sure we are using "Activate" (action 1 of the security setup object) to change the security suite level.
We have some doubts about what you said. In fact, when we activate the security suite it will go to the svr_postAction() function, it will first check "if e->target == BASE(securitySetupHigh)" which is the case so it will trigger the saveSecurity() function (which not include the saving of the security suite like described above).
The problem it will never access the saveSettings() function to update the security setup object because we have an else if after the condition above (check the picture). Even if it was an "if" instead of the "else if" the function svr_isChangedWithAction(e->target->objectType, e->index)) doesn't cover the DLMS_OBJECT_TYPE_SECURITY_SETUP, it covers only DLMS_OBJECT_TYPE_ASSOCIATION_LOGICAL_NAME, DLMS_OBJECT_TYPE_SAP_ASSIGNMENT and DLMS_OBJECT_TYPE_DISCONNECT_CONTROL only. So in conclusion it will never save the new security suite in the settings file because we have no access to the saveSettings() function through the action "Activate".
So we think there is two solution: to save new security policy in the security file that you described not practical due to several security setup objects or to give access to the saveSettings function when changing the security suite through the "Activate" action.
Let me know if you have any doubts about this or if you need more information.
We noticed that the object PrimeNbOfdmPlcMacNetworkAdministrationData has his own method reset and it is implemented in the server side through the function invoke_PrimeNbOfdmPlcMacNetworkAdministrationData() in the gxinvoke.h file. But in the GXDLMSDirector we do not have the reset button to trigger this action.
If you can please add this feature in the new release of the GXDLMSDirector.
We are facing the same problem of the action schedule described above with the SAP assignment object.
Let me now describe the different steps:
- After connected the client-server for the first time, we read the SAP assignment object then we added a new item to the SAP list. So we have 2 items in the list in total.
- Then when we restarted the code it is failing to load settings file
- So we followed the failure to know the reason, we noticed in the ser_loadObjects() -> ser_loadObject() -> ser_loadSapAssignment(), the hlp_getObjectCount2(serializer, &count) function is giving count = 2 like expected BUT the size of the sapAssignmentList is equal to 1 (old one) not 2 (with the new one) so when we are looping the function ret = arr_getByIndex(&object->executionTime, pos, (void**)&tm, sizeof(gxtime)) is returning
DLMS_ERROR_CODE_OUTOFMEMORY because index(1) >= arr->size(1 instead of 2)
We are supposing that there is a problem when saving the sapAssignmentList in the postWrite more specifically in the ser_saveSapAssignment() function.
If you can check it and if you need more information feel free to ask.
We tried to trigger the scriptTableGlobalMeterReset, we noticed the below points:
1- You did not call the createObjects(), but you called only the loadSettings() and loadSecurity() functions, is it intended and enough or not?
2- You only cleared the settings file so it will be saved again, but we think you forget to clear the security file so it will be saved as new not load the old one.
3- Then we tried to clear both files settings and security so saveSettings() and saveSecurity() were triggered, but we noticed that the value of the keys were saved as the new one and were not reset like expected to the old values but the minimumInvocationCounter was back to 0. So more specifically the value linked to the settings.base.cipher was not cleared and reset to the original value (the last updated values were the ones to be saved) but the security setup object was cleared so the minimumInvocationCounter was only the one to be cleared.
There is an important issue that should be solve in the next release. We created an object of interface class Data (ID = 1) and the value type is equal to array[2] of bit-string[256] (the one that you help us to create)
You can find attached the function that we wrote to create that object (check the picture)
When we save the settings for the first time it is done successfully, but when we try to load the list of objects from the file settings it is crashing when trying to load the object above and returning DLMS_ERROR_CODE_INVALID_PARAMETER.
getVariantFromBytes
To follow the error : ser_loadObjects()->ser_loadObject()->ser_loadData()->getVariantFromBytes()->cosem_getVariant()->dlms_getData() in this function we have "switch (info->type)" but obviously the value type array[2] of bit-string[256] is not supported yet because it is going directly to the default case where is written "assert(0);" instead of entering the "case DLMS_DATA_TYPE_ARRAY" for example.
There is something wrong because the type seems unknown, the problem could be coming from the saving or loading part of this object. We hope that you will try to repeat the problem.
PS: Let me add that the same problem is appearing with another object gxData with value type equal to array[2] of octet-string[12] (the second new type that you help us to create)
Hi,
Hi,
GX_DATETIME set data type to date-time, not octet-string.
You can return the date-time as an octet string in preRead like in the example.
https://github.com/Gurux/GuruxDLMS.c/blob/c49ea8f8f59e57a66189d0e1c2749…
BR,
Mikko
Hi,
Hi,
Sorry but we did not get what do you mean and what are we supposed to do. Can you please write for us an example code in order to understand how to create this object?
When we tried to create this object using GX_DATETIME and we tried to capture a profile generic having one of his columns equal to this object, it is crashing. There is a problem in the function dlms_setData() used in the getProfileGenericBufferColumnSizes() function.
Best Regards,
Lara Wakim
Hi,
Hi,
Get the latest version. It's now released and there is support for PLC. We'll start to make an example server tomorrow. There is also support for the bit-string array, etc. Let me know if you have any problems. There is also a fixed one issue for date-time that might be the reason for your problem.
BR,
Mikko
Hi Mikko,
Hi Mikko,
Thank you really appreciated.
We will start checking and testing the new release. We will be waiting for the server example so we can test more easily and efficiently the new features.
Best Regards,
Lara Wakim
Hello Mikko,
Hello Mikko,
We downloaded the latest version and when we tried to run it, it showed a lot of errors related to the ws2def.h and winsock2.h files (check the picture).
Any idea what is the problem and what we should do?
Best Regards,
Lara Wakim
Hi,
Hi,
Get the latest version from the server examples. The application must use Winsock2 and not Winsock because support for IPv6 is added.
BR,
Mikko
Hey,
Hey,
We downloaded the latest release and it worked. We were able to run it and connect with the client.
If you remember we did have a problem with the event notification (it is looping forever in the GXDLMSDirector until it is crashing). We tested it with the new release and the problem is still here.
To repeat the problem, these are the steps:
1- In the svr_preaction add sendEventNotification when triggering the disconnect control:
updateState(GURUX_EVENT_CODES_OUTPUT_RELAY_STATE);
line 2616 -> sendEventNotification2(settings); <-
2- Then connect with the client and try to trigger the reconnect method of the disconnect control object
3- The issue should appear. We are supposing that the problem is from the client side because we did visualize the message sent from the server, it is sending only one message not multiple one.
If you can please check it and tell us the origin of the problem if it is our code or from the server or from the client.
Best Regards,
Lara Wakim
Hi,
Hi,
Thanks for the detailed steps. We'll follow your steps and I'll let you know as soon as I have more info from this.
BR,
Mikko
Hi Mikko,
Hi Mikko,
You are welcome if you need more information to repeat the problem feel free to ask.
We have three questions till now concerning the new release:
1 - When downloading the latest release we noticed that in the preread() function you replaced DLMS_DATA_TYPE_DATETIME by DLMS_DATA_TYPE_OCTET_STRING when reading the clock1 object
Is there a clear reason or explanation for this change? because we tested with the both type and the result is the same in the both cases
2 - If we create an object of type octet-string but we want to see it in the GXDLMSDirector as format date-time we wrote the same code of the clock1 object. But surprisingly in the client side, when we read this object, it has a format of octet-string but a meaning of date-time (check the picture).
What are we supposed to do to see it as date-time format also? If you know another way to do it please share like creating it as date-time format from the start (but we are finding difficulties to initialize this type)?
3 - When we create an object of type octet--string this way:
char* dt = "012345678901";
GX_OCTECT_STRING(passiveEndOfBillingPeriod1Contract1.value, dt, strlen(dt));
and we try to restart the meter it is crashing when loading the settings files more specifically in the function getOctetString() (dlms.c file) it is returning DLMS_ERROR_CODE_OUTOFMEMORY because value->capacity(4) < len (12). Why is this happening?
But when we replaced the above by this:
static char dt[12] = "012345678901";
GX_OCTECT_STRING(passiveEndOfBillingPeriod1Contract1.value, dt, sizeof(dt));
The problem was solved and the load of the settings worked fine but we didn't understand why it is working for one not for the other way. Is it a bug or a normal thing? if you please can clear this idea
Best Regards,
Lara Wakim
Hi,
Hi,
Correct data type is DLMS_DATA_TYPE_OCTET_STRING and not DLMS_DATA_TYPE_DATETIME.
It doesn't affect in any way for the result and the memory is clear correctly. It's was changed only for clarification.
Your data is not static. It's destroyed after you leave the function. You have also allocated space for the pointer and the compiler doesn't know the size of the allocated memory.
You are seeing byte string and not date-time because this is a custom identifier for Spain. The client doesn't know that this should be shown as a date-time. We can add support for Spain OBIS codes for GXDLMSDirector if you sent the list of OBIS codes and descriptions to me.
BR,
Mikko
Hi,
Hi,
Thank you for these precious information. Yes sure we will filter the objects needed as date-time format and share it with you through email.
Let me now highlight a possible bug that we found in the new release:
- After connected the client-server for the first time, we read the action schedule disconnect control object then we added 2 execution time.
- Then when we restarted the code it is failing to load settings file
- So we followed the failure to know the reason, we noticed in the ser_loadObjects() -> ser_loadObject() -> ser_loadActionSchedule(), the hlp_getObjectCount2(serializer, &count) function is giving count = 2 like expected BUT the size of the executionTime is equal to 0 not 2 so when we are looping the function ret = arr_getByIndex(&object->executionTime, pos, (void**)&tm, sizeof(gxtime)) is returning
DLMS_ERROR_CODE_OUTOFMEMORY because index(0) >= arr->size(0 instead of 2)
We are supposing that there is a problem when saving the execution time in the postWrite more specifically in the ser_saveActionSchedule() function.
If you can check it and if you need more information feel free to ask.
Best Regards,
Lara Wakim
Hi Mikko,
Hi Mikko,
Let me kindly add another bug we think it is important to correct.
We noticed that in the saveSecurity() function, we are saving the blockCipherKey, authenticationKey, kek, invocationCounter and minimumInvocationCounter but we were not saving the security policy level.
So when we activated the security policy from none to authenticatedEncrypted and then restarted the code and loading the security information, it was back to none instead of being authenticatedEncrypted like expected so we think you should save also the security policy level.
Best Regards,
Lara Wakim
Hi Mikko,
Repetition
Hi,
Hi,
We'll check this. We have added support for the Spain DLMS subset. OBIS codes are updated in the next release of GXDLMSDirector.
BR,
Mikko
Hi,
Hi,
Kindly check your email, we sent you the list of Spain identifier to be supported as date-time in the GXDLMSDirector.
We are sorry for the same message sent twice above.
Best Regards,
Lara Wakim
Hi,
Hi,
This is now fixed and tests have started. A new version is released this week.
BR,
Mikko
Hi,
Hi,
Security policy level is saved in the Security Setup object. The reason for this is that there might be several security setup objects for different associations. Correct security setup is updated in svr_isTarget. Let me know if you have any doubts about this.
Note! You need to press the "Activate" button in GXDLMSDirector to activate the security suite. Just selecting a different policy is not activate the new security policy level.
BR,
Mikko
Hi,
Hi,
We are testing Spanish OBIS codes and release the next version from GXDLMSDirector next week.
BR,
Mikko
Hi,
Hi,
We will send you by email a detailed list of all the objects specific for Spain.
Best Regards,
Lara Wakim
Hi Mikko,
Hi Mikko,
We want to highlight a problem that we faced. We uncommented the DLMS_IGNORE_PLC in the gxignore.h file for testing purposes. A lot of errors appeared (check the picture).
If you please can solve this problem by repeating it.
Best Regards,
Lara Wakim
Hi,
Hi,
Yes sure we are using "Activate" (action 1 of the security setup object) to change the security suite level.
We have some doubts about what you said. In fact, when we activate the security suite it will go to the svr_postAction() function, it will first check "if e->target == BASE(securitySetupHigh)" which is the case so it will trigger the saveSecurity() function (which not include the saving of the security suite like described above).
The problem it will never access the saveSettings() function to update the security setup object because we have an else if after the condition above (check the picture). Even if it was an "if" instead of the "else if" the function svr_isChangedWithAction(e->target->objectType, e->index)) doesn't cover the DLMS_OBJECT_TYPE_SECURITY_SETUP, it covers only DLMS_OBJECT_TYPE_ASSOCIATION_LOGICAL_NAME, DLMS_OBJECT_TYPE_SAP_ASSIGNMENT and DLMS_OBJECT_TYPE_DISCONNECT_CONTROL only. So in conclusion it will never save the new security suite in the settings file because we have no access to the saveSettings() function through the action "Activate".
So we think there is two solution: to save new security policy in the security file that you described not practical due to several security setup objects or to give access to the saveSettings function when changing the security suite through the "Activate" action.
Let me know if you have any doubts about this or if you need more information.
Best Regards,
Lara Wakim
Hi Mikko,
Hi Mikko,
We noticed that the object PrimeNbOfdmPlcMacNetworkAdministrationData has his own method reset and it is implemented in the server side through the function invoke_PrimeNbOfdmPlcMacNetworkAdministrationData() in the gxinvoke.h file. But in the GXDLMSDirector we do not have the reset button to trigger this action.
If you can please add this feature in the new release of the GXDLMSDirector.
Best Regards,
Lara Wakim
Hi Mikko,
Hi Mikko,
We are facing the same problem of the action schedule described above with the SAP assignment object.
Let me now describe the different steps:
- After connected the client-server for the first time, we read the SAP assignment object then we added a new item to the SAP list. So we have 2 items in the list in total.
- Then when we restarted the code it is failing to load settings file
- So we followed the failure to know the reason, we noticed in the ser_loadObjects() -> ser_loadObject() -> ser_loadSapAssignment(), the hlp_getObjectCount2(serializer, &count) function is giving count = 2 like expected BUT the size of the sapAssignmentList is equal to 1 (old one) not 2 (with the new one) so when we are looping the function ret = arr_getByIndex(&object->executionTime, pos, (void**)&tm, sizeof(gxtime)) is returning
DLMS_ERROR_CODE_OUTOFMEMORY because index(1) >= arr->size(1 instead of 2)
We are supposing that there is a problem when saving the sapAssignmentList in the postWrite more specifically in the ser_saveSapAssignment() function.
If you can check it and if you need more information feel free to ask.
Best Regards,
Lara Wakim
Hi,
Hi,
Thank you for pointing this out. This is added and the new version will be released next week.
BR,
Mikko
Hi Lara,
Hi Lara,
This is fixed and the new version is released on Monday.
BR,
Mikko
Hi Mikko,
Hi Mikko,
We tried to trigger the scriptTableGlobalMeterReset, we noticed the below points:
1- You did not call the createObjects(), but you called only the loadSettings() and loadSecurity() functions, is it intended and enough or not?
2- You only cleared the settings file so it will be saved again, but we think you forget to clear the security file so it will be saved as new not load the old one.
3- Then we tried to clear both files settings and security so saveSettings() and saveSecurity() were triggered, but we noticed that the value of the keys were saved as the new one and were not reset like expected to the old values but the minimumInvocationCounter was back to 0. So more specifically the value linked to the settings.base.cipher was not cleared and reset to the original value (the last updated values were the ones to be saved) but the security setup object was cleared so the minimumInvocationCounter was only the one to be cleared.
If you please can check it .
Best Regards,
Lara Wakim
Hi,
Hi,
This is also fixed for the next release.
BR,
Mikko
Hi,
Hi,
#1. Global meter reset don't create objects again, but it will load the default settings.
#2. I'll check this.
#3. I'll check this.
BR,
Mikko
Hi Mikko,
Hi Mikko,
Thank you for the above answers.
There is an important issue that should be solve in the next release. We created an object of interface class Data (ID = 1) and the value type is equal to array[2] of bit-string[256] (the one that you help us to create)
You can find attached the function that we wrote to create that object (check the picture)
When we save the settings for the first time it is done successfully, but when we try to load the list of objects from the file settings it is crashing when trying to load the object above and returning DLMS_ERROR_CODE_INVALID_PARAMETER.
getVariantFromBytes
To follow the error : ser_loadObjects()->ser_loadObject()->ser_loadData()->getVariantFromBytes()->cosem_getVariant()->dlms_getData() in this function we have "switch (info->type)" but obviously the value type array[2] of bit-string[256] is not supported yet because it is going directly to the default case where is written "assert(0);" instead of entering the "case DLMS_DATA_TYPE_ARRAY" for example.
There is something wrong because the type seems unknown, the problem could be coming from the saving or loading part of this object. We hope that you will try to repeat the problem.
PS: Let me add that the same problem is appearing with another object gxData with value type equal to array[2] of octet-string[12] (the second new type that you help us to create)
Can you please check this major issue?
Best Regards,
Lara Wakim