Avr проекты программирование на си. Вы еще не программируете микроконтроллеры? Тогда мы идем к вам! Какую среду разработки использовать для программирования выбранного микроконтроллера

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

Общая информация

Микроконтроллеры можно встретить везде. Они есть в холодильниках, стиральных машинах, телефонах, станках на производстве, умных домах и ещё во множестве различных технических устройств. Их повсеместное применение обусловлено возможностью замены более сложных и масштабных аналоговых схем устройств. Программирование МК AVR позволяет обеспечить автономное управление над электронными устройствами. Эти микроконтроллеры можно представить как простейший компьютер, что может взаимодействовать с внешней техникой. Так, им под силу открывать/закрывать транзисторы, получать данные с датчиков и выводить их на экраны. Также микроконтроллеры могут осуществлять различную обработку входной информации подобно персональному компьютеру. Если освоить программирование AVR с нуля и дойти до уровня профессионала, то откроются практически безграничные возможности для управления различными устройствами с помощью портов ввода/вывода, а также изменения их кода.

Немного о AVR

В рамках статьи будет рассмотрено семейство микроконтроллеров, выпускаемых фирмой Atmel. Они имеют довольно неплохую производительность, что позволяет использовать их во многих любительских устройствах. Широко применяются и в промышленности. Можно встретить в такой технике:

  1. Бытовой. Стиральные машины, холодильники, микроволновые печи и прочее.
  2. Мобильной. Роботы, средства связи и так далее.
  3. Вычислительной. Системы управления периферийными устройствами, материнские платы.
  4. Развлекательной. Украшения и детские игрушки.
  5. Транспорт. Системы безопасности и управления двигателем автомобиля.
  6. Промышленное оборудование. Системы управления станками.

Это, конечно же, не все сферы. Они применяются там, где выгодно использовать не набор управляющих микросхем, а один микроконтроллер. Это возможно благодаря низкому энергопотреблению и Для написания программ используются языки С и Assembler, немного изменённые под семейство микроконтроллеров. Такие изменение необходимы из-за слабых вычислительных возможностей, которые исчисляются, как правило, в десятках килобайт. AVR-программирование без изучения этих языков не представляется возможным.

Как получить свой первый микроконтроллер?

AVR-программирование требует:

  1. Наличия необходимой среды разработки.
  2. Собственно самих микроконтроллеров.

Второй пункт рассмотрим подробнее. Существует три возможности обзавестись требуемым устройством:

  1. Купить непосредственно сам микроконтроллер.
  2. Обзавестись устройством в составе конструктора (например - Arduino).
  3. Собрать микроконтроллер самостоятельно.

В первом пункте ничего сложного нет, поэтому сразу перейдём ко второму и третьему.

Обзавестись устройством в составе конструктора

В качестве примера будет выбран известный Arduino. Это по совместительству удобная платформа для быстрой и качественной разработки различных электронных устройств. Плата Arduino включает в себя определённый набор компонентов для работы (существуют различные конфигурации). В неё обязательно входит AVR-контроллер. Этот подход позволяет быстро начать разработку устройства, не требует специальных умений и навыков, имеет значительные возможности в плане подключения дополнительных плат, а также в интернете можно найти много информации на интересующие вопросы. Но не обошлось и без минусов. Покупая Arduino, человек лишает себя возможности более глубоко окунуться в AVR-программирование, лучше узнать микроконтроллер, специфику его работы. Также негатива добавляет и относительно узкая линейка моделей, из-за чего часто приходится покупать платы под конкретные задачи. Особенностью также является и то, что программирование на "СИ" здесь отличается довольно сильно от стандартной формы. Несмотря на все свои недостатки, Arduino подходит для изучения новичкам. Но злоупотреблять не стоит.

Самостоятельная сборка

Следует отметить, что микроконтроллеры AVR отличаются достаточной дружелюбностью к новичкам. Собрать их самостоятельно можно с доступных, простых и дешевых комплектующих. Если говорить о плюсах, то такой подход позволяет лучше ознакомиться с устройством, самостоятельно выбирать необходимые комплектующие, подгоняя конечный результат под выдвигаемые требования, использование стандартных языков программирования и дешевизна. Из минусов можно отметить только сложность самостоятельной сборки, когда она осуществляется впервые, и нет нужных знаний и навыков.

Как работать?

Итак, допустим, что вопрос с микроконтроллером решился. Далее будет считаться, что он был приобретён или же куплен самостоятельно. Что ещё нужно, чтобы освоить AVR-программирование? Для этой цели нужна среда разработки (в качестве базиса подойдёт и обычный блокнот, но рекомендую остановиться на Notepad++). Хотя существуют и другие программы для программирования AVR, приведённое обеспечение сможет справиться со всеми требованиями. Также необходим программатор. Его можно приобрести в ближайшем магазине, заказать по интернету или собрать самостоятельно. Не помешает и печатная плата. Она не обязательна, но её использование позволяет сэкономить свои нервы и время. Также покупается/создаётся самостоятельно. И последнее - это источник питания. Для AVR необходимо обеспечить поступление напряжения на 5В.

Где и как учиться?

Создавать шедевры с нуля не получиться. Здесь необходимы знания, опыт и практика. Но где их взять? Существует несколько путей. Первоначально можно самостоятельно выискивать нужную информацию в мировой сети. Можно записать на курсы программирования (дистанционные или очные) для получения базовых навыков работы. Каждый подход имеет свои преимущества. Так, дистанционные курсы программирования будут более дешевыми, а может и бесплатными. Но если что-то не будет получаться, то при очных занятиях опытный разработчик сможет быстрее найти причину проблемы. Также не лишним будет ознакомиться с литературой, что находится в свободном доступе. Конечно, на одних книгах выехать не получится, но получить базовые знания про устройство, программирование на "СИ", "Ассемблере" и о других рабочих моментах можно.

Порты ввода/вывода

Это чрезвычайно важная тема. Без понимания того, как работают порты ввода/вывода, не представляется возможным внутрисхемное программирование AVR вообще. Ведь взаимодействие микроконтроллера с внешними устройствами осуществляется именно при их посредничестве. На первый взгляд новичка может показаться, что порт - это довольно запутанный механизм. Чтобы избежать такого впечатления, не будем детально рассматривать схему его работы, а только получим общее представление об этом. Рассмотрим программную реализацию. В качестве примера устройства был выбран микроконтроллер AtMega8 - один из самых популярных из всего семейства AVR. Порт ввода/вывода представляет собой три регистра, которые отвечают за его работу. На физическом уровне они реализовываются как ножки. Каждой из них соответствует определённый бит в управляющем реестре. Каждая ножка может работать как для ввода информации, так и для её вывода. Например, на неё можно повесить функцию зажигания светодиода или обработку нажатия кнопки. Кстати, три регистра, о которых говорилось, это: PORTx, PINx и DDRx. Каждый из них является восьмиразрядным (не забываем, что мы рассматриваем AtMega8). То есть один бит занимается определённой ножкой.

Работа регистров

Наиболее весомым в плане ориентации является управляющий DDRx. Он также является восьмиразрядным. Значения для него могут быть записаны 0 или 1. Как меняется работа контроллера при использовании нулей и единицы? Если в определённом бите выставить 0, то соответствующая ему ножка будет переключена в режим входа. И с неё можно будет считывать данные, что идут с внешних устройств. Если установить 1, то микроконтроллер сможет управлять чем-то (например, дать приказ транзистору пропустить напряжение и зажечь светодиод). Вторым по важности является PORTx. Он занимается управлением состояния ножки. Давайте рассмотрим пример. Допустим, у нас есть порт вывода. Если мы устанавливаем логическую единицу в PORTx, то посылается сигнал от микроконтроллера управляющему устройству начать работу. Например, зажечь светодиод. При установлении нуля он будет гаситься. То есть работать с управляющим регистром DDRx постоянно, нет надобности. И напоследок давайте о PINx. Этот регистр отвечает за отображение состояния ножки контроллера, когда она настроена на состояние ввода. Следует отметить, что PINx может работать исключительно в режиме чтения. Записать в него ничего не получится. Но вот прочитать текущее состояние ножки - это без проблем.

Работа с аналогами

AVR не являются единственными микроконтроллерами. Этот рынок поделен между несколькими крупными производителями, а также между многочисленными китайскими имитирующими устройствами и самоделками. Во многом они подобны. К примеру, программирование PIC/AVR сильно не отличается. И если есть понимание чего-то одного, то понять всё остальное будет легко. Но начинать путь рекомендуем всё же с AVR благодаря его грамотной структуре, дружелюбности к разработчику и наличию большого количества вспомогательных материалов, из-за чего процесс разработки можно значительно ускорить.

Техника безопасности

Когда будет вестись программирование микроконтроллеров AVR на "СИ" или на "Ассемблере", то необходимо работать очень осторожно. Дело в том, что выставив определённую комбинацию регистров и изменив внутренние настройки, можно спокойно заблокировать микроконтроллер. Особенно это касается фьюзов. Если нет уверенности в правильности своих действий, то лучше отказаться от их использования. Это же относится и к программаторам. Если покупать заводскую аппаратуру, то она будет прошивать микроконтроллеры без проблем. При сборке своими руками может возникнуть печальная ситуация, при которой программатор заблокирует устройство. Это может произойти как из-за ошибки в программном коде, так и через неполадки в нём самом. Кстати, об ещё одном (на этот раз позитивном) моменте, который ранее вскользь упоминался, но так и не был раскрыт полностью. Сейчас практически все современные микроконтроллеры обладают функцией внутрисхемного программирования. Что это значит? Допустим, что устройство было запаяно на плате. И чтобы сменить его прошивку, сейчас не нужно его выпаивать, ведь такое вмешательство может повредить сам микроконтроллер. Достаточно подключиться к соответствующим выводам и перепрограммировать его при их посредстве.

Какую модель выбрать?

В рамках статьи была рассмотрена AtMega8. Это довольно посредственный за своими характеристиками микроконтроллер, которого, тем не менее, хватает для большинства поделок. Если есть желание создать что-то масштабное, то можно брать уже своеобразных монстров вроде Atmega128. Но они рассчитаны на более опытных разработчиков. Поэтому, если нет достаточного количества опыта, то лучше начинать с небольших и простых устройств. К тому же они и значительно дешевле. Согласитесь, одно дело случайно заблокировать микроконтроллер за сто рублей, а совсем иное - за полтысячи. Лучше набить себе руку и разобраться в различных аспектах функционирования, чтобы в последующем не терять значительные суммы. Первоначально можно начать с AtMega8, а потом уже ориентироваться по своим потребностям.

Заключение

Вот и была рассмотрена тема программирования AVR в самых общих чертах. Конечно, ещё о многом можно рассказывать. Так, к примеру, не было рассмотрено маркирование микроконтроллеров. А оно может о многом сказать. Так, в основном микроконтроллеры работают на напряжении в 5В. Тогда как наличие, к примеру, буквы L может сказать о том, что для работы устройства достаточно только 2,7 В. Как видите, порой знания о маркировке могут сыграть очень важную роль в плане корректной и долговечной работы устройств. Время функционирования микроконтроллеров - это тоже интересная тема. Каждое устройство рассчитано на определённый период. Так, некоторые могут отработать тысячу часов. Другие же имеют гарантийный запас в 10 000!

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

Более подробную информацию можно посмотреть на английском языке в CodeVision User Manual, а также рекомендую сайт http://somecode.ru с видеоуроками по Си для микроконтроллеров и книгу «Как программировать на С» автор Дейтель, это единственная годная книга, с которой я сам начинал.

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

Сама прошивка имеет расширение.hex и представляет собой набор инструкций, в виде единиц и нулей, который понятен микроконтроллеру. Откуда взять прошивку? Ее можно скачать с сайтов по электронике, либо написать самому. Написать ее можно в специальных программах, которые называются средой разработки. Из наиболее известных мне AVR Studio, IAR, CodeVision, WinAVR… Нельзя сказать, что какая из этих сред лучше или хуже, каждому свое. Можно сказать, что различаются эти программы в основном удобством, языком программирования и ценой. В пределах данного сайта, рассматривается только CodeVision.

Со средой разобрались, теперь разберемся с процессом написания прошивки. В CodeVision изначально нужно создать проект. Его можно создать при помощи мастера кода или пустой. В любом случае, нужно выбрать тип используемого микроконтроллера и указать его частоту. При использовании мастера, вам будет предложено выбрать начальные настройки и сгенерировать исходный код с настройками. Далее появится окно, в котором можно редактировать этот код. Хотя вы можете написать свой исходный код, в блокноте и потом прицепить его к проекту в настройках.

Файл с исходным кодом является набором команд на языке программирования, задача CodeVision`а перевести эти команды в двоичный код, ваша задача написать этот исходный код. CodeVision понимает язык Си, файлы с исходным кодом имеют расширение «.c». Но у CodeVision есть некоторые конструкции, которые не используются в Си, за это его многие программисты не любят, а используемый язык называют Си подобным. Однако, это не мешает писать серьезные проекты. Множество примеров, генератор кода, большой набор библиотек дает большой плюс CodeVision`у. Единственный минус, то что он платный, хотя есть бесплатные версии с ограничением кода.

Исходный код должен содержать заголовок с используемым типом микроконтроллера и функцию main. Например, используется ATtiny13

#include void main(void ) { } ;

#include void main(void) { };

До функции main можно подключить необходимые библиотеки, объявить глобальные переменные, константы, настройки. Библиотека это отдельный файл, обычно с расширением «.h», в котором уже есть заранее написанный код. В одних проектах этот код может быть нам нужен, а в других не нужен. Например, в одном проекте мы используем жк дислей, а в другом не используем. Подключить библиотеку для работы с жк дисплеем «alcd.h», можно так:

#include #include void main(void ) { } ;

#include #include void main(void) { };

Переменные это участки памяти, в которые можно поместить некие значения. Например, сложили два числа, результат нужно, где то сохранить, чтобы использовать в дальнейшем. Сначала необходимо объявить переменную, т.е. выделить под нее память, например:
int i=0;
т.е. мы объявили переменную i и поместили в нее значение 0, int – тип переменной, или проще говоря, означает размер выделенной памяти. Каждый тип переменных может хранить только определенный диапазон значений. Например, int можно записать числа от -32768 до 32767. Если нужно использовать числа с дробной частью значит, переменную нужно объявлять как float, для символов используют тип char.

bit, _Bit 0 или 1 char от -128 до 127 unsigned char от 0 до 255 int от -32768 до 32767 unsigned int от 0 до 65535 long int от -2147483648 до 2147483647 unsigned long int от 0 до 4294967295 float от ±1.175e-38 до ±3.402e38

Внутри функции main уже выполняется основная программа. После выполнения функции программа остановится, поэтому делают бесконечный цикл while, который крутит одну и ту же программу постоянно.

void main(void ) { while (1 ) { } ; } ;

void main(void) { while (1) { }; };

В любой части исходного кода можно написать комментарий, на работу программы он влиять никак не будет, но будет помогать сделать пометки к написанному коду. Закомментировать строку можно двумя слешами //после этого компилятор будет игнорировать всю строку, либо несколько строк /**/, например:

/*Основные математические операции:*/ int i= 0 ; //объявляем переменную i и присваиваем ей значение 0 //Сложение: i = 2 + 2 ; //Вычитание: i = 2 - 2 ; //после выполнения данного выражения переменная i будет равна 0 //Умножение: i = 2 * 2 ; //после выполнения данного выражения переменная i будет равна 4 //Деление: i = 2 / 2 ; //после выполнения данного выражения переменная i будет равна 1

/*Основные математические операции:*/ int i=0; //объявляем переменную i и присваиваем ей значение 0 //Сложение: i = 2+2; //после выполнения данного выражения переменная i будет равна 4 //Вычитание: i = 2-2; //после выполнения данного выражения переменная i будет равна 0 //Умножение: i = 2*2; //после выполнения данного выражения переменная i будет равна 4 //Деление: i = 2/2; //после выполнения данного выражения переменная i будет равна 1

Зачастую в программе требуется выполнить переход от одного куска кода к другому, в зависимости от условий, для этого существует условные операции if(), например:

if(i>3) //если i больше 3, то присвоить i значение 0 { i=0; } /*если i меньше 3, то перейти к коду следующему после тела условия, т.е. после скобок {}*/

Также if можно использовать совместно с else – иначе

if(i<3) //если i меньше 3, то присвоить i значение 0 { i=0; } else { i=5; //иначе, т.е. если i больше 3, присвоить значение 5 }

Также имеется операция сравнения «==» ее нельзя путать с «=» присвоить. Обратная операция не равно «!=», допустим

if(i==3)//если i равно 3, присвоить i значение 0 { i=0; } if(i!=5) //если i не равно 5, присвоить i значение 0 { i=0; }

Перейдем к более сложным вещам – функциям. Допустим, у вас есть некий кусок кода, который повторяется несколько раз. Причем этот код довольно большой в размерах. Писать его каждый раз неудобно. Например, в программе, каким то образом изменяется переменная i, при нажатии на кнопку 0 и 3 порта D выполняется одинаковый код, который в зависимости от величины переменной i включает ножки порта B.

void main(void ) { if (PIND.0== 0 ) //проверяем нажата ли кнопка на PD0 { if (i== 0 ) //если i==0 включить PB0 { PORTB.0= 1 ; } if (i== 5 ) // если i==5 включить PB1 { PORTB.1= 1 ; } } … if (PIND.3== 0 ) // выполняем тоже самое, при проверке кнопки PD3 { if (i== 0 ) { PORTB.0= 1 ; } if (i== 5 ) { PORTB.1= 1 ; } } }

void main(void) { if(PIND.0==0) //проверяем нажата ли кнопка на PD0 { if(i==0) //если i==0 включить PB0 { PORTB.0=1; } if(i==5) // если i==5 включить PB1 { PORTB.1=1; } } … if(PIND.3==0)// выполняем тоже самое, при проверке кнопки PD3 { if(i==0) { PORTB.0=1; } if(i==5) { PORTB.1=1; } } }

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

void i_check() { if (i== 0 ) { PORTB.0= 1 ; } if (i== 5 ) { PORTB.1= 1 ; } }

void i_check() { if(i==0) { PORTB.0=1; } if(i==5) { PORTB.1=1; } }

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

void i_check() { if(i==0) { PORTB.0=1; } if(i==5) { PORTB.1=1; } } void main(void) { if(PIND.0==0) //проверяем нажата ли кнопка на PD0 { i_check(); } … if(PIND.3==0) { i_check(); } }

Когда код будет доходить до строчки i_check(); то он перепрыгнет внутрь функции и выполнит код внутри. Согласитесь, код компактнее и нагляднее, т.е. функции помогают заменить одинаковый код, всего на одну строчку. Обратите внимание, что функция объявляется вне основного кода, т.е. до функции main. Можно сказать, да зачем мне это надо, но изучая уроки вам часто будут попадаться функции, например очистка жк экрана lcd_clear() — функция не принимает никаких параметров и ничего не возвращает, однако очищает экран. Иногда эта функция используется чуть ли не через строчку, так что экономия кода очевидна.

Намного интереснее выглядит применение функции, когда она принимает значения, например, есть переменная c и есть функция sum, которая принимает два значения типа int. Когда основная программа будет выполнять эту функцию, то в скобках уже указаны аргументы, таким образом «a» станет равной двум, а «b» станет равной 1. Функция выполнится и «с» станет равна 3.

int c= 0 ; void sum(int a, int b) { c= a+ b; } void main(void ) { sum(2 , 1 ) ; }

int c=0; void sum(int a, int b) { c=a+b; } void main(void) { sum(2,1); }

Одна из часто встречаемых подобных функций это перевод курсора у жк дисплея lcd_gotoxy(0,0); которая, кстати, тоже принимает аргументы – координаты по х и у.

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

int c= 0 ; int sum(int a, int b) { return a+ b; } void main(void ) { с= sum(2 , 1 ) ; }

int c=0; int sum(int a, int b) { return a+b; } void main(void) { с=sum(2,1); }

Результат будет такой же как и в прошлый раз c=3, однако обратите внимание, мы переменной «с» присваиваем значение функции, которая уже не void, а возвращает сумму двух чисел типа int. Таким образом мы не привязываемся к конкретной переменной «с», что добавляет гибкости в использовании функций. Простой пример подобной функции — чтение данных АЦП, функция возвращает измеренное значение result=read_adc();. На этом закончим с функциями.

Теперь перейдем к массивам. Массив это связанные переменные. Например, у вас есть таблица синуса с несколькими точками, не будете же вы создавать переменные int sinus1=0; int sinus2=1; и т.д. для этого используют массив. Например, создать массив из трех элементов можно так:
int sinus={0,1,5};
в квадратных скобках указывается общее количество элементов массива. Присвоить переменной «с» значение третьего элемента можно таким образом:
с=sinus;
Обратите внимание, нумерация элементов массива начинается с нуля, т.е. «с» станет равна пяти. У данного массива элемента sinus не существует!!!
Отдельному элементу можно присвоить значение так:
sinus=10;

Возможно, вы уже успели заметить, что в CodeVision нет строковых переменных. Т.е. нельзя создать переменную string hello=”привет”; для этого придется создавать массив из отдельных символов.

lcd_putchar(hello); lcd_putchar(hello); lcd_putchar(hello);

и т.д.
Получается довольно громоздко, тут на помощь приходят циклы.
Например цикл while

while(PINB.0!=0) { }

Пока кнопка не нажата ничего не делать – гонять пустой цикл.

Еще один вариант цикл for

int i; for (i= 0 ; i< 6 ; i++ ) { lcd_putchar(hello[ i] ) ; }

int i; for(i=0;i<6;i++) { lcd_putchar(hello[i]); }

Смысл точно такой же, как и у while только добавлено начальное условие i=0 и условие, выполняемое каждый цикл i++. Код внутри цикла максимально упрощен.

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

Не стоит сразу стараться использовать циклы, массивы и функции в своих прошивках. Ваша главная задача заставить прошивку работать, поэтому делайте так как вам проще не обращайте внимание на размер кода. Придет время когда захочется не просто писать рабочий код, а написать его красиво и компактно. Тогда можно будет углубиться в дебри языка Си. Желающим овладеть всем и сразу еще раз рекомендую книгу «Как программировать на Си», там много примеров и задач. Ставьте Visual Studio, создавайте консольное приложение win32 и там вволю тренируйтесь.


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

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

4. Какую литературу изучать?

Попробуем ответить на эти вопросы.

1. Какой микроконтроллер выбрать для работы?

Большой популярностью у радиолюбителей пользуются 8-битные микроконтроллеры PIC фирмы Microchip Technology и AVR фирмы Atmel, 16-битные MSP430 фирмы TI, а также 32-битные микроконтроллеры, архитектуры ARM .

В промышленности, несколько иначе, первое место с большим отрывом занимает Renesas Electronics на втором Freescale , на третьем Samsung , затем идут Microchip и TI , далее все остальные.
Популярность определяется ценой и доступностью, немалую роль играют наличие технической информации и стоимость программного сопровождения.

Мы будем изучать 8-битные микроконтроллеры AVR, семейства ATMEGA 8 и 16 серии . Выбор определился, опять же доступностью, наличием множества любительских разработок, огромным количеством учебного материала. Наличием разнообразных встроенных компонентов и функциональностью этого семейства.

2. Какую среду разработки использовать для программирования выбранного микроконтроллера?

Для AVR созданы разные интегрированные среды разработки (IDE, Integrated development environment).
IDE – это система программных средств, используемая программистами для разработки программного обеспечения (ПО), в состав которой входят:
текстовый редактор,
компилятор и/или интерпретатор,
средства автоматизации сборки,
отладчик.

Наиболее распространенные из них AVRStudio, ATmelStudio, WINAVR, CodeVision, IAR Embedded Workbench .
Для того, чтобы писать программы, мы воспользуемся бесплатной IDE ATmelStudio версии 6 и выше.
Скачать Atmel Studio можно с официального сайта после регистрации (регистрация абсолютно бесплатная и ни к чему не обязывает!)

ATmelStudio позволяет создавать проекты, и писать программы как в ассемблере, так и на СИ.

Изначально всегда стоит вопрос: какой язык программирования выбрать, чтобы писать эффективные программы?

Отвечу просто: нужно уметь писать как минимум на двух языках ассемблере и СИ. Ассемблер просто необходим, когда нужно написать быстрые и компактные подпрограммы и макросы, различные драйверы устройств. Но, когда требуется создать объемный проект, построенный на сложных алгоритмах, без знания СИ может быть потрачено очень много времени, особенно в процессе отладки, а если возникнет желание перенести на другую платформу, например PIC18, или STM, может стать неразрешимой проблемой.
Кроме этого, сейчас появились аппаратные вычислительные платформы Arduino , работа с которыми требует знаний языка СИ++.
Поэтому будем писать программы как в ассемблере, так и на СИ.

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

3. Как прошивать контроллер, и какие дополнительные приборы и акссесуары нужны для удобной работы с ними?

Используем датагорский . Кроме этого, нужно будет приобрести макетные платы, блок питания с выходным напряжением 5 Вольт. Можно в качестве БП с малыми пульсациями использовать , применив стабилитрон на 5 Вольт.
Возможно, со временем мы с Игорем предложим проект для сборки отладочной платы.

4. Какую литературу изучать?

А вот, например:
Практическое программирование AVR на ассемблере. Ревич, 2011
1000 и одна микроконтроллерная схема Вып. 1-2. Рюмик, 2010-2011
10 практических устройств на МК AVR Книга 1-2. Кравченко, 2008-2009
Самоучитель разработчика устройств на МК AVR. Белов, 2008
МК AVR семейств Tiny и Atmega. Ефстифеев, 2008
CodeVisionAVR. Пособие для начинающих. Лебедев, 2008
Микропроцессорное управление устройствами, тиристоры, реле. Белов, 2008
Аналоговые интерфейсы МК. Стюард, Болл, 2007
Создаем устройства на МК AVR. Белов, 2007
МК AVR в радиолюбительской практике. Полный разбор ATTINY2313. Белов, 2007
Сетевой и межсетевой обмен данными с МК. Иди, 2007
МК AVR. практикум для начинающих. Хартов, 2007
Применение AVR Схемы, алгоритмы, программы. Баранов, 2006
Микроконтроллеры AVR. Вводный курс. Мортон, 2006
Измерение, управление и регулирование с помощью AVR. Трамперт, 2006
Программирование на языке С для AVR и PIC МК. Шпак, 2006
Конструирование устройств на МК. Белов, 2005
МK - это же просто, тома 1-3. Фрунзе, 2002-2003
Язык программирования Си, 2-е издание. Керниган, Ритчи, 2009
Программирование микроконтроллеров ATMEL на языке С. Прокопенко, 2012

5. Где в интернете можно задавать вопросы и получать конкретные ответы?

Задавать вопросы вы можете на нашем или любом другом форуме, где так или иначе затронуты темы по микроконтроллерам. Главное на форумах правильно формулировать вопросы, чтобы четко получать ответы. Абстрактные вопросы не приветствуются, и скорее всего вместо ответа вы получите жесткую критику, или ваш вопрос останется без внимания!

Теперь рассмотрим поближе нашего фаворита, микроконтроллер ATMEGA 8

8-разрядный высокопроизводительный AVR микроконтроллер с малым потреблением
Прогрессивная RISC архитектура
130 высокопроизводительных команд, большинство команд выполняется за один тактовый цикл
32 8-разрядных рабочих регистра общего назначения
Полностью статическая работа
Приближающаяся к 16 MIPS (при тактовой частоте 16 МГц) производительность
Встроенный 2-цикловый перемножитель

Энергонезависимая память программ и данных
8 Кбайт внутрисистемно программируемой Flash памяти (In-System Self-Programmable Flash)
Обеспечивает 1000 циклов стирания/записи
Дополнительный сектор загрузочных кодов с независимыми битами блокировки
Обеспечен режим одновременного чтения/записи (Read-While-Write)
512 байт EEPROM
Обеспечивает 100000 циклов стирания/записи
1 Кбайт встроенной SRAM
Программируемая блокировка, обеспечивающая защиту программных средств пользователя

Встроенная периферия
Два 8-разрядных таймера/счетчика с отдельным предварительным делителем, один с режимом сравнения
Один 16-разрядный таймер/счетчик с отдельным предварительным делителем и режимами захвата и сравнения
Счетчик реального времени с отдельным генератором
Три канала PWM
8-канальный аналого-цифровой преобразователь (в корпусах TQFP и MLF)
6 каналов с 10-разрядной точностью
6-канальный аналого-цифровой преобразователь (в корпусе PDIP)
4 канала с 10-разрядной точностью
2 канала с 8-разрядной точностью
Байт-ориентированный 2-проводный последовательный интерфейс
Программируемый последовательный USART
Последовательный интерфейс SPI (ведущий/ведомый)
Программируемый сторожевой таймер с отдельным встроенным генератором
Встроенный аналоговый компаратор

Специальные микроконтроллерные функции
Сброс по подаче питания и программируемый детектор кратковременного снижения напряжения питания
Встроенный калиброванный RC-генератор
Внутренние и внешние источники прерываний
Пять режимов пониженного потребления: Idle, Power-save, Power-down, Standby и снижения шумов ADC

Выводы I/O и корпуса
23 программируемые линии ввода/вывода
28-выводной корпус PDIP, 32-выводной корпус TQFP и 32-выводной корпус MLF

Рабочие напряжения
2,7 - 5,5 В (ATmega8L)
4,5 - 5,5 В (ATmega8)

Рабочая частота
0 - 8 МГц (ATmega8L)
0 - 16 МГц (ATmega8)

отличия ATMEGA16 от 8
16 Кбайт внутрисистемно программируемой Flash памяти (In-System Self-Programmable Flash)

Интерфейс JTAG (совместимый с IEEE 1149.1)
Возможность сканирования периферии, соответствующая стандарту JTAG
Расширенная поддержка встроенной отладки
Программирование через JTAG интерфейс: Flash, EEPROM памяти, перемычек и битов блокировки

Четыре канала PWM / ШИМ

8-канальный 10-разрядный аналого-цифровой преобразователь
8 несимметричных каналов
7 дифференциальных каналов (только в корпусе TQFP)
2 дифференциальных канала с программируемым усилением в 1, 10 или 200 крат (только в корпусе TQFP)

Шесть режимов пониженного потребления: Idle, Power-save, Power-down, Standby, Extended Standby и снижения шумов ADC

32 программируемые линии ввода/вывода

40-выводной корпус PDIP и 44-выводной корпус TQFP

AtmelStudio

Если Вы только начинаете, то нужно скачать и установить программу AtmelStudio с официальной страницы atmel.com
После установки программы AtmelStudio можно приступить к созданию проекта.
Проект – это ваша программа, которую вы будете писать, отлаживать и прошивать, после компиляции, в память микроконтроллера.

Чтобы создать проект, надо открыть программу, появиться такая заставка,

и откроется страница создания проекта

Чтобы создать новый проект, нужно кликнуть по «New Project…»
В этом случае откроется новое окно, где можно выбрать язык программирования, название проекта, его месторасположение, название пакета с файлами проекта и возможность создания каталога для дальнейшего использования в других перекрестных проектах. Чтобы создать проект, где мы будем программировать в ассемблере, нужно выбрать - Assembler , после этого поменяем название проекта, его расположение, и выбираем ОК.

Появится следующее окно

Выбираем “megaAVR, 8-bit” и находим нужный нам микроконтроллер, мы выбрали ATmega8. В правой части заставки появляется список устройств, работающих с этим микроконтроллером, один из которых мы можем подключить. Выбираем ОК.

Появляется страница редактора текста, которая позволяет редактировать и отлаживать программу. Пока страница чистая, указано время и дата создания и название файла проекта, имя пользователя. Есть дополнительные окно устройств ввода-вывода, окно отчетов компиляции программы. Теперь мы


можем программировать в ассемблере.
Аналогично создается проект для программирования на языке СИ.

Для программирования AVR-микроконтроллеров существует немало средств разработки, однако, наиболее популярным, несомненно, следует признать пакет AVR Studio . Есть ряд причин такой популярности – это бесплатный пакет, разработанный фирмой ATMEL , он объединяет в себе текстовый редактор, ассемблер и симулятор. Пакет AVR Studio также используется совместно с аппаратными средствами отладки. В предлагаемой статье на примерах рассматриваются приемы работы с пакетом, что поможет начинающим программистам быстрее понять взаимодействие отдельных компонентов AVR Studio.

В следующей части статьи будет рассказано об отладке в среде AVR Studio программ, написанных на языке Си.

Пакет AVR Studio имеет солидную историю развития, что отражается в количестве существующих версий. В конце 2003 г. выпущена версия 4.08, которая имеет ряд полезных дополнений, а в начале 2004 г. вышло обновление (Service Pack 1), добавляющее поддержку AVR-контроллеров третьего поколения семейства ATmega48. Производство микросхем этого семейства намечено на вторую половину 2004 г.

Дистрибутив пакета и Service Pack можно загрузить с сайта www.atmel.com или получить компакт-диск с этим дистрибутивом у российского дистрибьютора фирмы ATMEL.

Работу пакета AVR Studio удобно рассматривать на какой-либо конкретной программе. В качестве илюстрации мы рассмотрим создание проекта для простейшей программы, которая будет по очереди зажигать два светодиода. Для определенности возьмем микросхему Atmega128 и подключим два светодиода в выводам 31 и 32 (это биты 6 и 7 порта D микросхемы ATmega128). AVR-контроллеры имеют мощные выходные каскады, типовой ток каждого вывода составляет 20 мА, максимальный ток вывода – 40 мА, причем это относится как к втекающему, так и к вытекающему току. В нашем примере светодиоды подключены анодами к выводам контроллера, а катоды через гасящие резисторы соединены с землей. Это означает, что светодиод зажигается подачей «1» на соответствующий вывод порта. Принципиальная схема приведена на рисунке. На схеме также показаны две кнопки, которые будут использованы в одной из программ.

Здесь уместно сделать небольшое отступление о выборе типа микросхемы для простейшего примера. Действительно, с первого взгляда может показаться странным, зачем нужен такой мощный кристалл в 64-выводном корпусе там, где хватит и 8-выводной микросхемы ATtiny12 ? Однако, в таком подходе есть логика. Известно, что в основе практически любого AVR-контроллера лежит одинаковое ядро. По большому счету, контроллеры различаются объемом памяти, количеством портов ввода/вывода и набором периферийных модулей. Особенности каждого конкретного контроллера – привязка логических имен регистров ввода/вывода к физическим адресам, адреса векторов прерываний, определения битов портов и т.д. описаны в файлах с расширением.inc, которые входят в состав пакета AVR Studio. Следовательно, используя конкретный тип кристалла, можно отлаживать программу как собственно для него, так и для любого младшего кристалла. Далее, если использовать в качестве отладочного самый старший кристалл, на сегодня это ATmega128, можно отлаживать программу практически для любого AVR-контроллера, надо просто не использовать аппаратные ресурсы, которые отсутствуют у целевого микроконтроллера. Таким образом, например, можно отлаживать на ATmega128 программу, которая будет выполняться на ATtiny13 . При этом исходный код останется практически тем же, изменится лишь имя подключаемого файла с 128def.inc на tn13def.inc. У такого подхода также есть свои преимущества. Например, «лишние» порты ввода/вывода можно использовать для подключения ЖК-индикатора , на который можно выводить отладочную информацию. Или, воспользоваться внутрисхемным эмулятором, который подключается к JTAG-порту микросхемы ATmega128 (контроллер ATtiny13 такой порт не имеет). Таким образом, можно использовать единственную отладочную плату, на которой установлен «старший» AVR-контроллер, для отладки любых вновь разрабатываемых систем, естественно, базирующихся также на AVR-микроконтроллерах. Одна из таких плат называется AS-megaM. Именно она использовалась для создания примеров программ, приводимых в статье. Это универсальный одноплатный контроллер на базе микросхемы ATmega128, который содержит внешнее ОЗУ, два порта RS-232 , порт для подключения ЖК-индикатора, внутрисхемного программатора и эмулятора AT JTAG ICE . На плате также есть место для распайки микросхемы FLASH-ПЗУ серии АТ45 в корпусах TSOP32/40/48 и двухканального ЦАП серии AD5302/ AD5312/ AD5322 . Теперь, после объяснения причин использования AVR-монстра для зажигания пары сватодиодов, можно идти дальше.

При программировании в среде AVR Studio надо выполнить стандартную последовательность действий:

  • компиляция
  • Создание проекта начинается с выбора строки меню Project\New Project. В открывшемся окне “Create new Project” надо указать имя проекта, (в нашем случае – sample1) и имя файла инициализации. После нажатия кнопки “Next” открывается окно “Select debug platform and device”, где выбирается отладочная платформа (симулятор или эмулятор) и тип микроконтроллера.

    Можно выбрать один из предлагаемых внутрисхемных эмуляторов, заметим, что у каждого эмулятора свой список поддерживаемых микросхем. Для рассматриваемого примера мы выбираем в качестве отладочной платформы AVR Simulator и микросхему ATmega128. После нажатия кнопки “Finish” нашему взору предстают собственно рабочие окна пакета AVR Studio, пока пустые. Следует в правое окно поместить исходный текст программы. Это можно сделать двумя способами, либо набрать весь текст непосредственно в окне редактора, либо загрузить уже существующий файл. Ниже приведен полный текст простейшей программы с комментариями.

    ; Пример «Управление светодиодами» ; написан для отладочной платы AS-MegaM ; Частота задающего генератора 7,37 МГц; светодиоды подключены к выводам PD6 и PD7 и через резисторы - на общий провод. ; подключение файла описания ввода-вывода микросхемы ATmega128 .include "m128def.inc" ; начало программы begin: ; первая операция - инициализация стека; если этого не сделать, то вызов подпрограммы или прерывания; не вернет управление обратно; указатель на конец стека устанавливается на последний адрес внутреннего ОЗУ - RAMEND ldi r16,low(RAMEND) out spl,r16 ldi r16,high(RAMEND) out sph,r16 ; для того, чтобы управлять светодиодами, подключенными к выводам PD6 и PD7, ; необходимо объявить эти выводы выходными. ; для этого нужно записать "1" в соответствующие биты регистра DDRD (DataDiRection) ldi r16,(1<<6) | (1<<7) out DDRD,r16 ; основной цикл программы loop: ldi r16,(1<<6) ; светится один светодиод out PORTD,r16 rcall delay ; задержка ldi r16,(1<<7) ; светится второй светодиод out PORTD,r16 rcall delay ; задержка rjmp loop ; повторение цикла; процедура задержки; примерно полсекунды при частоте 7,37 МГц; три пустых вложенных цикла соответственно delay: ldi r16,30 ; 30 delay1: ldi r17,200 ; 200 delay2: ldi r18,200 ; и еще 200 итераций delay3: dec r18 brne delay3 dec r17 brne delay2 dec r16 brne delay1 ret ; возврат в главную программу

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

    Компиляция проекта производится командой \Project\Build или нажатием кнопки F7. Процесс компиляции отображается в окне “Output”. Это окно можно «вытащить» командой \View\Output.

    В принципе, мы уже получили выходной файл в формате.hex, который уже можно загружать в микросхему и наблюдать перемигивание светодиодов. Однако, цель статьи – показать полный цикл работы в среде AVR Studio, поэтому мы переходим к стадии отладки. Это делается командой \Debug\Start Debugging.

    Теперь устанавливаем в окне “Simulator Options” частоту кварца 7,3728 МГц для точного измерения времени выполнения программы.

    Остальные опции следует оставить без изменения. Теперь можно выполнять программу в пошаговом режиме при помощи мыши или кнопки F11.

    Пакет AVR Studio содержит мощные средства для просмотра и редактирования состояния внутренних регистров и портов ввода/вывода отлаживаемого микроконтроллера, а также время, выполнения программы. Доступ к ним осуществляется через окно “I/O”.

    На самом деле, количество информации, доступное через окна просмотра пакета AVR Studio настолько велико, что для получения максимального комфорта нужно использовать компьютер в двухмониторной конфигурации.

    Для отладки нашего примера, чтобы получить доступ к битам порта D, надо раскрыть строку I/O ATMEGA128 и затем строку PORTD. Теперь видны все три регистра этого порта, PORTD, DDRD и PIND. Чтобы увидеть поля Value, Bits и Address, придется расширить правую границу окна, потеснив при этом окно с исходным текстом программы.

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

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

    ; Пример «Управление светодиодами от кнопок» ; написан для отладочной платы AS-MegaM ; светодиоды подключены к выводам PD6 и PD7 и через резисторы - на общий провод. ; кнопки - на PE4 и PE5 .include "m128def.inc" ; основная программа begin: ; инициализация стека ldi r16,low(RAMEND) out spl,r16 ldi r16,high(RAMEND) out sph,r16 ; инициализация светодиодов ldi r16,(1<<6) | (1<<7) out DDRD,r16 ; инициализация выводов, к которым подключены кнопки (на вход) ; внутренние подтягивающие резисторы подключены; для этого в PORTE нужно установить соответствующие биты в единицы ldi r16,(1<<4) | (1<<5) out PORTE,r16 ; а в DDRE - в нули ldi r16,0 out DDRE,r16 ; бесконечный цикл forever: in r16,PINE ; теперь в r16 находится текущее "состояние" кнопок com r16 ; кнопка "нажимается" нулем, поэтому инвертируем регистр lsl r16 ; переносим биты 4,5 в позиции 6,7 lsl r16 ; и обновляем "показания" светодиодов andi r16,(1<<6) | (1<<7) out PORTD,r16 rjmp forever ; цикл выполняется бесконечно

    Таким образом, на примере простейших программ показаны некоторые возможности пакета AVR Studio. Надо понимать, что это лишь первое знакомство, позволяющее быстрее освоиться с базовыми командами пакета. Между тем, возможности рассматриваемого пакета намного шире. Например, здесь можно отлаживать программы написанные на языках высокого уровня. В частности, Си-компилятор фирмы ImageCraft пользуется отладчиком AVR Studio «как родным». Для этого при компиляции исходного кода надо установить опцию генерации выходного файла в формате, совместимом с AVR Studio. При этом появляется возможность производить отладку в исходных кодах.

    Еще одна из многих характеристик пакета AVR Studio - возможность подключения внешних программ. Например, для обеспечения вызова оболочки внутрисхемного программатора AS2 нужно выполнить несколько простых операций.

    В меню Tools главного окна AVR Studio надо выбрать пункт Customize;

    В окне Customize выбрать пункт Tools;

    Двойным нажатием кнопки мыши или нажав Insert на клавиатуре, добавить новую команду в список и назвать ее "Программатор AS2";

    Указать путь к исполняемому файлу программатора, введя его непосредственно в поле для ввода "Command", или нажав на кнопку "…" справа от этого поля;

    Теперь в меню Tools появился пункт "Программатор AS2".

    Средства пакета AVR Studio 4.08 позволяют подключать вспомогательные программы – plugins. Первый plugin для AVR Studio – это программа графического редактора, упрощающая процесс инициализации ЖК-индикатора, которым может непосредственно управлять AVR-контроллер ATmega169. Максимальный логический размер ЖК-индикатора составляет 100 сегментов, каждому элементу индикатора ставится в соответствие бит в специальном регистре контроллера. Чтобы упростить рутинную процедуру привязки определенных битов к каждому сегменту, можно использовать вышеупомянутую программу.

    Во время посещения «родины AVR» - норвежского офиса фирмы ATMEL, один из авторов статьи беседовал с Ларсом Квенилдом, руководителем группы программистов, которая создала и поддерживает пакет AVR Studio. Этот человек, классический программист, с бородой, в свитере и обутый в сандали на носки, рассказал о перспективах развития пакета. В следующую версию (4.09) - будет включен интерфейс для нового внутрисхемного эмулятора – JTAGICE mkII (он называется также AT JTAGICE2), который во второй половине года придет на смену AT JTAGICE. У этого эмулятора есть два существенных отличия. С одной стороны, добавлена поддержка нового однопроводного отладочного интерфейса для младших AVR-контроллеров, debugWIRE. Этот интерфейс интересен тем, что он не занимает для своей работы дополнительные выводы микроконтроллера, так как использует для обмена вывод Reset микроконтроллера! С другой стороны (можно понимать это выражение буквально), у эмулятора AT JTAGICE2 появится, наконец, интерфейс USB для связи с компьютером.

    Литература

    1. Материалы технического семинара AVR Technical Training. Atmel. Norway. December 2003.
    2. Николай Королев, Дмитрий Королев AVR-микроконтроллеры второго поколения: средcтва разработчика. // Компоненты и технологии, 2003 № 7
    3. AVR-микроконтроллеры второго поколения: новые аппаратные возможности // Компоненты и технологии. 2003. № 4 .
    4. Николай Королев, Дмитрий Королев. AVR-микроконтроллеры: большое в малом. //Схемотехника», 2001, №5
    5. Николай Королев, Дмитрий Королев. AVR-микроконтроллеры: программные средства // Компоненты и технологии, 2000. № 4 .
    6. Николай Королев. AVR: аппаратные средства разработчика // Компоненты и технологии, 1999 № 1
    7. Николай Королев. RISC- микроконтроллеры фирмы ATMEL //Chip-News 1998, №2
    8. Николай Королев, Дмитрий Королев AVR: новые 8-разрядные RISC-микроконтроллеры фирмы ATMEL //Микропроцессор Ревю, 1998, №1

    Министерство образования и науки Российской Федерации

    Государственное образовательное учреждение

    высшего профессионального образования

    «САНКТ-ПЕТЕРБУРГСКИЙ ГОСУДАРСТВЕННЫЙ

    МОРСКОЙ ТЕХНИЧЕСКИЙ УНИВЕРСИТЕТ»

    Е. В. Коротицкий, Ю. Е. Коротицкая

    Основы языка си для микроконтроллеров avr

    Учебное пособие

    Санкт-Петербург

    1. Основы языка Си для микроконтроллеров avr

    Универсальный язык С был разработан как инструмент для написания операционной среды UNIX.

    Язык С поддерживает процедурно-ориентированную парадигму программирования, т.е. парадигма – взаимосвязанный набор процедур.

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

      1. Препроцессор языка Cи его команды

    Препроцессор (макропроцессор) - это составная часть языка Си, которая обрабатывает исходный текст программы до того, как он пройдет через компилятор. Препроцессор читает строки текста и выполняет действия, определяемые командными строками. Если первым символом в строке, отличным от пробела, является символ #, то такая строка рассматривается препроцессором как командная. Командные строки называются директивами препроцессора.

    Препроцессор компилятора CodeVisionAVRимеет несколько директив. В Табл. 1 даётся их краткое описание.

    Табл. 1 –Директивы препроцессора компилятора CodeVisionAVR

    Директива

    Назначение

    Используется для включения в программу

    другого файла

    Используется для замены одних лексических единиц языка Си на другие, а также для генерации макросов

    Используется для отмены действия директивы #define

    Используются для условной компиляции

    Используется для изменения встроенных макросов _LINE_и_FILE_

    Позволяет остановить компиляцию и отобразить сообщение об ошибках

    Используются для включения в исходную программу ассемблерного кода

    Разрешает специальные директивы компилятора

    ВСЕ директивы препроцессора начинаются со знака #. После директив препроцессора точка с запятой НЕ СТАВИТСЯ.

        1. Директива #include

    Пример:

    Директива # include

    #include "имя_файла" и #include <имя_файла>

    Имя_файла состоит из имени файла.

    Директива # include широко используется для включения в программу так называемых заголовочных файлов (файлы с расширением. h ), содержащих определения периферийных устройств и векторов прерываний используемого микроконтроллера, прототипы библиотечных функций, прототипы функций, определённых пользователем, и т. д.

    #include "имя_файла.h"

        1. Директивы #define, #undef

    Директива # define служит для замены часто использующихся одних лексических единиц языка Си (констант, ключевых слов, операторов или выражений) на другие, так называемыеидентификаторы. Идентификаторы, заменяющие текстовые или числовые константы, называютименованными константами. Идентификаторы, заменяющие фрагменты программ, называютмакроопределениями, причём макроопределения могут иметь аргументы.

    Директива # define имеет две синтаксические формы:

    #define идентификатор текст

    #define идентификатор (список параметров) текст

    Перед компиляцией программы препроцессор в соответствии с директивой # define заменит все идентификаторы, встречающиеся в программе, на соответствующий им текст.

    Пример:

    #define А 15 #define В (А+20) // Эти директивы заменят в тексте программы

    каждый идентификатор А на число 15, а каждый идентификатор В на выражение (15+20) вместе с окружающими его скобками.

    Пример:

    #define X(a,b,c) ((а)*(b)-(с)) // Препроцессор в соответствии с этой директивой заменит фрагмент Y=X(k+m,k-m,n); на фрагмент