Объявление

Свернуть
Пока нет объявлений.

Работа с RS-485 на АГАВА ПЛК-40.07 W

Свернуть
X
 
  • Фильтр
  • Время
  • Показать
Очистить всё
новые сообщения

  • Работа с RS-485 на АГАВА ПЛК-40.07 W

    Здравствуйте!
    Решил разобраться как организовать передачу данных по RS-485 на контроллере АГАВА ПЛК-40.07 W.

    Используемое оборудование:
    1. АГАВА ПЛК-40.07 W с таргет-файлом 3.5.10.0 с корневой файловой системой 2020.2;
    2. Компьютер с ОС Windows 10 и программами Modbus Poll Master 9.4.0 и Modbus Poll Slave 7.3.0;
    3. Преобразователь USB-RS485 модели ARC-485;
    4. Среда программирования Codesys 3.5 SP14 Patch 3;

    Настройки передачи:
    1. Порт 1;
    2. Скорость обмена 9600;
    3. Паритета нет;
    4. Стоповый бит 1;
    5. Номер устройства в сети 1;
    6. Количество запрашиваемых регистров 10;
    7. Начальный адрес 1.

    Полученные результаты:
    1. Компьютер с программой Modbus Poll Master 9.4.0 и контроллер АГАВА ПЛК-40.07 W с проектом ModbusRTUSlave:

    1) Практически все примеры режима RTUSlave в SDK (в независимости от версии), кроме ModbusRTUSlave_ (расположенной в SDK 10.7), являются не рабочими, так как в программе RTUSlave :
    а) в условии bFirstCycle не хватает строки: xEnable:=TRUE;
    или
    б) в строке: MBRTUSlave (xEnable=xEnable, xError=>xError, resIEC=>result); - нужно заменить xEnable=xEnable на xEnable=TRUE

    2)Практически во всех примерах режима RTUSlave в SDK (в независимости от версии), кроме ModbusRTUSlave_ (расположенной в SDK 10.7), отсутствует визуализация (что, мне как начинающему (студенту), сильно усложняет понимание работы RS в данном контроллере), поэтому модифицировал пример, в пределах своих знаний, (с русскими комментариями и визуализацией) для считывания Holding и/или Input регистров ПЛК. (хотел прикрепить файл проекта, однако форум выдал, что нельзя)


    2. Компьютер с программой Modbus Poll Slave 7.3.0 и контроллер АГАВА ПЛК-40.07 TV/WV с проектом ModbusRTUMaster:

    1) Так же как и
    ModbusRTUSlave, везде отсутствует визуализация и мало пояснений о работе примера программы;
    2) Непонятно:
    а) В какие переменные считываются данные из регистров подчиненного устройства?
    б) Где и какая переменная задает время опроса и время задержки между опросами?

    3) при использование проектов RTUReadHoldRegSync и RTUReadHoldRegAsync:
    1) Программа большую часть времени находится в режиме ошибки (MODE_ERROR), хотя по преобразователю интерфейса видно, что прием и передача происходит (RX и TX мигают с частотой соответствующей 1 с);
    2) Непонятно в какую переменную считываются данные из Holding регистра подчиненного устройства?


    Пожалуйста помогите разобраться как организовать работу контроллера АГАВА ПЛК-40 по RS-485 в режиме Master.

  • #2
    Сообщение от Никадим Посмотреть сообщение
    Здравствуйте!
    Решил разобраться как организовать передачу данных по RS-485 на контроллере АГАВА ПЛК-40.07 W.

    Используемое оборудование:
    1. АГАВА ПЛК-40.07 W с таргет-файлом 3.5.10.0 с корневой файловой системой 2020.2;
    2. Компьютер с ОС Windows 10 и программами Modbus Poll Master 9.4.0 и Modbus Poll Slave 7.3.0;
    3. Преобразователь USB-RS485 модели ARC-485;
    4. Среда программирования Codesys 3.5 SP14 Patch 3;

    Настройки передачи:
    1. Порт 1;
    2. Скорость обмена 9600;
    3. Паритета нет;
    4. Стоповый бит 1;
    5. Номер устройства в сети 1;
    6. Количество запрашиваемых регистров 10;
    7. Начальный адрес 1.

    Полученные результаты:
    1. Компьютер с программой Modbus Poll Master 9.4.0 и контроллер АГАВА ПЛК-40.07 W с проектом ModbusRTUSlave:

    1) Практически все примеры режима RTUSlave в SDK (в независимости от версии), кроме ModbusRTUSlave_ (расположенной в SDK 10.7), являются не рабочими, так как в программе RTUSlave :
    а) в условии bFirstCycle не хватает строки: xEnable:=TRUE;
    или
    б) в строке: MBRTUSlave (xEnable=xEnable, xError=>xError, resIEC=>result); - нужно заменить xEnable=xEnable на xEnable=TRUE

    2)Практически во всех примерах режима RTUSlave в SDK (в независимости от версии), кроме ModbusRTUSlave_ (расположенной в SDK 10.7), отсутствует визуализация (что, мне как начинающему (студенту), сильно усложняет понимание работы RS в данном контроллере), поэтому модифицировал пример, в пределах своих знаний, (с русскими комментариями и визуализацией) для считывания Holding и/или Input регистров ПЛК. (хотел прикрепить файл проекта, однако форум выдал, что нельзя)


    2. Компьютер с программой Modbus Poll Slave 7.3.0 и контроллер АГАВА ПЛК-40.07 TV/WV с проектом ModbusRTUMaster:

    1) Так же как и
    ModbusRTUSlave, везде отсутствует визуализация и мало пояснений о работе примера программы;
    2) Непонятно:
    а) В какие переменные считываются данные из регистров подчиненного устройства?
    б) Где и какая переменная задает время опроса и время задержки между опросами?

    3) при использование проектов RTUReadHoldRegSync и RTUReadHoldRegAsync:
    1) Программа большую часть времени находится в режиме ошибки (MODE_ERROR), хотя по преобразователю интерфейса видно, что прием и передача происходит (RX и TX мигают с частотой соответствующей 1 с);
    2) Непонятно в какую переменную считываются данные из Holding регистра подчиненного устройства?


    Пожалуйста помогите разобраться как организовать работу контроллера АГАВА ПЛК-40 по RS-485 в режиме Master.
    Для реализации работы мастера на ПЛК-40 если у Вас возникают трудности Вы можете использовать реализацию мастера от компании 3s. Там все достаточно просто. Инструкций по Modbus 3S master в интернете очень много.

    Адресация портов у плк-40
    RS485-1: 3
    RS485-2: 4


    В примере у Slave в глобальной области определения переменных у Вас есть 4 типа таблицы согласно протоколу Modbus

    // Определения размера(адресации) таблиц.
    var_global constant

    REG_COILS_START: uint := 0;
    REG_COILS_NREGS: UINT := 2000;

    REG_DESCRETE_START: uint := 0;
    REG_DESCRETE_NREGS: uint := 2000;

    REG_HOLDING_START: uint := 0;
    REG_HOLDING_NREGS: uint := 2000;

    REG_INPUT_START: uint := 0;
    REG_INPUT_NREGS: uint := 2000;

    end_var


    // Приемные буферы для RTU Slave(сами таблицы)
    RegCoilsStart: uint := REG_COILS_START;
    RegCoilsBuf: array [ 0 .. REG_COILS_NREGS / 8 + 2 ] of byte;

    RegDiscreteStart: uint := REG_DESCRETE_START;
    RegDiscreteBuf: array [ 0 .. REG_DESCRETE_NREGS / 8 + 2 ] of byte;

    RegHoldingStart: uint := REG_HOLDING_START;
    RegHoldingBuf: array [ 0 .. REG_HOLDING_NREGS - 1 ] of word;

    RegInputStart: uint := REG_INPUT_START;
    RegInputBuf: array [ 0 .. REG_INPUT_NREGS - 1 ] of word;



    а) В какие переменные считываются данные из регистров подчиненного устройства?

    Пишите данные в нужную таблицу, согласно типу данных, например запись 16 бит значения в таблицу HolgingReg по адресу 100

    value := 1234;
    RegHoldingBuf[100] := value;

    пример записи в таблицу coils:

    SetBits( adr( RegCoilsBuf ), 1200, 1, sel(BoolValue, 0, 1 ) );

    Функция SetBits установит нужный бит в 0 либо 1 с нужным смещением

    RegCoilsBuf - приемный буфер coils
    1200 - адрес в таблице
    1 - количество записываемых бит
    sel(BoolValue, 0, 1 ) само записываемое значение.

    по discredInputs аналогично за исключением приемного буфера (RegDiscreteBuf)

    Если нужно записать float значение(32бит) то его нужно поместить в 2 holding регистра, например так

    RegHoldingBuf[1100] := Mem.LowWord( oscat_basic.REAL_TO_DW(FloatValue));
    RegHoldingBuf[1101] := Mem.HighWord( oscat_basic.REAL_TO_DW(FloatValue));

    в таком случае при запросе мастер нужно будет читать регистр 1100 длиной 2 слова


    б) Где и какая переменная задает время опроса и время задержки между опросами?

    ПЛК работает в режиме Slave. Он может только выдавать данные , время опроса и задержки это прерогатива мастера.
    Тут Вы лишь должны обеспечить условие постоянного вызова FB RTUModbusSlave в каждом цикле программы.


    3) при использование проектов RTUReadHoldRegSync и RTUReadHoldRegAsync:
    1) Программа большую часть времени находится в режиме ошибки (MODE_ERROR), хотя по преобразователю интерфейса видно, что прием и передача происходит (RX и TX мигают с частотой соответствующей 1 с);


    Тут нужно смотреть что и куда пишите , возможно где то допускаете ошибку по запросу.

    Комментарий


    • #3
      Спасибо за разъяснения по режиму Slave.

      Данные вопросы: а) В какие переменные считываются данные из регистров подчиненного устройства?
      б) Где и какая переменная задает время опроса и время задержки между опросами? -
      относятся к режиму Master.

      В примере ModbusRTUMaster, отсутствует область глобальных переменных и метод SetBits (и вообще методы есть только в примере ModbusRTUSlave).
      В примере ModbusRTUMaster только одна программа PLC_PRG, в которой, после настройки режима связи (возник вопрос б)), с помощью CASE последовательно выполняются функции чтения и записи регистров (возник вопрос а), так как отсутствуют упомянутая вами область глобальных переменных и методы)
      Нажмите на изображение для увеличения. 

Название:	ModbusRTUMaster.png 
Просмотров:	568 
Размер:	113.6 Кб 
ID:	663

      Примеры RTUReadHoldRegSync и RTUReadHoldRegAsync были взяты (без изменений) из SDK и загружены в контроллер.
      В Modbas Poll Slave были выставлены следующие настройки:

      Числа, которые должен прочитать ПЛК:



      Если я правильно понял, то надо смотреть на tmpbuf: array [0...255] of BYTE, тогда в режиме отладки ПЛК выдает следующее:


      И отсюда видно, что ПЛК считывает, не 10 регистров, а 8 и переданные числа, даже если их перевести в 2 систему исчисления, не совпадают с принятыми.
      Если я не туда смотрю, то тогда куда надо смотреть:
      Рисунок до запуска программы.


      Рисунок после запуска программы:
      ​ ​​​​​​​

      Комментарий


      • #4
        Сообщение от Никадим Посмотреть сообщение
        Спасибо за разъяснения по режиму Slave.

        Данные вопросы: а) В какие переменные считываются данные из регистров подчиненного устройства?
        б) Где и какая переменная задает время опроса и время задержки между опросами? -
        относятся к режиму Master.

        В примере ModbusRTUMaster, отсутствует область глобальных переменных и метод SetBits (и вообще методы есть только в примере ModbusRTUSlave).
        В примере ModbusRTUMaster только одна программа PLC_PRG, в которой, после настройки режима связи (возник вопрос б)), с помощью CASE последовательно выполняются функции чтения и записи регистров (возник вопрос а), так как отсутствуют упомянутая вами область глобальных переменных и методы)
        Нажмите на изображение для увеличения. 

Название:	ModbusRTUMaster.png 
Просмотров:	568 
Размер:	113.6 Кб 
ID:	663

        Примеры RTUReadHoldRegSync и RTUReadHoldRegAsync были взяты (без изменений) из SDK и загружены в контроллер.
        В Modbas Poll Slave были выставлены следующие настройки:

        Числа, которые должен прочитать ПЛК:



        Если я правильно понял, то надо смотреть на tmpbuf: array [0...255] of BYTE, тогда в режиме отладки ПЛК выдает следующее:


        И отсюда видно, что ПЛК считывает, не 10 регистров, а 8 и переданные числа, даже если их перевести в 2 систему исчисления, не совпадают с принятыми.
        Если я не туда смотрю, то тогда куда надо смотреть:
        Рисунок до запуска программы.


        Рисунок после запуска программы:
        все что было сказано выше , относится к Slave. К мастеру отношение не имеет.

        В примере с мастером демонстрируется работа с каждой функцией через case выполняется запрос.

        если смотрите пример ModbusExRTUMasterSync.project , а похоже вы смотрите его если у вас там есть tmpbuff , то данные из буфера нужно извлечь и привести к нормальному виду.

        как это сделать показано тут: http://forum.kb-agava.ru/filedata/fetch?id=97


        Комментарий


        • #5
          Здравствуйте!
          Спасибо за помощь.

          С режимом Master разобрался, но остался вопрос по следующей части кода:
          Код:
          iIndex1_1:                                                                                        INT;                                                          // Переменная для цикла считывания в методе 1 подчиненного устройства
          btQuantity:                                                                                       BYTE :=16;                                              //Количество считываемых регистров
          arrValueRead1:                                                                                ARRAY [0..btQuantity-1] OF REAL;        // читаем 4 функцией в методе устройство 1 адреса 0..btQuantity-1
          pBytes:                                                                                             POINTER TO BYTE;                               //Указатели на биты во временном буфере
          dw:                                                                                                   WORD;                                                    //Слово полученное объединением 2 байт
          pIntValue:                                                                                         POINTER TO INT;                                   //Указатель на слово, содержащее значение типа INT16
          
          pBytes := ADR( tmpbuf [iIndex1_1] );                                                               //Получаем адрес начального байта слова во временном буфере
          dw := Mem.PackBytesToWord( pBytes [iIndex1_1], pBytes [iIndex1_1+1] );   //Объединяем 2 байта в слово с начального байта по плюс первый байт
          pIntValue := ADR(dw);                                                                                      //Получаем адрес объединенного слова
          arrValueRead1[ iIndex1_1] := INT_TO_REAL (pIntValue^);                              //Разыменовываем указатель объединенного слова и преобразуем из целочисленного значения в значение с плавающей запятой
          Вопрос следующий:
          Для 1 значения получаем:
          pBytes := ADR( tmpbuf [0] );- адрес первого байта в первом слове
          dw := Mem.PackBytesToWord( pBytes [0], pBytes [1] ); - получается здесь объединяется 0 и 1 байты для первого слова

          Для 2 значения получаем:
          pBytes := ADR( tmpbuf [1] );- адрес первого байта во втором слове
          dw := Mem.PackBytesToWord( pBytes [1], pBytes [2] ); - получается здесь объединяется 1 и 2 байты для второго слова, но на самом деле происходит объединение 2 и 3 байтов

          Для 3 значения получаем:
          pBytes := ADR( tmpbuf [2] );- адрес первого байта в третьем слове
          dw := Mem.PackBytesToWord( pBytes [2], pBytes [3] ); - получается здесь объединяется 2 и 3 байты для третьего слова, но на самом деле происходит объединение 4 и 5 байтов

          Можете объяснить данную логику работы?

          Добавил в ваши примеры для Master (2 примера: 1-для чтения и записи на 1 подчиненное устройство; 2- для чтения с 2 подчиненных устройств) и Slave визуализацию, комментарии (насколько понял принцип работы) и убрал не используемые переменные: ModbusRTU_PLC40W.zip
          Последний раз редактировалось Никадим; 30-12-2020, 10:47 AM.

          Комментарий


          • Пушкарев Андрей
            Пушкарев Андрей комментирует:
            Редактировать комментарий
            Чтение 16 бит значения из буфера.

            tmpbuf[0] - тип byte
            tmpbuf[2] - тип byte
            tmpbuf[4] - тип byte

            смещение по буферу согласно его размеру по байтно , значение 16 бит записанное в буфер занимает 2 байта



            // значение 1 чтение.
            pBytes := adr( tmpbuf[0] );
            dw := Mem.PackBytesToWord( pBytes[0], pBytes[1] );
            pIntValue := adr( dw );

            Value1Read := pIntValue^;

            // значение 2 чтение.
            pBytes := adr( tmpbuf[2] );
            dw := Mem.PackBytesToWord( pBytes[0], pBytes[1] );
            pIntValue := adr( dw );

            Value2Read := pIntValue^;

            // значение 3 чтение.
            pBytes := adr( tmpbuf[4] );
            dw := Mem.PackBytesToWord( pBytes[0], pBytes[1] );
            pIntValue := adr( dw );

            Value3Read := pIntValue^;
            Последний раз редактировалось Пушкарев Андрей; 30-12-2020, 04:59 AM.

        • #6
          Спасибо за разъяснения. Поправил примеры согласно вашим рекомендациям: ModbusRTU_PLC40W.zip

          Комментарий


          • #7
            Здравствуйте! С наступившим!
            Можете объяснить что я сделал не так при добавлении в проект ФБ TMBRTUSlave?

            Нажал ПКМ на Application => В выпадающем меню выбрал Добавление объекта=> POU.
            В открывшемся окне ввел:
            Имя: TMBRTUSlave
            Тип: Функциональный блок
            Extends: TModbusRTUSlave
            Язык: ST
            Нажмите на изображение для увеличения. 

Название:	ModbusRTUSlave добавление ФБ в проект.png 
Просмотров:	476 
Размер:	24.8 Кб 
ID:	672

            Но вместо набора методов, приведенных в примере, получил 4 набора свойств с 2 вложенными свойствами в каждом (Get и Set).
            Нажмите на изображение для увеличения. 

Название:	ModbusRTUSlave.png 
Просмотров:	474 
Размер:	48.3 Кб 
ID:	673
            В чем я ошибся или что мне нужно сделать, чтобы настроить режим Slave в моё проекте?

            Комментарий


            • #8

              Сообщение от Никадим Посмотреть сообщение
              Здравствуйте! С наступившим!
              Можете объяснить что я сделал не так при добавлении в проект ФБ TMBRTUSlave?

              Нажал ПКМ на Application => В выпадающем меню выбрал Добавление объекта=> POU.
              В открывшемся окне ввел:
              Имя: TMBRTUSlave
              Тип: Функциональный блок
              Extends: TModbusRTUSlave
              Язык: ST
              Нажмите на изображение для увеличения.   Название:	ModbusRTUSlave добавление ФБ в проект.png  Просмотров:	11  Размер:	24.8 Кб  ID:	672

              Но вместо набора методов, приведенных в примере, получил 4 набора свойств с 2 вложенными свойствами в каждом (Get и Set).
              Нажмите на изображение для увеличения.   Название:	ModbusRTUSlave.png  Просмотров:	11  Размер:	48.3 Кб  ID:	673
              В чем я ошибся или что мне нужно сделать, чтобы настроить режим Slave в моё проекте?
              Здравствуйте FB TMBRTUSlave наследуется от другого класса. Если добавите к нему соответствующие наследование , то у Вас в вашем экземпляре появятся все нужные методы.

              объявление
              function_block TMBRTUSlave extends TModbusRTUSlave



              в реализации fb
              super^( xEnable := xEnable, xError => xError );

              Все методы уже имеются у данного экземпляра FB. Если Вы не видите данные методы , это не означает что их не существует у данного экземпляра FB


              По свойствам либо удалите их , о чем написано в самом свойстве и используйте базовую реализацию, либо создайте собственную реализацию.

              {error 'добавить реализацию свойства или удалить свойство, чтобы использовать базовую реализацию'}
              (* Количество стоп-битов.*)
              PROPERTY StopBits : SysCom.COM_StopBits
              Последний раз редактировалось Пушкарев Андрей; 11-01-2021, 05:34 AM.

              Комментарий


              • #9
                Спасибо за разъяснения!

                Комментарий

                Обработка...
                X