Портал для радиолюбителей и разработчиков электроники · с 2003 годаРеклама на сайте
Найти компонент, схему или даташит

Даташиты, справочник отечественных приборов, схемы с разбором и живой форум

AVR Раздел по микроконтроллерам компании Atmel - AVR / ATtiny / ATmega / ATMega128 / ATxmega, вопросы по программированию в AVR studio и все, относящееся к AVR...

 
Опции темы

Помогите найти ошибку AVR asm

Непрочитано 28.01.2013, 21:31  
omercury
Почётный гражданин KAZUS.RUN
 
Аватар для omercury
 
Регистрация: 25.05.2010
Адрес: г. Королёв
Сообщений: 8,487
Сказал спасибо: 30
Сказали Спасибо 3,070 раз(а) в 2,011 сообщении(ях)
omercury на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

Сообщение от Boba_spb Посмотреть сообщение
Пора объявить конкурс на самую замысловатую работающую программу с DS18B20, и DS18S20.
Ой, ну несите уже приз!..
PHP код:
;*************************************************  *********************
;Программы работы с интерфейсом 1-wire при тактировании Таймером
;*************************************************  *********************
w1_Timer_Overflow:
        in        tempSreg,SREG        ;Сохраняем SREG
        subAddrGet                ;Чтение адреса возврата из стека
        retAddrLoad                    ;Загружаем адрес и делаем переход
        ret                            ;Без включения прерывания
;****************************************
Del64:
        subAddrGet                    ;Читаем адрес возврата
        subAddrSave                    ;Сохранение адреса подпрграммы
        Ini_TMR0_64                        ;Запускаем таймер
Del64_1:
        ldi        indH,High(Del64_2)        ;Грузим адрес возврата
        ldi        indL,Low(Del64_2)        ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
Del1024:
        subAddrGet                    ;Читаем адрес возврата
        subAddrSave                    ;Сохранение адреса подпрграммы
        Ini_TMR0_1024                    ;Запускаем таймер
        rjmp    Del64_1                    ;Грузим адрес возврата
Del64_2:
        rjmp    w1stop                    ;Выход из прерывания
;****************************************
; Output : T - presence bit    (поменял - теперь флаг "w1use")
;****************************************
w1Reset:
    ;    sbr        w1flag,(1‹‹w1work)        ;Ставим флаг использования 1-wire
        subAddrGet                    ;Читаем адрес возврата
        subAddrSave                    ;Сохранение адреса подпрграммы
        cbi        w1Port,w1                ;Подключили порт
        sbi        w1Dir,w1                ; "0" в шину
        ldi        w1del,w1wait480us        ;480 микросекунд(470)
        Ini_TMR0_64                        ;Запускаем таймер
        ldi        indH,High(w1Reset1)        ;Грузим адрес возврата
        ldi        indL,Low(w1Reset1)        ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1Reset1:
        cbi        w1Dir,w1                ; "1" в шину (освобождаем)
        ldi        w1del,w1wait70us        ;Загр. время - 70us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1Reset2)        ;Грузим адрес возврата
        ldi        indL,Low(w1Reset2)        ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1Reset2:
        set                            ;Ставим флаг T
        sbis    w1Pin,w1            ;Пропускаем следующую команду, если шина "1"
        clt                            ;Сбросили флаг T
        bld        w1flag,w1use        ;Читаем T в регистр флагов(если "w1use" - устройства есть)
        ldi        w1del,w1wait240us        ;240 микросекунд(240)
        Ini_TMR0_64                        ;Запускаем таймер
        ldi        indH,High(w1Reset3)        ;Грузим адрес возврата
        ldi        indL,Low(w1Reset3)        ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1Reset3:
        ;rjmp    w1stop                    ;Выход из прерывания
;****************************************
w1stop:    Stop_TMR0        ;Останов Timer0
        subAddrLoad                    ;Восстанавливаем адрес возврата
        subAddrSet                    ; в стек
w1out:    out        SREG,tempSreg        ;Восстанавливаем SREG
        reti                            ;Выход из прерывания
;****************************************
w1save:    retAddrSave                        ;Сохраняем адрес возврата
        skipAddrLoad                ;Подменяем адрес возврата
        skipAddrSet                    ; в стек
        out        SREG,tempSreg        ;Восстанавливаем SREG
        reti                            ;Выход из прерывания
;****************************************
; Чтение байта из 1-wire в регистр    (w1rdbuf)
;****************************************
w1readByte:
        subAddrGet                    ;Читаем адрес возврата
        subAddrSave                    ;Сохранение адреса подпрграммы
        ldi        w1cnt,8                ;Счетчик битов
w1readLoop:
;    rcall    w1ReadBit
;****************************************
w1ReadBit:            ;Короткий (5us) импульс в шину
        sbi        w1Dir, w1                ;Шину выход в "0" на 5 us
        ldi        w1del,w1wait5us            ;Загр. время - 5us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1ReadBit1)    ;Грузим адрес возврата
        ldi        indL,Low(w1ReadBit1)    ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1ReadBit1:            ;Короткий (5us) импульс в шину
        cbi        w1Dir, w1                ; "1" в шину (освобождаем)
        ldi        w1del,w1wait5us            ;Загр. время - 5us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1ReadBit2)    ;Грузим адрес возврата
        ldi        indL,Low(w1ReadBit2)    ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1ReadBit2:
        lsr        w1rdbuf        ;сдвигаем влево
        sbic    w1Pin,w1    ;Пропустить, если шина ="0"
        sbr        w1rdbuf,$80        ;Прибавляем 1 (устанавливаем бит 7 в "1")
        bst        w1rdbuf,7            ;Сохраняем принятый бит
        rcall    GetCRC                ;Вычисляем контрольную сумму
        ldi        w1del,w1wait50us        ;Загр. время - 50us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1ReadBit3)    ;Грузим адрес возврата
        ldi        indL,Low(w1ReadBit3)    ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1ReadBit3:
;****************************************
        dec        w1cnt                    ;Следующий бит
        brne    w1ReadLoop                ;Зациклились
        rjmp    w1stop                    ;Выход из прерывания
;****************************************
; Запись байта в 1-wire из регистра    (w1rdbuf)
;****************************************
w1writeByte:
    subAddrGet                        ;Читаем адрес возврата
    subAddrSave                        ;Сохранение адреса подпрграммы
        ldi        w1cnt,8                ;Счетчик битов
w1WriteLoop:
        bst        w1rdbuf,0            ;Сохраняем бит к передаче
        rcall    GetCRC                ;Вычисляем контрольную сумму
        ror        w1rdbuf                ;Сдвигаем младший бит в флаг переноса
;****************************************
w1WriteBit:
        brcs    w1WriteOne                ;Если флаг С установлен - переход на запись "1"
w1WriteZero:        ;Длинный (60us) импульс в шину
        sbi        w1Dir, w1                ; "0" в шину
        ldi        w1del,w1wait60us        ;Загр. время - 60us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1WriteZero1)    ;Грузим адрес возврата
        ldi        indL,Low(w1WriteZero1)    ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1WriteZero1:
        cbi        w1Dir, w1                ; "1" в шину (освобождаем)
        rjmp    w1WriteEnd
w1WriteOne:            ;Короткий (5us) импульс в шину
        sbi        w1Dir, w1                ; "0" в шину
        ldi        w1del,w1wait5us            ;Загр. время - 5us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1WriteOne1)    ;Грузим адрес возврата
        ldi        indL,Low(w1WriteOne1)    ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1WriteOne1:
        cbi        w1Dir, w1                ; "1" в шину (освобождаем)
w1WriteEnd:
        ldi        w1del,w1wait60us        ;Загр. время - 60us
        Ini_TMR0_8                        ;Запускаем таймер
        ldi        indH,High(w1WriteEnd1)    ;Грузим адрес возврата
        ldi        indL,Low(w1WriteEnd1)    ;Грузим адрес возврата
        rjmp    w1save                    ;Выход из прерывания с сохранением
w1WriteEnd1:
;****************************************
        dec        w1cnt                    ;Следующий бит
        brne    w1WriteLoop                ;Зациклились
        rjmp    w1stop                    ;Выход из прерывания
;*************************************************  **************
;Подпрограмма вычисления контрольной суммы 1го бита (в флаге Т)
; в w1CRCtmp - контрольная сумма
;*************************************************  **************
GetCRC:
        clr        w1CRCtmp1            ;Очищаем переменную для вычисления CRC
        bld        w1CRCtmp1,0            ;Восстанавливаем принятый бит
        eor        w1CRCtmp1,w1CRCtmp    ;Исключающее или с принятым битом
        ror        w1CRCtmp1            ;Смотрим - "0" или "1"
        mov        w1CRCtmp1,w1CRCtmp    ;Перезагружаем контрольную сумму
        brcc    Z0                    ;Если приняли "0" - переход
        ldi        w1del,$18            ;Если приняли "1" - загружаем константу
        eor        w1CRCtmp1,w1del        ;Исключающее или с константой
Z0:        ror        w1CRCtmp1            ;Сдвигаем контрольную сумму на бит вправо
        mov        w1CRCtmp,w1CRCtmp1    ;Сохраняем текущую контрольную сумму
        ret
;**************************************** 
Пожалуй этого достаточно.
Реклама:
omercury вне форума  
Непрочитано 29.01.2013, 00:32  
Boba_spb
Почётный гражданин KAZUS.RUN
 
Регистрация: 08.06.2008
Сообщений: 1,393
Сказал спасибо: 4
Сказали Спасибо 183 раз(а) в 167 сообщении(ях)
Boba_spb на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

Ну да, поразвлекались. Я чуть по другому переключаю прерывания.
Что то типа такого



ADDR_INTERRUPT: .BYTE 2



INTERRUPT:
push ZL
in ZL,SREG
push ZL
push ZH
lds ZL,ADDR_INTERRUPT
lds ZH,ADDR_INTERRUPT + 1
ijmp

InterruptExit:
sts ADDR_INTERRUPT,ZL
sts ADDR_INTERRUPT+1,ZH
pop ZH
pop ZL
out SREG,ZL
pop ZL
reti
//==============
INTERRUPT1:
....
....
ldi ZL,low(INTERRUPT2)
ldi ZH,HIGH(INTERRUPT2)
jmp InterruptExit
//============
INTERRUPT2:
....
....
ldi ZL,low(INTERRUPT3)
ldi ZH,HIGH(INTERRUPT3)
jmp InterruptExit
//============
INTERRUPT3:
....
....
ldi ZL,low(INTERRUPT2)
ldi ZH,HIGH(INTERRUPT2)
jmp InterruptExit



А когда не нужны прерывания, то просто

INTERRUPT10:
....
.....
ldi ZL, LOW(InterruptExit)
ldi ZH,HIGH(InterruptExit)
jmp InterruptExit
Boba_spb вне форума  
Непрочитано 29.01.2013, 00:57  
omercury
Почётный гражданин KAZUS.RUN
 
Аватар для omercury
 
Регистрация: 25.05.2010
Адрес: г. Королёв
Сообщений: 8,487
Сказал спасибо: 30
Сказали Спасибо 3,070 раз(а) в 2,011 сообщении(ях)
omercury на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

В принципе те же помидоры, токлько у мну выделена ещё одна приоритетная задача...
Пробовал на указателях, но получилось ещё медленней.
omercury вне форума  
Непрочитано 29.01.2013, 09:23  
Boba_spb
Почётный гражданин KAZUS.RUN
 
Регистрация: 08.06.2008
Сообщений: 1,393
Сказал спасибо: 4
Сказали Спасибо 183 раз(а) в 167 сообщении(ях)
Boba_spb на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

Так с - где борьба за приз ?
Boba_spb вне форума  
Непрочитано 29.01.2013, 10:40  
omercury
Почётный гражданин KAZUS.RUN
 
Аватар для omercury
 
Регистрация: 25.05.2010
Адрес: г. Королёв
Сообщений: 8,487
Сказал спасибо: 30
Сказали Спасибо 3,070 раз(а) в 2,011 сообщении(ях)
omercury на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

Сообщение от Boba_spb Посмотреть сообщение
Так с - где борьба за приз ?
Действительно... а я ещё макросы не показал...

Кстати, а что за приз?
omercury вне форума  
Непрочитано 29.01.2013, 11:11  
Boba_spb
Почётный гражданин KAZUS.RUN
 
Регистрация: 08.06.2008
Сообщений: 1,393
Сказал спасибо: 4
Сказали Спасибо 183 раз(а) в 167 сообщении(ях)
Boba_spb на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

Сообщение от omercury Посмотреть сообщение
Кстати, а что за приз?
Еще не думал. Давайте обсудим
Boba_spb вне форума  
Непрочитано 04.02.2013, 16:58  
omercury
Почётный гражданин KAZUS.RUN
 
Аватар для omercury
 
Регистрация: 25.05.2010
Адрес: г. Королёв
Сообщений: 8,487
Сказал спасибо: 30
Сказали Спасибо 3,070 раз(а) в 2,011 сообщении(ях)
omercury на пути к лучшему
По умолчанию Re: Помогите найти ошибку AVR asm

Кладу сюдой весь прожект...

Не доделан...
Вложения:
Тип файла: zip 1wire_m8_no_mod.zip (103.2 Кб, 38 просмотров)
omercury вне форума  
 
Опции темы

Ваши права в разделе
Вы не можете создавать новые темы
Вы не можете отвечать в темах
Вы не можете прикреплять вложения
Вы не можете редактировать свои сообщения

BB коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.

Быстрый переход

Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Помогите найти ошибку barbuss Микроконтроллеры, АЦП, память и т.д 9 16.10.2013 18:05
Помогите найти ошибку в моделировании 172senator Proteus 0 22.12.2010 14:18
Помогите найти ошибку в исходнике (+) Don_Ambrosio Микроконтроллеры, АЦП, память и т.д 1 29.04.2008 18:30
Помогите найти ошибку в PROTEUS maxNTF Proteus 2 29.11.2007 10:26
Помогите найти ошибку в схеме с двумя симисторами lisergin Автоматика и аппаратура связи 7 07.08.2005 00:39


Часовой пояс GMT +4, время: 13:36.


Powered by vBulletin® Version 3.8.4
Copyright ©2000 - 2026, Jelsoft Enterprises Ltd.