Технология автоматного программирования для ПЛК на языке LD

Моя цель - предложение широкого ассортимента товаров и услуг на постоянно высоком качестве обслуживания по самым выгодным ценам.

В предыдущих статьях мы фрагментарно описали практику автоматного программирования для ПЛК. Здесь мы сведем все в одном месте и кое-что добавим. Ответы на вопросы, которые все же могут возникнуть после прочтения данного материала, можно найти в ранее написанных статьях автора. Перечень базовых статей следующий:

1. Автоматное программирование: определение, модель, реализация. https://habr.com/ru/post/682422/

2. Вот, как просто! Автоматы в деле. Для ПЛК фирмы DELTA. https://habr.com/ru/post/685098/

3. Автоматы в деле. Штабелер. Засады ПЛК. https://habr.com/ru/post/688480/

Задание на проектирование программы

В предшествующей статье мы уже рассматривали штабелер. Здесь будет более сложный его  вариант. Это узкое «крыло», которое, находясь в исходном состоянии, с паузой после старта проката подхватывает лист металла и поддерживает его в процессе движения. После останова проката и отсечения листа оно выполняет «отскок» вперед, освобождая конец листа, который падает на приемное устройство - гидростол.  После этого "крыло" возвращается в исходное состояние. Во время этих движений прокат должен быть остановлен. После исполнения задания (формирования нужного числа листов заданной длины)  «крыло» перемещается в заключительную позицию за пределы гидростола. Возврат в исходное состояние происходит после нажатия кнопки «Штабелер». Выполнение самого задания начинается с нажатия кнопки «Прокат», а длина отдельного листа и общее их количество указывается на панели оператора. 

После нажатия кнопки «Сброс» (прокат останавливается, переходя в режим паузы) штабелер должен войти в режим паузы. Повторное нажатие кнопки выполняет реальный сброс системы управления. Продолжить прокат, находясь в ситуации паузы,  можно с помощью кнопки «Прокат». Штабелер, находясь в режиме «Автомат», может входить в тот же режим паузы, но после формирования текущего листа.   Работа штабелера в режиме системы «Полуавтомат» несколько отличается от работы в режиме «Автомат». В первом случае он останавливается после выполнения проката и ожидает срабатывания гильотины (в режиме «Полуавтомат» она запускается вручную). Дождавшись, он сбрасывает лист и перемещается в заключительную позицию. Из нее нажатием кнопки Штабелер «крыло» возвращается в исходное состояние. В режиме «Автомат» перемещение в заключительную позицию происходит только после выполнения задания.

Алгоритм управления штабелером в форме двух взаимодействующих конечных автоматов (КА) представлен на рис. 1. Более простой автомат  представляет алгоритм работы с датчиками, другой - алгоритм управления штабелером. Реакцию на сигнал паузы, на кнопку «Штабелер», а также на сигнал запуска реализуется обычными средствами языка LD и вынесено за рамки нашего обсуждения.  

Рис. 1. Алгоритм работы «Штабелера-крыло»
Рис. 1. Алгоритм работы «Штабелера-крыло»

Процесс создания модели программы

Программирование начинается с модели программы. В нашем случае это будет модель в форме конечного автомата. Ее (модель) можно «держать в голове», рисовать на листе бумаги, но настоятельный совет – используйте графический редактор. У нас это редактор Microsoft Office Visio. Он обладает всем, что помогает нарисовать граф, подобный графу автомата на рис. 1. Причем, чем сложнее автомат, тем больше выгоды будет от его применения. Далее, например, путем обычного копирования элементов имеющегося графа можно создавать графы уже любой сложности.

 В нашем случае от графического редактора нужно не так уж много. Рисовать, во-первых, состояния в форме кружков с пометками внутри – именами состояний (у нас это будут только номера). Во-вторых, соединять состояния направленными дугами и помечать их условиями переходов и выдаваемых сигналов. Кроме этого, Visio позволяет легко изменять вид графа, перемещая вершины, что ведет к автоматическим изменениям соединяющих их дуг.

Вершинам графа можно поставить в соответствие то или иное действие, ассоциировать с ним некую предысторию работы алгоритма и т.д. и т.п. Например (см. рис.1), вершина 0 – это начальное состояние алгоритма. Вершина с номером 33 – состояние ошибки. В состоянии 1 выдаются сигналы управления движением крыла. В состоянии 4 – лист сброшен и выполняется «отскок», при котором крыло попадает в состояние 2. Из него модель может продолжить работу или, выполнив задание, перейти в состояние 44 и т.д. и т.п.

Фактически каждое состояние алгоритма имеет тот или ной смысл, а потому, наблюдая за ними (а мы такую уникальную возможность имеем!), можно понять, что происходит с алгоритмом в любой момент времени. Возможность наблюдения за состояниями превращает тестируемый алгоритм из «черного ящика» в «белый ящик».

Автоматная модель позволяет объективно оценить сложность будущей программы. Она зависит от числа состояний автомата, количества входных/выходных каналов, связности графа, т.е. множества и разнообразия переходов, и сложности предикатов и действий.  Предикаты и действия в случае ПЛК достаточно просты. Обычно это: прочитать вход ПЛК в случае предиката и/или установить выходной сигнал в случае действия. А вот логика алгоритма, особенно при взаимодействии с другими функциональными блоками, способна доставить массу хлопот.

Так что программирование для ПЛК не столь уж простое, как это может показаться на первый взгляд.

Процесс кодирования

Создав модель, мы переходим к ее реализации. Перейдя в дерево проекта, в папке функциональных блоков (ФБ), создаем заготовку - функциональный блок. Он должна иметь элементы, соответствующие конструкции автомата на языке LD. Как минимум, это два входа и один выход. Входные каналы – это канал сигнала сброса и канал с присвоенным автомату элементом массива текущих состояний автомата. Выходной канал – элемент массива теневых состояний с индексом равным индексу текущих состояний.

Код вызова ФБ для штабелера представлен на рис. 2. Данный функциональный блок имеет описанные выше каналы. Остальные каналы задаются локальными переменными соответствующего типа. Так, переменные типа VAR_INPUT создают входные каналы, VAR_OUTPUT – выходные, VAR_IN_OUT – совмещенные входные/выходные каналы, а тип VAR – это обычные локальные переменные.

Рис.2. Функциональный блок управления штабелером
Рис.2. Функциональный блок управления штабелером

Рис.3 дает полное представление о локальных переменных. Переменные с именами bClear, inState, outState соответствуют упомянутым выше каналам. На рис. 4 приведен код инициализации ФБ и код работы с таймерами. Инициализация при включении ПЛК и/или получении сигнала сброса устанавливает автомат в начальное состояние.

Создав заготовку, можно приступить к кодированию автомата. Код каждого перехода автомата имеет единый вид: сначала идет проверка текущего состояния автомата и входных условий, затем, если это необходимо (для автоматов Мили), - выполнение действий и в завершение изменение текущего состояния. Если текущее состояние не изменяется, то последнюю операцию можно опустить. Образец кодирования переходов, исходящих из начального состояния 0 (см. рис.1) дан на рис. 5.

Рис.3. Локальные переменные ФБ Крыло2ДБУ
Рис.3. Локальные переменные ФБ Крыло2ДБУ
Рис.4. Инициализация ФБ и управление таймерами
Рис.4. Инициализация ФБ и управление таймерами
Рис.5. Пример кодирования переходов автомата
Рис.5. Пример кодирования переходов автомата

Реверс-инжиниринг

Не секрет, что программисты не любят документировать программы. От этого часто страдают они же сами, т.к. часто спустя уже какое-то время даже сам автор программы с трудом может разобраться в своем творении.  Но, даже понимая это, рисование блок-схем, графов, детальное описание алгоритма и т.п. – это не про программистов. Достаточно кратко, весьма ярко и доходчиво процесс документирования программ описан в статье [1]. Полемизируя с ней,  можно утверждать, что в рамках технологии автоматного программирования программы все же обладают свойством самодокументирования и это совсем не чушь.

Безусловно, разобраться с алгоритмом программы по ее коду весьма проблематично.  На рис. 6 приведен код программы, созданный для модели на рис.1, в режиме просмотра для последующей распечатки. Это восемь убористо заполненных листов на языке LD. Сравните его с графом автомата. Что из них нагляднее и понятнее, думаю, вопрос риторический.

Но, с другой стороны, зная принцип кодирования автоматной программы, вы можете по коду программы легко восстановить граф автомата. Так, во-первых, сразу ясно, сколько состояний имеет программа. Во-вторых, легко восстановить переходы между состояниями, т.к. каждой цепи соответствует, как правило, ровно один переход, а действия программы привязаны или к состояниям программы, или представлены на соответствующих переходах. Останется только добавить смысловую интерпретацию условий и действий, в чем может помочь уже комментарий. Конечно, если их нет (совсем уж, видимо, «гениальный» программист создавал программу или комментарии просто не доступны), то придется все интерпретировать самому.

Тестирование программы

Тестирование, наверное, самый важный этап во всем процессе разработки программы. Программа, работающая с ошибками, ни кому не нужна, будь она трижды автоматной или какой-то там еще. Но автоматы и здесь предоставляют возможность, которой нет у программ, спроектированных обычным способом. Только автоматная программа позволяет автоматически отслеживать текущее состояние программы. А это может сказать о многом, т.к. отражает поведение программы в динамике.

Конечно, в программу можно ввести флаги, отражающие ее поведение. Но, во-первых, флаги нужно придумать, правильно расставить и предусмотреть код для их установки и сброса. Т.е. то, что на уровне автомата формируется естественным образом, в случае использования флагов требует определенных усилий и сосредоточенности. В конце концов, использование флагов просто ненадежно, за что их не критиковал разве что только ленивый.

Но у ПЛК есть одна неприятная особенность – отсутствие пошаговой отладки. Присуще ли это только ПЛК фирмы DELTA или и другим – не знаю, но в данном случае, как говорится, что есть, то есть. Для программистов, привыкших к возможностям современных отладчиков, это будет, скорее всего, если не шоком, то определенной «новостью» (как это было для автора).  Но и здесь состояния автомата более чем кстати.

 

     

Рис.6. Код ФБ на языке LD (режиме просмотра печати)
  Рис.6. Код ФБ на языке LD (режиме просмотра печати)

Рис. 7 демонстрирует процесс отладки. Из него следует: штабелер находится в состоянии 1 и идет процесс проката, т.к. флаг проката bЕслиПрокат = true. «Крыло» находится в движении, о чем говорят установленные сигналы управления двигателем – Y20 и Y22. При этом оно явно сошло с исходной позиции, т.к. awState[47] = 2 (см. автомат датчиков на рис.1). Режим работы выбран автоматический – bM10M11 = true, т.е. это режим «Полуавтомат» или «Автомат». Нам остается только крутить энкодер и отслеживать состояние проката на панели оператора, где отображается текущая длина листа в поле «Исполнено» (см. рис.8).

 

Рис.7. Процесс отладки программы
Рис.7. Процесс отладки программы

Рис.8. Пульт оператора
Рис.8. Пульт оператора

 

Заключение

Существует просто огромный пласт информации, обсуждающий этапы проектирования программ (см., например, [2]). Но среди этой информации мало такой, которая бы за базу брала модель программы. А от нее зависит многое, если не все. В основе технологии автоматного программирования лежит сетевая конечно-автоматная алгоритмическая модель. Это позволяет охватить и параллельные процессы, без которых современное проектирование просто немыслимо.  И если обычное программирование только-только осваивает параллелизм, то в ПЛК в той или иной мере его используют давно. Здесь он может быть представлен модулями POU, которые содержать разнообразные функциональные блоки, работающие параллельно.

Но параллельно работающие ФБ, взаимодействуя друг с другом, порождают достаточно сложные процессы, поведение которых необходимо анализировать. Анализ этого - весьма сложная и трудоемкая задача.  Для модели штабелера это еще выполнимо и сводится к построению для сети из двух автоматов эквивалентного однокомпонентного автомата. Это будет автомат, имеющий 27 состояний. Уже одно их количество (а, ведь, нужно еще найти все переходы между состояниями) способно подавить любое желание строить подобные планы.

Поэтому дальнейший анализ на уровне параллельных процессов, как правило, делается на основании интуитивных предположений. Например, если нет сомнений в правильности созданных автоматов, то не так уж много причин беспокоиться и по поводу их совместной работы. Хотя в этом случае только полноценное тестирование способно рассеять все сомнения на этот счет.  

И все же основной вывод, к которому пришел лично я, как программист,  уже довольно давно: только следование технологии - необходимая основа качественного программирования. Нынешнее программирование, если и является, как принято считать, искусством, то искусством кустарным. Все в нем сделано как-то - "на коленке". Чтобы искусство превратилось в мастерство, нужна технология, опирающаяся на теорию. Я выбрал и выбираю автоматную технологию, которую описал в своих статьях.

Если бы была технология, которой бы я доверял больше, чем своим автоматам, то я бы использовал  ее. И, казалось бы, есть из чего выбирать. Тот же UML или Simulink, на память приходят автоматы в Qt, SWITCH- технология, в конце концов, и т.д. и т.п. Но на поверку оказывается, что это или вовсе не автоматы, а только их названия, или весьма ограниченные версии автоматов. Поэтому я выбираю те автоматы, где ... правильно работает модель RS-триггера. Почему он? Потому что объективные доказательства правильности его работы доказывают корректность параллельных свойств среды исполнения параллельных процессов. Ведь, все так просто!

Ну, вы понимаете о чем я... Лично у меня-то выбора уже нет, а у вас ... на одну испытанную технологию больше. Везет же! Но только кому?...

  


Литература.

1. Самодокументируемый код – это (как правило) чушь. https://habr.com/ru/company/piter/blog/460725/

2. Проектирование программного обеспечения. https://habr.com/ru/company/edison/blog/267569/

Источник: https://habr.com/ru/post/690690/


Интересные статьи

Интересные статьи

NewLang — это язык программирования высокого уровня в котором можно сочетать стандартные алгоритмические конструкции с декларативным программированием и тензорными вычислениями для задач машинного о...
Здравствуйте, уважаемые читатели.Обычно, когда речь заходит о создании какого-либо расширения для существующего языка программирования, в воображении неминуемо начинают рождаться разнообразные сложные...
В этом посте я расскажу о простом блокноте на языке программирования Vala. Программа создавалась с использованием среды разработки GNOME Builder и редактора интерфейсов ...
Натуральные языки — это очень пластичные системы, которые постоянно меняются. В английском языке, к примеру, каждый день появляется примерно 30 новых слов и ровно столько же устаревае...
Привет, Хабр. Эта статья будет в немного «пятничном» формате, сегодня мы займемся NLP. Не тем NLP, про который продают книжки в подземных переходах, а тем, который Natural Language Processing ...