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

 
 
2 страниц V   1 2 >  
Reply to this topicStart new topic
> Таймеры atmega32a
ishpanec
сообщение Dec 19 2014, 09:57
Сообщение #1





Группа: Новичок
Сообщений: 6
Регистрация: 19-12-14
Пользователь №: 84 192



Здравствуйте
Проблема возникла такая, есть у меня atmega32a китайский. постигаю таймеры. использую таймер0 (8 бит).
Логика моих мыслей такова:

если там частота 16МГц а таймер считает до 256 то каждое переполнение таймера будет происходить (1 / 16 000 000) * 256 = 16 микросекунд (0,000016).
Соответственно, что бы получить 1 секунду надо таких отрезков 62 500 (0,000016 * 62 500 = 1 сек.)
Что бы особо не мучиться с 16 битными числами я разбил на две 8 битные, т.е. 250 и 250.
Значит в прерывании по переполнению мы считаем первый счетчик, када он доходит до 250 мы увеличиваем второй и обнуляем первый.
Сразу что скажу что cksel биты не менял, они все отключены, значит частота должна быть нормальной. В коде не устанавливаю предделитель для таймера.
Внешнего кварца, как и осциллографа, не имею. замерить частоту не выходит. пробовал всю партию контроллеров (10 штук) результат один и тот же, либо у них у всех не 16 МГц, либо логика моих действий не верна.
Go to the top of the page
 
+Quote Post
zombi
сообщение Dec 19 2014, 14:11
Сообщение #2


Гуру
******

Группа: Свой
Сообщений: 2 076
Регистрация: 10-09-08
Пользователь №: 40 106



Цитата(ishpanec @ Dec 19 2014, 13:57) *
результат один и тот же

Не плохо было бы узнать полученный результат, способ наблюдения оного.
И перепроверить cksel сравнив с DS.
Go to the top of the page
 
+Quote Post
Dust112
сообщение Dec 19 2014, 14:16
Сообщение #3


Участник
*

Группа: Участник
Сообщений: 18
Регистрация: 6-04-06
Пользователь №: 15 890



ishpanec, Вы раздел 8-bit Timer/Counter0 with PWM документации читали? В частности про делители ( prescaler ) частоты.
Go to the top of the page
 
+Quote Post
stells
сообщение Dec 19 2014, 14:26
Сообщение #4


внештатный сотрудник
******

Группа: Участник
Сообщений: 2 458
Регистрация: 10-05-08
Из: МО, Медвежьи озера
Пользователь №: 37 401



Цитата(ishpanec @ Dec 19 2014, 12:57) *
если там частота 16МГц

а там точно 16МГЦ? не 8?

пс: таблицу 9 смотрите

Сообщение отредактировал stells - Dec 19 2014, 14:34
Go to the top of the page
 
+Quote Post
demiurg1978
сообщение Dec 19 2014, 15:10
Сообщение #5


Местный
***

Группа: Участник
Сообщений: 333
Регистрация: 19-12-13
Из: Новосибирск
Пользователь №: 79 709



У меня такой способ получить 1 мс при 8 и 16 мгц:
CODE
/========================================================================
#define ST_TCNT TCNT0
#define ST_TIMSK TIMSK
#define ST_OCIE OCIE0
#define ST_OCR OCR0
#define ST_TCCR TCCR0
#define CS0 CS00
#define CS1 CS01
#define CS2 CS02
//========================================================================

//========================================================================
#define SYS_TICK_FLG 0
//------------------------------------------------------------------------

//========================================================================
#pragma vector = TIMER0_COMP_vect
__interrupt void Timer0Comp(void)
{
ST_OCR += 250;
sys_tick |= 1<<SYS_TICK_FLG;
}
//========================================================================

//========================================================================
void init_sys_timer (void)
{
sys_tick = 0;
ST_TCNT = 0;
ST_TIMSK |= 1<<ST_OCIE;
ST_OCR = 250;
ST_TCCR |= (1<<CS0) | (1<<CS1);
}
//------------------------------------------------------------------------


При 8 мгц 125, при 16 мгц 250.

Делаем счетчики и получаем любую времянку с дискретностью в 1 мс. 1000 мс = 1 с.

Сообщение отредактировал demiurg1978 - Dec 19 2014, 15:11
Go to the top of the page
 
+Quote Post
akl
сообщение Dec 20 2014, 09:56
Сообщение #6


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

Группа: Свой
Сообщений: 127
Регистрация: 4-04-07
Из: Ижевск
Пользователь №: 26 773



С точностью до такта можно временной интервал формировать так. Писано для tiny13, но и для mega32 будет примерно также.
CODE
.INCLUDE "tn13def.inc"


.equ Fo=7890123
;.equ Fo=8000000


.org $0000
.CSEG
RJMP START
.org $0003
TIMER0_OVER:
SBIW YL,1
RET
.org $0006
TIMER0_COMPA:
RET
;*******************************
START:
SBI DDRB,0

LDI YH,BYTE3(Fo-1)
LDI YL,BYTE2(Fo-1)
LDI R22,BYTE1(Fo-1)
OUT OCR0A,R22

LDI R22,1<<SE
OUT MCUCR,R22 ; SLEEP IDLE

CLR R19
OUT TCCR0A,R19

LDI R21,1<<OCIE0A

LDI R20,1<<TOIE0
OUT TIMSK0,R20 ; разрешить прерывание переполнения
OUT TIFR0,R20

LDI R20,1
OUT TCCR0B,R20 ; старт Т0

SEI
WAIT:
SLEEP
BRNE PC-2

LDI R19,1<<WGM01
OUT TCCR0A,R19 ; режим сравнения с самоочисткой CTC

OUT TIMSK0,R21 ; разрешить прерывание сравнения
OUT TIFR0,R21
SEI
WAIT_COMP:
SLEEP
SBI PINB,0 ; инвертировать выход
RJMP START

.EXIT
Go to the top of the page
 
+Quote Post
ishpanec
сообщение Dec 21 2014, 13:54
Сообщение #7





Группа: Новичок
Сообщений: 6
Регистрация: 19-12-14
Пользователь №: 84 192



отвечу всем по порядку)

Цитата(zombi @ Dec 19 2014, 15:11) *
Не плохо было бы узнать полученный результат



значит при счете до 62 500 мигает он раз в 15 секунд %) наблюдал просто, ни каких особых измерений, это если бы там миллисекунды погрешности было, другое дело) вот биты из программки

Цитата(Dust112 @ Dec 19 2014, 15:16) *
Вы раздел 8-bit Timer/Counter0 with PWM документации читали?


я исключительно по книжкам. не думал что там особая разница есть.

Цитата(stells @ Dec 19 2014, 15:26) *
не 8?


пробовал клепать расчеты под 8, все равно заметные глазу отличия есть) мигание ~ раз в 7 секунд
что за таблица 9?

Цитата(demiurg1978 @ Dec 19 2014, 16:10) *
У меня такой способ получить 1 мс при 8 и 16 мгц:


с Си не дружу) после того как gcc танцы с бубном устраивать заставлял)))))

Цитата(akl @ Dec 20 2014, 10:56) *
С точностью до такта можно временной интервал формировать так. Писано для tiny13, но и для mega32 будет примерно также.


вашу магию тоже не совсем понял...

вот моя магия

CODE

device atmega32a
.include "D:\asm\include\m32def.inc"
.def temp = r16 ; темповая переменная
.def countTimer = r17 ; счетчик задержки
.def countTimer2 = r27
.def posR = r25

.equ timerSleep = 250
.equ timerSleep2 = 125

; начало программы
.org 0
rjmp RESET

.org $16 ; перывание таймера 0
rjmp TIMER0

TIMER0: ;начало таймер0

inc countTimer
cpi countTimer, timerSleep
ldi temp, 0
out TCNT0, temp
breq showsInt
reti

showsInt:

clr countTimer
inc countTimer2
cpi countTimer2, timerSleep2
breq IncsSeconds
reti

IncsSeconds:
clr countTimer2
inc posR
cpi posR,1
breq showReg1
cpi posR,2
breq showReg2

showReg1:
ldi temp, 0b11111111
rjmp continueTimers

showReg2:
ldi temp, 0b00000000
ldi posR,0


continueTimers:
out PORTA, temp
reti ;конец таймер 0


RESET:

ldi temp,low(RAMEND) ;загружаем указатель на стек
out SPL,temp

ldi temp,high(RAMEND) ; указатель стека, старший байт
out SPH,temp

ldi temp,0b11111111 ; контакт 0-7 порта A на выход
out DDRA,temp ;

ldi temp, 0b00000001 ; контакт 0-1 порта В на выход
out DDRB, temp
out PORTB,temp

clr countTimer
clr countTimer2

ldi temp,0b00000001
out TIMSK,temp

ldi temp,0b00000001
out TCCR0,temp

clr posR

sei ;разрешить прерывания

END:
rjmp END ;бесконечный цикл

там у меня просто циферблат стоит, пока им моргаю...)
Go to the top of the page
 
+Quote Post
ishpanec
сообщение Dec 21 2014, 15:17
Сообщение #8





Группа: Новичок
Сообщений: 6
Регистрация: 19-12-14
Пользователь №: 84 192



Цитата(ishpanec @ Dec 21 2014, 14:54) *
не та картинка...

Go to the top of the page
 
+Quote Post
zombi
сообщение Dec 21 2014, 16:06
Сообщение #9


Гуру
******

Группа: Свой
Сообщений: 2 076
Регистрация: 10-09-08
Пользователь №: 40 106



получается Internal Calibrated RC Oscillator 1 MHz.
Если галочка соответствует биту равному нулю.
Table 9-8. Internal Calibrated RC Oscillator Operating Modes
DS
Go to the top of the page
 
+Quote Post
stells
сообщение Dec 21 2014, 16:29
Сообщение #10


внештатный сотрудник
******

Группа: Участник
Сообщений: 2 458
Регистрация: 10-05-08
Из: МО, Медвежьи озера
Пользователь №: 37 401



Цитата(ishpanec @ Dec 21 2014, 16:54) *
что за таблица 9?

таблица 9 из даташита... или 9-8 из приведенного выше... в принципе все уже понятно
Go to the top of the page
 
+Quote Post
ishpanec
сообщение Dec 21 2014, 18:19
Сообщение #11





Группа: Новичок
Сообщений: 6
Регистрация: 19-12-14
Пользователь №: 84 192



да, уже разобрался, всем спасибо за помощь!)
по умолчанию в мк и правда был 1МГц, поменял биты, рпсчитал на 8 и все заработало как надо)
Код
Table 9. Internal Calibrated RC Oscillator Operating Modes
CKSEL3..0    Nominal Frequency (MHz)
0001        1.0
0010        2.0
0011        4.0
0100        8.0
Go to the top of the page
 
+Quote Post
akl
сообщение Dec 22 2014, 04:18
Сообщение #12


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

Группа: Свой
Сообщений: 127
Регистрация: 4-04-07
Из: Ижевск
Пользователь №: 26 773



Ваш код дает интервал 1 секунды, за счёт сравнений в обработчике, на 39мс больше. Если такая погрешность устраивает, нет проблем. Без ручного пересчёта чисел сравнения Вы не можете менять частоту. По мне, лучше поручить эту работу ассемблеру.
CODE
ldi temp, 0b00000001 ; контакт 0-1 порта В на выход
out DDRB, temp
out PORTB,temp

;*******************************
;.equ Fo=8000000
.equ Fo=7890123

MOV R0,TEMP
SET_SEC:

IN TEMP,PINB
EOR TEMP,R0

LDI R20,BYTE3(Fo-8); загрузка 1 секунды в тиках Fo за вычетом установок
LDI R21,BYTE2(Fo-8);
LDI R22,BYTE1(Fo-8);

SEC_WAIT:
SUBI R22,BYTE1(5);
SBCI R21,BYTE2(5)
SBCI R20,BYTE3(5)

BRCC SEC_WAIT
OUT PORTB,TEMP
RJMP SET_SEC
;*******************************
.EXIT
Go to the top of the page
 
+Quote Post
alexeyv
сообщение Dec 22 2014, 04:39
Сообщение #13


Местный
***

Группа: Участник
Сообщений: 298
Регистрация: 26-01-09
Из: Пермь
Пользователь №: 43 940



Зачем для этой цели использовать 8-ми разрядный счетчик? Не проще использовать 16-ти разрядный в режиме CTC ? Один раз настроил - и будет Вам прерывание 1 раз в сек без всяких дополнительных счетчиков на Си/Асме
Go to the top of the page
 
+Quote Post
akl
сообщение Dec 22 2014, 05:57
Сообщение #14


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

Группа: Свой
Сообщений: 127
Регистрация: 4-04-07
Из: Ижевск
Пользователь №: 26 773



Цитата(alexeyv @ Dec 22 2014, 09:39) *
Не проще использовать 16-ти разрядный в режиме CTC ? Один раз настроил - и будет Вам прерывание 1 раз в сек без всяких дополнительных счетчиков на Си/Асме
Проще, конечно. Попробуйте настроить один раз без дополнительных счётчиков формирователь 1.000'000 секунды для частоты 7'890'123 Гц на 16-ти разрядном таймере в режиме CTC.
Go to the top of the page
 
+Quote Post
RabidRabbit
сообщение Dec 22 2014, 07:35
Сообщение #15


Местный
***

Группа: Свой
Сообщений: 397
Регистрация: 3-12-09
Из: Россия, Москва
Пользователь №: 54 040



Цитата(akl @ Dec 22 2014, 08:57) *
Проще, конечно. Попробуйте настроить один раз без дополнительных счётчиков формирователь 1.000'000 секунды для частоты 7'890'123 Гц на 16-ти разрядном таймере в режиме CTC.

Ну, в обычных мегах эти Ваши 7'890'123 Гц можно было поделить на 256 предделителем и для CTC поставить значение 30820. Будет частота 0,999993283, разве плохо? sm.gif А для Ваших 1.000'000 секунды поди надо кварц специально отобранный да ещё и в термостат всю конструкцию засунуть...
Go to the top of the page
 
+Quote Post

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

 


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


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