Лекция CoDeSys (Новиков). Вызов ф-ии. С перечислением значений параметров. В языках Паскаль и Си вызов ф-ии производится по имени, с перечислением в скобках списков актуальных входных параметров, через запятую, слева – направо. Аналогичный способ применён в языке ST. Например Y:=MUX(0, x1,x2); (*возвращает нулевой вход х1*) Здесь обратим внимание на то, что наименования параметров нам не нужны. При перечислении параметров важно только правильно соблюсти последовательность в соответствии объявлениями функции. В графических языках порядок входных параметров определяется сверху – вниз. (Вставить рисунок.) 0-----| Х1---| X2 Некоторые ф-ии могут иметь равнозначные параметры. В этом случае их порядок безразличен. Например: Y:=MAX(x1,x2)(*Возвращает наибольшее по значению входных параметров*) Y:=MAX(x2,x1)(*Возвращает то же*) Присваивание значений параметроам ф-ии. Вторым способом вызова ф-ии предусмотрено непосредственное присвоение значний параметрам ф-ии по именам. Пример: stHello:=concat(st:=’Добрый’, str2:=’День’); Тоже самое можно записать так: stHellow:= (‘Добрый’,_'день'); Возможны модификации этих записей когда, допустим Добрый может быть указано просто в апострофах, а переменная str2 будет принимать значение день. Если в программе уже определена переменная с именем совпадающим со значением входного параметра, то следующий вызов может показаться нелогичным: stHellow:=concat(str1:=str1, str2:=’День’) На самом деле здесь всё правильно т.к. слева от знака присваивания находится параметр функции, справа – переменная. Данный способ вызова функции предполагает возможность задавать параметры в произвольном порядке и опускать некоторые из них. (Данная версия 2.4 CoDeSys не обеспечивает ф-ям такой возможности. С версией 3 всё работает) Ф-ии с переменным числом параметров. Для многих ф-ий трудно предугадать сколько значений нужно будет обработать в конкретном случае. Например для ф-ии AND можно ограничиться двумя входами и использовать «лесенку вызова ф-ии» для обработки большего числа переменных. Например: Данная конструкция не очень красивая, логичней было бы иметь возможность расширить ф-ию: Лекция CoDeSys (Новиков). Так как показано на рисунке. МЭК предусматривает такую возможность. В текстовых языках расширение производиться добавлением переменных в конец списка параметров. В графических языках щелчком на правой клавиши мыши и выбор добавить параметр. Операторы и ф-ии. Операторы – это символы определённых операций. Их можно определить и как ф-ии наделённые определёнными привилегиями. Во-первых вход для оператора транслятор задаёт сам и е требует подключения библиотек. Во-вторых многие операторы меют особые формы записи в выражениях st например математич операторы (сложение, вычитание, умн., деление.) имеют традиционное представление в символьных языках. Соответсвенно + - * /. В графич языках эти опер-ры выглядят как обычные ф-ии. Можно обходиться без символьного представления. Например: Y:=SUB(MUL(4,x),3); Но символьно представление проще и нагляднее Y:=4*x-3, В математике ещё проще Y=4x-3 Все записи равнозначны по смыслу. Символьное представление понятнее и даёт возможность больше сконцентрироваться на сути выражения, а не на форме представления. Перегрузка ф-ий и операторов. Существует много ф-ий имеющих смысл для переменных разного типа. Например ф-ия MAX возвращает наибольшее из входных значений. Очевидно, что подкоманд микропроцессора, оперирующих с переменными типа Sin и Real, должен быть разным . Но с т. зрения МЭК – это одна и та же ф-ия. Автоматическая генерация разного кода для одной ф-ии, в зависимости от типа переменной называется перегрузкой. Реализация перегрузки польз-ой ф-ии достаточно сложна для транслятора. Перегрузка операторов прозрачна для компилятора только с т.зрения типов. В пользовательских ф-ях это приводит к сложно локализуемым ошибкам. Многие стандартные ф-ии и операторы поддерживают перегрузку. Тип самой ф-ии определяется требованием совместимости с входными параметрами. Так, если ф-ия MAX, с входными параметрами типа INT, в этом случае выход будет типа INT. Пример ф-ии. Рассмотрим пример ф-ии целого типа с именем Near_by . Возвращающий ближайший к образцу вариант обращения из двух входных переменных in1, in2, patt. FUNKTION NEAR_by: INT VAR_INPUT Patt, in1, in2: INT; END_VAR На языке ST тело ф-ии выглядит следующим образом: IF ABS(in1-patt)<ABS(in2-patt) THEN NEAR_by:=Iin1; ELSE NEAR_by:=Iin2; END_IF Локальные переменные в этом примере не использованы, соответственно секция объявления переменных VAR отсутствует. На языке IL данная прога будет выглядеть так: Лекция CoDeSys (Новиков). LD in2 SUB patt ST tmp LD in1 SUB patt ABS LT tmp NOT JMPC ret_in2 LD in1 ST NEAR_by RET Ret_in2: LD in2 ST NEAR_by В данном примере исп-ся промежуточная переменная tmp , которую необходимо объявить в разделе объявления локальных переменных. VAR Tmp:int; END_VAR Аналогичная ф-ия на языке FBD может быть реализована с применением бинарного мультиплексора. Ограничение возможностей ф-ии. Можно ли написать ф-ию с внутренней памятью? Ответ – можно, если пойти на хитрость и использовать в ф-ии глобальную переменную. Значение такой переменной сохраняется при повторном вызове. При этом сама ф-ия будет обладать уникальной глобальной переменной. В этом случае можо сделать ф-ию счётчик, подсчитывающих число вызовов ф-ии в глобальной переменной. Создать несколько независимых счётчиков на основе такой ф-ии невозможно. Кроме того можно обратиться из ф-ии к неким аппаратным средствам посредством прямоадресуемых переменных, например к системному таймеру. В этом случае ф-ия будет возвращать разные значения для одинаковых входных данных. Но на самом деле глобальная переменная и аппаратный ресурс ф-ии не принадлежат. В этом случае они для ф-ии являются формальными параметрами. Разница в том, что законный параметры для ф-ии готовят вызывающий код, а значение глобальной переменной она добывает сама. Локальные переменные, имеющие явно заданные начальные значения, получают их всякий раз в начале работы, если начальные значения не заданы ситуация может быть различной. Транслятор может обнулить их принудительно или не тратить на это время и возьмёт случайные значения – это зависит от реализации системы. Некоторые генераторы кода имеют специальный флажок в настройках, который предоставляет программисту выбор – скорость или дополнительная страховка от случайных ошибок. Обычно транслятор размещает локальные переменные и параметры ф-ии в стеке, но это не всегда так. Возможно, что из соображений оптимизации или в силу аппаратных ограничений (некоторые процессоры имеют очень маленький стек) для ф-ии отводится место в статической области памяти данных. Тогда может получиться, что ф-ия может сохранять свои значения между вызовами – это Лекция CoDeSys (Новиков). исключение из правил используется крайне редко и оно крайне опасно . Компоненты SFC диаграмм требуют некоторой области памяти данных для запоминания своего текущего состояния. Поэтому они и не используются в ф-ях. C экземплярами функциональных блоков ситуация похожа. Если экземпляр ф-ого блока создать в локально памяти ф-ии, то его переменные будут принимать начальные значения при каждом вызове ф-ии. Иногда это не существенно. CoDeSys не ограничивает такую возможность следуя з-ну Кейсара «Можно сделать защиту от дурака, если дурак не изобретательный.» По определению ф-ия возвращает только одно значение, но это можно обойти. Тип ф-ии может быть составным, например структурой. Здесь нужно иметь ввиду, что прежде чем использовать данные этой структуры, её придётся присвоить некоторой относительной переменной. Такое присвоение выполняется транслятором путём побайтного копирования. Фактически – это цикл скрытый от глаз программиста цикл за знаком равенства. При копировании структуры или массива, требуется некоторое время, пропорциональное размеру. Ф-ия обязательно должна иметь хотя бы один входной параметр и обязательно должна возвращать значение. Если возвращать нечего – возвращаем BOOL!!! Можно даже не присваивать значение выходной переменной, тогда по умолчанию возвращается False. Возврат BOOL имеет мизерные затраты кода для любого типа процессора. Если применение ф-ии по каким-либо причинам затруднено или нецелесообразно – используется ф-ый блок. Функции в логических выражениях. Они имеют одну тонкость, которая заключается в том, что логические выражения не всегда вычисляются целиком. Возможно, что по некоторой начальной части выражения можно сделать вывод об итоговом значении, т.е. если выражение содержит ф-ии, то нельзя гарантировать, что все они будут вызваны. Пример IF FUNC1(X) OR FUNC2(X) THEN Если func1(x) возвращает True, то Func2(x) возвращать не будет. В данном примере нельзя гарантировать, что ф-ия NORMA будет вызвана 2 раза. Если первый вызов даст FAlse, то понятно, что дальше логическое выражение можно не проверять. В ф-ях крайне не желательно выполнять запись выходов ПЛК и глобальных переменных. Отловить такую ошибку практически не возможно. Связанно это с тем , что даже, если конкретная программа успешно работает на 1-ом ПЛК, ошибка может проявиться в другой версии компилятора или в другой программной среде. Функциональный блок. FB – это программный продукт(компонент), отображающий множество значений входных параметров на множество выходных. После выполнения функционального блока все его переменные сохраняются до следующего вызова. Следовательно, ф-ый блок вызываемый с одними и теми же входными параметрами может выдавать различные выходные значения. В нём сохраняются все переменные, включая входные и выходные. Так, если вызвать FB не определяя значения некоторых входных переменных, он будет использовать ранее установленные значения. Возможность задания переменного числа входных значений заложено по определению. Из вне достпны только входы и выходы ф-ого блока. Получить доступ к внутренним переменным блока нельзя. С позиции ООП FB – объект. Лекция CoDeSys (Новиков). Создание экземпляров FB. Прежде чем использовать FB, необходимо создать его экземпляр. Эта операция по смыслу аналогична объявлению переменной. Описав новый блок мы, фактически создаём новый блок, подобный структуре. Каждый FB может иметь любое количество экземпляров. Так например экземпляры блока ТАЙМЕР, совершенно не зависимы друг от друга. Каждый из них имеет собственные настройки. Каждый блок имеет собственный идентификатор и свою область значения в статической памяти. Объявление доп. Экземпляра FB приводит лишь, к ещё одной области памяти данных, код остаётся общим. Экземпляр FB создаётся в разделе переменных или в разделе глобальных переменных. Как и переменная, получает уникальный идентификатор. Например, создание стандартного экземпляра FB – инкрементный счётчик с идентификатором ctuTIMEMETER: ctu; Из этого следует,что создавать экземпляры можно только для известных системе блоков. Это библиотечные блоки или блоки созданные пользователем. С точки зрения транслятора создание экземпляра означает выделение необходимой памяти для реализации необходимых блоков. Экземпляр FB можно не только вызывать, но и использовать в качестве других переменных других FB. Доступ к переменным экземпляра. После создании экземпляра FB можно начинать с его данными, при это совсем не обязательно вызывать блок. Обращение к переменным экземпляра точно такое же как к элементам структуры данных – через точку. ctuTIMEMETER.RESET:=FALSE; ctuTIMEMETER.pv:=100; x1:= ctuTIMEMETER.cv; Специальный индекс «=>» позволяет получить значения выхода сразу после выполнения блоков. На языке IL можно написать CAL ctuTIMEMETER (RESET:=FALSE, cu:=INP1, cv => x1); На языке ST запись выглядит также только без CAL. При вызове FB можно определять только необходимые Лекция CoDeSys (Новиков). параметры, причём в произвольном порядке. Входы экземпляра доступны для записи и чтения. Выходы только для чтения. Изменять значения выходов можно только из тела блока из вне нельзя. Транслятор отслеживает подобные действия и выдаёт соответствующие ошибки. Вызвать экземпляр FB с перечислением параметров как ф-ию нельзя. Значения входных переменный должны присваиваться непосредственно. В текстовых языках входный переменные перечисляются в скобках, сразу после имени экземпляра. В графических языках неиспользуемые входы и выходы остаются неподключёнными. На языке ST при отсутствии параметров после имени экземпляра скобки ставить не нужно. Т.е. ПРИМЕР: ctuTIMEMETER(); - лишние пустые скобки Использовать экземпляр FB в выражении нельзя, но можно использовать входы и выходы. Например, X1:=ctuTIMEMETER.pv – ctuTIMEMETER.cv +1; Моджно определять значения входов блока заранее и вызывать экземпляр ф-ого блока вообще без параметров. Пример на языке ST: ctuTIMEMETER.RESET:=FALSE; На языке IL: LD ctuTIMEMETER.RESET; ST ctuTIMEMETER.RESET; Cal ctuTIMEMETER; Инициализация данных экземпляров. При описании FB в разделе объявления переменных, можно явно присвоить начальное значение переменной. Например FUNCTION BLOCK SyncSwich Var ……….. Sync:BOOL:=FALSE; При создании функционального блока пеменная Sync получит значение FALSE, если начальное значение не заданно – используются нулевые значения. Экземпляр FB может потребовать индивидуальной инициализации, отличной от той, которая определена при реализации. Установку начальных значений проще выполнить при создании экземпляра. Значения данных при создании экземпляра сильнее значений, заданных при реализации блока. SyncSw1:SyncSwich:=(sync:=TRUE) // Теперь переменная SyncSw1. Получит начальное значение True, не смотря на значение, указанное при объявлении блока. Физические ч значения переменная получает ещё до использования экземпляра. Возможны случаи, когда экземпляру FB . Например при настройке блока необходимо произвести некоторые вычисления. Специальной процедурой инициализации в FB не предусмотрено, поэтому на инициализации придётся потратить несколько первых циклов выполнения экземпляров. Окончание инициализации обычно индицируется выходом ENO – выходом готовности. Часто удобно применять для инициализаии действия и сосредоточить контроль для инициализации в одном месте (обычно шаг InitSfc). Такой подход позволяет производить инициализацию данных, экземпляров блок и программ в необходимой последовательности и взаимосвязи. На практике для блоков требующих определённой настройки достаточно ввести несколько дополнительных блоков (уставов), так делается во всех стандартных блоках. Лекция CoDeSys (Новиков). Особенности реализации и применения FB. Входные переменные внутри блока доступны для записи – это вызывает определённый соблазн для программиста. Так например входную переменную удобно использовать в качестве перемнной счётчика. Это позволяет избежать создания дополнительной локальной переменной. Т.к. при вызове экземпляра блока вводная переменная должна получать новое значение ничего страшного, на первый взгляд, в этом нет. Вызов экземпляра не обязан сопровождаться присваиванием значений все формальным параметрам. Возможно, что в какой-то момент мы решим, что входной параметр определён и можно не задавать его повторно, в результате значение параметра будет равно тому значению, которое он имел в роли локальной переменной при предыдущем вызове экземпляра. Использовать такой приём нужно крайне осторожно. В общем случае входная переменная экземплярного блока нужно рассматривать как константу. Применение глобальных переменных в FB вызывает такие же проблемы. В этом случае экземпляры перестают быть независимыми. Применение глобальных переменных в функции блоках вызывает теже проблемы,ч то и в функциях, экземпляры блока перестают быть независимыми. Изменение переменной, выполняемое одни блоком, проявляет себя совсем в другом месте. Иногда это необходимо, в обычной практике желательно ограничить такое применение глобальных переменных. Если экземпляры FB используют глобальную переменную по чтению – проблем не будет. Аналогичная ситуация с прямо-адресуемой памятью. Единственная проблема – это повторное использование блоков. При использовании других адресов в другой программе или блоке их придётся поправить. Решение этой проблемы даёт использование шаблонных переменных. ШАБЛОННЫЕ ПЕРЕМЕННЫЕ Шаблонные переменные – конфигурационные переменные. Являются частично-определёнными, прямо-адресуемыми переменными. Прямой адрес заменяется звёздочкой (*). Определение полного адреса определяется в специальном разделе ресурсов. Пример: Создание функционального блока Shaman. Пусть этот блок содержит локальную переменную bMAR. FUNCTION BLOCK SHAMAN VAR bMAR AT % I*: bool; END_VAR Создадим два экземпляра FB в главной программе: PROGRAMM PLC_PRG VAR SHAM1: SHAMAN; SHAM2: SHAMAN; END_VAR Для того чтобы окончательно разобраться с шаблонной переменной экземпляров их необходимо описать в разделе ресурсов проекта. В разделе ресурсов появится: VAR CONFIG PLC_PRG.SHAM1.bMAR AT%I1.0:bool; PLC_PRG.SHAM2.bMAR AT%I1.1:bool; Типы данных шаблонной переменной указанной в объявлении блока и при настройке адреса в ресурсах обязаны совпадать. ПРИМЕР ФУНКЦИОНАЛЬНОГО БЛОКА. В качестве простого примера реализуем блок синхронного переключателя SyncSwitch. Алгоритм его работы следующий: выход переключателя – Q принимает значения равные входу START, но переключение выхода разрешено только при SYNC=True. Лекция CoDeSys (Новиков). Диаграмма работы синхронного переключателя. Условие включения выхода выражается следующей формулой: Q = Start and Sync, а условие выключения – Q= NOT START and Sync. Значение выхода должно сохраняться между синхроимпульсами. Поэтому использовать для программирования этого устройства функцию нельзя. Пример реализации блока SyncSwitch на языке IL: FUNCTION BLOCK SYNCSWITCH VAR_INPUT START: BOOL; SYNC: BOOL; END_VAR VAR_OUTPUT Q: BOOL; LD SYNC AND START ST Q LD SYNC ANDN START ST Q Такой блок полезен для реализации «безуадарного» переключения в цепях переменного тока. Импульсы синхронизации должны отражать интервалы, когда мгновенное значение интервала = 0. В этом случае переключение силовой цепи с выхода SYNCSWITCH будет происходить без броска тока. ДЕЙСТВИЕ В функциональных блоках не хватает возможности выполнять несколько различных операций, особенно, если блок содержит объёмные данные. Можно, конечно сделать дополнительный вход и по нему анализировать, что мы хотим от блока. В CoDeSys такая возможность реализована. Функциональные блоки и программы можно дополнять действиями. Действия работают внутри блока с полным доступом ко всем данным. Его можно вызвать как из блока так и из вне. Действие указывается через точку (.) после названия экземпляра блока и может иметь значения входов и выходов. При вызове действия из тела блока наименование экземпляра не требуется. Действие не имеет собственных данных и использует входы, выходы и локальные переменные блока. Язык Лекция CoDeSys (Новиков). реализации действия произвольный Дополним блока SYNCSWITCH действием Break. Пусть вызов данного действия приводит к безударному переключению выходов. Для определения действия необходимо выбрать блок в организаторе объектов и дать команду ADD ACTION. Опишем действия на языке ST как Q:=False. Вызвать действие из ST программы можно так: SYNCSWITCH1.BREAK(Q=>q); В графических языках прямоугольник представляющий данное действие будет иметь заголовок SYNCSWITCH1.BREAK (обратим внимание на то что окно редактора для действия не имеет радела объявления переменных). Компоненты программ с действиями имеют раскрывающиеся списки в организаторе объектов. Список действий в разделе объявлений POU не отражается. В CoDeSys действия можно использовать как код программы. ПРОГРАММЫ Программа – глобальный программный глобальный компонент, отображающий множество значений входных параметров на множество выходных. Программа похожа на функциональный блок. Она является самым крупным компонентном. При помощи программ организуется верхний уровень проекта и управление многозадачностью. ИСПОЛЬЗОВАНИЕ ПРОГРАММ Обращение к переменным и вызов программ ничем не отличается от работы с экземпляром FB. Правильные, с точки зрения стандарта проект должен включать одну или несколько программ, ассоциированных с задачами. При этом число функций и FB не ограниченно. Экземпляров программ не существует в отличие от FB. Все программы определены глобально, существуют в единственном экземпляре. Ограничений на количество и способ использования программ в CoDeSys нет. При создании проекта codesys автоматически создаёт программу PLC_PRG в однозадачном проекте она является главной. Цикл выполнения в пользовательской задаx сводится циклическому вызову PLC_PRG, которая в свою очередь содержит вызовы всех почих необходимых компонент. СТРУКТУРА ПРОГРАММНОГО ОБЕСПЕЧЕНИЯ ПЛК Назначение задача – это управление работой, проекта, используемых одним процессором. Как и программы задача должна иметь собственный уникальный идентификатор. Задачи бывают циклическими и разовыми. Выполнение разовой задачи запускается по фронту логической тригерной переменной. Циклические задачи выполняются через определённые промежутки времени. Каждая задача может включать вызов одной или нескольких программ. Если программа имеет входные переменные VAR_INPUT они задаются в описании задачи. Все программы одной задачи выполняются в одном рабочем цикле ПЛК. Описание задач в системах программирования ПЛК выполняется по-разному, это может быть текстовое описание или графическое представление. CoDeSys содержит специальный инструмент – менеджер задач (Task Configuration). В любом проекте всегда как минимум существует одна задача. ПО умолчанию – это циклическая задача, вызываемая в каждом рабочем цикле. В CoDeSys она включает единственную программу PLC_PRG. Каждая задача обладает определённым приоритетом. Приоритет лежит в пределах от 0 до 32. Чем выше число тем меньше приоритет. Если две или более задач должны получить управление одновременно, то побеждает задача с более высоким приоритетом. Так если две или более задачи всегда совпадают по времени и имеют разные приоритеты, то задача с меньшим приоритетом не будет работать. При одинаковом приоритете управление получает задача имеющая большее время ожидания. Т.е. две равно-приоритетные задачи будут работать поочерёдно. В системе исполнении CoDeSys реализована не вытесняющая многозадачность – это означает, что любая задача, даже более приоритетная даёт работать текущей задаче до конца одного, рабочего цикла. Работа циклических задач является аппаратно независимой. Механизм управления задачами всегда опирается на аппаратный системный таймер, поэтому нельзя гарантировать, что будет обеспечена точность вызова задач в миллисекундах. (до 1ой миллисекунды). Как правило минимальная дискретность временного интервала на который мы можем рассчитывать = 10 миллисекунд. Для CoDeSys = 10микросекунд. Когда речь идёт для медленных задачах интервалы измеряются десятыми долями секунды. При таких интервалах Лекция CoDeSys (Новиков). времени одного рабочего цикла несоизмеримо мало, поэтому механизм, не вытесняющий многозадачности оказывается в достаточном для высокой точности работы циклических задач. Например, задачу поддержания рабочего давления воздуха в ресивере при помощи включения и выключения компрессора. Двигателю компрессора необходимо не менее 5 секунд для разгона, а допустимое увеличение давления произойдёт, лишь через полторы-две минуты. Следовательно, дёргать компрессор чаще, чем в 2 минуты бессмысленно. На данном рисунке показано определение трёх задач. Задача Т1 имеет приоритет =10 и должна вызываться каждые 200 миллисекунд. Задача Т2 имеет приоритет = 20, должна вызываться в каждом рабочем цикле, не занятом другими задачами. Задача Т3 имеет самый высокий приоритет = 1, должна вызываться через каждые 800 миллисекунд. Windows эмулятор даёт рабочий цикл () 55 миллисекунд, он привязан к тикам системного таймера. РЕСУРСЫ С точки зрения МЭК ресурс – это один процессор, снабжённый собственной системой управления. Т.е. одна или несколько задач загружается в ресурс и исполняются им. В CoDeSys используется понятие «Проект» - это программное обеспечение, обеспечивающее работу конкретного приложения. Слово «Ресурсы» употребляется во множественном числе и определяет набор аппаратно зависимых модулей проекта. Таким образом проект включает аппаратно независимую реализацию программ (функции, ФБ и их локальный данные) и требующие настройки ресурсы. Ресурсы содержат: 1) Определение глобальных и прямо адресуемых переменных. 2) Конфигурацию ПЛК. 3) Установки целевой системы исполнения (Тип микропроцессора, распределение памяти, порядок байт в слове, параметры сети и т.д.) 4) Менеджер задач. В ресурсы включается также дополнительные фирменные инструменты, зависящие от особенностей конкретной системы исполнения. В нашем случае – это модуль трассировки переменных, терминал для работы с фирменными командами ядра, ПЛЦ – броузер, конфигуратор сети и т.д. Эти элементы являются необязательными. Их наличие и тонкости реализации зависят от конкретной аппаратуры и встроенного ПО ПЛК. Конфигурация Лекция CoDeSys (Новиков). В стандарте Мэк есть понятие боле высокого уровня чем - это конфигурация – множество ресурсов, взаимодействующих определённым образом (сконфигурированных). В одной системе может быть несколько интеллектуальных ресурсов, каждый из которых обладает собственным процессором, памятью и системой исполнения. Каждый из них можно программировать. Это могут быть реальные модули или виртуальные машины, эмулируемые одним процессором. Все они имеют доступ к определённым наборам входов и выходов, и координируют свою работу с помощью глобальных переменных, расположенных в общедоступной памяти. Таким образом, для программирования каждого ресурса (в рамках МЭК конфигурации) должен быть создан отдельный проект. Т.к. система программирования универсальная, то различий между ресурсом и конфигурацией не делается. Техника реализации, распределённых систем существенно зависит от конфигурации конкретного ПЛК. Таким образом инструмент «PLC Configuration» на вкладке ресурсов проекта CoDeSys – это инструмент выполняющий конфигурирование ПЛК. ЯЗЫКИ МЭК. ПРОБЛЕМЫ ПРОГРАММИРОВАНИЯ ПЛК Мы говорим, что ПЛК функционирует циклически – читает входы, выполняет прикладную программу и записывает выходы. В результате прикладное программирование для МЭК-ПЛК существенно отличается от традиционной модели, применяемой при работе с языками высокого уровня. Рассмотрим простейшую задачу: Необходимо запрограммировать мерцающий индикатор. Очевидно, что алгоритм проекта должен быть следующим. 1) Включить выход 2) Выдержать паузу 3) Включить выход 4) Выключить паузу 5) Переход к шагу 1 (начало цикла) 6) Конец программы. Реализованная по этому алгоритму программа работать не будет. Во-первых, она содержит бесконечный цикл. Весь код прикладной программы выполняется в каждом рабочем цикле от начала и до конца, любая прикладная программа ПЛК является частью рабочего цикла и должна возвращать управление системе исполнения. Следовательно, шаг 5 является лишним. Если его удалить – программа работать будет, но не так как задумана. Выход всегда будет находиться во включённом состоянии, т.к. его установка происходит по окончанию работы прикладной программы 1 раз. Промежуточные изменения значений выходов не отображаются на аппаратные средства. Что ещё плохо в данном алгоритме – это задержки времени. Вполне вероятно, что кроме мерцания выхода ПЛК будет выполнять и другую работу, т.е. программу необходимо будет дополнять, но, если контролер занят ожиданием это означает, что он ничего больше сделать не сможет. Следовательно, задержки времени нужно реализовать иначе. Достаточно засечь время и заняться другой работой, периодически контролировать часы. Также поступают и люди. С учётом выше изложенного алгоритм станет следующим. 1) Проверить таймер, если время паузы вышло, то: А) инвертировать выход ( включить если выключен и наоборот) Б) начать отсчёт новой паузы 2) Конец программы. Алгоритм получился гораздо проще. Технология ПЛК ориентирована именно на такие задачи. ПЛК КАК КОНЕЧНЫЙ АВТОМАТ Чтобы хорошо писать программы для ПЛК необходимо научиться думать определённым образом. Секрет состоит в том, чтобы представить себе контроллер не как машину, непосредственно выполняющую команды программы, а как конечный автомат. В любом автомате существует множество входов (Х), множество выходов (Y) и множество состояний (S). В нашем случае – это конечные множества, т.к. число входов и выходов ПЛК ограниченно также как и память переменных. Начальные состояния однозначно определены, т.е. s нулевое принадлежит S. Автомат работает по тактам. Для ПЛК – это рабочий цикл, в каждом такте значение входов известно, значение выходов определяется текущим значением входов и текущим состоянием. Лекция CoDeSys (Новиков). Реакция автомата зависит только от текущего состояния без предыстории, т.е. не важно, как он пришёл в это состояние. Вместе с тем текущее состояние изменяется также по тактам. Автомат переходит в новое состояние (сигма). В теории автоматов описанные 6 объектов А=(Х,Y,S,s,лямбда,сигма) принято называть конечным автоматом Мили. Классическая сфера применения ПЛК – программная реализация автоматов. Контроллер вычисляет программно заданную функцию выходов и функцию переходов. В каждом рабочем цикле ПЛК вычисляет значения для выходов, которые необходимо изменить. В итоге прикладная программа для ПЛК очень похожа на вычисление по формуле. Типовым примером дискретного автомата является управление стиральной машиной. Базовые механизмы этого устройства включают: 1) Клапан подачи воды 2) Помпу слива воды 3) Таймер Привод барабана 4) Нагреватель Каждому механизму можно сопоставить логическую переменную. Все возможные состояния определяются множеством переменных. Переход из одного состояния в другое происходит под воздействием входного сигнала. Таймер является самостоятельным блоком. Сигнал окончания выдержки времени является выходом. Если расширить понятия автомата можно рассматривать переходы как функции событий. События не обязательно связаны с входами. Таким образом, окончания тайм аута можно воспринимать, как событие при этом совершенно не важно, как реализован таймер. Модель такой системы можно изобразить с помощью графа состояния. Состояния отображаются овалами, содержащими , а переходы направленными дугами. Диаграмма состояний очень эффективный инструмент программирования и анализа автоматов. Граф состояний для двух переменных. Технически база для построения ПЛК разнообразна. Это реле, электронные схемы, пневмасистемы и т.д. Но в отличие от них технология ПЛК обеспечивает гибкое и быстрое решение. Безусловно программирование микропроцессоров и программируемых логических матриц с помощью графов состояний также возможно, но значительно более трудоёмко. Делается это пи наличии специального оборудования и специально подготовленным персоналом. Применение формализма количества информации позволяет значительно упростить процесс программирования . Следовательно хорошо проработанные спецификации проекта позволяют программисту выполнять качественно. Неточности в тех задании или плохо проработанная система неизбежно выливается в переделки и затяжную атаку. Поэтому описание задачи в виде словесного алгоритма и рисунков на бумаге всегда позволяет значительно упростить алгоритм и не упустить детали. Самое обидное, что детали как правило просты, но из-за отсутствия некоторых из них приходится пересматривать всю структуру построения управляющей программы. Например забыта кнопка аварийной блокировки или фиксации промежуточного положения для настройки механики (по аналогии с 1ой лабой, где забыта деталь реализации отпускания клавиш). Для выявления подобных тонкостей необходим действующий прототип системы и соответствующее средство, позволяющее его построить. Одной из важнейших задач при создании языков ПЛК и комплексов программирования являются возможностей реализовывать прототип без вложения Лекция CoDeSys (Новиков). средств. Приём это должен быть действующий прототип, а не картинка. Высокоуровневая модель даже созданная из пустых блоков должна работать так, чтобы её можно было продемонстрировать заказчику, обсудить и отработать. Далее прототип должен стать скелетом готовой программы без какой-либо переделки. Только так программист получит возможность сразу написать правильную и красивую программу, а не переписывать её по частям. СИМЕЙСТВО ЯЗЫКОВ МЭК Диаграммы SFC стоят особняком, а точнее выше по отношению к другим языкам являются высокоуровневым графическим инструментом. Благодаря SFC идея превращения модели системы в законченную программу становится реальностью. SFC даёт действующий непосредственно в ПЛК прототип. СЕТИ ПЕТРИ Одним из методов формального описания дискретных систем являются сети Петри. Он опирается на разделение системы или отдельных её систем на множество простых позиций. Позиции описываются состоянием части системы. Переходы между позициями происходят при выполнении определённых условий. Позиция отображается в виде окружности. Переходам соответствуют отрезки направленных дуг соединённых с позициями. Каждая позиция способна обладать маркером и передавать его другим позициям по исходящим дугам. Маркеры отображаются в виде жирной точки. Допускается присутствие нескольких маркеров. К переходу приходит одна или несколько дуг, идущих от разных позиций. От перехода также могут отходить несколько исходящих дуг, ведущих кК разным позициям. Проверка условия перехода производится, только если хотя бы одна из его позиций владеет маркером. Существенным моментом сетей Петри является то, что несколько позиций могут одновременно иметь маркер. ТУТ БУДЕТ РИСУНОК Таким образом, сети описывают процессы, работающие параллельно и взаимосвязано. Состояние сети определяется совокупностью позиций владеющих маркерами. SFC-ДИАГРАММЫ В отличии от сетей петри дуги в SFC имеют яркую направленность сверху вниз, позиции вызываются шагами или этапами, отображаются в виде прямоугольников. Задать несколько стартовых шагов в SFC нельзя. SFC-диаграмма состоит из шагов и переходов между ними. Разрешение перехода определяется условием. С шагом связаны определённые действия. Действие описывается на любом языке МЭК. В них можно также использовать вложенные SFCдиаграммы, но в конечном счёте действие нижнего уровня всё равно будет описано на языках IL, ST, LD, FBD. Каждая позиция SFC требует собственного признака активности. Из-за необходимости внутренней памяти только функциональные программы и блоки могут быть реализованы на SFX (функции не могут). Целью использования SFC является разделение на определённые этапы с формально определённой логикой работы. SFC даёт возможность быстрого построения прототипа системы без программирования. Причём для построения верхнего уровня не требуется детально описания действий, также как и привязки к аппаратным ресурсам. ШАГИ Любая SFC-схема составляется из элементов. Шаги на схеме могут быть пустыми – это не вызывает ошибки. Определить действие, привязанное к шагу можно в любое время. Нет ничего странного, что в полностью законченном проекте могут быть пустые шаги, т.к. шаг является ожиданием перехода. (Из sfc-диаграммы удалить шаг можно только вместе с переходом, предварительно выделив их.) Если правый верхний угол шага содержит признак затемнённого треугольника – шаг содержит действие Лекция CoDeSys (Новиков). ПЕРЕХОД Ниже шага на соединительной линии присутствует линия – она обозначает переход. Условием перехода может служить логическая переменная, логическое выражение, константа или прямой адрес. Переход выполняется при соблюдении двух условий: 1) Переход разрешён (соответствующий ему шаг активен); 2) Условие перехода имеет значение True. Простые условия отображаются непосредственно на диаграмме справа от черты, обозначающей переход. В CoDeSys на диаграмме можно записывать выражении только на языке ST. Для громоздких условий применяется другой подход. В этом случае на диаграмме записывается индикатор перехода. Само же условие записывается на одном из языков, кроме SFC в отдельном окне редактора. Переменные или прямые адреса используются в условиях перехода только для чтения. В условном выражении перехода нельзя вызывать экземпляры FB и использовать операцию присваивания. Признаком того, что идентификатор перехода на диаграмме является отдельным реализованным условием, является закрашенный угол перехода. В качестве условия перехода может использоваться логическая константа. Если задано TRUE, то шаг будет выполнен однократно за один рабочий цикл. Далее управление передаётся следующему шагу. Если задано False, то шаг будет выполняться бесконечно. НАЧАЛЬНЫЙ ШАГ Каждая SFC-диаграмма начинается с шага, выделенного двойной линией по всему периметру. Наименование начального шага может быть произвольным. По умолчанию Init. Он присутствует обязательно, может быть пустым. ПАРАЛЛЕЛЬНЫЕ ВЕТВИ Несколько ветвей SFC могут быть параллельными. Признаком параллельности является двойная горизонтальная линия. Каждая параллельная ветвь начинается и заканчивается шагом, т.е. условие входа в параллельность всегда одно, условие выхода тоже одно. Параллельные ветви выполняются теоретически одновременно. На практике слева направо. Условие выхода, завершающее параллельность проверяется только в том случае, если в каждой параллельной ветви активны последние шаги. В нашем конкретном случае Sharking Лекция CoDeSys (Новиков). будет выполнено однократно, а Degustation и Making будут работать параллельно по достижении условия READY. АЛТТЕРНАТИВНЫЕ ВЕТВИ Несколько ветвей могут быть альтернативными. Их признаком является одинарная горизонтальная линия. Каждая альтернативная ветвь начинается и заканчивается с условия перехода. Проверка альтернативных условий выполняется слева направо. Если альтернатива найдена, то оставшиеся условия не проверяются. В альтернативных условиях работает только одна ветвь, поэтому её окончание и будет означать переход к следующему за альтернативной группой шагу. В данном примере альтернатива STOP оценивается первой, шаги DOWN и UP могут стать активными, только если STOP-FALSE. При создании альтернативных ветвей используются только взамо в этом случае вероятность допустить ошибку исключена ПЕРЕХОД НА ПРОИЗВОЛЬНЫЙ ШАГ В общем случае SFC-диаграмма выполняется сверху вниз. Стандартом допускается переход на произвольный шаг, для этого применяются соединительные линии с промежуточными стрелками или поименованные переходы, т.е. осуществляется переход на шаг, имя которого, указано под стрелкой (JUMP). В данном примере при условии STOP-FALSE шаги M_D и M_UP соединены в логическое кольцо, при этом STOP проверяться больше не будет. В этом случае имеется два варианта входа, но ни одного варианта выхода. Маркер активности при этом будет перемещаться исключительно в этом кольце. Прыжок из одной ветви параллельного блока наружу, вызывает эффект размножения маркера. Прыжок внутрь параллельного блока нарушает параллельность ветвей. Подобных трюков следует избегать. Есть возможность использовать упрощённую SFC-диаграмму. Смысл её заключается в применении более простого, компактного и быстрого последовательного SFCисполнителя. Само построение упрощённого SFC получается компактнее и проще для понимания. В упрощённом SFC нельзя использовать включение и выключение действий в рамках одного шага и управлять активностью действия по времени. Действия могут быть трёх классов – текущее, входное и выходное. Графически эти действия никак не отображаются. Их редактирование выполняется в отдельных окнах. В упрощённом SFC действие принадлежит шагу, т.е. действие нельзя вызвать из другого шага или откуда-либо ещё. Можно считать, что каждый шаг содержит 3 Лекция CoDeSys (Новиков). раздела, соответствующие трём возможным действиям. Такие действия не требуют отдельных идентификаторов и называются по имени шага. Для создания новго или редактирования существующего действия CoDeSys достаточно щёлкнуть по прямоугольнику шага. Это приводит к открытию окна редактора и вызывается диалог создания нового действия. ВХОДНОЕ И ВЫХОДНОЕ ДЕЙСТВИЕ Весьма вероятен слуяай когда определённое действие нужно выполнить в шаге только один раз. Напрмер включить нагрев в начале активности шага и выключить при переходе на другой шаг. Для этого предусмотрены входное и выходное действие. Входное – E(entry). Выходное – X (exit). На диаграмме в шаге входное действие располагается в левом нижнем углу, выполняется однократно при активации шага. Выходное Х располагается в левом нижнем углу, выполняется однократно при завершении шага. МЕХАНИЗМ УПРАВЛЕНИЯ ШАГОМ Для каждого шага CoDeSys создаёт две логические переменные. Допустим шаг называется Step_1. Для него будут определены 2 переменные: 1) _Step1 2) Step1 Объявление переменных происходит неявно, т.е. в разделе объявления переменных никаких записей делать не надо. Переменная с лидирующим подчёркиванием _STEP1 получает значение TRUE, когда шаг активируется () условие выполнено, и сбрасывается при деактивации шага (сразу после выполнения условия). Переменная STEP1 отстаёт на один рабочий цикл, т.е. получает значение TRUE, после выполнения входного действия и сбрасывается после выполнения выходного действия. Комбинация двух этих переменных _STEP1 и STEP1 образует 4 возможных состояния шага: 0 0 – не выполняется; 1 0 – входное действие; 1 1 и 1 0 – текущее действие; 0 1 – выходное действие. Данные переменные можно использовать для определения активности шага. Например с целью синхронизации параллельных ветвей. ЗДЕСЬ Ещё РИСУНОК Так в примере шаг STEP4 не может быть закончен раньше STEP2. Для доступа к переменным шага вне данного компонента из Отладчика их необходимо определить как логические переменные. Предварительная установка переменных шагов в отладчике даёт возможность быстро перейти к отладке определённого действия системы. Обращаться к переменным шага в пользовательской программе нельзя, это может привести к тому, что SFC – диаграмма будет работать совсем не так как это следует из её графического представления. На самом деле запись не запрещена, используется только при отладке. СТАНДАРТНЫЕ SFC Выше описанная техника настраивает на то, что изначально определяются шаги, которые наполняются определённым содержимым в процессе работы над проектом. При использовании МЭК-действий подход меняется. Сначала определяются действия (виды работ), которая должна выполнить система, а затем составляется диаграмма в которой определяется их порядок и взаимосвязь. Каждое действие сопоставляется одному или нескольким шагам. Причём допустимо, что некоторое действие может допускаться в одном шаге и останавливаться в другом. Возможно также, что действие должно будет закончить свою работу, независимо не от каких шагов. Например: кабина лифта как минимум должна доехать до ближайшего этажа и выпустить Лекция CoDeSys (Новиков). пассажиров даже если дана команда на окончание работы. Действие на SFC-диаграмме показываются справа у шага и привязываются к нему графически. И ЕЩЁ ОДИН РИСУНОК Так в данном примере в шаге Cooling (охлаждение) и шаге Drying (сушка) используется действие AirCondition (воздушный обдув). Видно, что действие не принадлежит конкретному шагу, является отдельным самостоятельным программным элементом. Идентификаторы должны быть уникальными в пределах одного компонента POU и не должны совпадать с именами шагов и переходов. КЛАССИФИКАТОРЫ ДЕЙСТВИЙ Прямоугольник, отображающий действие содержит в левой части специальное поле – классификатор действий. Классификатор определяет способ влияния активного шага на данное действие. Возможны следующие классификаторы: .N – несохраняемое действие, данное действие выполняется в каждом рабочем цикле, пока активен шаг. РИСУНОК P – импульс. Действие выполняется один раз при активации шага и один раз при деактивации. РИСУНОК S - Сохраняемое действие. Действие активируется и остаётся активным до сброса. Действие продолжает выполняться в каждом цикле даже тогда, когда шаг уже неактивен. РИСУНОК R – сброс. Действие деактивируется. РИСУНОК L – ограниченное по времени. Действие инициализируется вместе с шагом и остаётся активным на заданное время, но не дольше чем шаг. На рисунке показано два возможных случая. В первом действие деактивируется по истечению времени. Во втором по деактивации шага. РИСУНОК SL – ограниченное и сохраняемое по времени. Действие активируется вместе с шагом и остаётся активным в заданное время вне зависимости от активности шага. Действие можно деактивировать досрочно из другого шага с классификатором R. РИСУНОК Лекция CoDeSys (Новиков). D – отложенное действие. Действие активируется через заданное время после активации шага и остаётся активным, пока шаг активен. Если шаг окажется активным меньше заданного времени, то действие активировано не будет. РИСУНОК DS – отложенное и сохраняемое действие. Действие активируется через заданное время после активации шага и остаётся активным до сброса. Если шаг активен меньше заданного времени – действие не будет активировано. При параллельном выполнении сброса в процессе отсчёта времени (из другого шага с классификатором R) действие активироваться не будет. РИСУНОК SD – сохранённое и отложенное действие. Действие активируется через заданное время после активации шага, даже если шаг уже не активен. Но если в процессе активации выполнить сброс (в другом шаге с классификатором R) то активация не произойдёт. РСИУНОК Активированное действие остаётся активным до сброса. Классификаторы L, D, SD, DS и SL требуют указание константы времени в формате Time. Как видно из временных диаграмм – каждое активное действие выполняется ещё один раз уже после деактивации. Это не обходимо для того чтобы действия могли отработать потерю активности и выполнить некоторые завершающие операции. Пример: IF STEP1.X THEN iC:=iC+1; (*счётчик активности*) ELSE iD:=iD+1; (* счётчик деактивации*) END_IF ДЕЙСТВИЕ ПЕРЕМЕННОЕ Действие стандартного SFC не обязательно должно что-либо делать. В качестве имени действия можно использовать логическую переменную, внутреннюю или внешнюю. Переменное действие применяется для синхронизации различных ветвей диаграммы или программы всего проекта. Пример: bUP AT%QX2.2:bool; Переменная bUP соответсвует Классификатор работает. Такая переменная гораздо полезней чем может показаться на первый взгляд. Вполне вероятно, что необходимо управлять одним дискретным выходом, а вся логика уже прописана в SFC – диаграмме, поэтому никакого дополнительного программирования здесь не нужно. МЕХАНИЗМ УПРАВЛЕНИЯ ДЕЙСТВИЕМ Лекция CoDeSys (Новиков). Классификаторы определяют достаточно сложные возможности управления работы действия. Очевидно что действие как и шаг имеет внутреннюю память и логику управления. Для реализации управления в каждое действие неявно включается экземпляр функционального блока SFCActionControl. ФБ – имеет входы соответствующие классификаторам. Если какой-либо шаг включает действие, то это приводит к присваиванию логической единицы соответствующему входу SFCActionControl. После отработки всех активных шагов по состоянию выхода Q система исполнения принимает решение о необходимости вызова данного действия. Все действия вызываются один раз в рабочем цикле. Порядок выполнения действий зависит от реализации исполнения. Интерфейс ФБ SFCActionControl описан в библиотеке IESFC.lib в ней входы S и R обозначены через Sнулевое и Fнулевое (это сделано для исключения конфликтов с ключевыми словами). В CoDeSys есть лазейка позволяющая получить доступ к блоку управления действия. SFCActionControl доступен в каждом действии. Пример: IF A3.AC.Q ……. END_IF Пример: Рисунок 1: вызов действия А_2 происходит дважды и один раз запрещается Как отражено ранее вызвать действие в каждом цикле можно вызвать один раз. Поэтому пример рисунка 2 абсолютно бессмысленный, т.к. действие вызывается трижды, но выполнено будет только один раз в рабочем цикле. На рисунке1 действие вызывается дважды затем сбрасывается. В результате выполнено оно не будет. (При параллельной обработке шаги выполняются слева направо, условно, одновременно). ВНУТРЕННЯЯ ПЕРЕМЕННАЯ ШАГА И ДЕЙСТВИЯ Лекция CoDeSys (Новиков). Для каждого МЭК – шага неявно объявлена структура из двух доступных по чтению переменных. Первая переменная – X:bool – является признаком активности шага. По смыслу она равноценна логической переменной шага «StepName». Логическая единица является признаком активности. Вторая переменная типа Time – T: Time – указывет время активности шага. Доступ к переменной возможен через имя шага и точку. Переменные шага можно использовать в условных переходах. Пример: ФУНКЦИОНАЛЬНЫЕ БЛОКИ И ПРОГРАММЫ SFC Применение SFC в объёмных компонентах позволяет сократить время выполнения и соответственно время реакции системы. При помощи шагов монолитная программа разбивается на короткие фрагменты, выполняемые в разных рабочих циклах ПЛК. Реализация ФБ в SFC отсутствуют первая и последняя команды. Оператор RETURN не используется. Программа как бы не имеет конца. Каждый вызов SFC_POU равносилен выполнению одного цикла. Что, конкретно будет выполнять POU зависит от предыдущего состояния. Принудительно вернуть компонент в начальное состояние можно только путём сброса ПЛК. Принудительная активация начального шага в SFC не означает автоматический сброс компонента. Это приводит только к тому, что кроме текущих активных действий активным становится и начальный шаг. Начальный шаг не содержит скрытых действий, не запрещает другие шаги и действия. Пример: В данном примере параллельная ветвь содержит пустой шаг S4 затем она передаёт управление начальному шагу. Другая параллельная ветвь Step2 – S3 зациклена сама на себя. Она продолжает работать независимо ни от чего. Отработка реакции на все необходимые события включая экстренные обязательно должна быть предусмотрена в SFC явным образом. Перевод системы в начальное или в безопасное состояние предусматривает для ПЛК установку заданного положения исполнительных механизмов и управления ими. Нажатия аварийной клавиши или отработка аварийного сигнала, который обесточит исполнительные механизмы должно корректно отрабатываться программным обеспечением. Установка и поддержание безопасного состояния системы – это даже более сложная работа, чем обычное функционирование. В этих случаях не рекомендуется использовать программный сброс ПЛК (даже в стандартных библиотеках такая функция отсутствует). В CoDeSys экстренный сброс программ и ФБ всё же разрешён. Проблема решается с помощью специальных лагов SFC-init и Sfc –reset. ЯЗЫК IL Текст на Il – список последовательных инструкций. Каждая запись в отдельной строке. Инструкция может содержать 4 поля, разделённые пробелом или горизонтальной табуляцией. Метка не является обязательной. Ставится только там, где нужна. Оператор присутствует обязательно, операнд – по необходимости. Комментарий – не обязательное поле, ставится в конце строки. Ставить комментарий между полями инструкций нельзя. Для лучшего восприятия колонки полей выравнивают. ПРИМЕР: Лекция CoDeSys (Новиков). Метка M1 Оператор LD 2 ADD 1 ST Y LE 3 Операнд JMP M2 Комментарий (*y = 2 + 2*) Редактор CoDeSys выравнивает текст автоматически. Кроме того он выполняет синтаксический контроль и выделение цветом ошибки(некорректно введённый оператор выделяется голубым цветом). АККУМУЛЯТОР Абсолютное большинство операторов IL выполняет некоторую инструкцию с аккумулятора. Операнд тоже может участвовать в инструкции, но результат помещается в аккумулятор. НАПРИМЕР инструкция add 2 прибавляет к содержимому оператора число 2 и помещает результат в аккумулятор. Команды сравнения сравнивают содержимое операнда и аккумулятора, результат сравнения ИСТИНА или ЛОЖЬ помещается в аккумулятор. Команды перехода на метку способны анализировать содержимое аккумулятора и принимать решение – выполнять переход или нет. Таким образом, аккумулятор IL является универсальным, способным сохранять значения переменных любого типа. В аккумулятор можно поместить значение типа BOOL затем Int или Real – транслятор ошибки не выдаст. Такая гибкость не означает, что аккумулятор может одновременно содержать несколько значений различных типов. Он содержит только одно значение, причём тип значения фиксируется в аккумуляторе, и, если операция потребует значение другого типа транслятор выдаст ошибку. ПЕРЕХОД НА МЕТКУ Программа на IL выполняется подряд сверху вниз. Для изменения порядка выполнения используется оператор JMP. Этот оператор выполняется всегда независимо ни от чего. Оператор JMPC выполняется только при значении аккумулятора – ИСТИНА. Переход можно выполнять как вверх так и вниз. Метки только локальные (т.е. переход на метку в другом POU не возможен). Переходы нужно организовывать аккуратно, чтобы не получить бесконечный цикл. ПРИМЕР: LD 2 M2: ADD 2 ST Y LE 3 JMPC M2 В данном примере предполагалось бы организация цикла на одно повторение, при условии, если бы использовался JMPN. В CoDeSys команда безусловного перехода выполняется очень быстро, т.к. транслируется в одну машинную команду. Ограничения на число переходов нет. LD 2 ADD 1 ST Y LE 3 JMP M2 СКОБКИ Последовательный порядок выполнения команд можно поменять при помощи скобок. Открывающая скобка ставится в инструкции сразу после операнда, закрывающая – в последней строке. Инструкция заключ1нная в скобке выполняется в первую очередь. Результат вычисления инструкции в скобках помещается в дополнительный аккумулятор. После чего выполняется команда, содержащая открывающую скобку. ПРИМЕР Лекция CoDeSys (Новиков). LD 5 MUL (2 SUB 1 ) ST Y (*Y=5*(2-1)*) *********************************** LD 5 MUL 2 SUB 1 ST Y (* Y=5*2-1 *) Скобки могут быть вложенными. Каждое вложение требует временного аккумулятора. Это может вызвать неоднозначность при выходе из блока скобок командами JMP, RET, CAL, LD. Применять эти команды в скобках нельзя. ВЫЗОВ ФУНКЦИОНАЛЬНОГО БЛОКА Вызвать экземпляр FB или программу в IL можно с одновременным присваиванием переменных. ПРИМЕР CAL CTD(CD:= TRUE, LOAD:=FALSE, PV:=100) LD CTD.CV ST Y Аналогичный вызов можно выполнить с предварительным присваиванием значений входных переменных. LD ST LD ST LD ST CAL LD ST TRUE CTD.CD FALSE LOAD 100 PV CTD CTD.CV Y ВЫЗОВ ФУНКЦИИ При вызове функции перечисление параметров в IL присутствует одна немало важная особенностью – в качестве первого параметра используется аккумулятор. ПРИМЕР LD TRUE SEL 3,4 На языке ST это равносильно вызову SEL(TRUE,3,4). Очевидно, при вызове функции или оператора с одним параметром список параметров вообще не нужен