- Вложения
-
- Alg.JPG
- (38.64 КБ) 1184 скачивания
Таймеры/счётчики в AVR
Это просто - см. схему. Главной прграмме остается только посматривать на флаг ДАННЫЕ ОБНОВЛЕНЫ, сбрасывать его, если установлен, принимать данные и делать с ними что хошь : усреднять, индицировать, на хлеб намазывать ...

- Реклама
вот чего то пытался написал код , по которому моргать светодиод должен, не получилось он просто тускло горит
подскажите что не так? это первая попытка приручить таймер)
подскажите что не так? это первая попытка приручить таймер)
Спойлер
Код: Выделить всё
; по идее программа зажигает и гасит светодиод С0 (посажен светодиод на массу) по переполнению таймера Т0
;
;
;
.cseg
.include "m8Adef.inc"
;***********************************************************************
.org $000 rjmp RESET ;Reset Handler
;.org $001 reti ;rjmp EXT_INT0 ; IRQ0 Handler
;.org $002 reti ;rjmp EXT_INT1 ; IRQ1 Handler
;.org $003 reti ;rjmp TIM2_COMP ; Timer2 Compare Handler
;.org $004 reti ;rjmp TIM2_OVF ; Timer2 Overflow Handler
;.org $005 reti ;rjmp TIM1_CAPT ; Timer1 Capture Handler
;.org $006 reti ;rjmp TIM1_COMPA ; Timer1 CompareA Handler
;.org $007 reti ;rjmp TIM1_COMPB ; Timer1 CompareB Handler
;.org $008 reti ;rjmp TIM1_OVF ; Timer1 Overflow Handler
.org $009 rjmp TIM0_OVF ;rjmp TIM0_OVF ; Timer0 Overflow Handler
;.org $00a reti ;rjmp SPI_STC ; SPI Transfer Complete Handler
;.org $00b reti ;rjmp USART_RXC ; USART RX Complete Handler
;.org $00c reti ;rjmp USART_UDRE ; UDR Empty Handler
;.org $00d reti ;rjmp USART_TXC ; USART TX Complete Handler
;.org $00e reti ;rjmp ADC ; ADC Conversion Complete Handler
;.org $00f reti ;rjmp EE_RDY ; EEPROM Ready Handler
;.org $010 reti ;rjmp ANA_COMP ; Analog Comparator Handler
;.org $011 reti ;rjmp TWSI ; Two-wire Serial Interface Handler
;.org $012 reti ;rjmp SPM_RDY ; Store Program Memory Ready Handler
;***********************************************************************
RESET:
cli ; запретить прерывания
ldi r16,low(RAMEND) ; загрузка указателя стека
out SPL,r16
ldi r16,high(RAMEND)
out SPH,r16
ldi r16, 0b00000001 ; разрешаем прерыв таймера Т0
out TIMSK, r16
ldi r16, 0b00000001 ; сбрасываем флаг в индикаторе установив в 1, хз вроде так)
out TIFR, r16
ldi r16, 0b00000101 ;
out TCCR0, r16 ; пределитель 1024, интервал до прерывания 0,26 сек
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
sbi DDRC,0 ; ножка 0 порта с на вых
sei ; разрешить прерывания
;**********************************************************************************************************************
TIM0_OVF:
cli ; запретить прерывания
push r16 ; сохраняем используемые регистры r16 (этих пушей может быть много)
push r17 ; сохраняем используемые регистры r17 (этих пушей может быть много)
in r17, SREG ; сохраням флаги
push r17 ; и запихиваем их в стек
sbis PORTC,0 ; читаем бит С0, если этот бит установлен, пропускает следующую команду
sbi PORTC, 0 ; зажигаем светодиод на ножке С0
cbi PORTC, 0 ; гасим светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
sei ; разрешить прерывания
retiглаза боятся, а руки что то не делают))
А где главный цикл программы? Куда она пойдет после первой команды sei?
В прерывании не обязательно использовать запрет и разрешение прерываний. Это делается автоматически.
Для того, чтобы что-то увидеть нужно ввести задержку между включением светодиода и его отключением. В противном случае у Вас получается, что тот включается и через 1 такт выключается. 1 такт ~ 1 мкс. Глазом такого не заметить.
К тому же, ножка у Вас на выход сформирована. По умолчанию там 0. Т.е. команда зажигания светодиода у Вас будет всегда пропускаться.
сбрасывать каждый раз предделители тоже не обязательно. В регистре SFIOR помимо сброса предделителей есть другие функции. Правильнее использовать команды чтения-модификации-записи, а не прямой записи. Сбрасывать можно и нужно предделитель того таймера, который используете.
В прерывании регистр r17 Вы не используете - можно не сохранять. Операций, меняющих флаги тоже нет - регистр флагов можно также не трогать.
Лучше попробуйте без всяких условий зажигать и гасить светодиод по таймеру
Светодиод, надеюсь, через резистор подключили?
В прерывании не обязательно использовать запрет и разрешение прерываний. Это делается автоматически.
Для того, чтобы что-то увидеть нужно ввести задержку между включением светодиода и его отключением. В противном случае у Вас получается, что тот включается и через 1 такт выключается. 1 такт ~ 1 мкс. Глазом такого не заметить.
К тому же, ножка у Вас на выход сформирована. По умолчанию там 0. Т.е. команда зажигания светодиода у Вас будет всегда пропускаться.
сбрасывать каждый раз предделители тоже не обязательно. В регистре SFIOR помимо сброса предделителей есть другие функции. Правильнее использовать команды чтения-модификации-записи, а не прямой записи. Сбрасывать можно и нужно предделитель того таймера, который используете.
В прерывании регистр r17 Вы не используете - можно не сохранять. Операций, меняющих флаги тоже нет - регистр флагов можно также не трогать.
Лучше попробуйте без всяких условий зажигать и гасить светодиод по таймеру
Светодиод, надеюсь, через резистор подключили?
Последний раз редактировалось ИС-пытатель Вт май 06, 2014 00:31:03, всего редактировалось 1 раз.
Спойлер
Код: Выделить всё
; по идее программа зажигает и гасит светодиод С0 (посажен светодиод на массу) по переполнению таймера Т0
;
;
;
.cseg
.include "m8Adef.inc"
;***********************************************************************
.org $000 rjmp RESET ;Reset Handler
;.org $001 reti ;rjmp EXT_INT0 ; IRQ0 Handler
;.org $002 reti ;rjmp EXT_INT1 ; IRQ1 Handler
;.org $003 reti ;rjmp TIM2_COMP ; Timer2 Compare Handler
;.org $004 reti ;rjmp TIM2_OVF ; Timer2 Overflow Handler
;.org $005 reti ;rjmp TIM1_CAPT ; Timer1 Capture Handler
;.org $006 reti ;rjmp TIM1_COMPA ; Timer1 CompareA Handler
;.org $007 reti ;rjmp TIM1_COMPB ; Timer1 CompareB Handler
;.org $008 reti ;rjmp TIM1_OVF ; Timer1 Overflow Handler
.org $009 rjmp TIM0_OVF ;rjmp TIM0_OVF ; Timer0 Overflow Handler
;.org $00a reti ;rjmp SPI_STC ; SPI Transfer Complete Handler
;.org $00b reti ;rjmp USART_RXC ; USART RX Complete Handler
;.org $00c reti ;rjmp USART_UDRE ; UDR Empty Handler
;.org $00d reti ;rjmp USART_TXC ; USART TX Complete Handler
;.org $00e reti ;rjmp ADC ; ADC Conversion Complete Handler
;.org $00f reti ;rjmp EE_RDY ; EEPROM Ready Handler
;.org $010 reti ;rjmp ANA_COMP ; Analog Comparator Handler
;.org $011 reti ;rjmp TWSI ; Two-wire Serial Interface Handler
;.org $012 reti ;rjmp SPM_RDY ; Store Program Memory Ready Handler
;***********************************************************************
RESET:
cli ; запретить прерывания
ldi r16,low(RAMEND) ; загрузка указателя стека
out SPL,r16
ldi r16,high(RAMEND)
out SPH,r16
ldi r16, 0b00000001 ; разрешаем прерыв таймера Т0
out TIMSK, r16
ldi r16, 0b00000001 ; сбрасываем флаг в индикаторе установив в 1, хз вроде так)
out TIFR, r16
ldi r16, 0b00000101 ;
out TCCR0, r16 ; пределитель 1024, интервал до прерывания 0,26 сек
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
sbi DDRC,0 ; ножка 0 порта с на вых
sei ; разрешить прерывания
;**********************************************************************************************************************
MAIN:
RJMP MAIN
;*************************************************************************************************************************
TIM0_OVF:
cli ; запретить прерывания
push r16 ; сохраняем используемые регистры r16 (этих пушей может быть много)
push r17 ; сохраняем используемые регистры r17 (этих пушей может быть много)
in r17, SREG ; сохраням флаги
push r17 ; и запихиваем их в стек
sbis PORTC,0 ; читаем бит С0, если этот бит установлен, пропускает следующую команду
RJMP KUKA ; зажигаем светодиод на ножке С0
cbi PORTC, 0 ; гасим светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
sei ; разрешить прерывания
reti
;*****************************************************************************************************************
KUKA:
sbi PORTC, 0 ; зажигаем светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
sei ; разрешить прерывания
RJMP MAINвроде исправил) моргает)
Испытатель да, через резистор 300 ом)
Последний раз редактировалось sergo80zxc Вт май 06, 2014 00:33:47, всего редактировалось 1 раз.
глаза боятся, а руки что то не делают))
А из прерывания по-человечески кто выходить будет?
Последний раз редактировалось ИС-пытатель Вт май 06, 2014 00:35:49, всего редактировалось 1 раз.
- Реклама
как по человечески?)) все заклинил код) перестал моргать)
глаза боятся, а руки что то не делают))
Вы в прерывании прыгаете на КУКУ, а оттуда сразу в главную процедуру. Либо выравнивайте стек перед прыжком, либо возвращайтесь из КУКИ по reti
Спойлер
Код: Выделить всё
; по идее программа зажигает и гасит светодиод С0 (посажен светодиод на массу) по переполнению таймера Т0
;
;
;
.cseg
.include "m8Adef.inc"
;***********************************************************************
.org $000 rjmp RESET ;Reset Handler
;.org $001 reti ;rjmp EXT_INT0 ; IRQ0 Handler
;.org $002 reti ;rjmp EXT_INT1 ; IRQ1 Handler
;.org $003 reti ;rjmp TIM2_COMP ; Timer2 Compare Handler
;.org $004 reti ;rjmp TIM2_OVF ; Timer2 Overflow Handler
;.org $005 reti ;rjmp TIM1_CAPT ; Timer1 Capture Handler
;.org $006 reti ;rjmp TIM1_COMPA ; Timer1 CompareA Handler
;.org $007 reti ;rjmp TIM1_COMPB ; Timer1 CompareB Handler
;.org $008 reti ;rjmp TIM1_OVF ; Timer1 Overflow Handler
.org $009 rjmp TIM0_OVF ;rjmp TIM0_OVF ; Timer0 Overflow Handler
;.org $00a reti ;rjmp SPI_STC ; SPI Transfer Complete Handler
;.org $00b reti ;rjmp USART_RXC ; USART RX Complete Handler
;.org $00c reti ;rjmp USART_UDRE ; UDR Empty Handler
;.org $00d reti ;rjmp USART_TXC ; USART TX Complete Handler
;.org $00e reti ;rjmp ADC ; ADC Conversion Complete Handler
;.org $00f reti ;rjmp EE_RDY ; EEPROM Ready Handler
;.org $010 reti ;rjmp ANA_COMP ; Analog Comparator Handler
;.org $011 reti ;rjmp TWSI ; Two-wire Serial Interface Handler
;.org $012 reti ;rjmp SPM_RDY ; Store Program Memory Ready Handler
;***********************************************************************
RESET:
cli ; запретить прерывания
ldi r16,low(RAMEND) ; загрузка указателя стека
out SPL,r16
ldi r16,high(RAMEND)
out SPH,r16
ldi r16, 0b00000001 ; разрешаем прерыв таймера Т0
out TIMSK, r16
ldi r16, 0b00000001 ; сбрасываем флаг в индикаторе установив в 1, хз вроде так)
out TIFR, r16
ldi r16, 0b00000101 ;
out TCCR0, r16 ; пределитель 1024, интервал до прерывания 0,26 сек
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
sbi DDRC,0 ; ножка 0 порта с на вых
sei ; разрешить прерывания
;**********************************************************************************************************************
MAIN:
RJMP MAIN
;*************************************************************************************************************************
TIM0_OVF:
cli ; запретить прерывания
push r16 ; сохраняем используемые регистры r16 (этих пушей может быть много)
push r17 ; сохраняем используемые регистры r17 (этих пушей может быть много)
in r17, SREG ; сохраням флаги
push r17 ; и запихиваем их в стек
sbis PORTC,0 ; читаем бит С0, если этот бит установлен, пропускает следующую команду
RJMP KUKA ; зажигаем светодиод на ножке С0
cbi PORTC, 0 ; гасим светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
sei ; разрешить прерывания
reti
;*****************************************************************************************************************
KUKA:
sbi PORTC, 0 ; зажигаем светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
pop r16 ; выдергиваем 2 байта ркаловских) так как выходим через жопу)
pop r16
sei ; разрешить прерывания
RJMP MAIN
все равно чето не то, что то намудрил
или вот так через рети?
Спойлер
Код: Выделить всё
; по идее программа зажигает и гасит светодиод С0 (посажен светодиод на массу) по переполнению таймера Т0
;
;работает программа
;
.cseg
.include "m8Adef.inc"
;***********************************************************************
.org $000 rjmp RESET ;Reset Handler
;.org $001 reti ;rjmp EXT_INT0 ; IRQ0 Handler
;.org $002 reti ;rjmp EXT_INT1 ; IRQ1 Handler
;.org $003 reti ;rjmp TIM2_COMP ; Timer2 Compare Handler
;.org $004 reti ;rjmp TIM2_OVF ; Timer2 Overflow Handler
;.org $005 reti ;rjmp TIM1_CAPT ; Timer1 Capture Handler
;.org $006 reti ;rjmp TIM1_COMPA ; Timer1 CompareA Handler
;.org $007 reti ;rjmp TIM1_COMPB ; Timer1 CompareB Handler
;.org $008 reti ;rjmp TIM1_OVF ; Timer1 Overflow Handler
.org $009 rjmp TIM0_OVF ;rjmp TIM0_OVF ; Timer0 Overflow Handler
;.org $00a reti ;rjmp SPI_STC ; SPI Transfer Complete Handler
;.org $00b reti ;rjmp USART_RXC ; USART RX Complete Handler
;.org $00c reti ;rjmp USART_UDRE ; UDR Empty Handler
;.org $00d reti ;rjmp USART_TXC ; USART TX Complete Handler
;.org $00e reti ;rjmp ADC ; ADC Conversion Complete Handler
;.org $00f reti ;rjmp EE_RDY ; EEPROM Ready Handler
;.org $010 reti ;rjmp ANA_COMP ; Analog Comparator Handler
;.org $011 reti ;rjmp TWSI ; Two-wire Serial Interface Handler
;.org $012 reti ;rjmp SPM_RDY ; Store Program Memory Ready Handler
;***********************************************************************
RESET:
cli ; запретить прерывания
ldi r16,low(RAMEND) ; загрузка указателя стека
out SPL,r16
ldi r16,high(RAMEND)
out SPH,r16
ldi r16, 0b00000001 ; разрешаем прерыв таймера Т0
out TIMSK, r16
ldi r16, 0b00000001 ; сбрасываем флаг в индикаторе установив в 1, хз вроде так)
out TIFR, r16
ldi r16, 0b00000101 ;
out TCCR0, r16 ; пределитель 1024, интервал до прерывания 0,26 сек
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
sbi DDRC,0 ; ножка 0 порта с на вых
sei ; разрешить прерывания
;**********************************************************************************************************************
MAIN:
RJMP MAIN
;*************************************************************************************************************************
TIM0_OVF:
cli ; запретить прерывания
push r16 ; сохраняем используемые регистры r16 (этих пушей может быть много)
push r17 ; сохраняем используемые регистры r17 (этих пушей может быть много)
in r17, SREG ; сохраням флаги
push r17 ; и запихиваем их в стек
sbis PORTC,0 ; читаем бит С0, если этот бит установлен, пропускает следующую команду
RJMP KUKA ; зажигаем светодиод на ножке С0
cbi PORTC, 0 ; гасим светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
sei ; разрешить прерывания
reti
;*****************************************************************************************************************
KUKA:
sbi PORTC, 0 ; зажигаем светодиод на ножке С0
ldi r16, 0b00000011
out SFIOR, r16 ; сброс предделителей (0 бит) PSR10 (1 бит) PSR2 установкой в них 1
pop r17 ; извлекаем из стека флаги в r17 (обратный порядок при извлечении из стека)
out SREG, r17 ; отправляем их обратно в регистр флагов
pop r17 ; восстанавливаем регистр r17
pop r16 ; восстанавливаем регистр r16
sei ; разрешить прерывания
retiсбрасывать каждый раз предделители тоже не обязательно. В регистре SFIOR помимо сброса предделителей есть другие функции. Правильнее использовать команды чтения-модификации-записи, а не прямой записи. Сбрасывать можно и нужно предделитель того таймера, который используете.
((команды чтения-модификации-записи, а не прямой записи )) это вы о чем?
((Сбрасывать можно и нужно предделитель того таймера, который используете.)) как?
((В регистре SFIOR помимо сброса предделителей есть другие функции)) какие?
Последний раз редактировалось Gudd-Head Вт май 06, 2014 10:43:35, всего редактировалось 1 раз.
Причина: Склеил
Причина: Склеил
глаза боятся, а руки что то не делают))
Оба варианта рабочие.
Загляните в даташит. Раздел Register Summary. Найдите там регистр SFIOR. В нем используются 4 бита. 3-й бит относится к компаратору. 2-й бит - общее отключение подтягивающих резисторов. 1-й и 0-й биты - сброс предделителей. Причем, 1-й бит PSR2 (видите циферку 2?) сбрасывает предделитель таймера 2, а 0-й бит PSR10 (опять-таки циферки нам подсказывают, к чему относится) сбрасывает предделители таймеров 0 и 1. Вы используете только таймер 0. Бит PSR2 можно не трогать. Сбросить достаточно 1 раз во время инициализации. И вообще сброс нужен для одновременного старта таймеров. В Вашем случае сброс не уместен (хотя не является ошибкой).
Далее, т.к. регистр SFIOR содержит другие управляющие биты, то правильнее делать не прямую запись
а чтение-модификацию-запись (это дословно). Смотрите:
При таком обращении Вы измените только младший бит (сбросите предделитель таймеров 0 и 1), оставив остальные без изменений.
сделайте такой код в прерывании:
Загляните в даташит. Раздел Register Summary. Найдите там регистр SFIOR. В нем используются 4 бита. 3-й бит относится к компаратору. 2-й бит - общее отключение подтягивающих резисторов. 1-й и 0-й биты - сброс предделителей. Причем, 1-й бит PSR2 (видите циферку 2?) сбрасывает предделитель таймера 2, а 0-й бит PSR10 (опять-таки циферки нам подсказывают, к чему относится) сбрасывает предделители таймеров 0 и 1. Вы используете только таймер 0. Бит PSR2 можно не трогать. Сбросить достаточно 1 раз во время инициализации. И вообще сброс нужен для одновременного старта таймеров. В Вашем случае сброс не уместен (хотя не является ошибкой).
Далее, т.к. регистр SFIOR содержит другие управляющие биты, то правильнее делать не прямую запись
Код: Выделить всё
ldi r16, xxxxx
out SFIOR, r16Код: Выделить всё
in r16, SFIOR; чтение
ori r16, 0b1 ; модификация. установим крайний бит. лишние нули слева можно не писать
out SFIOR, r16; записьсделайте такой код в прерывании:
Спойлер
Код: Выделить всё
TIM0_OVF:
in r16, PINC; читаем состояние ножек порта
ldi r17, 1; 0b00000001
eor r16, r17; меняем значение 0-й ножки на противоположное
out PORTC, r16; отправляем обратно в порт
reti
испытатель я все переправил)
Спойлер
Код: Выделить всё
.cseg
.include "m8Adef.inc"
;***********************************************************************
.org $000 rjmp RESET ;Reset Handler
;.org $001 reti ;rjmp EXT_INT0 ; IRQ0 Handler
;.org $002 reti ;rjmp EXT_INT1 ; IRQ1 Handler
;.org $003 reti ;rjmp TIM2_COMP ; Timer2 Compare Handler
;.org $004 reti ;rjmp TIM2_OVF ; Timer2 Overflow Handler
;.org $005 reti ;rjmp TIM1_CAPT ; Timer1 Capture Handler
;.org $006 reti ;rjmp TIM1_COMPA ; Timer1 CompareA Handler
;.org $007 reti ;rjmp TIM1_COMPB ; Timer1 CompareB Handler
;.org $008 reti ;rjmp TIM1_OVF ; Timer1 Overflow Handler
.org $009 rjmp TIM0_OVF ;rjmp TIM0_OVF ; Timer0 Overflow Handler
;.org $00a reti ;rjmp SPI_STC ; SPI Transfer Complete Handler
;.org $00b reti ;rjmp USART_RXC ; USART RX Complete Handler
;.org $00c reti ;rjmp USART_UDRE ; UDR Empty Handler
;.org $00d reti ;rjmp USART_TXC ; USART TX Complete Handler
;.org $00e reti ;rjmp ADC ; ADC Conversion Complete Handler
;.org $00f reti ;rjmp EE_RDY ; EEPROM Ready Handler
;.org $010 reti ;rjmp ANA_COMP ; Analog Comparator Handler
;.org $011 reti ;rjmp TWSI ; Two-wire Serial Interface Handler
;.org $012 reti ;rjmp SPM_RDY ; Store Program Memory Ready Handler
;***********************************************************************
RESET:
cli
ldi r16,low(RAMEND) ; стек инициализируем
out SPL,r16
ldi r16,high(RAMEND)
out SPH,r16
ldi r16, 0b00000001 ;
out TIMSK, r16 ; разрешаем прерывание Т0
ldi r16, 0b00000001 ;
out TIFR, r16 ; сбрасываем флаг
ldi r16, 0b00000101 ;
out TCCR0, r16 ; ;
in r16, SFIOR ; читаем порт регистра
ori r16, 0b1 ; логическое или, устанавливаем в бит 0 еденицу
out SFIOR, r16 ; пишем в бит 0 еденицу, сбрасываем предделитель Т0 и Т1
ldi r16, 0b00000001
out DDRC, r16 ; бит 0 порта С на выход
sei ;
;**********************************************************************************************************************
MAIN:
RJMP MAIN
;*************************************************************************************************************************
TIM0_OVF:
in r16, PINC ; читаем порт
ldi r17, 1 ; присваеваем 0b00000001
eor r16, r17 ; исключаещее или, если бит 0 порта С =1, то результат =0, если бит =0, то результат =1
out PORTC, r16 ; пишем результат в порт С
reti
;*****************************************************************************************************************
глаза боятся, а руки что то не делают))
Я ж Вас учил:
сначала настройка - потом разрешение прерываний. У Вас наоборот.
С портом аналогично. Сначала настройка порта - потом запуск прерывания, которое его менять будет.
После out PORTC,r16 еще команду nop добавить - и вообще шик будет!
См. даташит или Евстифеева. Глава про порты. Но в Вашей проге не критично.

P.S. Так как, заработало? )
сначала настройка - потом разрешение прерываний. У Вас наоборот.
С портом аналогично. Сначала настройка порта - потом запуск прерывания, которое его менять будет.
После out PORTC,r16 еще команду nop добавить - и вообще шик будет!
Осталось только орфографию в русских комментах исправить - и вообще не придерешься.я все переправил)
P.S. Так как, заработало? )
испытатель
заработала) nop то зачем?
заработала) nop то зачем?
глаза боятся, а руки что то не делают))
А это Вы сами почитайте. ))) в Вашей программе она не нужна, но в некоторых случаях требуется.
- Сообщения: 4
- Зарегистрирован: Сб май 10, 2014 00:39:35
Приветы .
Вопрос по счётчикам - что можно почитать для тупых ?
А то уже руки опускаются - читаю , читаю - и ничего не понимаю .
Тему всю прочёл , по ссылкам ходил , в гугл ходил , к яндексу ходил .... я нипанимат !
возьмём просто (нулевой) таймер .
TCNT0 8-ми разрядный таймер счётчик.
TCCR0 - его делитель.
если объявить делитель :
TCCR0=1 // или =0b00000001 ? или =0x01 ? или TCCR0 = (1<<CS0X) где X - 1-3 ?а если 0 то таймер не работает ?
то-есть TCNT0 будет бегать от 0 до 255 (от 0x00 до 0xhh , или от 0b00000000 - до 0b11111111 ) ? его можно прочитать ? записать ? сравнить ? что-то сделать по переполнению ?
Вопрос по счётчикам - что можно почитать для тупых ?
А то уже руки опускаются - читаю , читаю - и ничего не понимаю .
Тему всю прочёл , по ссылкам ходил , в гугл ходил , к яндексу ходил .... я нипанимат !
возьмём просто (нулевой) таймер .
TCNT0 8-ми разрядный таймер счётчик.
TCCR0 - его делитель.
если объявить делитель :
TCCR0=1 // или =0b00000001 ? или =0x01 ? или TCCR0 = (1<<CS0X) где X - 1-3 ?а если 0 то таймер не работает ?
то-есть TCNT0 будет бегать от 0 до 255 (от 0x00 до 0xhh , или от 0b00000000 - до 0b11111111 ) ? его можно прочитать ? записать ? сравнить ? что-то сделать по переполнению ?
Предполагаю, что речь идёт о самом простом Т0 на борту mega8. Тогда
Теория не закреплённая практикой - время на ветер.
даsevpers писал(а): TCNT0 8-ми разрядный таймер счётчик.
это регистр управления таймера. Для Т0 mega8 осуществляет разрешение/запрет счёта Т0 импульсов от общего с Т1 предделителя или внешних импульсов по заданному перепаду. Для других камней, у которых возможности Т0 гораздо шире, состояний TCCR0x значительно больше.sevpers писал(а):TCCR0 - его делитель.
на первые 3 вопроса - да; на последний - для определения переполнения лучше пользоваться регистром TIFR и TIMSK, если событие будет обрабатываться прерыванием.sevpers писал(а):его можно прочитать ? записать ? сравнить ? что-то сделать по переполнению ?
Теория не закреплённая практикой - время на ветер.
А вот эту мою ссылку видели?Тему всю прочёл , по ссылкам ходил , в гугл ходил , к яндексу ходил .... я нипанимат !
http://radiokot.ru/forum/download/file. ... &id=183616
- Вложения
-
- Таймер АВР.rar
- (211.55 КБ) 409 скачиваний
- Сообщения: 3
- Зарегистрирован: Чт май 15, 2014 14:42:05
Помогите плз. Где я торможу? Нужен меандр в 40 кГц. А у меня только звуковая частота получается.
Код: Выделить всё
/*******************************************************
МК: ATtiny2313A-SU
Кварцевый резонатор: 7,372800 MHz
http://easyelectronics.ru/avr-uchebnyj-kurs-tajmery.html
*******************************************************/
#include <tiny2313a.h>
// Declare your global variables here
unsigned char Tim; // Объявляем переменную-аргумент для wait1
// Описываем функцию задержки на "Tim" тактов
void wait1 (void)
{
TCNT1=0;
while (TCNT1<Tim) {};
}
void main(void) // Главная функция программы
{
// Declare your local variables here
// Crystal Oscillator division factor: 1
#pragma optsize-
CLKPR=(1<<CLKPCE);
CLKPR=(0<<CLKPCE) | (0<<CLKPS3) | (0<<CLKPS2) | (0<<CLKPS1) | (0<<CLKPS0);
#ifdef _OPTIMIZE_SIZE_
#pragma optsize+
#endif
// Input/Output Ports initialization
ACSR=0x80; //Отключили компаратор для экономии энергии
// Port B initialization
PORTB=0xFF;
DDRB=0xFF;
// Инициализация таймера TCNT1
TCCR1A=0x00;
TCCR1B=0x05;
// Задаем аргумент для wait1
Tim=1;
while (1)
{
PORTB.3=1; //Подаем 1 на 15 ножку
wait1 (); // Вызов функции задержки
PORTB.3=0; //Подаем 0 на 15 ножку
wait1 (); // Вызов функции задержки
}
}
- Вложения
-
- khazama.jpg
- фьюзы в хазаме
- (61.53 КБ) 493 скачивания
- Сообщения: 4
- Зарегистрирован: Сб май 10, 2014 00:39:35
Да - вчера читал, но ничего не понял . Сегодня - на ура.ИС-пытатель писал(а): А вот эту мою ссылку видели?
http://radiokot.ru/forum/download/file. ... &id=183616
Вообще, у Вас все реализовано как-то.. мягко говоря через анальный проход. проще было бы через прерывание сделать.Помогите плз. Где я торможу?
Ну, если фузы выставили правильно, то у Вас получается, что задержка реализует частоту 7,372800 MHz / 1024 (коэффициент деления таймера) / 1 (значение переменной Tim, с которой сравниваете) = 7200 герц. А так как у Вас используются 2 задержки для 1 цикла, то результирующая частота = 7200 / 2 = 3600 Гц. Уменьшайте коэффициент деления таймера и подбирайте Tim нужную частоту
Diola Попробуйте так
Спойлер
Код: Выделить всё
.equ Fclk=7372800
LDI R20,Fclk/40000/2-1
OUT OCR0A,R20
LDI R20,$42 ; включить режим независимого переключения вывода PB2(OCR0A)
OUT TCCR0A,R20
LDI R20,1
OUT TCCR0B,R20 ; Пуск Т0 для независимого от ядра переключения состояния на лапе PB2(OCR0A)
ttt:
RJMP ttt


