sadr0b0t / stepper_h

Stepper motor control library for ChipKIT/Arduino
GNU Lesser General Public License v3.0
3 stars 1 forks source link

Минимальная задержка между двумя шагами не учитывает погрешность частоты таймера #6

Closed sadr0b0t closed 7 years ago

sadr0b0t commented 7 years ago

Сейчас при настройках мотора задаётся минимальная задержка между двумя шагами. Она может зависеть от аппаратных свойств мотора или драйвера: например, если делать шаг каждые 1000 микросекунд, то мотор вращается нормально, а если каждые 500 микросекунд, мотор начнет вращаться нестабильно, пропускать шаги, с еще меньшей задержкой вообще не будет вращаться.

Этот параметр определяет максимальную скорость вращения мотора: при выполнении шагов с минимальной задержкой мотор вращается с максимальной скоростью.

Алгоритм шагания мотором учитывает это значение и программно не разрашает мотору вращаться быстрее указанной скорости (те. задавать задержку между шагами меньше, чем указана при его создании).

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

Например, у нас есть мотор с минимальной задержкой 1000 микросекунд (1 миллисекунда), который мы запустили с максимальной скоростью.

В идеальной ситуации (если бы могли отсылать ипульсы мотору не по таймеру, а в точно установленное время без допустимых погрешностей) он должен делать шаги каждые 1000 микросекунд:

1000, 2000, 3000, 4000, ...

Теперь, если мы включаем рабочий таймер с периодом 200 микросекунд, то любой мотор может потенциально шагать на порогах через каждые 200*3=600 микросекунд (каждый шаг занимает минимум 3 тика таймера - по реализации алгоритма) (через каждые 200 микросекунд: минимум 3 тика на шаг - правда, но отсчет 3х тиков с любого тика исходного периода - см коменты ниже):

600, 1200, 1800, 2400, 3000, 3600, 4200, 4800, 5400, 6000, ...

1й шаг мотор сделает на пороге 600 микросекунд от начала вращения, 2й шаг - 1800 3й шаг - ровно 3000 (в этом месте реальный тайминг совпадает с идеальным) 4й шаг - 3600

Итого, задержка между 1м и 2м шагами - 1800-600=1200 микросекунд (ок) 2м и 3м шагами - 3000-1800=1200 микросекунд (ок) 3м и 4м шагами - 3600-3000=600 микросекунд (НЕ ОК - реальная вычисленная задержка меньше допустимой аппаратной на 1000-600=400 микросекунд).

В итоге видим, что в некоторых случаях реальная задержка между шагами получается неизбежно меньше минимально допустимой аппаратной. Это будет получаться всегда как минимум в тех случаях, когда мотор вращается с максимальной скоростью и реальное время очередного шага выпало на его "идеальный" вариант.

Если увеличить частоту таймера, то величину ошибки можно уменьшить. Например, если возьмем таймер с частотой 100 микросекунд, пороги для шагов будут каждые 100*3=300 микросекунд. Если на шаге n реальное время шага совпало с "идеальным", следующий шаг n+1 будет сделан через 900 микросекунд, т.е. за 100 микросекунд до "идельного" времени для этого шага. Выход за предел аппаратных характеристик мотора уже не так велик, как для частоты 200 микросекунд, но все равно остается.

Очевидно, что проблема алгоритмическая. Для ее решения при расчете минимальной задержки между шагами нужно учитывать не только аппаратные свойства мотора, но и частоту, на которой работает таймер. Судя по всему, реальную скорость мотора придется еще немного ограничить так, чтобы вычисляемая реальная задержка между шагами всегда была больше или равна минимальной аппаратной.

sadr0b0t commented 7 years ago

Так, вычисления выше не корректны - вычисления для порогов шагов по таймеру вычисляются не верно.

При частоте таймера 200 микросекунд мотор может сделать шаг реально в любой из тиков, т.е. шаг потенциально может случаться через каждые 200 микросекунд. Главное, чтобы между новым шагом и предыдущим уместилось как минимум 3 тика таймера.

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

sadr0b0t commented 7 years ago

Еще точнее: ошибка не будет появляться в тех случаях, когда внутри минимальной аппаратной задержки будет умещаться целое количество тиков таймера. Пересчитаем случай для таймера с периодом 200 микросекунд и минимальной задержкой мотора 1000 микросекунд.

"Идеальные" шаги - каждые 1000 микросекунд:

1000, 2000, 3000, 4000, ...

тики таймера:

200, 400, 600, 800, 1000, 1200, 1400, 1600, 1800, 2000, 2200, 2400, 2600, 2800, 3000, 3200, 3400, 3600, 3800, 4000, 4200 ...

в итоге, реальные шаги по тикам таймера на порогах:

1000, 2000, 3000, 4000, ...

Те же, что и "идеальные". Между двумя шагами получаем 5 тиков таймера (нужно минимум 3), значит успеваем сделать все необходимые проверки и вычисления даже при максимальной скорости мотора.

Теперь попробуем немного увеличить скорость мотора так, чтобы идеальные задержки между шагами и реальные шаги по тикам не совпадали. Пусть мотор шагает с задержкой 1050 микросекунд, "идеальные" шаги будут:

1050, 2100, 3150, 4200, 5250, 6300, 7350, 8400 ...

пороги на тиках все те же

200, 400, 600, 800, 1000, 1200, 1400, 1600, 1800, 2000, 2400, 2600, 3000, 
3200, 3400, 3600, 4000, 4200, 4400, 4600, 5000, 6200, 6400, 6600, 6800, 7000, 
7200, 7400, 7600, 7800, 8000, 8200, 8400, 8600, 8800 ...

шаги на порогах:

1000, 2000, 3000, 4200, 5200, 6200, 7200, 8400 ...

реальные задержки между шагами:

1000, 1000, 1200, 1000, 1000, 1000, 1200 ...

Ниже минимальной аппаратной задержки тем более не опускаемся - описанная проблема не проявится.

И для полноты картины возьмем еще один случай, когда период таймера не умещается нацело в минимальную задержку мотора. В этом случае мы должны опять получить описанную выше ошибку и проблему.

Минимальная задержка между шагами мотора - 1000 микросекунд, период таймера - 300 микросекунд.

"Идеальные" шаги мотора на максимальной скорости:

1000, 2000, 3000, 4000, 5000, 6000 ...

Тики таймера

300, 600, 900, 1200, 1500, 1800, 2100, 2400, 2700, 3000, 3300, 3600, 3900, 4200, 4500, 4800, 5100, 5400, 5700, 6000 ...

Реальные шаги на порогах:

900, 1800, 3000, 3900, 4800, 6000 ...

реальные задержки между шагами:

900, 1200, 900, 900, 1200 ...

видим реальная задержка 900 микросекунд меньше минимальной аппаратно 1000 микросекунд на 100 микросекунд - проблема проявилась.

sadr0b0t commented 7 years ago

В итоге 2 пути решения проблемы:

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

Минус: пожертвовать универсальностью Плюс: жертва универсальностью не так страшна, т.к. моторы скорее всего чаще 1 миллисекунды не шагают (правда, это следует проверить), а частота таймера задаётся под микроконтроллер на этапе компиляции. Плюс: не нужно усложнять кодовую базу Минус: вместо кодовой базы придется усложнить документацию (объяснять пользователям библиотеки, а в перспективе - настройщикам софта, если настройки моторов задаются через конфиг, почему некоторые значения максимальной скорости/минимальной задержки могут вызвать описанные проблемы)

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

Минус: придется еще немного усложнить код (медленнее от пары лишних сложений/вычитаний он работать не станет, но для чтения/правки придется разобраться и в этом нюансе) Плюс: универсальность (можно задавать любые задержки и частоты) Плюс: не нужно напрягать пользователя объяснением этих нюансов в документации Минус: хотя, скорее всего все равно придется это сделать, чтобы объяснить, почему в некоторых случаях мотор не может крутиться с максимальной скоростью

sadr0b0t commented 7 years ago

Если мы хотим учитывать погрешность автоматом.

Формула, похоже, будет

мин_задержка = аппаратная_задержка + мин_порог

здесь

Для случая с частотой таймера 300 микросекунд и аппаратной минимальной задержкой 1000 микросекунд:

мин_задержка=1000 + 300 = 1300

"Идеальные" шаги мотора на максимальной скорости:

1300, 2600, 3900, 5200, 6500, 7800, 9100, 10400, 11700, 13000, 14300 ...

Тики таймера

300, 600, 900, 1200, 1500, 1800, 2100, 2400, 2700, 3000, 
3300, 3600, 3900, 4200, 4500, 4800, 5100, 5400, 5700, 6000,
6300, 6600, 6900, 7200, 7500, 7800, 8100, 8400, 8700, 9000,
9300, 9600, 9900, 10200, 10500, 10800, 11100, 11400, 11700, 12000,
12300, 12600, 12900, 13200, 13500, 13800, 14100, 14400 ...

Реальные шаги на порогах:

1200, 2400, 3900, 5100, 6300, 7800, 9000, 10200, 11700, 12900, 14100 ...

реальные задержки:

1200, 1500, 1200, 1200, 1500, 1200, 1200, 1500, 1200, 1200 ...

в этом случае получаем самые маленькие реальные задержки 1200 микросекунд - меньше, чем вычисленная по формуле минимальная задержка (1300 микросекунд), но больше чем аппаратная минимальная задержка 1000 микросекунд. Таким образом, мотор на "максимальной" скорости будет двигаться помеднее, чем мог бы, но зато не будет выходить за пределы аппаратных ограничений скорости при выбранной частоте таймера.

sadr0b0t commented 7 years ago

короче, нафиг запретил, добавил тесты https://github.com/1i7/stepper_h/commit/7b41d29934bdc3727890f377dfdd00f7daa161e4