Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: Программа asm gередача по UART attiny25
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > AVR
addict
Доброго времени суток.
Нужно передать 1 байт на скорости 19200 бод (8 бит 1 стоп) от мк attiny25 на устройство.
МК программируется программатором громова через uniprof.при подключении питания на мк устройство принимает 1 байт 0FFh вместо 05fh.
МК работает от внутренного тактвого генератора на заводских установках, частоте- 1мгц.
сперва сделал код на таймере.Ничего не получилось, решил считать такты.Исходил из того, что, при частоте 1мгц длительность 1 такта занимает 0,000001 секунды.длительность 1 бита(бода) при скорости 19200 будет 0,000052083 секунды, тоесть задержка между перепадами уровней должна быть 52 такта.Вроде написал код, вроде правильно.Но не работает, подскажите, что может быть не так.


CODE
rjmp RESET ; Reset Handler

RESET:
cli
ldi r17, 0xd0
out 0x3D, r17 ;инициализация стэка

ldi R16, 0b00000011 ;порты как выход
out 0x17, r16
LDI R30, low(fing_cmp*2) ;
lpm r18, Z ;загрузим байт

trx_idle: ;2 такта
ldi R16, 0b00000001 ;логический 1 (idle)
out 0x18, r16

;Задержка 52-2 = 50
ldi r20, 16
delay1:
dec r20
brne delay1
nop
nop

trx_start: ;2 такта
ldi R16, 0b00000000 ;логический 0 (start bit)
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay2:
dec r20
brne delay2
nop
nop
trx_bit0: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay3:
dec r20
brne delay3
nop
nop
trx_bit1: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay4:
dec r20
brne delay4
nop
nop
trx_bit2: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay5:
dec r20
brne delay5
nop
nop
trx_bit3: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay6:
dec r20
brne delay6
nop
nop
trx_bit4: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16


;Задержка 52-5 = 47
ldi r20, 15
delay7:
dec r20
brne delay7
nop
nop
trx_bit5: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay8:
dec r20
brne delay8
nop
nop
trx_bit6: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16


;Задержка 52-5 = 47
ldi r20, 15
delay9:
dec r20
brne delay9
nop
nop
trx_bit7: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16


;Задержка 52-2 = 50
ldi r20, 16
delay13:
dec r20
brne delay13
nop
nop
trx_idle2: ;2 такта
ldi R16, 0b00000001 ;логический 1 (idle)
out 0x18, r16


stop:
nop
nop
rjmp stop

fing_cmp: .db 0xf5
zombi
R31 ненужно грузить?
addict
Цитата(zombi @ Apr 14 2018, 08:35) *
R31 ненужно грузить?



нет, r31 cодержит 0, когда под отладчиком в avr studio прогоняешь то в r18 грузится нужное число -05fh.B биты в портах, когда сдвигаешь r18 щелкают правильно.

Цитата(zombi @ Apr 14 2018, 08:35) *
R31 ненужно грузить?


загрузил регистр r18 напрямую значением.вроде заработало, но иногда приходит df.

Спасибо)получается когда мк включается состояние регистров не определено ?
zombi
Цитата(addict @ Apr 14 2018, 12:09) *
Спасибо)получается когда мк включается состояние регистров не определено ?

конечно не определено biggrin.gif
И изучите макросы что ли, если циклы лень использовать.
глаза сломать можно глядя на вашу писанину.

Цитата(addict @ Apr 14 2018, 12:09) *
в r18 грузится нужное число -05fh

Просто интересно, компилятор выдаёт какие либо варнинги?
Если да, то читаете ли Вы их?

Задавались ли Вы вопросом какую точность имеет Internal RC Oscillator? и может ли это влиять на качество передачи?
addict
Цитата(zombi @ Apr 14 2018, 17:56) *
Просто интересно, компилятор выдаёт какие либо варнинги?
Если да, то читаете ли Вы их?

Задавались ли Вы вопросом какую точность имеет Internal RC Oscillator? и может ли это влиять на качество передачи?


нет, варнингов нет. Насчет точности..в книге прочитал что встроенный rc генератор может давать существенные погрешности, и вроде нужно подстраивать частоту.Вообщем переписал малость код, также с подсчетом тактов, на этой частоте на этом мк на реальном железе пока ошибок нет, все работает.
zombi
Цитата(addict @ Apr 14 2018, 20:25) *
нет, варнингов нет.

Странно. И на это не ругается?
Цитата
fing_cmp: .db 0xf5

второй байт слова не определён.
и никакого беспокойства у компилятора это не вызывает?
addict
Цитата(zombi @ Apr 14 2018, 19:06) *
Странно. И на это не ругается?

второй байт слова не определён.
и никакого беспокойства у компилятора это не вызывает?


нет, никаких ошибок, Assembly complete, 0 errors. 0 warnings
.avr studio 4
zombi
Цитата(addict @ Apr 14 2018, 23:05) *
нет, никаких ошибок, Assembly complete, 0 errors. 0 warnings
.avr studio 4

А какой последний байт в файле прошивки?
Скорее всего конечно 0хFF, но просто интересно.
addict
Цитата(zombi @ Apr 15 2018, 06:51) *
А какой последний байт в файле прошивки?
Скорее всего конечно 0хFF, но просто интересно.


Код
020000020000FC
:1000000002C09DC07FC0F89410ED1DBF03E007BB88
:10001000F1E0EEE35527259101E008BB40E14A9568
:10002000F1F70000000000E008BB4FE04A95F1F74F
:1000300000000000889400272795001F08BB4FE0B0
:100040004A95F1F700000000889400272795001FCB
:1000500008BB4FE04A95F1F70000000088940027A4
:100060002795001F08BB4FE04A95F1F700000000FC
:10007000889400272795001F08BB4FE04A95F1F7A9
:1000800000000000889400272795001F08BB4FE060
:100090004A95F1F700000000889400272795001F7B
:1000A00008BB4FE04A95F1F7000000008894002754
:1000B0002795001F08BB4FE04A95F1F700000000AC
:1000C000889400272795001F08BB40E14A95F1F767
:1000D0000000000001E008BB5395583009F09BCFA9
:1000E00003E007BB01E008BB00E00ABF00E20BBF72
:1000F00004E005BBBB27CC27F1E0E6E4259178942A
:100100000000FECFB03071F0B93071F000272795B4
:10011000001F16B316951695011771F4B39500E0FC
:100120000ABF1895B3951895BB27C395C83011F031
:100130002591189502E008BBF8940000FDCFF50C5E
:0E014000000000000CF5F50C000101000CF5AC
:00000001FF
Прошивка уже немного другая.Но все также- константы в коде на конце.
не знаю почему на конце AC00000001FF, сигнатура чтоли какая или выравнивание, ну 1-2 байта выровнять, зачем то хвост такой вставляет.Или там страницы, блоки, банки, что там еще.Да и вообще дурацкая какая то студия -когда входишь в обработчик и у тебя флаг прерывания сбрасывается, как и должно.следующий раз он не сбрасывается.Или после команды обращения к памяти вдруг флаги прерываний устанавливаются.Порты PINB не меняют своего статуса после установки в DDRB бита 1, или не сразу.
У меня теперь другая засада biggrin.gif теперь прочитать не могу 8 байт.Запарился уже.Что может быть не так.8 байт уходит в устройство, прикладываю к нему палец, должен прийти ответ и мк зажечь светодиод.

CODE
rjmp RESET ; Reset Handler
rjmp EXT_INT0 ; IRQ0 Handler
rjmp PCINT0 ; PCINT0 Handler
;rjmp TIM1_COMPA ; Timer1 CompareA Handler
;rjmp TIM1_OVF ; Timer1 Overflow Handler
;rjmp TIM0_OVF ; Timer0 Overflow Handler
;rjmp EE_RDY ; EEPROM Ready Handler
;rjmp ANA_COMP ; Analog Comparator Handler
;rjmp ADC ; ADC Conversion Handler
;rjmp TIM1_COMPB ; Timer1 CompareB Handler
;rjmp TIM0_COMPA ;
;rjmp TIM0_COMPB ;
;rjmp WDT ;
;rjmp USI_START ;
;rjmp USI_OVF ;

;f50c000000000cf5 ;запрос на скан
;F5 0C 01 01 01 00 0D F5 ;средний палец
;F5 0C 00 01 01 00 0C F5 ;указательный палец





RESET:

cli
ldi r17, 0xd0
out 0x3D, r17 ;инициализация стэка

ldi R16, 0b00000011 ;порты как выход
out 0x17, r16

LDI R31, high(fing_cmp*2) ;настройка строки
LDI R30, low(fing_cmp*2) ;настройка строки

clr r21 ;счетчик байтов

trx_symbol:
lpm r18, Z+ ;загрузим байт

trx_idle: ;2 такта
ldi R16, 0b00000001 ;логический 1 (idle)
out 0x18, r16

;Задержка 52-2 = 50
ldi r20, 16
delay1:
dec r20
brne delay1
nop
nop

trx_start: ;2 такта
ldi R16, 0b00000000 ;логический 0 (start bit)
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay2:
dec r20
brne delay2
nop
nop
trx_bit0: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay3:
dec r20
brne delay3
nop
nop
trx_bit1: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay4:
dec r20
brne delay4
nop
nop
trx_bit2: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay5:
dec r20
brne delay5
nop
nop
trx_bit3: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay6:
dec r20
brne delay6
nop
nop
trx_bit4: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16


;Задержка 52-5 = 47
ldi r20, 15
delay7:
dec r20
brne delay7
nop
nop
trx_bit5: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16

;Задержка 52-5 = 47
ldi r20, 15
delay8:
dec r20
brne delay8
nop
nop
trx_bit6: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16


;Задержка 52-5 = 47
ldi r20, 15
delay9:
dec r20
brne delay9
nop
nop
trx_bit7: ;5 тактов
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16


;Задержка 52-2 = 50
ldi r20, 16
delay13:
dec r20
brne delay13
nop
nop
trx_idle2: ;2 такта
ldi R16, 0b00000001 ;логический 1 (idle)
out 0x18, r16

inc r21 ;обработали очередной байт
cpi r21, 8
breq receive
rjmp trx_symbol


receive:
ldi R16, 0b00000011 ;порт 2 как вход, 0 и 1 как выходы
out 0x17, r16
ldi R16, 0b00000001 ;вход 2 сделаем HI-z а нулевой оставим установленным - пассивным
out 0x18, r16
ldi R16, 0b00000000 ;очистим все флаги прерываний
out 0x3a, r16
ldi R16, 0b00100000 ;разрешим прерывание по изменению на пине
out 0x3b, r16
ldi R16, 0b00000100 ;разрешим прерывание только от 2-ого пина (0 1 2)
out 0x15, r16

clr r27 ;счетчик бодов
clr r28 ;счетчик байтов
LDI R31, high(middle_fing*2) ;настройка строки
LDI R30, low(middle_fing*2) ;настройка строки
lpm r18, Z+ ;загрузим байт
sei

stop:
nop
rjmp stop

PCINT0:
cpi r27, 0
breq start_bit
cpi r27, 9
breq stop_bit
clr r16
ror r18 ;младший байт уходит в C
adc r16, r16
in r17, 0x16 ;прочитаем порт PINB
lsr r17
lsr r17
cp r16, r17
brne error
inc r27
ldi R16, 0b00000000 ;очистим все флаги прерываний
out 0x3a, r16
reti

start_bit:
inc r27
reti

stop_bit:
clr r27 ;все боды прошли
inc r28 ;обработали очередной байт
cpi r28, 8
breq succes
lpm r18, Z+ ;загрузим байт
reti

succes:
ldi r16, 0b00000010
out 0x18, r16

error:
cli
nop
rjmp error

EXT_INT0:


fing_cmp: .db 0xf5, 0x0c,0x00,0x00, 0x00, 0x00, 0x0c, 0xf5
middle_fing: .db 0xf5, 0x0c,0x00,0x01, 0x01, 0x00, 0x0c, 0xf5
k155la3
сперва решите Вашу задачу с использованием кварцевого тактирования от встроенного (если есть возможность) или внешнего генератора.
Когда все будет работать как надо и без сбоев - переводите на RC и отлаживаете (считаете такты, подстраиваете генератор итп).
ps Снизьте скорость UART пока отлаживаете софт. Или надо будет такты пересчитывать ? sm.gif
zombi
bb-offtopic.gif
Цитата
Прошивка уже немного другая.Но все также- константы в коде на конце.

Так теперь константы кратны 2 и выравнивать ничего не нужно biggrin.gif
Цитата
У меня теперь другая засада biggrin.gif теперь прочитать не могу 8 байт.Запарился уже.Что может быть не так.

не, нет времени.
Могу только посоветовать увеличить паузу между байтами раз по одному все норм.
И internal RC проверить.
Если есть осциллограф то просто зациклить ногодрыг и смотреть какая частота на ноге получилась.
KGB
Цитата(addict @ Apr 14 2018, 13:09) *
нет, r31 cодержит 0,

шутить изволите?
не сравнивайте компилятор с реальным авр!!! при включении там может быть мусор!

вы используете софтовую реализацию компорта и передаёте байт описывая каждый бит..
это занимает очень много памяти..
вот попробуйте это...
подогнать под свою скорость и частоту кварца сможете?
CODE
;**********************************************************************
*********
*******************

; передача одного байта в формате РС-232 16МГЦ 115200
TX_232:

push r16
push r17
push r18
; заносим в...
cbi PORTB,1 ; формирум СТАРТ бит 1=>0
ldi r17,0x08 ; заносим в CNT_BIT - 9. количество сдвигов
;---------------------
ldi r18,43 ; корекция скорости передачи
sta_bit:
dec r18
brne sta_bit
;---------------------
Loop_TX:
sbrs r16,0
cbi PORTB,1
sbrc r16,0
sbi PORTB,1

;------------------
ldi r18,43 ; корекция скорости передачи
tx_bit:
dec r18
brne tx_bit
nop
nop
;------------------

lsr r16 ; здвигаем
dec r17
brne Loop_TX


sbi PORTB,1 ; формирум СТОП бит
;------------------
ldi r18,80 ; 15 корекция скорости передачи
st_bit:
dec r18
brne st_bit;
;------------------

pop r18
pop r17
pop r16

ret



;*******************************************************************************
*******************



LDI R30, low(fing_cmp*2)
LDI R31, high(fing_cmp*2)
lpm r18, Z ;загрузим байт

и R31 обязателен!!!

вот и вся прога... отправки 8ми байт в ком из таблицы
CODE
;**********************************************************************
****************************
;
_reset:

clr r1
out SREG,r1

ldi r16, LOW(RAMEND) ;setup stack pointer
out SPL, r16
; ldi r16, HIGH(RAMEND)
; out SPH, r16


ldi ZL,low(Table_1*2) ; считываем адрес таблицы
ldi ZH,high(Table_1*2)

ldi r19,8

lp:
lpm r24,Z+

call TX_232

dec r19
brne lp


sss:
jmp sss


Table_1:
.db 0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08

;*******************************************************************************
*******************
addict
[quote name='KGB' date='Apr 17 2018, 23:33' post='1557047']
шутить изволите?
не сравнивайте компилятор с реальным авр!!! при включении там может быть мусор!

вы используете софтовую реализацию компорта и передаёте байт описывая каждый бит..
это занимает очень много памяти..
вот попробуйте это...
подогнать под свою скорость и частоту кварца сможете?

и R31 обязателен!!!



Уже понял) спасибо.Мне память не критична в данном случае.На отправку у меня давно получилось, а вот прием.С приемом тоже разобрался, там уже циклы.Жаль по прерываниям от переполнения счетчика таймера не получится реализовать на данном мк.
KGB
Цитата(addict @ Apr 20 2018, 13:02) *
Жаль по прерываниям от переполнения счетчика таймера не получится реализовать на данном мк.

не понял что не можете реализовать
addict
Цитата(KGB @ Apr 20 2018, 20:46) *
не понял что не можете реализовать


вот к примеру почему не работает этот код на отправку, мк тотже, частота теже

CODE

rjmp RESET ; Reset Handler
rjmp EXT_INT0 ; IRQ0 Handler
rjmp PCINT0 ; PCINT0 Handler
rjmp TIM1_COMPA ; Timer1 CompareA Handler
rjmp TIM1_OVF ; Timer1 Overflow Handler

RESET:
cli
ldi r17, 0xd0
out 0x3D, r17 ;инициализация стэка


ldi R16, 0b00000011 ;порты как выход
out 0x17, r16

LDI R30, low(fing_cmp*2)
clr r31

lpm r18, Z+
clr r28 ;счетчик бодов
clr r29 ;счетчик байтов

ldi R16, 0b00000100 ;разрешим прерывание по переполнению таймера 1
out 0x39, r16
ldi R16, 0xf3 ;дозаполним счетчик
out 0x2f, r16
ldi R16, 0b00000010 ;сброс предделителя
out 0x2c, r16
ldi R16, 0b00000011 ;установка предделителя- CK\4 итоговая частота
out 0x30, r16 ;после установки частоты счетчик тутже начинает считать
sei

wt:
nop
rjmp wt ;заглушка до прерывания



TIM1_OVF:
ldi R16, 0xf3 ;дозаполним счетчик
out 0x2f, r16
ldi R16, 0b00000010 ;сброс предделителя
out 0x2c, r16

transmit:
cpi r28, 1
brlo trx_idle ;если меньше 1, тоесть 0 то выставляем лог.единицу
breq trx_start ;лог единица уже стоит и значит пишем стартовый бит
cpi r28, 10
brlo trx_bit
clr r28 ;все, все боды прошли
inc r29 ;обработали очередной байт
cpi r29, 8 ;сколько байт обработали
breq stop ;если 8 то все.
lpm r18, Z+
reti

trx_idle:
ldi R16, 0b00000001 ;логический 1 (idle онже потом stop бит)
out 0x18, r16
inc r28
reti


trx_start:
ldi R16, 0b00000000 ;логический 0 (start bit)
out 0x18, r16
inc r28
reti

trx_bit:
clc
clr r16
ror r18 ;младший бит уходит в C
adc r16, r16
out 0x18, r16
inc r28
reti

stop:
nop
nop
rjmp stop

EXT_INT0: ; IRQ0 Handler
PCINT0: ; PCINT0 Handler
TIM1_COMPA: ; Timer1 CompareA Handler

fing_cmp: .db 0xf5, 0x0c,0x00,0x00, 0x00, 0x00, 0x0c, 0xf5

Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.