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

Обсуждаем контроллеры компании Atmel.
Аватара пользователя
Серый_
Опытный кот
Сообщения: 708
Зарегистрирован: Пт ноя 30, 2007 14:40:44

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

Сообщение Серый_ »

А у меня случалось на похожем примере: опрос матричной клавиатуры, первая строка кнопок "активируется" нулём с порта "B0", через кнопку - нуль поступает на pinB5.

cbi portB,0 ;активировать строку кнопок (0 активный = нажато)
nop ;cbi происходит в 2 такта поэтому pin здесь заценивать рано
sbic pinB,5 ;кнопка 1 = 0? (зажата?)
rjmp b2 ;НЕТ, к следующей кнопке
;...или далее

Как результат при отсутствии "nop" не работали все первые кнопки в строках.
trofim2
Встал на лапы
Сообщения: 106
Зарегистрирован: Чт сен 10, 2015 06:59:03
Откуда: Гродно, BY

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

Сообщение trofim2 »

При вводе/выводе - да надо. Если клавиатура подключена через длинный шлейф, то может одного "nop" и не хватить.
Alexeyslav
Друг Кота
Сообщения: 4550
Зарегистрирован: Чт май 05, 2011 21:26:34
Откуда: Украина, Славутич
Контактная информация:

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

Сообщение Alexeyslav »

sbiw сама отработает за два такта и ничего не будет отложено "на потом". Там всё нормально.
А вот с кнопками у вас именно аппаратная беда - емкость входа, выставили значение и пройдёт сотни наносекунд пока оно установится, поэтому нужны какие-то задржки. Кстати когда плата загрязнится одного нопа может оказаться недостаточно - это потенциально проблемное место, работа которого зависит от "RACE CONDITION". Поэтому я делаю наоборот - сначала читаю кнопки с ПРЕДЫДУЩЕЙ линии, потом меняю линию опроса - к следующему такту(через 1-2мс) всё давно уже устаканится.
akl
Друг Кота
Сообщения: 4444
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

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

Сообщение akl »

Для "устаканивания" данных вместо NOPов обычно хватает

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

   CBI   PORTB,0
   RCALL   PAUSE_RET   ; 7 тактов
   SBIC   PINB,5
;................................
;................................
;................................
   RET
;********************************
PAUSE_RET:
   RET
;********************************

Серый_ писал(а):в данном случае "по научному" нужно ставить "nop"?

sbiw x,1 ;минуснуть 1 из пары (выполнится за 2 такта)
nop ;(поэтому пустотакт перед отправкой куда-либо)
out ocr1AH,xH ;отправить
out ocr1AL,xL
NOP не нужен. Вот режим работы модуля сравнения имеет значение, т.к. OCR1 может принять данные не только напрямую, а ещё и защёлкнуться в буфере. Перенос содержимого буфера в OCR1 произойдет при выполнении условия режима работы.
Аватара пользователя
Kavka
Мудрый кот
Сообщения: 1810
Зарегистрирован: Чт июн 10, 2010 08:55:35
Откуда: Сибирские Афины

Сдвиг 4-байтового числа на 4 бита быстрее 16 тактов

Сообщение Kavka »

Приветствую.

Коллеги, есть ли способ сдвинуть 4-байтовое число на 4 бита быстрее 16 тактов.
Для определённости пусть используются 4 старших регистра, а сдвиг вправо.
Сомнения терзают из-за наличия командочки swap...
Когда уже ничего не помогает - прочтите, наконец, инструкцию.
Лучший оптимизатор находится у вас между ушей. (Майкл Абраш, программист Quake и QuakeII)
Избыток информации ведёт к оскудению души - Леонтьев А. (сказано в 1965 г.)
Аватара пользователя
Серый_
Опытный кот
Сообщения: 708
Зарегистрирован: Пт ноя 30, 2007 14:40:44

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

Сообщение Серый_ »

Для "устаканивания" данных вместо NOPов обычно хватает... PAUSE_RET:

В общем да, было так:
Спойлерsbi portB,0 ;деактивация 1-й строки
cbi portB,1 ;и сразу активация 2-й строки

Были ложные срабатывания в 1-ом столбце (по нажатию первых кнопок любой строки). Между данными командами вклинил:
rcall bl_zvon ;блокировка звона меж строк

bl_zvon:
nop
ret ;и того 3+1+4 такта
Ложных срабатываний не выдавил при всём желании. :) Что до "блокировки звона" по кнопке 2...3mS, то все последующие нажатия блокируются на 0,5сек. по таймеру (оно же отвечает и за "турбирование" кнопок).
Аватара пользователя
pyzhman
Друг Кота
Сообщения: 7016
Зарегистрирован: Вс июл 12, 2009 19:15:29
Откуда: Ижевск
Контактная информация:

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

Сообщение pyzhman »

Перед применением swap нужно в текущем регистре на место младшего ниббла поместить младший ниббл старшего регистра. И уложиться в меньше 3-х тактов, т.е. в два или один. Хороша задачка.
Docendo discimus
Аватара пользователя
BOB51
Друг Кота
Сообщения: 15539
Зарегистрирован: Вт мар 16, 2010 22:02:27
Откуда: ДОНЕЦК

Re: Сдвиг 4-байтового числа на 4 бита быстрее 16 тактов

Сообщение BOB51 »

Приветствую.

Коллеги, есть ли способ сдвинуть 4-байтовое число на 4 бита быстрее 16 тактов.
Для определённости пусть используются 4 старших регистра, а сдвиг вправо.
Сомнения терзают из-за наличия командочки swap...

Для одиночного байта
SWAP Rd - обмен тетрадами
и
XCH Z,Rd - для обмена только с ОЗУ по указателю в Z (но не во всех подгруппах МК и для АВРстудио 4.19 неведомое)
плюсиком макрос обмена между регистрами

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

.macro XCHRR
 EOR @0,@1
 EOR @1,@0
 EOR @0,@1
.endmacro

Если было б в наборе подобие
XCHD a,@Ri
как у mcs51 -возможно было бы проще.
Иначе макрос делать придется...
:dont_know:
Аватара пользователя
Kavka
Мудрый кот
Сообщения: 1810
Зарегистрирован: Чт июн 10, 2010 08:55:35
Откуда: Сибирские Афины

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

Сообщение Kavka »

pyzhman, BOB51, как работает swap и про обмен xor-ом я знаю. Спасибо за напоминание. :tea:

Хороша задачка.
Да, есть такое. Решил, вот, поискать на просторах интернета, да людей поспрашивать прежде чем предпринять попытку изобрести велосипед.

PS: Что-то "велосипед" на swap-е меньше 17 тактов не выходит. Видать никак...
Когда уже ничего не помогает - прочтите, наконец, инструкцию.
Лучший оптимизатор находится у вас между ушей. (Майкл Абраш, программист Quake и QuakeII)
Избыток информации ведёт к оскудению души - Леонтьев А. (сказано в 1965 г.)
Аватара пользователя
Starichok51
Модератор
Сообщения: 19039
Зарегистрирован: Сб авг 14, 2010 15:05:51
Откуда: г. Озерск, Челябинская обл.

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

Сообщение Starichok51 »

4 байта сдвинуть 4 раза и без swap займет 16 циклов (а не тактов).
Мудрость приходит вместе с импотенцией...
Когда на русском форуме переходят на Вы, в реальной жизни начинают бить морду.
Аватара пользователя
BOB51
Друг Кота
Сообщения: 15539
Зарегистрирован: Вт мар 16, 2010 22:02:27
Откуда: ДОНЕЦК

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

Сообщение BOB51 »

SWAP - быстрый обмен тетрадами.
(7-4) <-> (3-0) в текущем регистре меняются местами тетрады.
Использовался для скоростных преобразований в двоично-десятичной математике (Упакованный двоично-десятичный формат, ежли склероз не изменяет). Также удобен при формировании тетрадных цифирек под БИС с аппаратным дешифратором семисегментного кода.
На сегодня такие алгоритмы весьма редко применяются, ибо почти всюду используется табличный знакогенератор, да и быстродействие МК заметно возросло.
Из современных СБИС в которых возможно встретиться с режимом тетрадного дешифратора - MAX7219 к примеру.
8)
Аватара пользователя
Kavka
Мудрый кот
Сообщения: 1810
Зарегистрирован: Чт июн 10, 2010 08:55:35
Откуда: Сибирские Афины

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

Сообщение Kavka »

4 байта сдвинуть 4 раза и без swap займет 16 циклов (а не тактов).

Именно поэтому я и спрашивал про быстрее 16 циклов/тактов. :)
Когда уже ничего не помогает - прочтите, наконец, инструкцию.
Лучший оптимизатор находится у вас между ушей. (Майкл Абраш, программист Quake и QuakeII)
Избыток информации ведёт к оскудению души - Леонтьев А. (сказано в 1965 г.)
4epemyxa
Родился
Сообщения: 6
Зарегистрирован: Сб июн 01, 2013 18:51:03

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

Сообщение 4epemyxa »

Если допускается получение результата в других регистрах и сдвиг не циклический, то можно быстрее 16-ти:

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

      ldi      r16,16    ;сдвиг на 4 
      mul      r31,r16
      movw   r4,r0
      mul      r30,r16
      mov      r3,r0
      or      r4,r1
      mul      r29,r16
      mov      r2,r0
      or      r3,r1
      mul      r28,r16
      or      r2,r1

Это вправо, результат в R5-R2
Аватара пользователя
BOB51
Друг Кота
Сообщения: 15539
Зарегистрирован: Вт мар 16, 2010 22:02:27
Откуда: ДОНЕЦК

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

Сообщение BOB51 »

Тогда уж просто умножение на 16 одним разом. Равноценно сдвигу влево на 4 бита.
Но... с занесением младших нулей, а не замена тетрад - придется добавлять несколько команд
для помещения старшей тетрады на новое место.
Хотя... как алгоритм... ЗАСЛУЖИВАЕТ ВНИМАНИЯ, особо в тех МК, где есть аппаратное умножение.
:idea:
4epemyxa
Родился
Сообщения: 6
Зарегистрирован: Сб июн 01, 2013 18:51:03

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

Сообщение 4epemyxa »

Так тут и есть умножение на 16, которое "разбирает" регистр на две тетрады с одновременным обнулением второй. Причем для сдвига влево или вправо меняется только порядок сборки тетрад в байты.
Аватара пользователя
BOB51
Друг Кота
Сообщения: 15539
Зарегистрирован: Вт мар 16, 2010 22:02:27
Откуда: ДОНЕЦК

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

Сообщение BOB51 »

То для одного байта - эквивалент SWAP, а вот при длинном составном в несколько регистров... надо отслеживать, что удобнее...
:dont_know:
4epemyxa
Родился
Сообщения: 6
Зарегистрирован: Сб июн 01, 2013 18:51:03

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

Сообщение 4epemyxa »

Да, если результат умножения байта собрать в один регистр, то получается точный эквивалент SWAP. Естественно, смысла в этом нет - что может быть быстрее одноциклового SWAP. А вот использовать умножение на 16 для выделения чистых тетрад без дополнительных ANDI очень даже быстро.
Аватара пользователя
BOB51
Друг Кота
Сообщения: 15539
Зарегистрирован: Вт мар 16, 2010 22:02:27
Откуда: ДОНЕЦК

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

Сообщение BOB51 »

У меня были подобные задачи по смещению части битового поля для ЖКИ индикаторов на основе NJU6432 и KS0035...
Там весьма помудрить порой приходится - помимо прочего зависит и от конкретной привязки сегментов к ячейкам ОЗУ (при изготовлении индикатора).
:facepalm:
Аватара пользователя
shonty
Мучитель микросхем
Сообщения: 473
Зарегистрирован: Ср янв 11, 2012 18:20:26

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

Сообщение shonty »

Здравствуйте.
Коротко о себе и моём уровне подготовки:
Я перевожу один проект под свои нужды. Основная цель - замена дисплея на цветной TFT.
Хоть я и радиолюбитель с определённым стажем, но мой род занятий и образование не связаны с электроникой и тем более программированием. Так же нет возможности "развиваться в команде" - то есть одиночество абсолютное.

Тем не менее три месяца тотального красноглазия над AVR Assembler-ом дало ощутимые плоды.

Суть проблемы такая:
При выводе текста на дисплеи бОльших размеров моноширинный шрифт смотрится (мяхко говоря) неуклюже. (кстати шрифты делаю сам, практически в ручную, на коленке, попиксельно).
Решил использовать пропорциональный шрифт и создать свою таблицу ASCII. Полный знак примерно 8x16px. Три нижних строки пустые для вывода хвостов от всяких q, y, g, ... щ, ц, ... и запятых.

Ну и естественно вопрос: как реализовать нахождение шрифта в таблице символов и получить ширину символа при выводе.

Готовых решений не прошу.
Буду признателен за любую информацию, которая укажет правильное направление.
Аватара пользователя
ARV
Ум, честь и совесть. И скромность.
Сообщения: 18544
Зарегистрирован: Чт дек 28, 2006 08:19:56
Откуда: Новочеркасск
Контактная информация:

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

Сообщение ARV »

Да в общем-то, так же, как и на Си или другом языке. Традиционно есть 2 подхода:
1. При описании каждого символа шрифта указываетс его ширина. Т.е. в массиве байтов, описывающих пикселы символа первый байт задает ширину этого символа.
2. Создается отдельная таблица, в которой хранится ширина и адрес начала символа в знакогенераторе, а сам знакогенератор в отдельной таблице

Оба подхода вынуждают использовать не традиционный массив с одинаковыми элементами, а "хитрый" массив (точнее - по сути список), в котором размер всех элементов разный, а значит адрес доступа к любому элементу уже невозможно вычислить простым умножением размера на номер элемента.
Поэтому в первом подходе приходится "сканировать" знакогенератор с самого первого символа, всякий раз вычисляя адрес начала следующего (первый байт - количество столбцов, умножаем на количество строк, прибавляем 1 и получаем адрес следующего символа) до тех пор, пока не найдется нужный. Процесс доступа долгий, зато создание знакогенератора простое.

Во втором случае наличие отдельной таблицы с размерами и адресами начала символа в знакогенераторе (т.е. по сути это таблица индексов, как в базах данных) резко ускоряет доступ к символам: все элементы этой таблицы одинаковы по размеру, поэтому вычисление реального адреса символа в шрифте осуществляется просто. Но создавать знакогенератор по этому принципу гораздо сложнее.

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

Кстати, есть специальные программы для создания пиксельных шрифтов, поддерживающих ОБА способа, и позволяющих практически мышкой нарисовать любой знакогенератор и получить на выходе исходник со всеми данными на любом языке программирования, в т.ч. и ассемблере. Рекомендую поискать. Ключевые слова LCD font editor или generator
если рассматривать человека снизу, покажется, что мозг у него глубоко в жопе
при взгляде на многих сверху ничего не меняется...

Мой уютный бложик... заходите!
Ответить

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