Cpp DLMS client launch example

35 posts / 0 new
Last post
Ingvar
Cpp DLMS client launch example

Good day!
In the GuruxDLMSClientExample example, the application is launched with the parameters - IP, port, as well as the parameter 'o' - OutputFile (as I understand the file with DLMS meters objects)
Is there an example of the application launch line and this file (any) for Windows? This would make learning code easier.
thanks

Kurumi
Kurumi's picture

Hi,

The command-line parameters depend from the meter. -o is optional and it's used to make meter reading faster. I understand that reading DLMS meters can be a real pain. You should also check GXDLMSDirector. I believe it can help you to read your meter.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Thanks for the answer.
Did I understand correctly - if an OutputFile is used, then variables from it are read, otherwise all meter variables are read?
I don’t have a meter yet, but I plan to get it soon. Therefore the question was more theoretical - I wanted to study the code in more detail.
Maybe you have an example of such a file and an example of a launch line (from any meter )?
Or maybe GXDLMSDirector can generate this file (I have not studied this product yet).

Kurumi
Kurumi's picture

Hi,

There is an association view that describes what kind of functionality meter can offer (registers, etc). Reading the association view is taking a long time and for this reason, the output file parameter is added. You can save it to the file and read it from there.

You can start GuruxDLMSServerExample. It's a simple meter and work against that.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Thanks, the connection with the GuruxDLMSServerExample was established, the file was generated. Now trying to read individual OBIS. Please tell me in what format to specify readObjects variable?
I understand this is a comma-separated OBIS, but in this code uses colon too.
If I indicate this:
readObjects = "1.1.0.0.0.255: 0";
Does not read.
If so:
readObjects = "1.1.0.0.0.255";
Fails with error (p2 == NULL)
How to specify the OBIS I need?

Kurumi
Kurumi's picture

Hi,

Give command line parameter ex. -g 1.1.0.0.0.255:2

#2 is attribute index number that you want to read.

BR,

Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Thanks for the answer.
Trying to read Profile Generic from GuruxDLMSServerExample - OBIS 1.0.99.1.0.255. I try to read ByRange - the server responds with a short message. Does it support reading in this mode?
I try to read ByEntry. The SetValue method returns 258 (DLMS_ERROR_CODE_INVALID_PARAMETER). How to read rows from a profile?

Kurumi
Kurumi's picture

Hi,

Have you read the capture objects list (Attribute index 2) before reading the buffer?
You must read it first.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Thanks.
Only an attribute list attribute index is 3.
Another question. I correctly understood that in DLMS each OBIS and its indexes are read by individual requests? There is no possibility of polling several OBIS?

Kurumi
Kurumi's picture

Hi,

You can read multiple objects using ReadList-method.
Not all meters support it.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Thanks for the answer. Two more questions:
1. If the exchange is carried out via HDLC, it is necessary to indicate the physical address of the counter (on the bus). How to do it correctly?
2. The Profile Generic object has attribute 4 — the capture period. By standard, it returns a value in seconds (or 0 if not automatic capture). When polling GuruxServer an object 1.0.99.1.0.255 of index 4, value 60 is returned. Do you convert the value to minutes? What will be returned if there is a monthly capture interval?

Kurumi
Kurumi's picture

Hi,

1. If you have only one counter in the bus you USUALLY can use address 1 for it. There are some older meters that can't handle this.
2. This value is not converted. This is set to zero for monthly interval and "End of billing period" -Script table object calls capture-method of profile generic.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

1. If I understand correctly, there is a Wrapper mode - on TCP, there is an HDLC - COM (Rs-485 etc). If there are several counters on the RS-485 bus, then how to correctly set the address in the client?
2. "This value is not converted" - then 60 is what? Minutes?
About the monthly archive - I understood

Ingvar

So how to work with several counters (set addresses) on the RS-485 when working through HDLC?

Kurumi
Kurumi's picture

Hi,

Each meter has own server address. You can try to count it from the serial number but all the meters are not supporting it. Try to read your meter with GXDLMSDirector. Change "Address Type" from Default to SerialNumber.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

How to get the value of CGXDLMSVariant from the classes GXDLMSData, GXDLMSRegister and others without using a row vector (GetValues)?
These classes have a GetValue function, but the GXDLMSObject base class does not. How then is it better to do it?
I wrote a virtual function in GXDLMSObject, which returns an empty CGXDLMSVariant from it. Everything works, but I would not want to change your code.

Kurumi
Kurumi's picture

Hi,

GXDLMSData::GetValue or GXDLMSRegister::GetValue methods returns value attribute (index #2).

If you have GXDLMSObject* you can check the object type and then get the data.
Something like this:

CGXDLMSObject* it =...

if (it->GetObjectType() == DLMS_OBJECT_TYPE_DATA)
{
CGXDataObject* d = (CGXDataObject*)it;
d->GetValue();
}

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Of course, I know and tried this method.
It works however, but it is not considered an example of "good" programming.
Why not make the base class a virtual function? For heirs whose function is not overridden, an empty value (or exception) will be returned.

Kurumi
Kurumi's picture

Hi,

GetValue will work for Register and Data objects, but there are tens of objects that are not using value, and more importantly they are using complex data structures.

GetValue does not work because the data structure of each object is so different. There is no way to return collection of COSEM objects that is required for example with Push Setup.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

You're right. Redid it.
Another question. There is a group survey in DLMS. I tried using ReadList. It works fine with GuruxServer, but not with my device. Doesn't even try to send requests to the device. What is the reason for this?
Gurux Director have a group survey? I did not find such a setting.

Kurumi
Kurumi's picture

Hi,

Your meter don't support Multiple references. For this reason, each object must read separately.

https://www.gurux.fi/Gurux.DLMS.Conformance

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Do I understand correctly that the Gurux server simulator supports encryption through port 4060?
What parameters should be specified when (password, authentication type, security)? I drove the parameters that are issued in the console window - an error is issued.
Through DLMS Director also failed to connect.

Kurumi
Kurumi's picture

Hi Ingvar,

Encryption is supported.
If you are using Short Name referencing use port 4060, but I believe that you want to use Logical Name referencing (it's the default) and you should use port 4061.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

DLMS Director connected. I'm trying to connect with my encryption from my code. The keys is set just like an array
Hammered like this:
char* password = NULL;
authentication = DLMS_AUTHENTICATION_HIGH_SHA256;
security = DLMS_SECURITY_AUTHENTICATION;
char dedicatedKey[16]={0x31,0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31};
char systemTitle[8]={ 0x41,0x42,0x43 ,0x44 ,0x45 ,0x46 ,0x47 ,0x48 };
char authenticationKey[16]={0xD0,0xD1 ,0xD2 ,0xD3 ,0xD4 ,0xD5 ,0xD6 ,0xD7 ,0xD8 ,0xD9 ,0xDA ,0xDB ,0xDC ,0xDD ,0xDE ,0xDF};
char blockCipherKey[16]={ 0x00,0x01 ,0x02 ,0x03 ,0x04 ,0x05 ,0x06 ,0x07 ,0x08 ,0x09 ,0x0A ,0x0B ,0x0C ,0x0D ,0x0E ,0x0F };
int ServerAddress = CGXDLMSClient::GetServerAddress(ServerAddressIn,Address,4);
CGXDLMSSecureClient* cl = new CGXDLMSSecureClient(useLogicalNameReferencing, clientAddress, ServerAddress, authentication, password, interfaceType);

cl->GetCiphering()->SetSecurity(security);
cl->SetAutoIncreaseInvokeID(autoIncreaseInvokeID);
CGXByteBuffer bb;
if (systemTitle != NULL)
{
bb.Clear();
bb.SetHexString(systemTitle);
cl->GetCiphering()->SetSystemTitle(bb);
}
if (authenticationKey != NULL)
{
bb.Clear();
bb.SetHexString(authenticationKey);
cl->GetCiphering()->SetAuthenticationKey(bb);
}
if (blockCipherKey != NULL)
{
bb.Clear();
bb.SetHexString(blockCipherKey);
cl->GetCiphering()->SetBlockCipherKey(bb);
}
if (dedicatedKey != NULL)
{
bb.Clear();
bb.SetHexString(dedicatedKey);
cl->GetCiphering()->SetDedicatedKey(bb);
}
Connect does not occur:
[2020-06-02 17:40:15.530] TRACE : (127.0.0.1:4061) Tx: [0012] 7E A0 0A 00 02 00 03 03 93 A0 62 7E
[2020-06-02 17:40:16.036] TRACE : (127.0.0.1:4061) Rx: [0035] 7E A0 21 03 00 02 00 03 73 48 5C 81 80 12 05 01 80 06 01 80 07 04 00 00 00 01 08 04 00 00 00 01 53 3B 7E
[2020-06-02 17:40:16.036] SCRIPT : <<DLMS.Meter>> : AARQRequest failed (258) Invalid parameter.
What can be wrong?
Do you need a password in this mode?

Kurumi
Kurumi's picture

Hi,

SHA256 needs the password. Only GMAC doesn't use the password.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

What password then need to be specified? It is not displayed in the server window.
I tried to specify DLMS_AUTHENTICATION_HIGH_GMAC- also does not establish a connection.
[2020-06-03 9:56:27.016] SCRIPT : <<DLMS.Meter>> : read start
[2020-06-03 9:56:27.032] TRACE : (127.0.0.1:4061) Tx: [0012] 7E A0 0A 00 02 00 03 03 93 A0 62 7E
[2020-06-03 9:56:27.536] TRACE : (127.0.0.1:4061) Rx: [0035] 7E A0 21 03 00 02 00 03 73 48 5C 81 80 12 05 01 80 06 01 80 07 04 00 00 00 01 08 04 00 00 00 01 53 3B 7E
[2020-06-03 9:56:27.536] SCRIPT : <<DLMS.Meter>> : AARQRequest failed (258) Invalid parameter.
Code:
char* password = NULL;
authentication = DLMS_AUTHENTICATION_HIGH_GMAC;
security = DLMS_SECURITY_AUTHENTICATION;
char dedicatedKey[16]={0x31,0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31};
char systemTitle[8]={ 0x41,0x42,0x43 ,0x44 ,0x45 ,0x46 ,0x47 ,0x48 };
char authenticationKey[16]={0xD0,0xD1 ,0xD2 ,0xD3 ,0xD4 ,0xD5 ,0xD6 ,0xD7 ,0xD8 ,0xD9 ,0xDA ,0xDB ,0xDC ,0xDD ,0xDE ,0xDF};
char blockCipherKey[16]={ 0x00,0x01 ,0x02 ,0x03 ,0x04 ,0x05 ,0x06 ,0x07 ,0x08 ,0x09 ,0x0A ,0x0B ,0x0C ,0x0D ,0x0E ,0x0F };

Ingvar

Specified the same parameters in GuruxDLMSClientExample - also does not connect.
Log:
TX: 10:30:50 7E A0 07 03 03 93 8C 11 7E
RX: 10:30:50 7E A0 1E 03 03 73 40 CC 81 80 12 05 01 80 06 01 80 07 04 00 00 00 01 08 04 00 00 00 01 53 3B 7E
TX: 10:30:50 7E A0 07 03 03 53 80 D7 7E
RX: 10:30:50 7E A0 1E 03 03 73 40 CC 81 80 12 05 01 80 06 01 80 07 04 00 00 00 01 08 04 00 00 00 01 53 3B 7E

Kurumi
Kurumi's picture

Hi,
Do you try to connect to GuruxDLMSServerExample or what is your meter model and type?
You have not set a password because this error is given. AARQRequest failed (258) Invalid parameter.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

I am trying from GuruxDLMSClientExample to connect to GuruxDLMSServerExample with encryption. And I can’t do it. What parameters should be specified, for example, in DLMS_AUTHENTICATION_HIGH_GMAC mode

Kurumi
Kurumi's picture

Hi,

Try with this:
GuruxDLMSClientExample -h localhost -p 4061 -a HighGmac -t Verbose

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

About SHA I understood. Now I set GMAC but anyway i get a mistake.
Please give an example of the client launch line in DLMS_AUTHENTICATION_HIGH_GMAC mode and the systemTitle, blockCipherKey, dedicatedKey parameters with those parameters that the server has by default (parameters -T,-A,-D,-B). Particularly interested in blockCipherKey

Ingvar

The polling went when I removed the assignment of values to the dedicatedKey, systemTitle, etc. arrays.
Do they need to be set? I thought that you need to specify the value that the server displays in the window.

Kurumi
Kurumi's picture

Hi,

Those are default keys. You can also set them, but they must be the same for client and server.

BR,
Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi

Ingvar

Ok.
But why when I ask them - the survey does not go? Did I indicate them incorrectly?

Kurumi
Kurumi's picture

Hi,

You haven't set the correct authentication level or some of the keys are not valid.
WIth DLMS_AUTHENTICATION_HIGH_SHA256 you didn't set a password.

BR,

Mikko

________________________________________
Mikko Kurunsaari
Gurux Ltd
http://www.gurux.fi