Чт дек 06, 2012 22:42:56
Пт дек 07, 2012 08:09:31
pryanic писал(а):Пробовал сбрасывать флаги внешних прерываний и в обработчике INT0, и в обработчике таймера перед разрешением INT0. Не помогает.
Пт дек 07, 2012 09:47:07
Пт дек 07, 2012 09:52:58
EXT_INT0: push temp
in temp, SREG
push temp ;сохраняем temp и SREG в стеке
clr temp
out GICR, temp ;запрещаем INT0
sbic pinD, 1 ;если на проверяемом пине высокий уровень,
rjmp move_right ;идем по метке вправо, если низкий,
rjmp move_left ;то влево.
move_right: cpi count, 0b00001111
breq exit_INT0
inc count
eor count, invert
out PortC, count
rjmp exit_INT0
move_left: cpi count, 0b00000000
breq exit_INT0
dec count
eor count, invert
out portC, count
exit_INT0: ldi temp, 0b00000101 ;запускаем таймер0 с предделителем 256
out TCCR0, temp ;задержка при 4 MHz примерно 16 мс.
pop temp
out SREG, temp
pop temp
reti
TIM0_OVF: push temp ;в прерывани только лишь разрешаем INT0
in temp, SREG
push temp
clr temp
out TCCR0, temp ;останавливаем Таймер0
ldi temp, 0b01000000
out GICR, temp ;разрешаем INT0
pop temp
out SREG, temp
pop temp
reti
;*****************************END INTERRUPTS****************************************
RESET: ldi temp, high(RAMEND) ; Main program start
out SPH, temp ; Set Stack Pointer to top of RAM
ldi temp, low(RAMEND)
out SPL, temp
ser temp
out ddrc, temp ;C на вывод
ldi temp, 0b00001100
out portC, temp ;гасим светодиоды
clr temp
out ddrd, temp ;D на ввод
ser temp
out portd, temp ;потяжка
ldi temp, 0b00001100
mov invert, temp
ldi temp, 0b00000001
out timsk, temp ;разрешаем перывание таймера 0 по переполнению
ldi temp, 0b00000010
out mcucr, temp ;устанавливаем прерывание INT0 по спаду.
ldi temp, 0b01000000
out GICR, temp ;разрешаем прерывание INT0
clr count
sei ;глобальное разрешение прерываний
Gcykle: rjmp gcykle
Пт дек 07, 2012 10:11:47
TIM0_OVF: push temp
in temp, SREG
push temp
clr temp
out TCCR0, temp ;останавливаем Таймер0
ser temp
out GIFR, temp ;очищаем регистр флагов внешных прерываний
ldi temp, 0b01000000
out GICR, temp ;разрешаем INT0
pop temp
out SREG, temp
pop temp
reti
Пт дек 07, 2012 12:29:14
in temp, SREG
push temp
clr temp
out TCCR0, temp
ldi temp, 0b01000000 ТАК ПРАВИЛЬНО
out GIFR, temp ;очищаем регистр флагов внешных прерываний
ldi temp, 0b01000000
out GICR, temp ;разрешаем INT0
pop temp
out SREG, temp
pop temp
reti
Пт дек 07, 2012 12:53:38
Пт дек 07, 2012 13:31:29
Пт дек 07, 2012 13:43:51
А что с INT0 при выходе?
Пт дек 07, 2012 14:19:21
Пт дек 07, 2012 14:29:59
Пт дек 07, 2012 14:49:46
Пт дек 07, 2012 14:52:14
Пт дек 07, 2012 15:08:51
Пт дек 07, 2012 15:16:22
Пт дек 07, 2012 15:56:40
Дребезг нужно подавлять только по одной шторке, но фиксировать значение второй шторки по импульсам непосредственно от первой
Пт дек 07, 2012 16:08:08
Не всё. Попробуйте.pryanic писал(а):В симуляторе все отлично.
;программа обработки энкодера
;Fcl = 4MHz
.include "m8def.inc"
.def temp = r16
.def count = r17
.def invert = r0
.cseg
.org 0
rjmp RESET ; Reset Handler
rjmp EXT_INT0 ; IRQ0 Handler
reti;rjmp EXT_INT1 ; IRQ1 Handler
reti;rjmp TIM2_COMP ; Timer2 Compare Handler
reti;rjmp TIM2_OVF ; Timer2 Overflow Handler
reti;rjmp TIM1_CAPT ; Timer1 Capture Handler
reti;rjmp TIM1_COMPA ; Timer1 CompareA Handler
reti;rjmp TIM1_COMPB ; Timer1 CompareB Handler
reti;rjmp TIM1_OVF ; Timer1 Overflow Handler
TIM0_OVF:
; push temp ;в прерывани только лишь разрешаем INT0
; in temp, SREG
; push temp
; clr temp
out TCCR0,ZL ;останавливаем Таймер0
OUT TCNT0,ZL
ldi temp, 0b01000000
out GICR, temp ;разрешаем INT0
OUT GIFR,TEMP
; pop temp
; out SREG, temp
; pop temp
reti
; rjmp TIM0_OVF ; Timer0 Overflow Handler
; reti;rjmp SPI_STC ; SPI Transfer Complete Handler
; reti;rjmp USART_RXC ; USART RX Complete Handler
; reti;rjmp USART_UDRE ; UDR Empty Handler
; reti;rjmp USART_TXC ; USART TX Complete Handler
; reti;rjmp ADC ; ADC Conversion Complete Handler
; reti;rjmp EE_RDY ; EEPROM Ready Handler
; reti;rjmp ANA_COMP ; Analog Comparator Handler
; reti;rjmp TWSI ; Two-wire Serial Interface Handler
; reti;rjmp SPM_RDY ; Store Program Memory Ready Handler
;***************************INTERRUPTS**********************************************
EXT_INT0:
; push temp
; in temp, SREG
; push temp ;сохраняем temp и SREG в стеке
; clr temp
out GICR,ZL ;запрещаем INT0
sbic pinD, 1 ;если на проверяемом пине высокий уровень,
rjmp move_right ;идем по метке вправо, если низкий,
rjmp move_left ;то влево.
move_right: cpi count, 0b00001111
breq exit_INT0
inc count
eor count, invert
out PortC, count
rjmp exit_INT0
move_left: cpi count, 0b00000000
breq exit_INT0
dec count
eor count, invert
out portC, count
exit_INT0:
ldi temp, 0b00000001 ;запускаем таймер0
; ldi temp, 0b00000101 ;запускаем таймер0 с предделителем 256
out TCCR0, temp ;задержка при 4 MHz примерно 16 мс.
; pop temp
; out SREG, temp
; pop temp
reti
;*****************************END INTERRUPTS****************************************
RESET:
ldi temp, high(RAMEND) ; Main program start
out SPH, temp ; Set Stack Pointer to top of RAM
ldi temp, low(RAMEND)
out SPL, temp
;*************************************************
SER ZH
CLR ZL
;*************************************************
; ser temp
out ddrc,ZH ;C на вывод
; ldi temp, 0b00001100
out portC,ZL ;гасим светодиоды
; clr temp
out ddrd,ZL ;D на ввод
; ser temp
out portd,ZH ;потяжка
clr count
; ldi temp, 0b00001100
CLR invert
; mov invert, temp
ldi temp, 0b00000001
out timsk, temp ;разрешаем перывание таймера 0 по переполнению
ldi temp, 0b00000010
out mcucr, temp ;устанавливаем прерывание INT0 по спаду.
ldi temp, 0b01000000
out GICR, temp ;разрешаем прерывание INT0
; clr count
OUT GIFR,ZH
OUT TIFR,ZH
sei ;глобальное разрешение прерываний
Gcykle: rjmp gcykle
Пт дек 07, 2012 16:23:10
; out SREG, temp
; in temp, SREG
Пт дек 07, 2012 16:58:02
Пт дек 07, 2012 22:26:57