alessandro - 6 days ago

VAR
Data1:ARRAY[1..10] OF SINT ;
Data2:ARRAY[1..10] OF SINT ;

Data3:ARRAY[1..10] OF SINT ;
Data4:ARRAY[1..10] OF SINT ;

ex_1        : BOOL ;
ex_2        : BOOL ;
enable      : BOOL :=0 ;

END_VAR

// PROGRAM
// The scope of this example is compare and copy the values of two ARRAY only if some value is different using SysMemCmp and SysMemCpy.
// In this 2 example we don't use a FOR cicle for do this, and pBuffer1 and pBuffer2 is just a pointer to ARRAY. See details in Library util.SysMem of Codesys
// The compare funcion util.SysMem.SysMemCmp is bidirectional if Data1 chanege respect Data2 ex_1 go to 1 and if Data2 change respect Data1 also
// but the copy function util.SysMem.SysMemCpy work only from source ARRAY pSrc:=ADR(Data1) to destination ARRAY pDest:=ADR(Data2)

// Example 1 Full ARRAY compare and copy
// This compare 2 different equal ARRAY and if there is some difference ex_1 go to 1 and if you give enable he copy Data1 in Data2

ex_1 := TO_BOOL(util.SysMem.SysMemCmp(pBuffer1:=ADR(Data1), pBuffer2:=ADR(Data2), udiCount:=SIZEOF(Data1)));
IF ex_1 AND enable THEN
util.SysMem.SysMemCpy(pDest:=ADR(Data2), pSrc:=ADR(Data1), udiCount:=SIZEOF(Data1));
END_IF

// Example 2 Only selected area of the ARRAY compare and copy
// This compare 2 different equal ARRAY starting from position number [3] for 4 byte in this case start at position [3] and finish at position number [6]
// and if there is some difference only in area [3..6] of the ARRAY ex_2 go to 1 if you give enalbe he copy Data3[3..6] in Data4[3..6]
// if something change in other array position[0..2] or [7..10] are ingnored

ex_2 := TO_BOOL(util.SysMem.SysMemCmp(pBuffer1:=ADR(Data3[3]), pBuffer2:=ADR(Data4[3]), udiCount:=4));
IF ex_2 AND enable THEN
util.SysMem.SysMemCpy(pDest:=ADR(Data4[3]), pSrc:=ADR(Data3[3]), udiCount:=4);
END_IF

// Attention udiCount input is intended in <byte> in the example 1 I pass to udiCount:=SIZEOF(Data1) for compare and copy the intere ARRAY and
// SIZEOF pass the size of intere ARRAY in byte to the function input, in this 2 examples I used variable type SINT each one occupie 1 byte and one position in the ARRAY
// and in the example 2 I pass udiCount:=4 for compare and copy only 4 position of Data3/4[3..6] if you want to extend this example and use it for an ARRAY OF WORD
// remember that each WORD will occupe 2 byte (16 bit) and you will have to pass udiCount:=SIZEOF(Data1) if you need to compare intere ARRAY example 1
// but need udiCount:=(42) for the example 2 because need to compare and copy 4 word each occupie 2 byte (16 bit).
// For REAL (32 bit) need udiCount:=SIZEOF(4
4) for LREAL or (64 bit) need udiCount:=SIZEOF(416)
// a good rule is calculate the dimension of the ARRAY in byte without empty space at the end, multiple of data type number for variable bigger then 8 bit
// Example : If you want to create an ARRAY for 5 REAL (32 bit) each occupie 4 byte the correct size is ARRAY[0..19] OF REAL 5
4=20 position.
// NOTE : In the example the position of compare function util.SysMem.SysMemCmp is first and the copy function util.SysMem.SysMemCpy inside the IF is after
// in one cycle of the program the two array is compared and if there is some difference and enable are copied.
// If you move util.SysMem.SysMemCmp after the IF cycle he will copare the ARRAY in the current cycle but the copy of the value will do in the next cycle.</byte>

 

Related

Talk.ru: 3