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

Обсуждаем контроллеры компании Atmel.
Аватара пользователя
avreal
Опытный кот
Сообщения: 842
Зарегистрирован: Чт дек 31, 2009 19:27:45
Откуда: Бровари, Україна
Контактная информация:

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

Сообщение avreal »

После небольших «тактических» правок и без применения avr-gcc специфических вещей для правки avr-gcc-же специфических бякостей С-шный код сократился грубо на двести байт (с ~870 до ~670)

Продолжение там viewtopic.php?f=20&t=77142
Лень в виде мании величия: «ты гений, зачем стараться?». В виде комплекса: «всё равно не выйдет, зачем упираться?». Как логика: «если достаточно, зачем знать и уметь больше?». Цель одна: остановить. Не любит тепло работающих мышц и шум работающего мозга.
Аватара пользователя
specktr
Первый раз сказал Мяу!
Сообщения: 22
Зарегистрирован: Пн окт 31, 2011 00:06:45
Откуда: Ташкент

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

Сообщение specktr »

подскажите какой командой portb можно сделать выходом или можно не весь а только некоторые ноги и какими командами - мне для pic P16F84A

имею в виду не так , а еще как нибудь(одной строкой может быть)

bsf STATUS,5 ; переход в Банк 1
clrf TRISB
bcf STATUS,5 ; переход назад в Банк 0
одна бошка это хорошо....... , а две бошки это дпухполоска уже......
спящий
Потрогал лапой паяльник
Сообщения: 303
Зарегистрирован: Сб янв 08, 2011 13:48:41

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

Сообщение спящий »

Вопрос:у меня некоторые команды неработают такие как:
SBRS,sbrc тупо или перепрыгивают или неперепрыгивают,независимо от того есть 0 или 1(


Ldi r21,3;
sbrs r21,3;
rjmp lol;
ldi data,255;
в чем может быть косяк,неустановлен какойнить флаг? типа C(перенос)?
Аватара пользователя
КРАМ
Друг Кота
Сообщения: 25156
Зарегистрирован: Чт янв 10, 2008 22:01:02
Откуда: Московская область, Фрязино

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

Сообщение КРАМ »

В предложенном примере перескока не будет.
В регистр записывается число 3, а проверяется 3-ий бит. Он в данном случае равен 0 (00000011).
спящий
Потрогал лапой паяльник
Сообщения: 303
Зарегистрирован: Сб янв 08, 2011 13:48:41

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

Сообщение спящий »

мда чуть неправильно написал

Ldi r21,1;
sbrs r21,3;
rjmp lol;
ldi data,255;


Ldi r21,0;
sbrs r21,3;
rjmp lol;
ldi data,255;
неважно что написано,всеравно перескок.А когда inc r21,то иногда и срабатывает)



И еще одна проблемма: когда добавляю
.include "_ASCII_code.asm"

врубаю протеус выдает ошибку,а в AVRstudio нет,че делать?)
Аватара пользователя
КРАМ
Друг Кота
Сообщения: 25156
Зарегистрирован: Чт янв 10, 2008 22:01:02
Откуда: Московская область, Фрязино

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

Сообщение КРАМ »

specktr писал(а):подскажите какой командой portb можно сделать выходом или можно не весь а только некоторые ноги и какими командами - мне для pic P16F84A

имею в виду не так , а еще как нибудь(одной строкой может быть)

bsf STATUS,5 ; переход в Банк 1
clrf TRISB
bcf STATUS,5 ; переход назад в Банк 0

Совсем одной строкой не получится.
Команда побитной установки
bsf TRISB, <номер разряда порта>
Можно применять косвенную адресацию, тогда сама команда будет в одну строку, но будет занят адресом регистра TRISB регистр косвенной адресации FSR.
Аватара пользователя
КРАМ
Друг Кота
Сообщения: 25156
Зарегистрирован: Чт янв 10, 2008 22:01:02
Откуда: Московская область, Фрязино

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

Сообщение КРАМ »

спящий писал(а):мда чуть неправильно написал

Ldi r21,1;
sbrs r21,3;
rjmp lol;
ldi data,255;


Ldi r21,0;
sbrs r21,3;
rjmp lol;
ldi data,255;

И что Вы изменили???
теперь пишете в регистр 0 или 1, но по прежнему проверяете 3-ий разряд. У 1 и 0 он равен 0...
Третий разряд ненулевой у числа 0x08 и далее до 0x0F
Последний раз редактировалось КРАМ Вс авг 26, 2012 01:30:02, всего редактировалось 2 раза.
Аватара пользователя
ibiza11
Поставщик валерьянки для Кота
Сообщения: 1900
Зарегистрирован: Сб фев 21, 2009 13:11:40
Откуда: Москва

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

Сообщение ibiza11 »

КРАМ писал(а):Третий разряд ненулевой у числа 0x10 (десятичное выражение 16)
у числа 0х08 :beer:
Ставим плюсы: )
Аватара пользователя
КРАМ
Друг Кота
Сообщения: 25156
Зарегистрирован: Чт янв 10, 2008 22:01:02
Откуда: Московская область, Фрязино

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

Сообщение КРАМ »

ibiza11 писал(а):
КРАМ писал(а):Третий разряд ненулевой у числа 0x10 (десятичное выражение 16)
у числа 0х08 :beer:

Спасибо.
Ночь, спать пора, вот и ошибся...
Аватара пользователя
specktr
Первый раз сказал Мяу!
Сообщения: 22
Зарегистрирован: Пн окт 31, 2011 00:06:45
Откуда: Ташкент

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

Сообщение specktr »

спаибо КРАМ

Кому не трудно посмотрите че не так
Не реагирует на нажатие кнопок, должен переключать символывсемисегментном индикаторе


;tip ispolzuemogo mk;
LIST P=PIC16F84A
;fayl inc dannih mk;
#include P16F84A.INC
;konfiguraciya;
__CONFIG _XT_OSC & _WDT_OFF & _PWRTE_ON & _CP_OFF
;sopostavlenie imen chislam;
;selector;
;W EQU 0x0
;F EQU 0x1
;adresa registrov;
PC EQU 0x02
PORTB EQU 0x06
STATUS EQU 0x03
Reg_1 EQU 0x10
Reg_2 EQU 0xD
Reg_3 EQU 0xE
TRISB EQU 0x06
TRISA EQU 0x05
PORTA EQU 0x05
;sopostavlenie nomerov bitov v registre;
;Z EQU 2
;DC EQU 1
;C EQU 0
;nachalniy adres upravlyayushey programmi;
org 0 ; начало программы
;telo osnovnoy upravlyayushey programmy;
; подготовительные моменты
bsf STATUS,5 ; переход в Банк 1
movlw 0x1f
movwf TRISA
clrf TRISB
bcf STATUS,5 ; переход назад в Банк 0
clrf PORTB ; очистка порта

; отслеживание нажатия кнопок
m4 movlw .169
movwf Reg_1
movlw .69
movwf Reg_2
movlw .2
movwf Reg_3
wr2 btfss PORTA,2 ; бит-проверка ножки RA2
goto m1
btfss PORTA,3 ; бит-проверка ножки RA3
goto m2
btfss PORTA,4 ; бит-проверка ножки RA4
goto m3
decfsz Reg_1, F
goto wr2

decfsz Reg_2, F
goto wr2
decfsz Reg_3, F
goto wr2
btfsc PORTB,1
goto m5
goto m6
m5 bcf PORTB,1
goto m4
m6 bsf PORTB,1

goto m4
;===== сегмент отрисовки символов
m1 movlw 0x0
call TABLE ; переход на метку TABLE
movwf PORTB
call beep
goto m4
m2 movlw 0x1
call TABLE ; переход на метку TABLE movwf PORTB
call beep
goto m4
m3 movlw 0x2
call TABLE ; переход на метку TABLE
movwf PORTB
call beep
goto m4
;===== сегмент работы звукового излучателя
beep bsf PORTB,7
call Pause
clrf PORTB
return
;==================
;delay = 250000 machine cycles
Pause movlw .169
movwf Reg_1
movlw .69
movwf Reg_2
movlw .2
movwf Reg_3
wr decfsz Reg_1, F
goto wr
decfsz Reg_2, F
goto wr
decfsz Reg_3, F
goto wr
return
;==================
TABLE addwf PC,F ; Содержимое счетчика команд PC = PC + W
retlw 0x5d ; У
retlw 0x73 ; Р
retlw 0x7b ; А
retlw 0x4 ; _
;==================
end ; конец программы
одна бошка это хорошо....... , а две бошки это дпухполоска уже......
спящий
Потрогал лапой паяльник
Сообщения: 303
Зарегистрирован: Сб янв 08, 2011 13:48:41

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

Сообщение спящий »

здравствуйте.Мучает вопрос:протеус выдает ошибку invalid opcode
когда в код добавляю

.include "_ASCII_code.asm"

В чем косякто? или весь ASCII_code в исходник кидать?Притом AVR Studio невыдает ошибок.И как еще выводить шрифт?
Аватара пользователя
ibiza11
Поставщик валерьянки для Кота
Сообщения: 1900
Зарегистрирован: Сб фев 21, 2009 13:11:40
Откуда: Москва

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

Сообщение ibiza11 »

а разве в протеус указывается исходник? вроде как туда передается скомпилированный код (hex)... поправьте, если я не прав.
Ставим плюсы: )
Alexeyslav
Друг Кота
Сообщения: 4550
Зарегистрирован: Чт май 05, 2011 21:26:34
Откуда: Украина, Славутич
Контактная информация:

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

Сообщение Alexeyslav »

Да, помимо HEX туда можно приписать исходник, тогда он будет компилировать проект перед каждым запуском, можно будет отлаживать с именами меток с исходника и т.д.

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

Или перенести все строки в другой сегмент, где проверка эта не производится.
спящий
Потрогал лапой паяльник
Сообщения: 303
Зарегистрирован: Сб янв 08, 2011 13:48:41

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

Сообщение спящий »

Alexeyslav спасибо огромное,так я и сделал!!! примерно так:

.include "библеотека"
rjmp V:
.include "_ASCII_code.asm"
V:
заработало!!


Вот вопрос: я щас мужаюсь с RC5,немогу совместить кнопки и команды( поэтому я хочу команду полученную с RC5 записать в регистр или массив,а потом ее соответсвенно через комп прочитать,как это можно сделать?(желательно в массив!)
Аватара пользователя
Леонид Иванович
Друг Кота
Сообщения: 4779
Зарегистрирован: Сб апр 02, 2011 12:40:46
Откуда: Минск
Контактная информация:

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

Сообщение Леонид Иванович »

На asm писал когда-то вот такой декодер RC-5:

Спойлер

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

;----------

;Программа декодирования кода RC-5:
; - высокая помехозащищенность
; - низкая загрузка процессора

;Использует внешние прерывание от фотоприемника и прерывание таймера 0.
;Производится несколько выборок для каждой половинки бита
;(количество выборок задается константой SAMPLE_COUNT),
;логический уровень вычисляется по мажоритарному принципу.
;Кроме того, проверяется валидность кода Манчестер.

;----------

.include "2313def.inc"

;----------

;Константы:

.equ FCLK = 4000000  ;Hz
.equ PRE = 64
.equ RC5_SLOT = 1778 ;uS
.equ RC5_LENGTH = 14       ;количество принимаемых бит
.equ SAMPLE_COUNT = 3           ;количество выборок, должно быть
                                ;нечетным, чтобы сумма не могла быть нулем

.equ T_SAMPLE_US = RC5_SLOT / ((SAMPLE_COUNT + 1) * 2)
.equ F_TIMER = FCLK / PRE
.equ T_SAMPLE = (T_SAMPLE_US * F_TIMER /100000 + 5) / 10

;----------

;Полезные макросы:

.macro   clbr         ;clear bit in register
   cbr @0,exp2(@1)
.endm

.macro   stbr         ;set bit in register
   sbr @0,exp2(@1)
.endm

.macro   bbrc         ;branch if bit in register clear
   sbrs @0,@1
   rjmp @2
.endm

.macro   bbrs         ;branch if bit in register set
   sbrc @0,@1
   rjmp @2
.endm

;----------

.equ    IR_Signal = PD3         ;выход ик-приемника на ноге РD3 (INT1)

;Байты направления портов:

.equ    DIR_PORTB = 0xFF        ;направление для порта В.                         
.equ    DIR_PORTD = ~(1<<PD3)   ;порт D    нога PD3 - ввод, остальное вывод.
                                                   
;Байты первоначального состояния портов:

.equ    PUP_PORTB = 0x00        ;после сброса весь порт B ставим в 0
.equ    PUP_PORTD = (1<<PD3)    ;после сброса Pull-Up на PD3
                               
;----------

.DSEG       ;сегмент данных

SysVar:     .byte 1             ;сюда кладем принятый адрес системы
CommandVar: .byte 1             ;а сюда код команды
BitCounter: .byte 1             ;счетчик принятых бит
SampCnt:    .byte 1

;----------

;Глобальные регистровые переменные:

.def    RC5_CodeL  = r2         ;регистр принимаемого кода RC5 (мл. байт)
.def    RC5_CodeH  = r3         ;регистр принимаемого кода RC5 (ст. байт)
.def    SampVal    = r4

.def    temp = r16              ;temporary register temp

.def    Flags     = r20         ;флаги
.equ    PreVal    = 0           ;значение первой половины бита

;----------

.CSEG       ;сегмент кода


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

.org        0                   ;по адресу 0 вектор сброса
            rjmp       Init     ;переход на основную программу

.org        INT1addr            ;прерывание по внешнему сигналу INT1
            rjmp       EdgeRC5           

.org        OVF0addr            ;по адресу OVF0addr вектор прерывания по
            rjmp       Timer    ;переполнению таймера 0

;----------

;Программа начинает выполняться отсюда

;----------

;Здесь пишем всякую инициализацию, которая должна
;выполняться один раз при старте программы.

Init:       ldi        temp,low(RAMEND)    ;константа RAMEND определена в tn2313def.inc
            out        SPL,temp            ;инициализируем SatckPoiter
            ;ldi        temp,high(RAMEND)
            ;out        SPH,temp

;Инициализация переменных:

            ldi        temp,RC5_LENGTH
            sts        BitCounter,temp     ;инициализируем счетчик бит
       stbr       Flags,PreVal        ;первая половина старт-бита = 1
       clr        temp
       sts        SysVar,temp         ;очистка системы
       sts        CommandVar,temp     ;очистка команды

;Настройка портов:
   
            ldi        temp,PUP_PORTB           
            out        PORTB,temp          ;включаем Pull-Up в PORTB
            ldi        temp,DIR_PORTB
            out        DDRB,temp           ;настраиваем направление для PORTB
       
            ldi        temp,PUP_PORTD
            out        PORTD,temp          ;включаем Pull-Up в PORTD
            ldi        temp,DIR_PORTD
            out        DDRD,temp           ;настраиваем направление для PORTD

;Настройка оборудования:

            ldi        temp,(1<<CS00) | (1<<CS01) ;предделитель таймера ставим на СК/64
            out        TCCR0,temp          ;записываем в регистр TCCR0

            in         temp,MCUCR
       ori        temp,(1<<ISC11)     ;по спаду
            out        MCUCR,temp           
           
            in         temp,GIMSK
       ori        temp,(1<<INT1)      ;бит INT1 в GIMSK равен 1
            out        GIMSK,temp          ;разрешаем внешнее прерывание INT1
           
            sei                            ;global interrupts enable

;----------

;Основной цикл программы.

;----------

Main:       lds        temp,CommandVar     ;грузим код команды из переменной
            out        PORTB,temp          ;выводим на порт
            rjmp       Main                ;цикл

;----------

;Обработчик внешнего прерывания:

;----------

EdgeRC5:    sbi        PORTD,PD4           ;контроль на PD4 внешнего прерывания
            push       temp                ;сохранение темп
            in         temp,SREG
            push       temp                ;сохранение SREG
           
;Загружаем таймер:

            ldi        temp,256 - T_SAMPLE   ;грузим интервал до первой выборки
            out        TCNT0,temp
           
;Разрешаем прерывания таймера:

            ldi        temp,(1<<TOIE0)     ;ставим бит TOIE0 в 1
            out        TIMSK,temp          ;разрешаем прерывание по переполн ТС0
            out        TIFR,temp           ;очищаем флаг прерывания таймера

;Инициализируем переменные:

       ldi        temp,SAMPLE_COUNT * 2 ;количество выборок на периоде
       sts        SampCnt,temp
       clr        SampVal             ;очищаем суммарное значение выборок

            pop        temp
            out        SREG,temp           ;восст. SREG
            pop        temp                ;восст. temp
       cbi        PORTD,PD4
            reti                           ;выходим и разрешаем прерывания

;----------

;Обработчик по переполнению ТС0:

;----------

Timer:       sbi        PORTD,PD5           ;контроль на PD5 прерывания таймера
       push       temp                ;сохранение темп
            in         temp,SREG
            push       temp                ;сохранение SREG

;Проверка признака таймаута:   

            lds        temp,SampCnt
       tst        temp
       brne       DoSamp
            rjmp       RC5_Error           ;если SampCnt = 0, ошибка таймаута

;Делаем выборки:

DoSamp:     sbis       PIND,IR_Signal      ;проверяем выход приемника
            rjmp       Bit0
Bit1:       inc        SampVal             ;если единица, то SampVal + 1
       rjmp       CheckSmp   
Bit0:       dec        SampVal             ;если ноль, то SampVal - 1

;Проверка числа сэмплов:

CheckSmp:   dec        temp                ;уменьшаем количество сэмплов
            sts        SampCnt,temp
       breq       EvPre               ;если ноль, то закончена вторая половина

       cpi        temp,SAMPLE_COUNT
            breq       EvThis              ;закончена первая половина

            ldi        temp,256 - T_SAMPLE ;продолжаем выборки с периодом T_SAMPLE   
            out        TCNT0,temp
       rjmp       NextSam

;Оцениваем текущий бит по результатам сэмплирования первой половины:
     
EvThis:     ldi          temp,256 - T_SAMPLE * 2 ;грузим интервал между сериями сэмплов
            out        TCNT0,temp

;Определяем состояние:

            tst        SampVal              ;если SampVal > 0, то единица
       brmi       Store0               ;если SampVal < 0, то ноль

;Первая половина равна единице, бит равен нулю:   

Store1:     bbrs       Flags,PreVal,RC5_Error ;проверяем на ошибку Манчестера
       clc
            rjmp       SaveBit

;Первая половина равна нулю, бит равен единице:   

Store0:     bbrc       Flags,PreVal,RC5_Error ;проверяем на ошибку Манчестера
       sec

;Вдвигаем принятый бит:

SaveBit:    rol        RC5_CodeL
       rol        RC5_CodeH
       clr        SampVal             ;очищаем сумму выборок
       rjmp       NextSam             ;приступаем ко второй половине

;Закончено сэмплирование второй половины бита:

EvPre:      ldi          temp,256 - T_SAMPLE * 2 ;грузим интервал таймаута
            out        TCNT0,temp

;Определяем состояние:

            tst        SampVal
       brmi       Pre0

;Вторая половина равна единице, сохраняем в PreVal:   

Pre1:       stbr       Flags,PreVal

            in         temp,MCUCR
            andi       temp,~(1<<ISC10)     ;настраиваем прерывание по спаду
       out        MCUCR,temp
            rjmp       DecCnt

;Вторая половина равна нулю, сохраняем в PreVal:   

Pre0:       clbr       Flags,PreVal

            in         temp,MCUCR
            ori        temp,(1<<ISC10)     ;настраиваем прерывание по фронту
       out        MCUCR,temp

;Декремент счетчика бит:       

DecCnt:     lds        temp,BitCounter
       dec        temp                ;BitCounter - 1
       sts        BitCounter,temp
            breq       EndRec              ;0 - завершаем прием посылки
            rjmp       NextSam             ;прием следующего бита посылки               

;Прием закончен, раскладываем биты по переменным:

EndRec:     mov        temp,RC5_CodeL
       andi       temp,0x3F           ;чистим ненужные биты
            sts        CommandVar,temp     ;сохраняем код команды в переменную
       rol        RC5_CodeL
       rol        RC5_CodeH
       rol        RC5_CodeL
       rol        RC5_CodeH
       mov        temp,RC5_CodeH
       andi       temp,0x3F           ;чистим ненужные биты
            sts        SysVar,temp         ;сохраняем адрес системы в переменную
           
;Перезагрузка счетчика бит:

RC5_Error:  ldi        temp,RC5_LENGTH
            sts        BitCounter,temp     ;перезагружаем счетчик бит
       stbr       Flags,PreVal        ;первая половина старт-бита = 1

;Разрешаем прерывание по спаду:

            in         temp,MCUCR
            andi       temp,~(1<<ISC10)     ;по спаду
       out        MCUCR,temp

;Запрещаем прерывание таймера:

            ldi        temp,0 
            out        TIMSK,temp          ;запрещаем прерывание таймера

NextSam:    pop        temp                ;восст SREG
            out        SREG,temp
            pop        temp                ;восст temp
       cbi        PORTD,PD5
       reti

;----------
Аватара пользователя
ploop
Модератор
Сообщения: 13490
Зарегистрирован: Ср ноя 26, 2008 16:34:25
Откуда: Тамбовская обл.

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

Сообщение ploop »

Вот вопрос: я щас мужаюсь с RC5,немогу совместить кнопки и команды( поэтому я хочу команду полученную с RC5 записать в регистр или массив,а потом ее соответсвенно через комп прочитать,как это можно сделать?(желательно в массив!)

Я делал так: код нажатой кнопки посылал по UART на комп (в другом проекте выводил на индикатор, т.к. таковой был), выписывал кнопки, какой код какой кнопке соответствует, а потом создавал массив в EEPROM с этими значениями. Номер элемента в массиве строго соответствует коду кнопки.

Далее обычным индексным переходом попадаем на нужную подпрограмму обработки.

Так же делал вариант с обучением, когда в этом режиме предлагается последовательно по три раза (для надёжности) нажать каждую используемую кнопку, коды сохраняются в EEPROM, далее аналогично используются.
Аватара пользователя
shadivl
Открыл глаза
Сообщения: 76
Зарегистрирован: Пт май 28, 2010 13:41:16
Откуда: Мариинск, Томск

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

Сообщение shadivl »

Всем добрый день. Я только начал осваивать микроконтроллеры. Сейчас мучаюсь с Тини2313. Не могу запустить аппаратный шим на Timer/Counter0. Подскажите, что я не так инициализировал?
Спойлер

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

rjmp Reset
rjmp INT_0
rjmp INT_1
rjmp Timer1_capt1
rjmp Timer1_comp1
rjmp Timer1_OVF1
rjmp Timer0_OVF0
rjmp USART0_RXC
rjmp USART0_DRE
rjmp USART0_TXC
rjmp ANA_COMP
rjmp PCINT
rjmp TIMER1_COMPB
rjmp TIMER0_COMPA
rjmp TIMER0_COMPB
rjmp USI_START
rjmp USI_OVERFLOW
rjmp EE_READY
rjmp WDT_OVERFLOW

;Reset:
INT_0:
INT_1:
Timer1_capt1:
Timer1_comp1:
Timer1_OVF1:
Timer0_OVF0:
USART0_RXC:
USART0_DRE:
USART0_TXC:
ANA_COMP:
PCINT:
TIMER1_COMPB:
TIMER0_COMPA:
TIMER0_COMPB:
USI_START:
USI_OVERFLOW:
EE_READY:
WDT_OVERFLOW:
          reti
Reset:
ldi inf,ramend      
out spl,inf

ldi inf, 0b11111111
out DDRB, inf   

ldi inf, 0b0000011
out DDRD, inf      

ldi inf,0b1110000
out PortD, inf

ldi inf, 0b00000100
out OCR0A, inf      

ldi inf, (1<<COM0A0| 1<<WGM00| 1<<WGM01)
out TCCR0A, inf

ldi inf, (1<<WGM02| 1<<CS00)
out TCCR0B, inf

sei            

Start:
rjmp Start




На сайте есть спойлер
ploop
Аватара пользователя
Engineer_Keen
Друг Кота
Сообщения: 3868
Зарегистрирован: Пт янв 29, 2010 10:27:40
Откуда: Москва

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

Сообщение Engineer_Keen »

shadivl писал(а):Подскажите, что я не так инициализировал?


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

ldi inf, (1<<COM0A0| 1<<WGM00| 1<<WGM01)
out TCCR0A, inf

ldi inf, (1<<WGM02| 1<<CS00)
out TCCR0B, inf


При WGM00=WGM01=WGM02=1 в OCR0A будет не величина ШИМ, а верхний предел (TOP) счета (7-й режим, если смотреть таблицу в даташите). А вам видимо нужен 3-й режим (WGM02=0).
Аватара пользователя
shadivl
Открыл глаза
Сообщения: 76
Зарегистрирован: Пт май 28, 2010 13:41:16
Откуда: Мариинск, Томск

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

Сообщение shadivl »

Ага, точно :shock: Ёлки, спасибо, дня два убил уже из-за плохого знания английского.
Аватара пользователя
gauss
Держит паяльник хвостом
Сообщения: 920
Зарегистрирован: Сб янв 16, 2010 15:34:57
Откуда: Sevsk/Moscow

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

Сообщение gauss »

Перебирал старые исходники, нашел такой файл:

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

.def Temp=R16
.def Temp2=R17
.def Temp3=R18
.def Temp4=R19
.def Temp5=R20
.def ResCnt=R21
.cseg
[b].org 0[/b]
rjmp Reset
[b].org OC1Aaddr[/b]
rjmp TIM1_CompA
Reset:
   ldi Temp2,0
   ldi Temp3,0
l_res:
   dec Temp2
   brne l_res
   dec Temp3
   brne l_res
   inc ResCnt
   ldi Temp, 0b11111111
   out DDRB, Temp
   ldi Temp, 0b00010001
   out TIMSK, Temp
   ldi Temp, 0b00000011
   out TCCR1B, Temp
   ldi Temp, 0x23
   out OCR1AH, Temp
   ldi Temp, 0x28
   out OCR1AL, Temp
   ldi Temp,low(RamEnd)   ;[1]Спросить про неполную таюлицу прерываний. Разобраться со СТЕКом до конца.
    out SPL,Temp         ;
    ldi Temp,high(RamEnd)   ;СТЕК - разобраться - пошерстить даташит
    out SPH,Temp         ;Такая структура работает (в связи с особенностями Меги 8-ой), но прога не пашет. Разобраться! (Разобрался [1])
   ldi Temp2, 0b00000001
   ldi Temp, 0
   out TCNT1H, Temp
   out TCNT1L, Temp
   sei
Inf: rjmp Inf
TIM1_CompA:
   ldi Temp,0
   out TCNT1H, Temp
   out TCNT1L, Temp
SelectArray:                    ;выбор массива

         andi ResCnt,0b00000011 ;отсечка лишних разрядов сч. сбросов

         cpi ResCnt,0           ;сравнение счетчика сбросов с конст.
         brne Tst1              ;если не равно - след. проверка
         ldi ZH,High(Array0*2)  ;загрузка начального адреса массива
         ldi ZL,Low(Array0*2)
         rjmp ReadArray

Tst1:    cpi ResCnt,1
         brne Tst2
         ldi ZH,High(Array1*2)
         ldi ZL,Low(Array1*2)
         rjmp ReadArray

Tst2:    cpi ResCnt,2
         brne Tst3
         ldi ZH,High(Array2*2)
         ldi ZL,Low(Array2*2)
         rjmp ReadArray

Tst3:    ldi ZH,High(Array3*2)
         ldi ZL,Low(Array3*2)
         rjmp ReadArray


ReadArray:

         ldi Temp,0            ;прибавление относит. адреса
         add ZL,Temp2
         adc ZH,Temp

         lpm                   ;загрузка из ПЗУ

         mov Temp,R0           ;копирование в РОН
         cpi Temp,0            ;пороверка на нулевой элемент
         breq Init             ;если нулевой - в начало
         inc Temp2             ;увеличение относит адреса на 1

         rjmp Output           ;перейти на вывод в порт

Init:    ldi Temp2,0           ;загрузить нач. значение
         rjmp SelectArray

Output:  out PortB,Temp        ;вывод в порт
         reti                  ;выход из обработчика


Array0:
.db  0b10000000,0b01000000
.db  0b00100000,0b00010000
.db  0b00001000,0b00000100
.db  0b00000010,0b00000001
.db  0,0

Array1:
.db  0b00000001,0b00000010
.db  0b00000100,0b00001000
.db  0b00010000,0b00100000
.db  0b01000000,0b10000000
.db  0,0

Array2:
.db  0b10000001,0b01000010
.db  0b00100100,0b00011000
.db  0b00100100,0b01000010
.db  0,0

Array3:
.db  0b10000000,0b01000000,0b00100000,0b00010000
.db  0b00001000,0b00000100,0b00000010,0b00000001
.db  0b00000010,0b00000100,0b00001000,0b00010000
.db  0b00100000,0b01000000
.db  0,0


Больше всего интересуют выделенные фрагменты. Что означает строка .org OC1Aaddr? Почему, если ее
убрать, программа не работает, а если убрать .org 0, все нормально?
:idea:
Ответить

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