телевизори. Конзоли. Проектори и аксесоари. Технологии. Цифрова телевизия

Програмиране на микроконтролери на C. Как да започнете да програмирате AVR? Препоръки. Къде се използват микроконтролери?

Има различни езици за програмиране на AVR микроконтролери, но може би най-подходящите са асемблер и C, тъй като тези езици най-добре изпълняват всички необходими възможности за управление на хардуера на микроконтролера.

Асемблерният език е език за програмиране от ниско ниво, който използва директния набор от инструкции на микроконтролера. Създаването на програма на този език изисква добро познаване на командната система на програмируемия чип и достатъчно време за разработване на програмата. Асемблерният език е по-нисък от C по скорост и лекота на разработване на програми, но има забележими предимства в размера на крайния изпълним код и съответно скоростта на неговото изпълнение.

C ви позволява да създавате програми с много по-голям комфорт, предоставяйки на разработчика всички предимства на езика високо ниво.
Още веднъж трябва да се отбележи, че архитектурата и командната система на AVR са създадени с прякото участие на разработчиците на компилатора на езика C и отчитат характеристиките на този език. Компилирането на C изходен код е бързо и създава компактен, ефективен код.

Основните предимства на C пред асемблера: висока скоростразработване на програма; универсалност, която не изисква задълбочено проучване на архитектурата на микроконтролера; по-добра документируемост и четимост на алгоритъма; наличие на библиотеки с функции; поддръжка за изчисления с плаваща запетая.

Езикът C хармонично съчетава възможности за програмиране ниско нивосъс свойствата на език от високо ниво. Способността за програмиране на ниско ниво ви позволява лесно да работите директно с хардуера, а свойствата на езика на високо ниво ви позволяват да създавате лесно четим и модифицируем програмен код. В допълнение, почти всички C компилатори имат способността да използват вмъквания на асемблер за писане на програмни секции, които са критични по отношение на времето за изпълнение и потреблението на ресурси.

С една дума, C е най-удобният език както за начинаещи, запознаващи се с AVR микроконтролери, така и за сериозни разработчици.

Компилаторите се използват за преобразуване на изходния код на програма във файл на фърмуера на микроконтролера.

Atmel предоставя мощен асемблиращ компилатор, който е включен в средата за разработка Atmel Studio, работеща под Windows. Заедно с компилатора, средата за разработка съдържа дебъгер и емулатор.
Atmel Studio е напълно безплатно и достъпно на уебсайта на Atmel.

В момента има доста C компилатори за AVR. За най-мощен от тях се смята компилаторът на IAR Systems от Стокхолм. Неговите служители участваха в разработването на командната система AVR в средата на 90-те години. IAR C Compiler има обширни възможности за оптимизиране на кода и идва като част от интегрираната среда за разработка на IAR Embedded Workbench (EWB), която включва също асемблерен компилатор, линкер, мениджър на проекти и библиотеки и дебъгер. Цена пълна версияпакет е 2820 евро. От уебсайта на компанията можете да изтеглите безплатна пробна версия за 30 дни или неограничена версия с ограничение за размера на кода от 4 KB.

Американската компания Image Craft от Пало Алто, Калифорния произвежда компилатор на език C, който придоби доста широка популярност. JumpStart C за AVR има приемлива оптимизация на кода и не много висока цена (от $50 до $499 в зависимост от версията). Демо версията на JumpStart C за AVR е напълно функционална за 45 дни.

Румънският компилатор Code Vision AVR C придоби не по-малка популярност, цената на пълната версия на този компилатор е сравнително ниска и възлиза на 150 евро. Компилаторът идва с интегрирана среда за разработка, която в допълнение към стандартните функции включва доста интересна функция - CodeWizardAVR Automatic Program Generator. Наличието на сериен терминал в средата за разработка ви позволява да отстранявате грешки в програми, като използвате серийния порт на микроконтролера. Можете да изтеглите безплатна пробна версия от разработчиците с ограничение за размера на кода от 4 KB и деактивирано запазване на генерирания изходен код в C.

Компанията MikroElektronika, разположена в сръбския град Белград, произвежда цяло семейство компилатори за AVR микроконтролери. Компилатор за езика C, наречен mikroC PRO за AVR, струва $249. Има и mikroBasic и mikroPascal на същата цена. На уебсайта на разработчиците има демо версии с ограничение за размер на кода от 4096 байта. Предимството на това семейство компилатори е единна платформа и единна идеология, която може да осигури лесен преход не само между езици, но и между микроконтролери (има версии на компилатор за PIC, STM32, 8051...).

Интегрираната среда за разработка стана наистина емблематична. Той включва мощни компилатори за C и асемблер, програмиста AVRDUDE, програма за отстраняване на грешки, симулатор и много други поддържащи програми и помощни програми. WinAVR се интегрира безпроблемно със средата за разработка AVR Studio на Atmel. Асемблерът е идентичен по входен код с асемблера на AVR Studio. Компилаторите C и асемблер имат способността да създават файлове за отстраняване на грешки във формат COFF, което ви позволява да използвате не само вградени инструменти, но и да използвате мощния симулатор на AVR Studio. Друго важно предимство е, че WinAVR се разпространява безплатно без ограничения (производителите поддържат GNU General Public License).

Като обобщение си струва да се каже, че WinAVR е идеален избор за тези, които започват да овладяват AVR микроконтролери. Именно тази среда за разработка се счита за основна в този курс.

Реших да напиша кратка уводна статия за тези, които за първи път се занимават с програмиране на микроконтролери и никога преди не са били запознати с езика C. Няма да навлизаме в подробности, ще говорим за всичко малко, за да добием обща представа за работата с CodeVisionAVR.

| Повече ▼ подробна информацияможете да погледнете английски езикв Ръководството за потребителя на CodeVision, а също така препоръчайте сайта http://somecode.ru с видео уроци по C за микроконтролери и книгата „Как да програмираме на C“ от Deitel, това е единствената добра книга, с която самият аз започнах.

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

Самият фърмуер има разширение .hex и представлява набор от инструкции, под формата на единици и нули, които са разбираеми за микроконтролера. Откъде мога да взема фърмуера? Можете да го изтеглите от уебсайтове за електроника или да го напишете сами. Можете да го напишете специални програми, които се наричат ​​среда за разработка. Най-известните ми са AVR Studio, IAR, CodeVision, WinAVR... Невъзможно е да се каже коя от тези среди е по-добра или по-лоша, всеки сам. Можем да кажем, че тези програми се различават основно по удобство, програмен език и цена. В рамките на този сайт се взема предвид само CodeVision.

Подредихме средата, сега нека да разгледаме процеса на писане на фърмуер. В CodeVision първо трябва да създадете проект. Може да бъде създаден с помощта на съветника за код или празен. Във всеки случай трябва да изберете вида на използвания микроконтролер и да посочите неговата честота. Когато използвате съветника, ще бъдете помолени да изберете първоначални настройкии генериране на изходен код с настройки. След това ще се появи прозорец, в който можете да редактирате този код. Въпреки че можете да напишете своя изходен код в Notepad и след това да го прикачите към проекта в настройките.

Файлът с изходен код е набор от команди на език за програмиране, задачата на CodeVision е да преведе тези команди в двоичен код, вашата задача е да напишете този изходен код. CodeVision разбира езика C, файловете с изходен код имат разширение „.c“. Но CodeVision има някои конструкции, които не се използват в C, поради което много програмисти не го харесват и използваният език се нарича C-подобен. Това обаче не пречи да пишете сериозни проекти. Много примери, генератор на код и голям набор от библиотеки дават голямо предимство на CodeVision. Единственият минус е, че е платен, въпреки че има безплатни версиис ограничение на кода.

Изходният код трябва да съдържа заглавка с вида на използвания микроконтролер и основната функция. Например се използва ATtiny13

#включи void main(void) ( ) ;

#включи void main(void) ();

Преди основната функция можете да свържете необходимите библиотеки, да декларирате глобални променливи, константи и настройки. Библиотеката е отделен файл, обикновено с разширение ".h", което вече съдържа предварително написан код. В някои проекти може да се нуждаем от този код, но в други не се нуждаем от него. Например в един проект използваме LCD дисплеи, а в друг не. Можете да свържете библиотеката за работа с LCD дисплей “alcd.h” така:

#включи #включи void main(void) ( ) ;

#включи #включи 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.1 7 5e- 38 до ±3.402e38

Вътре в основната функция основната програма вече работи. След като изпълни функцията, програмата ще спре, така че те правят безкраен цикъл 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 - иначе

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

Има и оператор за сравнение “==”, който не трябва да се бърка с “=” assign. Обратната операция не е равна на "!=", да речем

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 е натиснат( ако (i== 0 ) //ако i==0 разреши PB0( PORTB.0= 1 ; ) ако (i== 5 ) // ако i==5 разреши PB1( PORTB.1= 1 ; ) ) … ако (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) //if i==0 включете PB0 ( PORTB.0=1; ) if( i==5) // if 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(); след това ще скочи във функцията и ще изпълни кода вътре. Съгласете се, кодът е по-компактен и по-ясен, т.е. функциите помагат да се замени един и същ код, само един ред. Моля, обърнете внимание, че функцията е декларирана извън основния код, т.е. преди основната функция. Можете да кажете защо имам нужда от това, но докато изучавате уроците, често ще срещнете функции, например изчистване на LCD екрана lcd_clear() - функцията не приема никакви параметри и не връща нищо, но изчиства екран. Понякога тази функция се използва почти на всеки друг ред, така че икономиите на код са очевидни.

Изглежда много по-интересно да се използва функция, когато тя приема стойности, например има променлива c и има функция сума, която приема две стойности от тип int. Когато основната програма изпълни тази функция, аргументите вече ще бъдат в скоби, така че "a" ще стане равно на две, а "b" ще стане равно на 1. Функцията ще бъде изпълнена и "c" ще стане равно на 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 дисплея lcd_gotoxy(0,0); който, между другото, също приема аргументи - x и y координати.

Друг вариант за използване на функция, когато тя върне стойност, сега тя вече няма да бъде празна, нека подобрим предишния пример на функция за събиране на две числа:

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, но имайте предвид, че присвояваме на променливата „c“ стойността на функция, която вече не е void, но връща сумата от две числа от тип int. По този начин не сме обвързани с конкретна променлива „c“, което добавя гъвкавост при използването на функциите. Прост пример за такава функция е четене на ADC данни, функцията връща измерената стойност result=read_adc();. Да приключим с функциите.

Сега да преминем към масивите. Масивът е свързани променливи. Например, имате синусова таблица с няколко точки, няма да създавате променливи int sinus1=0; int sinus2=1; и т.н. За това се използва масив. Например, можете да създадете масив от три елемента като този:
int sinus=(0,1,5);
Общият брой на елементите на масива е посочен в квадратни скоби. Можете да присвоите стойността на третия елемент на променливата "c" по следния начин:
с=синус;
Моля, обърнете внимание, че номерирането на елементите на масива започва от нула, т.е. "c" ще стане равно на пет. Този масив няма синусов елемент!!!
Можете да присвоите стойност на отделен елемент по следния начин:
синус=10;

Може би вече сте забелязали, че CodeVision няма низови променливи. Тези. не можете да създадете променлив низ hello=”hello”; За да направите това, ще трябва да създадете масив от отделни знаци.

lcd_putchar(здравей); lcd_putchar(здравей); lcd_putchar(здравей);

и т.н.
Оказва се доста тромаво, тук на помощ идват циклите.
Например цикъл while

докато (PINB.0!=0) ( )

Докато не бъде натиснат бутона, не правете нищо - стартирайте празен цикъл.

Друг вариант е for цикълът

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

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

Значението е абсолютно същото като това на while, добавят се само първоначалното условие i=0 и условието, което се изпълнява всеки цикъл i++. Кодът вътре в цикъла е максимално опростен.

След като напишете вашата програма, изходният код се компилира и ако няма грешки, ще получите желания фърмуер в папката на проекта. Сега можете да флашнете микроконтролера и да се насладите на работата на устройството.

Не трябва веднага да се опитвате да използвате цикли, масиви и функции във вашия фърмуер. Вашата основна задача е да накарате фърмуера да работи, така че го направете така, както ви е по-лесно и не обръщайте внимание на размера на кода. Ще дойде време, когато искате не само да напишете работещ код, но и да го напишете красиво и компактно. Тогава ще бъде възможно да се потопите в дебрите на езика C. За тези, които искат да овладеят всичко, отново препоръчвам книгата „Как да програмираме на C“, има много примери и задачи. Инсталирайте Visual Studio, създайте конзолно приложение win32 и практикувайте там до насита.

Задача: Нека разработим програма за управление на един светодиод. При натискане на бутона светодиодът светва и при отпускане изгасва.

Първо, нека разработим схематична диаграма на устройството. I/O портовете се използват за свързване на външни устройства към микроконтролера. Всеки от портовете може да работи както като вход, така и като изход. Нека свържем светодиода към един от портовете и бутона към другия. За този експеримент ще използваме контролер Atmega8. Този чип съдържа 3 I/O порта, има 2 осем-битови и 1 шестнадесет-битов таймер/брояч. Също така на борда има 3-канален ШИМ, 6-канален 10-битов аналогово-цифров преобразувател и много други. Според мен микроконтролерът е чудесен за изучаване на основите на програмирането.

За свързване на светодиода ще използваме линия PB0, а за четене на информация от бутона ще използваме линия PD0. Диаграмата е показана на фиг.1.

Урок No2. LED превключване

Урок No3. LED мига

Урок №4. Ходови светлини

Урок № 5. Ходови светлини с помощта на таймер

Урок No6. Ходови светлини. Използване на прекъсвания на таймера

Урок №7. Оператори за управление на битове

Урок № 8. Внедряване на ШИМ

Цифровите устройства, например, микроконтролерът може да работи само с две нива на сигнала, т.е. нула и едно или изключено и включено. По този начин можете лесно да го използвате за наблюдение на състоянието на натоварване, като например включване или изключване на светодиод. Можете също така да го използвате за управление на всяко електрическо устройство с помощта на подходящите драйвери (транзистор, триак, реле и др.) Но понякога се нуждаете от нещо повече от просто „включване“ и „изключване“ на устройството. Така че, ако искате да контролирате яркостта на LED (или лампа) или скоростта на DC мотор, цифровите сигнали просто не могат да го направят. Тази ситуация е много често срещана в цифровите технологии и се нарича Широчинно-импулсна модулация (PWM).

Програмиране на AVR микроконтролери за начинаещи Програмиране на най-популярните микроконтролери - ATMega8, ATTiny13.

Какво е микроконтролер? Микроконтролерът е по същество микрокомпютър с процесор, RAM и ROM, входно/изходни портове; много микроконтролери имат аналогово-цифров преобразувател.

На първо място, за да пишете програми за Atmel AVR, трябва да инсталирате програмата Atmel Studio, можете да я изтеглите от официалния уебсайт на Atmel на уебсайта на Microchip (Microchip купи Atmel), програмата е напълно безплатна:

http://www.microchip.com/mplab/avr-support/atmel-studio-7

За да тествате написана програма, а не постоянно да я сглобявате върху реални физически компоненти за тестване, ще ви трябва и програма, която емулира работата на хардуера и тази програма е Proteus, но вече не е безплатна.

(Забележка - понякога резултатът от работа върху реален хардуер може да се различава от резултата от хардуерна емулация, така че при изработването на финалната, крайна версия на написаната програма, тестването върху реален хардуер е задължително).

Atmel Studio е инсталиран.

(ако възникне грешка по време на стартиране или инсталиране " Не мога да намеря един или повече компоненти. Моля, преинсталирайте приложението"(Един или повече компоненти не бяха намерени. Моля, преинсталирайте приложението.) - трябва да премахнете програмата, да преименувате папката C:\ProgramData\Package Cache(не трябва да го изтривате, защото ако нещо се случи, можете да го преименувате отново на оригиналното му име, ако някои приложения спрат да работят след това) , тогава програмата ще се инсталира и стартира нормално).

Стартиран.

В горния ляв ъгъл изберете:

Файл => Нов => Проект

Избирам GCC C изпълним проект(на изображението под номера 1 ), В долната част, в Името ( 2 ) посочете името на нашия проект в полето Местоположение ( 3 ) можем да изберем местоположението на проекта или да оставим пътя по подразбиране, щракнете върху OK.

След това избираме модела на нашия микроконтролер от списъка, в нашия случай това е ATMEGA8 (можете да изберете Attiny13 или друг микроконтролер, от който се нуждаете и имате):

В прозореца ще се появи среда за разработка на кодиране, където вече ще има стандартен C код и няколко коментирани реда, указващи авторството и датата:

Под номер 1 има прозорец за писане на код, под номер 2 файлове с изходния код, библиотеки и всички файлове, свързани с изходния код, във файла main.c има текста на нашия код.

Какво прави този код?

линия #include свързва стандартна библиотека от входни и изходни портове на AVR микроконтролери,

може да се намери по пътя (ако не сте променили пътя по време на инсталацията) " C:\Program Files\Atmel\Studio\7.0\toolchain\avr8\avr8-gnu-toolchain\avr\include\avr"

Основната функция е стандартната функция за въвеждане на C, с която стартира програмата.

В основната функция има цикъл, който продължава вечно.

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

За да компилирате писмения код, трябва да изберете Build => Build “Your_Project_Name” в горната част.

Ако кодът е без грешки, програмата ще се компилира и най-отдолу ще бъде изписано Build succeeded.

В резултат на това компилираният фърмуер ще бъде във формат .HEX и ще се намира на адрес (отново, ако не сте променили стандартното местоположение):

C:\Users\UserName\Documents\Atmel Studio\7.0\ProjectName\ProjectName\Debug\ProjectName.hex

Забележка: Ако изберете опцията Release build, фърмуерът ще се намира в съответната папка, т.е. не в папката Debug, а в папката Releасе.

Кодът, който не прави нищо, не е много интересен, нека напишем програма, която мига светодиод 2 пъти в секунда:

#define F_CPU 1000000UL // 1 MHz Тук задаваме честотата на микроконтролера #включи //входно/изходна библиотека #включи // библиотека за забавяне int main(void) // стартиране на основната програма(DDRD = 0xff; // задайте всички портове D (вижте разводката на MK) като изходидокато (1) ( // безкраен цикъл PORTD = 0xff; // задайте "1" (включено) на всички линии на порт D _закъснение_ms(250) ; // изчакайте 250 милисекунди PORTD = 0x00; // задайте "0" (изключено) на всички линии на порт D _закъснение_ms(250) ; // изчакайте 250 милисекунди } //затваряща скоба на безкраен цикъл } //скоба на основната функция за въвеждане

#define F_CPU 1000000UL // 1 MHz Тук задаваме честотата на микроконтролера #include //входно/изходна библиотека #include // забавяне на библиотеката int main(void) // стартиране на основната програма ( DDRD = 0xff; // задаване на всички D портове (вижте μ pinout) като щифтове, докато (1) ( // безкраен цикъл PORTD = 0xff; // задаване "1 "(включено) на всички линии на порт D _delay_ms(250); // изчакайте 250 милисекунди PORTD = 0x00; // задайте "0" (изключено) на всички линии на порт D _delay_ms(250); // изчакайте 250 милисекунди) // затваряща скоба на безкраен цикъл ) // функция за въвеждане скоба основна

Компилираме кода и получаваме готов фърмуер.

Мигаме микроконтролера с този фърмуер и сглобяваме веригата на хардуера.

Ако не знаете как да го флашнете, можете да разберете тук:

В следващата статия ще научим как да проверяваме написан код в Proteus, т.е. Ще емулираме работата на хардуера.

Има много инструменти за разработка за програмиране на AVR микроконтролери, но най-популярният, несъмнено, е пакетът AVR студио. Има няколко причини за тази популярност: безплатен пакет, разработен от компанията ATMEL, съчетава текстов редактор, асемблер и симулатор. AVR Studio се използва и заедно с инструменти за отстраняване на грешки в хардуера. Тази статия използва примери, за да обсъди как да работите с пакета, което ще помогне на начинаещите програмисти бързо да разберат взаимодействието на отделните компоненти на AVR Studio.

Следващата част на статията ще говори за отстраняване на грешки в програми, написани на C в средата на AVR Studio.

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

Дистрибуцията на пакета и сервизния пакет могат да бъдат изтеглени от уебсайта www.atmel.com или можете да получите компактдиск с тази дистрибуция от руския дистрибутор на ATMEL.

Удобно е да се разгледа работата на пакета AVR Studio на всяка конкретна програма. За да илюстрираме, ще разгледаме създаването на проект за най-простата програма, което ще светне два светодиода на свой ред. За да бъдем конкретни, нека вземем микросхемата Atmega128и свържете два светодиода към щифтове 31 и 32 (това са битове 6 и 7 на порт D на чипа ATmega128). AVR контролериимат мощни изходни етапи, типичният ток на всеки изход е 20 mA, максималният изходен ток е 40 mA и това се отнася както за входящия, така и за изходящия ток. В нашия пример светодиодите са свързани чрез своите аноди към клемите на контролера, а катодите са свързани към земята чрез охлаждащи резистори. Това означава, че светодиодът свети чрез прилагане на „1“ към съответния щифт на порта. Схематична диаграмапоказано на фигурата. Диаграмата показва и два бутона, които ще се използват в една от програмите.

Тук е подходящо да направим кратко отклонение относно избора на типа микросхема за прост пример. Наистина, на пръв поглед може да изглежда странно защо е необходим такъв мощен кристал в 64-пинов пакет, където би била достатъчна 8-пинова микросхема ATtiny12? В този подход обаче има логика. Известно е, че почти всеки AVR контролер се базира на едно и също ядро. Като цяло контролерите се различават по капацитет на паметта, брой входни/изходни портове и набор от периферни модули. Характеристиките на всеки конкретен контролер са обвързването на логически имена на I/O регистри към физически адреси, адреси на вектори за прекъсване, дефиниции на битове на портове и др. са описани във файлове с разширение .inc, които са включени в пакета AVR Studio. Следователно, използвайки конкретен тип кристал, можете да отстраните грешки в програмата както за самия него, така и за всеки младши кристал. Освен това, ако използвате най-стария кристал като кристал за отстраняване на грешки, днес това е ATmega128, можете да коригирате грешки в програмата за почти всеки AVR контролер, просто трябва да не използвате хардуерни ресурси, които целевият микроконтролер няма. По този начин, например, можете да дебъгвате програма на ATmega128, която ще бъде изпълнена на ATtiny13. В този случай изходният код ще остане почти същият, само името на включения файл ще се промени от 128def.inc на tn13def.inc. Този подход има и своите предимства. Например, „допълнителни“ I/O портове могат да се използват за свързване LCD индикатор, към който може да се изведе информация за отстраняване на грешки. Или използвайте вграден емулатор, който се свързва към JTAG порта на чипа ATmega128 (контролерът ATtiny13 няма такъв порт). По този начин можете да използвате една платка за отстраняване на грешки, на която е инсталиран „старшият“ AVR контролер, за да отстранявате грешки във всички новоразработени системи, естествено също базирани на AVR микроконтролери. Една от тези платки се нарича AS-megaM. Именно това беше използвано за създаване на примерните програми, дадени в статията. Това е универсален контролер с една платка, базиран на чипа ATmega128, който съдържа външна RAM памет, два порта RS-232, порт за свързване на LCD индикатор, вграден програматор и емулатор В JTAG ICE. Платката също така има място за разпояване на FLASH-ROM серия чип AT45в корпуси TSOP32/40/48 и серия двуканални DAC AD5302/ AD5312/ AD5322. Сега, след като обяснихте причините за използването на AVR чудовище за запалване на чифт светодиоди, можете да продължите.

Когато програмирате в средата на AVR Studio, трябва да изпълните стандартната последователност от действия:

  • компилация
  • Създаването на проект започва с избиране на лентата с менюта Проект\Нов проект. В прозореца „Създаване на нов проект“, който се отваря, трябва да посочите името на проекта (в нашия случай sample1) и името на файла за инициализация. След като щракнете върху бутона „Напред“, се отваря прозорецът „Избор на платформа за отстраняване на грешки“. и устройство”, където се избира платформата за отстраняване на грешки (симулатор или емулатор) и типа на микроконтролера.

    Можете да изберете един от предложените вътрешносхемни емулатори; имайте предвид, че всеки емулатор има свой собствен списък с поддържани чипове. За разглеждания пример ние избираме симулатора на AVR и чипа ATmega128 като платформа за отстраняване на грешки. След като щракнете върху бутона „Край“, виждаме реално работещите прозорци на пакета AVR Studio, които все още са празни. Трябва да поставите изходния текст на програмата в десния прозорец. Това може да стане по два начина, или чрез въвеждане на целия текст директно в прозореца на редактора, или чрез зареждане на съществуващ файл. По-долу е пълният текст на най-простата програма с коментари.

    ; Пример "LED Control"; написано за платката за разработка AS-MegaM; Честота на главния осцилатор 7.37 MHz; Светодиодите са свързани към щифтове PD6 и PD7 и чрез резистори към общия проводник. ; свързване на I/O описателния файл за чипа ATmega128 .include "m128def.inc" ; стартиране на програмата start: ; първата операция е инициализация на стека; ако това не е направено, извикайте подпрограма или прекъсвайте; няма да върне контрола обратно; указателят към края на стека е настроен на последния адрес на вътрешната RAM - 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. Процесът на компилиране се показва в прозореца „Изход“. Този прозорец може да бъде изваден с помощта на командата \View\Output.

    По принцип вече получихме изходен файл във формат .hex, който вече може да бъде зареден в микросхемата и светодиодите да мигат. Въпреки това, целта на статията е да покаже пълния цикъл на работа в средата на AVR Studio, така че преминаваме към етапа на отстраняване на грешки. Това става с командата \Debug\Start Debugging.

    Сега задаваме кварцовата честота на 7,3728 MHz в прозореца „Опции на симулатора“, за да измерим точно времето за изпълнение на програмата.

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

    Пакетът AVR Studio съдържа мощни инструменти за преглед и редактиране на състоянието на вътрешните регистри и входно-изходните портове на дебъгвания микроконтролер, както и времето за изпълнение на програмата. Те са достъпни през прозореца „I/O“.

    Всъщност количеството информация, налична през прозорците за преглед на AVR Studio, е толкова голямо, че за максимален комфорт трябва да използвате компютър с двоен монитор.

    За отстраняване на грешки в нашия пример, за достъп до битовете на порт D, трябва да разширим линията I/O ATMEGA128 и след това линията PORTD. Сега и трите регистъра на този порт, PORTD, DDRD и PIND, са видими. За да видите полетата Value, Bits и Address, ще трябва да разширите дясната граница на прозореца, като по този начин изтласкате прозореца с изходния текст на програмата.

    Сега, преминавайки през програмата стъпка по стъпка, можете да видите промените в текущите състояния на тези регистри в полето Bits. Възможно е бързо да се промени състоянието на всеки бит от регистрите на порта, като това може да стане или чрез писане на нов код в полето Стойност, или директно чрез щракване върху желания бит в регистъра.

    За самостоятелни упражнения се предлага следната програма, която се различава от предишната по това, че светенето на светодиодите се управлява от два бутона.

    ; Пример “Управление на светодиоди от бутони”; написано за платката за разработка AS-MegaM; Светодиодите са свързани към щифтове PD6 и PD7 и чрез резистори към общия проводник. ; бутони - на PE4 и PE5 .include "m128def.inc" ; започва основната програма: ; инициализация на стека 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 C използва дебъгера на AVR Studio „като че ли е роден“. За да направите това, когато компилирате изходния код, трябва да зададете опцията за генериране на изходен файл във формат, съвместим с AVR Studio. В този случай става възможно отстраняването на грешки в изходните кодове.

    Друга от многото функции на пакета AVR Studio е възможността за свързване на външни програми. Например, за да извикате обвивката на програматора AS2 в схемата, трябва да извършите няколко прости операции.

    В менюто Инструменти на главния прозорец на AVR Studio изберете Персонализиране;

    В прозореца Персонализиране изберете Инструменти;

    Щракнете двукратно върху бутона на мишката или натиснете Insert на клавиатурата, добавете нова команда към списъка и я наименувайте „AS2 Programmer“;

    Посочете пътя до изпълнимия файл на програмиста, като го въведете директно в полето за въвеждане "Команда" или като щракнете върху бутона "..." вдясно от това поле;

    Сега елементът „AS2 Programmer“ се появи в менюто Инструменти.

    Инструментите на пакета AVR Studio 4.08 ви позволяват да свържете спомагателни програми - плъгини. Първият плъгин за AVR Studio е програма за графичен редактор, която опростява процеса на инициализиране на LCD дисплей, който може да се управлява директно от ATmega169 AVR контролера. Максималният логически размер на LCD индикатора е 100 сегмента, като на всеки елемент от индикатора се присвоява бит в специален регистър на контролера. За да се опрости процедурата за присвояване на специфични битове на всеки сегмент, може да се използва горната програма.

    По време на посещение в „родината на AVR“ - норвежкия офис на ATMEL, един от авторите на статията разговаря с Ларс Квенилд, ръководител на програмната група, която създаде и поддържа пакета AVR Studio. Този човек, класически програмист, с брада, облечен в пуловер и обути в сандали на чорапите, говори за перспективите за развитие на пакета. Следващата версия (4.09) ще включва интерфейс за нов вътрешносхемен емулатор - JTAGICE mkII (наричан още AT JTAGICE2), който ще замени AT JTAGICE през втората половина на годината. Този емулатор има две съществени разлики. От една страна, добавена е поддръжка за нов еднопроводен интерфейс за отстраняване на грешки за младши AVR контролери, debugWIRE. Този интерфейс е интересен, защото не заема допълнителни пинове на микроконтролера за своята работа, тъй като използва Reset pin на микроконтролера за смяна! От друга страна (можете да приемете този израз буквално), емулаторът AT JTAGICE2 най-накрая ще има USB интерфейс за комуникация с компютър.

    Литература

    1. Материали от техническия семинар AVR Technical Training. Atmel. Норвегия. декември 2003 г.
    2. Николай Королев, Дмитрий Королев AVR микроконтролери от второ поколение: инструменти за разработчици. // Компоненти и технологии, 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 // Microprocessor Review, 1998, № 1


    Свързани публикации