реклама на сайте
подробности

 
 
2 страниц V   1 2 >  
Reply to this topicStart new topic
> Точный подсчёт времени, как реализовать?
Leo_vrn
сообщение Aug 6 2006, 14:11
Сообщение #1





Группа: Участник
Сообщений: 12
Регистрация: 21-11-05
Из: Воронеж
Пользователь №: 11 151



Господа гуру в программировании AVR. Вопрос к вам.

Есть задачка точного измерения промежутков времени. Точность нужна до тысячной доли секунды. Подскажите, каким боком такое можно реализовать. Не должно быть погрешности измерения более 1 тысячной в интервале до 30 секунд.
В идеале нужна параллельная работа двух таких секундомеров. В принципе можно и по одному на разных кристаллах.
Выбор самого кристалла не очень важен. Главное, чтобы имел USART.
Go to the top of the page
 
+Quote Post
AVR
сообщение Aug 6 2006, 14:45
Сообщение #2


фанат Linux'а
*****

Группа: Свой
Сообщений: 1 353
Регистрация: 23-10-05
Из: SPB.RU
Пользователь №: 10 008



Цитата(Leo_vrn @ Aug 6 2006, 18:11) *
Точность нужна до тысячной доли секунды. Подскажите, каким боком такое можно реализовать
Не уверен конечно, но возможно просто поставить таймер в режим сравнения и очистки по совпадению. В прерывании по совпадении таймера инкрементируется счетчик времени. В конце подсчета просто добавляется оставшееся в значение в счетчике таймера (с учетом того что на конец подсчета могло тоже произой прерывание по переполнению).


--------------------
Go to the top of the page
 
+Quote Post
junoSynthesizer
сообщение Aug 6 2006, 19:33
Сообщение #3


Частый гость
**

Группа: Свой
Сообщений: 83
Регистрация: 25-11-05
Из: odessa
Пользователь №: 11 397



я конечно не гуру а тоже нуб =), но кажись математику никто не отменял

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

т.е. заносим в счётчик цифру 6, чтобы прерывание было вызвано через 0,25 мс
после этого строим внешний счётчик четвертинок секунд (в теле прерывания)
таким образом мы получам погрешность половину от максимально допустимой (если с точностью до 1 мс, тогда максимальная 0,5 получается, вроде так)

и прикол в том, что таких таймеров можно запустить и 2 =)


--------------------
Вся жизнь - ништяк, все бабы - леди, а солнце - шар дающий свет
Go to the top of the page
 
+Quote Post
bodja74
сообщение Aug 6 2006, 20:45
Сообщение #4


Знающий
****

Группа: Свой
Сообщений: 543
Регистрация: 22-10-05
Пользователь №: 9 984



1 Инициализируем таймер Т1,если нужна точность ,или кварц с подходящим делителем или внешнее тактирование.
2 Указываем прерывание по захвату от Т1
3 В прерывании с регитра ICR читаем полученную длину импульса
4 Отправляем значение в USART

Пойдет мега8,16 и т.д.
Go to the top of the page
 
+Quote Post
defunct
сообщение Aug 6 2006, 21:03
Сообщение #5


кекс
******

Группа: Свой
Сообщений: 3 825
Регистрация: 17-12-05
Из: Киев
Пользователь №: 12 326



Цитата(Leo_vrn @ Aug 6 2006, 17:11) *
Есть задачка точного измерения промежутков времени. Точность нужна до тысячной доли секунды.

Уточните задачу:
Как и какие события будут сигнализировать МК о старте измерения и о финише?

Потому что просто "отмерять" интервалы времени - тривиальная задача:
зная возможности аппаратуры - 16 битный таймер в режиме CTC с генерацией прерывания, обеспечит абсолютно точное деление частоты осциллятора на любое натуральное число больше 11+(количество тактов требующихся на обработку). Дальше не составит труда преобразовать полученную таким образом частоту в интервал времени: T = OCR1X/ Fosc. Ну и подобрать осциллятор который обеспечит Вам требующуюся точность.

Например пусть нужно точно отмерять интервал времени в 1ms, тогда, подставив этот интервал в формулу
OCR1X = Fosc * 0.001c.
для обеспечения высокой точности OCR1X должен быть натуральным числом >11, т.о. нам остается только подобрать кварц (любой из 4.000Mhz, 8.000Mhz, 10.000Mhz и т.п.).
Go to the top of the page
 
+Quote Post
arttab
сообщение Aug 7 2006, 01:45
Сообщение #6


Профессионал
*****

Группа: Свой
Сообщений: 1 432
Регистрация: 7-12-04
Из: Новосибирск
Пользователь №: 1 371



а если не серийка, то и поправочный коэфициетн для своего кварца измерить и корректировать измерения


--------------------
OrCAD, Altium,IAR, AVR....
Go to the top of the page
 
+Quote Post
Leo_vrn
сообщение Aug 7 2006, 07:49
Сообщение #7





Группа: Участник
Сообщений: 12
Регистрация: 21-11-05
Из: Воронеж
Пользователь №: 11 151



Цитата(defunct @ Aug 7 2006, 01:03) *
Цитата(Leo_vrn @ Aug 6 2006, 17:11) *

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

Уточните задачу:
Как и какие события будут сигнализировать МК о старте измерения и о финише?

Потому что просто "отмерять" интервалы времени - тривиальная задача:
зная возможности аппаратуры - 16 битный таймер в режиме CTC с генерацией прерывания, обеспечит абсолютно точное деление частоты осциллятора на любое натуральное число больше 11+(количество тактов требующихся на обработку). Дальше не составит труда преобразовать полученную таким образом частоту в интервал времени: T = OCR1X/ Fosc. Ну и подобрать осциллятор который обеспечит Вам требующуюся точность.

Например пусть нужно точно отмерять интервал времени в 1ms, тогда, подставив этот интервал в формулу
OCR1X = Fosc * 0.001c.
для обеспечения высокой точности OCR1X должен быть натуральным числом >11, т.о. нам остается только подобрать кварц (любой из 4.000Mhz, 8.000Mhz, 10.000Mhz и т.п.).


В качестве события для старта и останова замера времени используется подача лог.0 на какую-нибудь ногу контроллера. То-есть пришёл 0 на одну ногу - запускаем таймер, пришёл 0 на другую ногу - останавливаем таймер.
Получается, что во времяцикла измерения контроллер должен будет постоянно опрашивать состояние одной из своих ног.
Go to the top of the page
 
+Quote Post
Леонид Иванович
сообщение Aug 7 2006, 08:11
Сообщение #8


Местный
***

Группа: Участник
Сообщений: 318
Регистрация: 21-07-06
Из: Минск
Пользователь №: 18 986



Лучше всего использовать аппаратную схему захвата таймера. Только два разных сигнала СТАРТ и СТОП тогда нужно будет преобразовать в один импульс, длительность которого нужно измерить. Сделать это можно с помощью внешнего триггера. Этот импульс подаете на вход ICP1. Измеряем так:

1. Разрешаем прерывание по переполнению таймера 1.
2. Разрешаем прерывание по захвату таймера 1 при переходе из 0 в 1.
3. В обработчике прерывания по захвату, если сброшен флаг готовности данных, сохраняем значение регистра ICR1 в переменной A, очищаем переменную B, устанавливаем флаг начала измерения и перенастраиваем схему захвата на переход из 1 в 0.
4. В обработчике прерывания по переполнению таймера 1, если установлен флаг начала измерения, то считаем переполнения таймера в переменной B.
5. В обработчике прерывания по захвату, если установлен флаг начала измерения, сохраняем значение регистра ICR1 в переменной C, сбрасываем флаг начала измерения, устанавливаем флаг готовности данных.

Основная программа неспешно проверяет флаг готовности данных, когда он установится, делает вычисление интервала:

T = 65536 - A + 65536*B + C [периодов тактовой частоты]

Затем передает T по UART. Чтобы начать новый цикл, нужно сбросить флаг готовности данных.

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


--------------------
Go to the top of the page
 
+Quote Post
singlskv
сообщение Aug 7 2006, 09:03
Сообщение #9


дятел
*****

Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065



Цитата(Леонид Иванович @ Aug 7 2006, 12:11) *
Лучше всего использовать аппаратную схему захвата таймера. Только два разных сигнала СТАРТ и СТОП тогда нужно будет преобразовать в один импульс, длительность которого нужно измерить. Сделать это можно с помощью внешнего триггера. Этот импульс подаете на вход ICP1. Измеряем так:

1. Разрешаем прерывание по переполнению таймера 1.
2. Разрешаем прерывание по захвату таймера 1 при переходе из 0 в 1.
3. В обработчике прерывания по захвату, если сброшен флаг готовности данных, сохраняем значение регистра ICR1 в переменной A, очищаем переменную B, устанавливаем флаг начала измерения и перенастраиваем схему захвата на переход из 1 в 0.
4. В обработчике прерывания по переполнению таймера 1, если установлен флаг начала измерения, то считаем переполнения таймера в переменной B.

А что мы посчитаем если прерывание по захвату выставит флаг в момент обработки прерывания
по переполнению ?
Цитата(Леонид Иванович @ Aug 7 2006, 12:11) *
Точность такого метода плюс-минус период тактовой частоты, т.е. лучше микросекунды. И вычислительные ресурсы почти не тратятся.

ИМХО если прерывания совпадут, то точность получится 65536 тактов.
Go to the top of the page
 
+Quote Post
defunct
сообщение Aug 7 2006, 09:45
Сообщение #10


кекс
******

Группа: Свой
Сообщений: 3 825
Регистрация: 17-12-05
Из: Киев
Пользователь №: 12 326



Цитата(singlskv @ Aug 7 2006, 12:03) *
А что мы посчитаем если прерывание по захвату выставит флаг в момент обработки прерывания
по переполнению ?

Где-то уже обсуждали подобный вопрос. GetSmart тогда предложил гениально простое решение - в обработчике "по захвату" просто проверять флаг переполнения из регистра TIFR.

Цитата(Леонид Иванович @ Aug 7 2006, 12:11) *
ИМХО если прерывания совпадут, то точность получится 65536 тактов.

См. выше ;>

Сообщение отредактировал defunct - Aug 7 2006, 09:45
Go to the top of the page
 
+Quote Post
singlskv
сообщение Aug 7 2006, 10:50
Сообщение #11


дятел
*****

Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065



Цитата(defunct @ Aug 7 2006, 13:45) *
Где-то уже обсуждали подобный вопрос. GetSmart тогда предложил гениально простое решение - в обработчике "по захвату" просто проверять флаг переполнения из регистра TIFR.


Код
loop:
    rjmp loop; "захват" в середине 2х тактовой команды
                                              Вариант1           Вариант2
                                             B=5 ICR=0000     B=5 ICR=FFFD             в момент "захвата"
                                             "переполнение"  нет "переполнения"
ICR: ;обработчик прерывания "захват"
                                             "переполнение"    "переполнения"
    проверка "переполнения"  в TIFR
        inc  B                              B=6 ICR=0000     B=6 ICR=FFFD


ну вот мы и получили разницу >65000 тактов.
Go to the top of the page
 
+Quote Post
bodja74
сообщение Aug 7 2006, 11:44
Сообщение #12


Знающий
****

Группа: Свой
Сообщений: 543
Регистрация: 22-10-05
Пользователь №: 9 984



Цитата(singlskv @ Aug 7 2006, 12:03) *
А что мы посчитаем если прерывание по захвату выставит флаг в момент обработки прерывания
по переполнению ?


Ничего страшного не произойдет,счетный регистр TCNT в момент захвата перенесет свое значение в регистр ICR и выставится флаг ICF регистра TIFR ,после окончания обработки прерывания по переполнению прога перейдет на прерывание по захвату.
Go to the top of the page
 
+Quote Post
singlskv
сообщение Aug 7 2006, 11:50
Сообщение #13


дятел
*****

Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065



Цитата(singlskv @ Aug 7 2006, 12:03) *
А что мы посчитаем если прерывание по захвату выставит флаг в момент обработки прерывания
по переполнению ?

Я не очень точно там выразился, смотри мой последний пост.
Go to the top of the page
 
+Quote Post
defunct
сообщение Aug 7 2006, 11:56
Сообщение #14


кекс
******

Группа: Свой
Сообщений: 3 825
Регистрация: 17-12-05
Из: Киев
Пользователь №: 12 326



Долго искал, но таки отыскал ветку где обсуждался подобный вопрос:

http://electronix.ru/forum/index.php?showtopic=16900&hl=

см. коментарий #8
Go to the top of the page
 
+Quote Post
singlskv
сообщение Aug 7 2006, 12:13
Сообщение #15


дятел
*****

Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065



Цитата(defunct @ Aug 7 2006, 15:56) *
Долго искал, но таки отыскал ветку где обсуждался подобный вопрос:

http://electronix.ru/forum/index.php?showtopic=16900&hl=

см. коментарий #8

Цитата(defunct @ Jun 2 2006, 23:26) *
В таком виде как в примере - нельзя выполнять команды условного перехода и арифметические команды в основном цикле программы.

ну дык все правильно.
толко раскажите мне пожалуйста КАК не выполнять 2х/3х тактовые команды в основном
цикле программы ?
Go to the top of the page
 
+Quote Post

2 страниц V   1 2 >
Reply to this topicStart new topic
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 19th July 2025 - 00:02
Рейтинг@Mail.ru


Страница сгенерированна за 0.01493 секунд с 7
ELECTRONIX ©2004-2016