Перейти к содержанию
    

Программа asm gередача по UART attiny25

Доброго времени суток.

Нужно передать 1 байт на скорости 19200 бод (8 бит 1 стоп) от мк attiny25 на устройство.

МК программируется программатором громова через uniprof.при подключении питания на мк устройство принимает 1 байт 0FFh вместо 05fh.

МК работает от внутренного тактвого генератора на заводских установках, частоте- 1мгц.

сперва сделал код на таймере.Ничего не получилось, решил считать такты.Исходил из того, что, при частоте 1мгц длительность 1 такта занимает 0,000001 секунды.длительность 1 бита(бода) при скорости 19200 будет 0,000052083 секунды, тоесть задержка между перепадами уровней должна быть 52 такта.Вроде написал код, вроде правильно.Но не работает, подскажите, что может быть не так.

 

 

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

Изменено пользователем IgorKossak
[codebox] для длинного кода, [code] - для короткого!

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

R31 ненужно грузить?

 

 

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

 

R31 ненужно грузить?

 

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

 

Спасибо)получается когда мк включается состояние регистров не определено ?

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Спасибо)получается когда мк включается состояние регистров не определено ?

конечно не определено :biggrin:

И изучите макросы что ли, если циклы лень использовать.

глаза сломать можно глядя на вашу писанину.

 

в r18 грузится нужное число -05fh

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

Если да, то читаете ли Вы их?

 

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

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

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

Если да, то читаете ли Вы их?

 

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

 

нет, варнингов нет. Насчет точности..в книге прочитал что встроенный rc генератор может давать существенные погрешности, и вроде нужно подстраивать частоту.Вообщем переписал малость код, также с подсчетом тактов, на этой частоте на этом мк на реальном железе пока ошибок нет, все работает.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

нет, варнингов нет.

Странно. И на это не ругается?

fing_cmp: .db 0xf5

второй байт слова не определён.

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

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Странно. И на это не ругается?

 

второй байт слова не определён.

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

 

нет, никаких ошибок, Assembly complete, 0 errors. 0 warnings

.avr studio 4

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

нет, никаких ошибок, Assembly complete, 0 errors. 0 warnings

.avr studio 4

А какой последний байт в файле прошивки?

Скорее всего конечно 0хFF, но просто интересно.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А какой последний байт в файле прошивки?

Скорее всего конечно 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: теперь прочитать не могу 8 байт.Запарился уже.Что может быть не так.8 байт уходит в устройство, прикладываю к нему палец, должен прийти ответ и мк зажечь светодиод.

 

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

Изменено пользователем IgorKossak
[codebox] для длинного кода, [code] - для короткого!

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

сперва решите Вашу задачу с использованием кварцевого тактирования от встроенного (если есть возможность) или внешнего генератора.

Когда все будет работать как надо и без сбоев - переводите на RC и отлаживаете (считаете такты, подстраиваете генератор итп).

ps Снизьте скорость UART пока отлаживаете софт. Или надо будет такты пересчитывать ? :)

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

:bb-offtopic:

Прошивка уже немного другая.Но все также- константы в коде на конце.

Так теперь константы кратны 2 и выравнивать ничего не нужно :biggrin:

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

не, нет времени.

Могу только посоветовать увеличить паузу между байтами раз по одному все норм.

И internal RC проверить.

Если есть осциллограф то просто зациклить ногодрыг и смотреть какая частота на ноге получилась.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

нет, r31 cодержит 0,

шутить изволите?

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

 

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

это занимает очень много памяти..

вот попробуйте это...

подогнать под свою скорость и частоту кварца сможете?

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

;		передача одного байта в формате РС-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ми байт в ком из таблицы

;**********************************************************************
****************************
;
_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

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

Изменено пользователем IgorKossak
[codebox] для длинного кода. [code]-для короткого!!!

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

шутить изволите?

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

 

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

это занимает очень много памяти..

вот попробуйте это...

подогнать под свою скорость и частоту кварца сможете?

 

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

 

 

 

Уже понял) спасибо.Мне память не критична в данном случае.На отправку у меня давно получилось, а вот прием.С приемом тоже разобрался, там уже циклы.Жаль по прерываниям от переполнения счетчика таймера не получится реализовать на данном мк.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Жаль по прерываниям от переполнения счетчика таймера не получится реализовать на данном мк.

не понял что не можете реализовать

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

не понял что не можете реализовать

 

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

 

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

Изменено пользователем addict

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...