Сейчас выложу.
Вид для печати
Сейчас выложу.
Интересно, что если из прерывающей программе убрать
SteppersConfig_Pru1MemoryTransfer();
то все работает как надо.
CASE R200 OF
0: (* *)
Stop_Motor();
SSP_Y := FALSE; (* Нет исходного положения *)
TON3(IN := FALSE, PT:= T#0s);
R200 := 10;
10: (* Вперед или стоп *)
IF (D1) THEN
SteppersConfig_Pru1MemoryTransfer(
STEPPER1_PRU1_dir := FALSE,
STEPPER1_PRU1_stepper_accel_ramp := 5000,
STEPPER1_PRU1_stepper_decel_ramp := 50000,
STEPPER1_PRU1_stepper_max_speed := 10000,
STEPPER1_PRU1_stepper_min_speed := 0,
STEPPER1_PRU1_stepper_quantity := 1000000,
STEPPER1_PRU1_stepper_enable := TRUE
);
ELSE SteppersConfig_Pru1MemoryTransfer(STEPPER1_PRU1_st epper_enable := FALSE); R200 := 15; END_IF
15: (* Пауза *)
SteppersConfig_Pru1MemoryTransfer(STEPPER1_PRU1_st epper_enable := FALSE);
TON3(IN := TRUE, PT:= UT_1S); (* Запустили таймер *) Если уставка таймера 1 сек., то ФБ работает нормально, если 100 мс, то на шаге 20 все стопорится, вал ШД вращается, но с черепашьей частотой
IF (TON3.Q = TRUE) THEN TON3(IN := FALSE, PT:= T#0s); R200 := 20; END_IF
20: (* Назад *)
IF (NOT D1) THEN
SteppersConfig_Pru1MemoryTransfer(
STEPPER1_PRU1_dir := TRUE,
STEPPER1_PRU1_stepper_accel_ramp := 5000,
STEPPER1_PRU1_stepper_decel_ramp := 50000,
STEPPER1_PRU1_stepper_max_speed := 10000,
STEPPER1_PRU1_stepper_min_speed := 0,
STEPPER1_PRU1_stepper_quantity := 1000000,
STEPPER1_PRU1_stepper_enable := TRUE
);
ELSE R200 := 30; END_IF
30: (* Стоп *)
SteppersConfig_Pru1MemoryTransfer(STEPPER1_PRU1_st epper_enable := FALSE);
SSP_Y := TRUE;
END_CASE
Если дать возможность ШД отработать заданное количество импульсов, то все в дальнейшем корректно работает.
Проблема в дальнейшем возникает, если выдать
SteppersConfig_Pru1MemoryTransfer(STEPPER1_PRU1_st epper_enable := FALSE);
до того, как ШД отработает заданное количество импульсов.
Вот так работает корректно
CASE R200 OF
0: (* *)
Stop_Motor();
SSP_Y := FALSE; (* Нет исходного положения *)
TON3(IN := FALSE, PT:= T#0s);
R200 := 10;
10: (* Вперед или стоп *)
IF (D1) THEN
SteppersConfig_Pru1MemoryTransfer(
STEPPER1_PRU1_dir := FALSE,
STEPPER1_PRU1_stepper_accel_ramp := 5000,
STEPPER1_PRU1_stepper_decel_ramp := 50000,
STEPPER1_PRU1_stepper_max_speed := 10000,
STEPPER1_PRU1_stepper_min_speed := 0,
STEPPER1_PRU1_stepper_quantity := 1000000,
STEPPER1_PRU1_stepper_enable := TRUE
);
ELSE R200 := 15; END_IF
15: (* Ждем отработки заданного на предыдущем шаге количества импульсов *)
IF SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_state = STOP_STEPPER_RUN_STATE THEN
SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_enable := FALSE; R200 := 20; END_IF
20: (* Назад *)
IF (NOT D1) THEN
SteppersConfig_Pru1MemoryTransfer(
STEPPER1_PRU1_dir := TRUE,
STEPPER1_PRU1_stepper_accel_ramp := 5000,
STEPPER1_PRU1_stepper_decel_ramp := 50000,
STEPPER1_PRU1_stepper_max_speed := 10000,
STEPPER1_PRU1_stepper_min_speed := 0,
STEPPER1_PRU1_stepper_quantity := 1000000,
STEPPER1_PRU1_stepper_enable := TRUE
);
ELSE R200 := 30; END_IF
30: (* Стоп *)
SteppersConfig_Pru1MemoryTransfer(STEPPER1_PRU1_st epper_enable := FALSE);
SSP_Y := TRUE;
END_CASE
Владимир, какое значение примет
SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_state
после того как буде выполнено
SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_enable := FALSE;
Вы не поняли.
DECEL и STOP были. Выдается SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_enable := FALSE;
После этого SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_state так и останется STOP ?
Нет, перейдёт в INIT.
Вот фрагмент кода PRU_STEPPER:
Вложение 30222
А состояние INIT что означает ?
Я вчера писал, что если во время работы ФБ Steper в произвольный момент времени подать
SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_enable := FALSE;
то ФБ на время примерно равное 1 сек. встает в ступор, т.е. не готов принимать параметры для очередного движения.
В связи с этим вопрос - какое состояние примет
SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_state
если в произвольный момент времени выполнить
SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_enable := FALSE; ?
И попутный вопрос. Как SteppersConfig_Pru1MemoryTransfer.STEPPER1_PRU1_st epper_state принудительно привести в состояние INIT ?
Владимир, сможет ли один PRU управлять двумя драйверами ШД, т.е. хватит ли памяти и прочих ресурсов ? Нужны два быстрых выхода для управления STEP. Для управления DIR буду использовать простые выходы ПЛК.
А почему бы не управлять каждым шд со своего PRU ядра?
Т.е.откуда берётся задача запитать два шд от одного PRU ядра?
А два шд заработали? Устраивают?
По ресурсам сходу может и не пролезть. Возможно будет проще вынести часть логики в КДС, чем впихивать текущие шд блоки в PRU.
Hardella 1.7.0
Из проекта достал <code class="highlighter-rouge">Step motors
</code><code>пр.кн.мыши по SteppersConfig -> Run -> указал путь -> RUN
Получил ошибку
</code>PRU создались, SteppersConfig.exp = 0кБКод:Please upload E:\Programs\Hardella\PRU\PRU0.prg to PLC110 M02
Note: PRU0.prg is always the same, so there's no need to upload it every time
Please upload E:\Programs\Hardella\PRU\PRU1.prg to PLC110 M02
Note: PRU1.prg is always the same, so there's no need to upload it every time
Writing output to E:\Programs\Hardella\PRU\SteppersConfig.exp
java.lang.ClassNotFoundException: pru.SteppersConfig_Pru0Program_CodeGenerator
at java.net.URLClassLoader.findClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Unknown Source)
at com.github.vlsi.iec61131.st2ti1808.runtime.compiler.CreateLibrary.main(CreateLibrary.java:87)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at jetbrains.mps.execution.lib.startup.ClassRunner.main(ClassRunner.java:93)
Что не так?
К сожалению, так уж сделан ПЛК110 (см https://hardella.com/docs/pru/featur...ики-ПЛК110-М02 )
Можно либо PRU0 (выхода 3 и 4, быстрые входа), либо вместе PRU0+PRU1 (тогда будут работать 1, 2, 3, 4).
Отдельно залить PRU1 (для 1 и 2 выходов) не заработает.
Сейчас в примере используется пара выходов на одном PRU, причем один из выходов занимается направлением (DIR), но этим заниматься может и обычный выход, тогда вопрос..
Можно подключить на каждый быстрый выход управление STEP, тоесть 4мя ШД управлять из 2 PRU?
4 быстрых выхода на STEP + 4 обычных для DIR?
Что и куда надо отправить чтобы ШД незамедлительно остановился?
Сделать саму PRU программу несложно (как-никак, это что-то типа простого blink'а).
Сложность возникает из того, что "ответный" КДС код должен тоже размножаться (по количеству ШД, реально используемых в PRU программе).
Допустим, PRU блок будет называться PRU_STEPPER_BLINK. При этом должна быть возможность указать, что "если пользователь задействовал блок", то в КДС программу нужно размножить вот эти блоки и программы (с ШД математикой).
В итоге, КДС и PRU части должны фигурировать в одном проекте, но система как-то должна понимать какой код предназначен для КДС, а какой для PRU.
У меня один ШД и один энкодер.
Загрузив с помощью hardella управление ШД Fast encoder не работает из конфигуратора?
У меня эти входа вообще не работают.
Теперь с ними надо работать из PRU?
Есть пример для ШД и есть пример Быстрого энкодера от hardella. А есть и то и другое?
Да, это ограничение самой технологии. При использовании PRU программы соответствующие входы-выходы перестают управляться из plc configuration.
Готового примера нет.
Но достаточно взять программу ШД и добавить туда вызов энкодера (как на 1-ой картинке в описании примера про энкодер).
Не получилось добавить энкодер к ШД
http://recordit.co/qtt4cFbPAF
Вложение 30904
В чем может быть проблема?
Вообще говоря, PRU1 отдельно от PRU0 не работает.
Т.е. либо просто PRU0, либо вместе PRU0+PRU1.
Все входы подключены к PRU0, поэтому энкодер нужно добавлять в программу PRU0.
Странно, что Hardella не выдала ошибку компиляции на использование FAST_INPUTS в программе для PRU1. Проверил у себя -- действительно не ругается. Нужно поправить.
Попробуйте использовать энкодер в программе для PRU0 (как вариант -- просто поменять местами записи в SteppersConfig)
Не понял, у меня в ПЛК загружено и PRU0 и PRU1, я сначало крутил ШД, через PRU1, в него входа и добавил т.к. не знаю какой PRU за что отвечает, информации нет.
По поводу SteppersConfig тоже не понял, для меня это лес какой-то.
Вот, переделал, так ?
Вложение 30907
Проект скомпилился.