Ассемблер (ASM) для AVR в вопросах и ответах

Обсуждаем контроллеры компании Atmel.
Ответить
akl
Друг Кота
Сообщения: 4473
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Второе приближение
Реклама
Потрогал лапой паяльник
Сообщения: 315
Зарегистрирован: Пт янв 29, 2010 19:42:27

Сообщение 12val12 »

Этот вариант никак не реагирует на вход
можно еще изменить

появляется питание контроллера
PORTB =0b00001111
ждем 9 сек

PORTB =0b11110000
ждем 200 ms //виртуальное нажатие кнопки sourse
PORTB =0b00001111

ждем 500 ms

PORTB =0b11110000
ждем 200 ms
PORTB =0b00001111

PORTB =0b11110000
ждем 200 ms
PORTB =0b00001111

ждем 500 ms

PORTB =0b11110000
ждем 200 ms
PORTB =0b00001111

ждем 500 ms

PORTB =0b11110000
ждем 200 ms
PORTB =0b00001111


порты оставляем в этом состоянии sleep
ух ты.... показывает
Реклама
akl
Друг Кота
Сообщения: 4473
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

12val12 писал(а):Этот вариант никак не реагирует на вход
Третье, финишное приближение. Включил подтяжку на кнопку.
TEST_1200.zip
Проверил на макете с ATtiny2313 (установил указатель стека, установил вектор таймера)
Изображение
Потрогал лапой паяльник
Сообщения: 315
Зарегистрирован: Пт янв 29, 2010 19:42:27

Сообщение 12val12 »

третий вариант работает если в момент включения на входе была единица
потом был спад в ноль и потом "0" -->"1"
если же при включении на входе был 0 то потом при перепаде "0"--"1" не сработает
---------

Ваши программы невозможно редактировать
Можно проще програмку-появилось питание - через секунду на выходе "1" ?

с прогрммной задержкой-тройной вложенный цикл

появилось питание
программная задержка 1-10 сек (без call- т е в основном теле )
выдали на выход 1
ух ты.... показывает
Реклама
Эиком - электронные компоненты и радиодетали
Потрогал лапой паяльник
Сообщения: 315
Зарегистрирован: Пт янв 29, 2010 19:42:27

Сообщение 12val12 »

Хочу что-то примерно такое
это я еще могу читать
где должна располагаться подпрограмма?

Код: Выделить всё

;	
.INCLUDE "tn2313def.inc"
	.INCLUDE "1200def.inc"
	.equ	Fo=4608000
;	.equ	Fo=1024000
	.def	COUNTER=R20	
	.CSEG
.ORG	$0000
	RJMP	INIT ; Reset Handler
	RJMP EXT_INT0 ; IRQ0 Handler
;.ORG	$0006
.ORG	$0002
  CLI
;
  LDI	R24,0b11110000
  OUT	PORTB,R24
  LDI	R24,0b11111111  ;all PORTB  out
  OUT	DDRB,R24
; ------------------------------
  ldi COUNTER,255
  rcall Delay
 ;------------------------
 LDI	R24,0b00001111
 OUT	PORTB,R24
 ; ------------------------
 ldi COUNTER,10
  rcall Delay
 ;------------------------
 LDI	R24,0b11110000
 OUT	PORTB,R24
 ; ---------------------------
  ldi COUNTER,100
  rcall Delay
 ;------------------------
 LDI	R24,0b00001111
 OUT	PORTB,R24
 ; ------------------------
 ldi COUNTER,10
  rcall Delay
 ;------------------------
 LDI	R24,0b11110000
 OUT	PORTB,R24
 ; ----------------------------
  ldi COUNTER,100
  rcall Delay
 ;------------------------
 LDI	R24,0b00001111
 OUT	PORTB,R24
 ; ------------------------
  ldi COUNTER,10
  rcall Delay
 ;------------------------
 LDI	R24,0b11110000
 OUT	PORTB,R24
 ; ----------------------------
  ldi COUNTER,100
  rcall Delay
 ;------------------------
 LDI	R24,0b00001111
 OUT	PORTB,R24
 ; ------------------------

 
 
 
;-----------------------------
Delay:  ;    R20 = Counter <--- time 
     DelayLoop1:
     ldi R21,255
       DelayLoop2:
        ldi R22,255
          DelayLoop3:
            dec R22
		    nop
		    nop
		    nop
		    nop
           brne DelayLoop3
        dec R21
        brne DelayLoop2
     dec R20
     brne DelayLoop1
 Ret
 
 

.EXIT
И еще как это компиллить?
avrasm2.exe -fI ??
Последний раз редактировалось 12val12 Ср мар 16, 2016 16:38:44, всего редактировалось 1 раз.
ух ты.... показывает
Реклама
akl
Друг Кота
Сообщения: 4473
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Почему не используете средства языка? Ведь афффигеть можно nop'ы считать.
Спойлер

Код: Выделить всё

;.INCLUDE "tn2313def.inc"
   .INCLUDE "1200def.inc"
   .equ   Fo=4608000
;   .equ   Fo=1024000
   .def   COUNTER=R20   
   .CSEG
.ORG   $0000
   RJMP   INIT ; Reset Handler
   RJMP EXT_INT0 ; IRQ0 Handler
;.ORG   $0006
.ORG   $0002

  CLI
;
EXT_INT0:

INIT:


  LDI   R24,0b11110000
  OUT   PORTB,R24
  LDI   R24,0b11111111  ;all PORTB  out
  OUT   DDRB,R24
; ------------------------------
;задержка 9000мс
D_9000:
	LDI	R20,BYTE3(9000*Fo/1000/5)
	LDI	R21,BYTE2(9000*Fo/1000/5)
	LDI	R22,BYTE1(9000*Fo/1000/5)
	RCALL	DELAY
;	RJMP	D_9000
;  ldi COUNTER,255
 ; rcall Delay
 ;------------------------
 LDI   R24,0b00001111
 OUT   PORTB,R24
 ; ------------------------
D_200:
	LDI	R20,BYTE3(200*Fo/1000/5)
	LDI	R21,BYTE2(200*Fo/1000/5)
	LDI	R22,BYTE1(200*Fo/1000/5)
	RCALL	DELAY
; ldi COUNTER,10
;  rcall Delay
 ;------------------------
 LDI   R24,0b11110000
 OUT   PORTB,R24
 ; ---------------------------
;
;
;
;
;-----------------------------
DELAY:
	SUBI	R22,BYTE1(1)
	SBCI	R21,BYTE2(1)
	SBCI	R20,BYTE3(1)
	BRNE	DELAY
	RET


;Delay:  ;    R20 = Counter <--- time
;     DelayLoop1:
;     ldi R21,255
;       DelayLoop2:
;        ldi R22,255
;          DelayLoop3:
;            dec R22
;          nop
;          nop
;          nop
;          nop
;           brne DelayLoop3
;        dec R21
;        brne DelayLoop2
;     dec R20
;     brne DelayLoop1
; Ret
Реклама
Потрогал лапой паяльник
Сообщения: 315
Зарегистрирован: Пт янв 29, 2010 19:42:27

Сообщение 12val12 »

ПОДСКАЖИТЕ чем компиллить?
разобрался
ух ты.... показывает
Потрогал лапой паяльник
Аватара пользователя
Сообщения: 386
Зарегистрирован: Чт окт 31, 2013 10:54:32

Сообщение alex38779 »

Возникла такая проблема, при отправке байта по SPI пишет spdr write collision, это в шпротеусе

код отправки такой

Код: Выделить всё

;ОТПРАВКА БАЙТА ПО SPI
 sendSPI:
	;PB2 = 0
	cbi PORTB, 2
	;шлем байт = temp2
	out SPDR, temp2
	;rcall Delay
	;проверка передачи
	in temp1, SPSR
	sbrs temp1, 7 ; если равен 1 то пропуск след команду
	rjmp sendSPI
	;PB2 = 1
	sbi PORTB, 2
	ret
Правильно ли я сделал проверку бита SPIF(7 бит в регистре SPSR)?

если добавляю задержку rcall Delay то все нормально. шлю данные в 595 регистр.
Контактная информация:
Говорящий с текстолитом
Аватара пользователя
Сообщения: 1525
Зарегистрирован: Чт июн 10, 2010 20:11:19

Сообщение COKPOWEHEU »

А что мешало воспользоваться примером из даташита?

Код: Выделить всё

SPI_MasterTransmit:
  ; Start transmission of data (r16)
  out SPDR,r16
Wait_Transmit:
  ; Wait for transmission complete
  in r16, SPSR
  sbrs r16, SPIF
    rjmp Wait_Transmit
ret
Потрогал лапой паяльник
Аватара пользователя
Сообщения: 386
Зарегистрирован: Чт окт 31, 2013 10:54:32

Сообщение alex38779 »

COKPOWEHEU Спасибо, заработало! Пытался сделать сам, переписывал код с си, забыл что в даташите есть примеры.
Контактная информация:
Потрогал лапой паяльник
Аватара пользователя
Сообщения: 386
Зарегистрирован: Чт окт 31, 2013 10:54:32

Сообщение alex38779 »

А как работать с большими числами?

Выделил в оперативке переменную в два байта, записал туда просто два числа.
Вот так:

Код: Выделить всё

	ldi YL, low(number)
	ldi YH, high(number)
	
	ld r16, Y+
	ld r17, Y+
	ldi r18, 124
	ldi r19, 231
	st Y+, r18
	st Y+, r19
А как записать одно число, например 124231, и дальше работать с ним?
Контактная информация:
akl
Друг Кота
Сообщения: 4473
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Запись беззнакового числа 0...4 294 967 295(FFFF FFFF)

Код: Выделить всё

LDI XH,BYTE4(124231)
LDI XL,BYTE3(124231)
LDI YH,BYTE2(124231)
LDI YL,BYTE1(124231)
Запись знакового числа -2 147 483 648...2 147 483 647(1000 0000...7FFF FFFF)

Код: Выделить всё

LDI XH,BYTE4(-124231)
LDI XL,BYTE3(-124231)
LDI YH,BYTE2(-124231)
LDI YL,BYTE1(-124231)
Встал на лапы
Аватара пользователя
Сообщения: 117
Зарегистрирован: Ср окт 15, 2014 12:45:46
Откуда: Анапа

Сообщение Jetetex »

люди добрые, помогите пож инициализировать МК:

Attiny 13
прерывание по переполнению таймера 0 (TIMER0_OVF)
частота - 4,8 МГц
предделитель - СК/256

Исходник прилагаю.

Вот опой чую, что где-то туплю, но вот только где? :shock:
Спойлер.include "d:\avr\avrasm\appnotes\tn13def.inc"

; Отсчет времени
; чтение кнопок
; Запись времени в ОЗУ

.def Temp=R16 ;\;
.def Temp1=R17 ; \ вспомогательные
.def Temp2=R18 ; / регистры
.def Temp3=R19 ;/;
.def HTemp=R20 ;старший счетный регистр |Вводим два дополнительных счетных регистра,
.def LTemp=R21 ;младший счетный регистр |т.к. счетчик 8-ми розрядный, а нам этого мало ))
.def Second=R22 ;счет секунд (0-60)
.def Min=R23 ;счет минут (0-60)
.def Hour=R24 ;счет часов (0-24)


.dseg


.cseg
.org 0


; ;*************************** Вектора прерываний ************************

rjmp RESET
;rjmp INT0 ;INT0_vect Внешнее прерывание 0
;rjmp PCINT0 ;PCINT0_vect Прерывание 0 по изменению состояния вывода
rjmp TIMER0_OVF ;TIMER0_OVF_vect Прерывание по переполнению таймера/счетчика 0
rjmp EE_READY ;EE_READY_vect EEPROM готова
rjmp ANALOG_COMP ;ANALOG_COMP_vect Аналоговый компаратор переключился
rjmp TIMER0_COMPA ;TIMER0_COMPA_vect Прерывание по сравнению, канал A таймера/счетчика 0
rjmp TIMER0_COMPB ;TIMER0_COMPB_vect Прерывание по сравнению, канал B таймера/счетчика 0
rjmp WDT ;WDT_vect Сторожевой таймер (если используется в качестве источника прерывания)



; *********** Коментируем используемые прерывания *********************

;RESET
;INT0:
;PCINT0:
;TIMER0_OVF
EE_READY:
ANALOG_COMP:
TIMER0_COMPA:
TIMER0_COMPB:
WDT:

reti



RESET: ldi Temp,0b11111111 ;настройка портов
out DDRB,Temp

ldi Temp,0b00000010 ;разрешить прерывание по переполнению таймера/счетчика 0
out TIMSK0,Temp

ldi Temp,0b00000001 ;тактовый сигнал = CK/256
out TCCR0B,Temp

; ldi Temp,0b00000000 ;Установить вывод OCOA в 1 при совпадении TCNT0 с OCR0A
; out TCCR0A,Temp

ldi Temp,0b00000000 ;
out TCNT0,Temp

ldi Temp,RamEnd ;инициализаци¤ стека
out SPL,Temp

ldi Temp1,0b00000001
sei

;********************** ************************
;********************** Загрузка начальных значений ************************
;********************** ************************

ldi Temp,0
mov HTemp,Temp
mov LTemp,Temp
mov Second,Temp
mov Min,Temp
mov Hour,Temp
mov Temp1,Temp

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

main: out PortB,Temp1
rjmp main




;********************** *********************
;********************** обработчик прерывания переполнения таймера *********************
;********************** TIMER0_OVF *********************

TIMER0_OVF: ldi Temp,0b00000000 ;
out TCNT0,Temp
ror Temp1
reti
Вложения
code.asm
(2.71 КБ) 189 скачиваний
Если я чего-то не знаю, это не говорит о моем невежестве, а только о том, что раньше этот вопрос лежал вне сферы моих интересов.
akl
Друг Кота
Сообщения: 4473
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Вектор прерывания переполнения таймера установлен неправильно.
Спойлер

Код: Выделить всё

.include "tn13def.inc"

; Отсчет времени
;	чтение кнопок
; Запись времени в ОЗУ

.def	Temp=R16	;\;
.def	Temp1=R17	; \ вспомогательные
.def	Temp2=R18	; / регистры
.def	Temp3=R19	;/;
.def	HTemp=R20	;старший счетный регистр |Вводим два дополнительных счетных регистра, 
.def	LTemp=R21	;младший счетный регистр	|т.к. счетчик 8-ми розрядный, а нам этого мало ))
.def	Second=R22	;счет секунд (0-60)
.def	Min=R23	;счет минут (0-60)
.def	Hour=R24	;счет часов (0-24)


.dseg


.cseg
.org 0
;*************************** Вектора прерываний ************************
	rjmp RESET	
;rjmp INT0	;INT0_vect	Внешнее прерывание 0
;rjmp PCINT0	;PCINT0_vect	Прерывание 0 по изменению состояния вывода
.org 3
;********************** обработчик прерывания переполнения таймера *********************
;**********************	TIMER0_OVF	*********************
TIMER0_OVF:
	LSL Temp1
	ANDI	Temp1,0b01111111
	CPI	Temp1,$40
	BRLO	PC+2
	LDI	Temp1,1
	reti

RESET:
	ldi Temp,0b11111111 ;настройка портов
	out DDRB,Temp

;********************** Загрузка начальных значений ************************

ldi Temp,0
mov HTemp,Temp
mov LTemp,Temp
mov Second,Temp
mov Min,Temp
mov Hour,Temp
mov Temp1,Temp

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

;ldi Temp,0b00000000 ;
out TCNT0,Temp

ldi Temp,0b00000010 ;разрешить прерывание по переполнению таймера/счетчика 0
out TIMSK0,Temp
out TIFR0,Temp

ldi Temp,0b00000100 ;тактовый сигнал = CK/256
out TCCR0B,Temp
;ldi Temp,0b00000001 ;тактовый сигнал = CK/256??????????????
;out TCCR0B,Temp

ldi Temp1,0b00000001
sei

main:	out PortB,Temp1
rjmp main
Встал на лапы
Аватара пользователя
Сообщения: 117
Зарегистрирован: Ср окт 15, 2014 12:45:46
Откуда: Анапа

Сообщение Jetetex »

То есть помимо пропущенного регистра TIFR0, я еще и нарушил порядок написания? Или в каком порядке описаны прерывания не имеет значения?
Если я чего-то не знаю, это не говорит о моем невежестве, а только о том, что раньше этот вопрос лежал вне сферы моих интересов.
Говорящий с текстолитом
Аватара пользователя
Сообщения: 1525
Зарегистрирован: Чт июн 10, 2010 20:11:19

Сообщение COKPOWEHEU »

Как показывает akl, делать не стоит. Лучше делать код читаемым и модифицируемым.

Код: Выделить всё

.include "tn13def.inc"
.def temp=r16
.org 0
     rjmp RESET
;адреса прерываний не просто так указаны в файле, стоит ими пользоваться
.org INT0addr
     rjmp RESET
.org	PCI0addr
     rjmp RESET
.org	OVF0addr
     rjmp TIM0_OVF ;поскольку обработчик прерывания не бывает короче 2 байт, делаем прыжок на обработчик, а не пихаем его в середину таблицы векторов
.org	ERDYaddr
     rjmp RESET
.org	ACIaddr
     rjmp RESET
.org	OC0Aaddr
     rjmp RESET
.org	OC0Baddr
     rjmp RESET
.org	WDTaddr
     rjmp RESET
.org	ADCCaddr
     rjmp RESET

TIM0_OVF:
;code
reti

RESET:
     ldi temp, low(RAMEND)
     out SPL,temp ;не забываем стек, лучше делать это сразу после сброса
     ldi temp, 0
     out TCCR0A, temp
;настраивать лучше сдвигами и логическими операциями, а не магическими числами
     ldi temp, (0b001 << CS00) ;частота таймера = F_CPU
     out TCCR0B, temp
     ldi temp, (1<<TOIE0)
     out TIMSK, temp ;локальное разрешение прерывания
     out TIFR, temp ;сброс флага
     sei ;глобальное разрешение прерываний
CYCLE:
     rjmp CYCLE
akl
Друг Кота
Сообщения: 4473
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Спойлер

Код: Выделить всё

.include "tn13def.inc"
.def temp=r16
.org 0
     rjmp RESET
;адреса прерываний не просто так указаны в файле, стоит ими пользоваться

;!!!!!!!!!!!!!!!правда, для этого нужно открыть tn13def.inc, выписать символику векторов

.org INT0addr
     rjmp RESET
.org   PCI0addr
     rjmp RESET
.org   OVF0addr
; в этом коде лишние команды
;     rjmp TIM0_OVF ;поскольку обработчик прерывания не бывает короче 2 байт, делаем прыжок на обработчик, а не пихаем его в середину таблицы векторов
;.org   ERDYaddr
;     rjmp RESET
;.org   ACIaddr
;     rjmp RESET
;.org   OC0Aaddr
;     rjmp RESET
;.org   OC0Baddr
;     rjmp RESET
;.org   WDTaddr
;     rjmp RESET
;.org   ADCCaddr
;     rjmp RESET

TIM0_OVF:
;code
reti

RESET:
;для tiny13 эти команды ненужные    ldi temp, low(RAMEND)
;										out SPL,temp ;не забываем стек, лучше делать это сразу после сброса
     ldi temp, 0
     out TCCR0A, temp
;настраивать лучше сдвигами и логическими операциями, а не магическими числами
     ldi temp, (0b001 << CS00) ;частота таймера = F_CPU
     out TCCR0B, temp
     ldi temp, (1<<TOIE0)
     out TIMSK0, temp ;локальное разрешение прерывания
     out TIFR0, temp ;сброс флага
;для tiny13 эти команды неправильные	out TIMSK, temp ;локальное разрешение прерывания
;									    out TIFR, temp ;сброс флага
     sei ;глобальное разрешение прерываний
CYCLE:
     rjmp CYCLE
.EXIT
В итоге, в этом простом учебном примере половина команд лишние, да ещё и с ошибками.:facepalm: "Скромнее надо быть, скромнее..."
Jetetex писал(а): Или в каком порядке описаны прерывания не имеет значения?
Таблица векторов прерываний для каждого камня фиксирована и приведена в DS.
таблица векторов tiny13.PNG
Друг Кота
Аватара пользователя
Сообщения: 15788
Зарегистрирован: Вт мар 16, 2010 22:02:27
Откуда: ДОНЕЦК

Сообщение BOB51 »

Ну дык ежли дотошно следовать концепции использования заранее объявленных имен фрагмент:
Спойлер.cseg
.org 0
;*************************** Вектора прерываний ************************
rjmp RESET
;rjmp INT0 ;INT0_vect Внешнее прерывание 0
;rjmp PCINT0 ;PCINT0_vect Прерывание 0 по изменению состояния вывода
.org 3
корректнее выглядит как
Спойлер.cseg
.org 0x0000
;*************************** Вектора прерываний ************************
irq_res:
rjmp init ; переход к началу программы инициализации системы
; блок размещения векторов активных прерываний
;irq_INT0: .org INT0addr
;rjmp INT0 ;INT0_vect Внешнее прерывание 0
;irq_PCINT0: .org PCI0addr
;rjmp PCINT0 ;PCINT0_vect Прерывание 0 по изменению состояния вывода
.org (irq_res+int_vectors_size) ; обход блока векторов прерываний
8)
Встал на лапы
Аватара пользователя
Сообщения: 117
Зарегистрирован: Ср окт 15, 2014 12:45:46
Откуда: Анапа

Сообщение Jetetex »

COKPOWEHEU писал(а):Как показывает akl, делать не стоит. Лучше делать код читаемым и модифицируемым.
Может и не стоит, но это работает. По крайней мере в протеусе... а в железе никак. :(

Собрал на макетке - отставание 13-14 сек в минуту. Возник вопрос - в регистр TCNT0 в Attiny 13 можно грузить свои значения, что бы считать не с 0, или перекраивать весь этот бардак под режим СТС?

Диод на 3й ноге (подключен "+" к МК) должен погаснуть через 1 мин, а гаснет через 74 сек, Хотя в симуляторе все как в сказке.



COKPOWEHEU, по поводу адресов из файла, которым вы посоветовали пользоваться, я вложил этот файл. Мож просветите, где они там, а то я не нашел?
Вложения
tn13def.txt
(15.11 КБ) 204 скачивания
Фьюзы.jpg
Считанные с МК
(195.98 КБ) 221 скачивание
Схема.jpg
(192.49 КБ) 381 скачивание
code.asm
(8.73 КБ) 339 скачиваний
Если я чего-то не знаю, это не говорит о моем невежестве, а только о том, что раньше этот вопрос лежал вне сферы моих интересов.
Говорящий с текстолитом
Аватара пользователя
Сообщения: 1525
Зарегистрирован: Чт июн 10, 2010 20:11:19

Сообщение COKPOWEHEU »

454 строка, неужели сложно было хотя бы провести поиск по файлу, раз уж просмотреть глазами не получается.
Режим CTC позволит настроить делитель точнее. А что у вас с тактированием? Не используете ли случайно внутренний RC-генератор, да еще без калибровки?
Ответить

Вернуться в «AVR»