Введение в программирование на языке PIC на ассемблере

  1. Зачем учить сборку
  2. Наш первый языковой код для сборки PIC
  3. Рассекая код
  4. CBLOCK
  5. Смена банков
  6. Задержка подпрограммы
  7. Резюме

Большинству людей снятся кошмары о программировании на ассемблере PIC, а некоторые говорят, что это пустая трата времени. Я испытал это оба, поэтому я согласен. PIC можно программировать гораздо проще, используя языки высокого уровня, такие как C и Basic. Тем не менее, изучение кода на ассемблере поможет вам узнать больше о внутреннем оборудовании микроконтроллера. Это, в свою очередь, позволяет адаптировать программы в соответствии с вашими намерениями. Во встроенных системах, где производительность критична, а код зависит от оборудования, это очень важно. Этот учебник поможет вам начать изучение программирования на ассемблере PIC.

Зачем учить сборку

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

Этот код при компиляции и сборке создает 182-байтовый шестнадцатеричный файл. Теперь возьмите этот код сборки PIC, который делает то же самое, что и код выше:

Шестнадцатеричный файл для этого кода составляет 163 байта. Разница в 19 байтов в программировании микроконтроллера уже значительна!

Наш первый языковой код для сборки PIC

В качестве введения в программирование сборки PIC мы будем использовать PIC16F84A В качестве введения в программирование сборки PIC мы будем использовать   PIC16F84A   , микроконтроллер архитектуры x14 от Microchip , микроконтроллер архитектуры x14 от Microchip. Это чип, который мы представили в предыдущая статья , PIC1684A, имеющий только несколько регистров для работы, хорош для начинающих программировать микроконтроллеры.

Мы еще раз посмотрим на код сборки, размещенный выше:

Одна вещь, которую вам нужно понять, это то, что ассемблерный код обрабатывается построчно. Скорость обработки строки - это цикл команд микроконтроллера. Время цикла инструкции дается как:

Где fosc - тактовая частота генератора. Это говорит нам о том, что цикл команд зависит от значения используемого вами кварцевого генератора. Значение общего кварцевого генератора составляет 4 МГц, поэтому:

Мы вернемся к этому позже.

Сэкономьте до 50% на избранных наборах для разработки микрочипов Сэкономьте до 50% на избранных наборах для разработки микрочипов

Рассекая код

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

Есть несколько комментариев к программе сборки выше.

Первая значимая строка в программе

Это говорит ассемблеру добавить файл включения для этого конкретного микроконтроллера. Каждый микроконтроллер имеет свой собственный файл включения, который можно найти в папке C: \ Program Files (x86) \ Microchip \ MPASM Suite . Включаемый файл позволяет вызывать имя регистра, а не его адрес.

Программирование микроконтроллера в сборке фокусируется на манипулировании регистрами. Вот регистры PIC16F84A:

По ходу этого урока мы узнаем функцию каждого показанного регистра.

Следующие значимые строки в программе

Это дает вектор сброса для кода. Вектор сброса указывает, какая часть программы будет выполняться первой. Здесь эта часть с надписью START. Другой используемый вектор - INT_VECT или вектор прерывания. Этот вектор обсуждается в учебник по прерыванию ,

Откройте файл P16F84A.INC и проверьте его содержимое. Постарайтесь ничего не менять внутри, если только вы не знаете, что делаете.

CBLOCK

Линии,

используйте CBLOCK сборка оперативная. Это присваивает псевдонимы COUNT1 и COUNT2 регистрам общего назначения с адресами 0Ch и 0Dh соответственно. Если вы посмотрите на карту регистрационных файлов PIC16F84A выше, эти адреса являются частью SRAM и не имеют конкретных имен. Это означает, что мы можем использовать их так, как нам нравится. Регистры COUNT1 и COUNT2 будут использоваться для нашей подпрограммы задержки.

Смена банков

Фактическое выполнение программы начинается на линии,

Команда BSF обозначает «регистр набора битов f», где следующим оператором является регистр f и бит, связанный с этим регистром. Посмотреть остальные набор инструкций , Для приведенного выше, регистр f является регистром STATUS:

Посмотреть остальные   набор инструкций   ,  Для приведенного выше, регистр f является регистром STATUS:

Бит RP0 называется битом выбора банка регистра. PIC16F84A группирует свои регистры в два банка. Давайте снова посмотрим на карту регистров устройства:

Давайте снова посмотрим на карту регистров устройства:

Прежде чем вы сможете манипулировать конкретным регистром, вы должны сначала обратиться в банк, где он находится. Это делается путем очистки (обнулить) или установки (обнулить) бита RP0. Обратите внимание, что некоторые регистры, включая регистр STATUS, расположены в обоих банках, что означает, что вам не нужно переключать банки для доступа к ним.

Так почему же мы установили бит RP0? Это потому, что следующие строки,

использует регистр TRISB, который расположен в банке 1.

Оперативный MOVLW означает «переместить буквенное значение в регистр W». Регистр W - это регистр общего назначения, который действует как временное хранилище при перемещении значений из регистра в регистр.

Оперативный MOVWF означает «переместить содержимое W в TRISB». Это означает, что после этих двух строк регистр TRISB теперь имеет значение 0xFE .

Так почему же это значение для TRISB? Сначала мы обсудим функцию регистра TRISB.

ТРИС это сокращение от трех государств . Это описывает характеристики портов микроконтроллера, означая, что порт может быть (1) входом, (2) выходом или (3) висящим слева. PIC16F84A имеет два порта: PORTA и PORTB. Это означает, что есть также два регистра TRIS: TRISA и TRISB. Ноль в любом бите TRIS делает соответствующий бит PORT выводом . И наоборот, единица в любом бите TRIS делает соответствующий бит PORT входным .

Для нашего примера значение TRISB равно 0xFE :

Вы видите, что только бит 0 низок или очищен. Это соответствует PORTB.0 или RB0, становящимся выходным контактом, а остальные - входными контактами. Например, если вы хотите сделать выходные выводы PORTB.0 и PORTB.1, а остальные - входными, то ваш TRISB будет:

который 0xFC в шестнадцатеричном значении.

Следующая строка:

просто возвращает нас к банку 0, потому что следующие строки:

предполагает использование регистра PORTB, который находится в банке 0.

Код операции BSF означает «бит установлен f». Строка BSF PORTB, 0 устанавливает нулевой бит регистра PORTB. Помните, что регистр PORTB связан с физическими выводами RB. Поэтому, когда установлен PORTB.0, вывод RB0 высокий.

Строка BCF PORTB, 0 делает противоположность только что обсужденной команде. Это сделает вывод RB0 низким.

Задержка подпрограммы

Между командами bsf и bcf находится вызов подпрограммы задержки, который находится в конце кода:

Зачем нужна эта рутина? Как упоминалось выше, каждая строка обрабатывается со скоростью 1 микросекунда для кварцевого генератора 4 МГц. Если подпрограмма задержки отсутствует, время между высоким и низким значениями RB0 будет всего 1 микросекунда! Мигание светодиода будет слишком быстрым, чтобы увидеть его в реальном времени.

Оперативный DECFSZ , используемый в подпрограмме задержки, является сокращением от «декремент f пропустить, если ноль». Он будет уменьшать COUNT1, пока не достигнет нуля, а затем пропустит следующую строку. Если COUNT1 по-прежнему не равен нулю, программа обработает цикл, как указано в инструкции «goto loop1». Число «1» рядом с COUNT1 означает, что результат уменьшения помещен в COUNT1. Другое возможное значение здесь - «0», которое поместит результат уменьшения в регистр W.

Кстати, COUNT1 имеет начальное значение 0xFF или 255. Это значение по умолчанию для неиспользуемых регистров. Это означает, что цикл будет продолжаться в течение 255 циклов команд!

Как только COUNT1 достигнет нуля, он выйдет из цикла и перейдет к строке DECFSZ COUNT2, 1 . Это уменьшит COUNT2, но вы увидите, что следующая строка указывает программе на loop1! Это означает, что COUNT1 будет уменьшаться снова и снова, пока не достигнет нуля. После этого COUNT2 (теперь со значением 254) будет уменьшен, и цикл продолжается.

В общем, для выполнения этой процедуры потребуется 255 x 255 циклов команд. Это эквивалентно 65 мс времени ожидания.

Резюме

Наша первая программа на языке ассемблера PIC теперь может быть обобщена сверху вниз:

  • Укажите метку START в качестве первой строки в программе (строки 3 и 4)
  • Зарегистрируйте COUNT1 и COUNT2 в качестве переменных для подпрограммы задержки (от 8 до 11)
  • Перейдите к банку 1 и установите RB0 в качестве выхода, а затем вернитесь к банку 0 (строки с 16 по 19)
  • Установите RB0, подождите 65 мс (с помощью подпрограммы задержки в строках с 22 по 23)
  • и затем очистите его, затем снова подождите 65 мс (строки с 24 по 25)
  • Вернитесь к той части программы с меткой «main», эффективно зацикливая код (строка 26).
  • Запуск подпрограммы задержки (строка 28)
  • Конец программы (строка 35)

Это оно! Я предлагаю вам попробовать приведенный выше код и использовать схему, предоставленную на Эта статья , Получайте удовольствие от написания кода на ассемблере PIC!

Далее >> Вход / Выход с микроконтроллерами PIC

Так почему же мы установили бит RP0?
Так почему же это значение для TRISB?