Добрый день. Имеется подпрограмма для чтения 8 аналоговых входов МВА8 и записи их в оперативные переменные на ПЛК63.
Обнаружил что примерно раз в неделю или чуть чаще, происходит обмен соседними значениями - например МВА8_5 получает значение МВА8_4, МВА8_4 получает значение МВА8_3. Обнаружил это совершенно случайно, когда поставил к этим переменным сбор статистики за сутки (Минимальное максимальное среднее) - увидел что переменная приняла минимальное значение, которое никогда не могло быть, но зато очень похоже на диапазон значений соседнего входа.
Замечено такое за МВА8? Или дело в коде:
Код:
tNext(IN:=TRUE,PT:=T#3s);
IF tNext.Q THEN
(*Устанавливаем настройки COM-порта*)
IF port_opened=0 THEN
Settings.Port:=com_num; (*номер COM-порта*)(*0 - RS-485, 1 - RS-232*)
Settings.dwBaudRate:=9600; (*скорость*)
Settings.byParity:=0;
Settings.dwTimeout:=0;
Settings.byStopBits:=1;
Settings.dwBufferSize:=0;
Settings.dwScan:=0;
END_IF
COM_SERVICE1(Enable:=(port_opened=0) , Settings:=Settings , Task:=OPEN_TSK );
(*Если COM-порт открыт, то переходим к приему и передачи данных *)
IF COM_SERVICE1.ready THEN
port_opened:=2;
END_IF
IF port_opened=2 THEN (*Удачно проинициализировали*)
CASE master1 OF
0:
CurAddr:=4;
1:
CurAddr:=10;
2:
CurAddr:=16;
3:
CurAddr:=22;
4:
CurAddr:=28;
5:
CurAddr:=34;
6:
CurAddr:=40;
7:
CurAddr:=46;
END_CASE
(* функция 03 флоат - ФБ считывает значение параметра типа real из прибора с адресом 16 в регистр с номаром CurAddr по протоколу Modbus-RTU *)
get3_modbus(
Enable:=enabl , (* разрешение работы блока *)
Mode:=MB_RTU , (*режим передачи*)
DevAddr:=16 , (*адрес*)
FirstAddr:=CurAddr , (*номер регистра*)
Quantity:=2, (*количество регистров*)
ComHandle:=Settings.Port ,(*номер COM-порта*)
TimeOut:=TimeOut , (*Таймаут T#50ms*)
Buffer:=Buffer , (* буфер данных *)
Complete=>cmpl , (* скопировать признак завершения операции *)
Exception=>err , (* скопировать регистр ошибок *)
ByteCnt=>DataSize ); (*кол-во считанных байтов *)
(*если установлен признак завершения операции, то *)
IF cmpl THEN
IF err=0 THEN (*Если нет ошибок, то получаем данные из буфера типа FLOAT*)
ptr_D:=ADR(d);
ptr_D^:=buffer[3];
ptr_D:=ptr_D+1;
ptr_D^:=buffer[2];
ptr_D:=ptr_D+1;
ptr_D^:=buffer[1];
ptr_D:=ptr_D+1;
ptr_D^:=buffer[0];
d:=slROUND1(d);
IF d<>0 THEN
CASE master1 OF
0:
MVA8_1:=d;
1:
MVA8_2:=d;
2:
MVA8_3:=d;
3:
MVA8_4:=d;
4:
MVA8_5:=d;
5:
MVA8_6:=d;
6:
MVA8_7:=d;
7:
MVA8_8:=d;
END_CASE
END_IF
END_IF
master1:=master1+1;
IF master1=8 THEN
master1:=0;
tNext(IN:=FALSE,PT:=T#3s);
END_IF
END_IF
IF enabl = FALSE THEN
enabl := TRUE;
END_IF
IF err <> 0 THEN
enabl := FALSE;
END_IF
END_IF
END_IF