Программирование микроконтроллеров AVR на языке C / C++ (Си) в Atmel Studio

Программирование на Си для микроконтроллеров немного отличается от обычного программирования тем, что приходится работать с битами и оперировать ими, я тут я приведу примеры часто используемых приемов программирования на языке C++ в Atmel Studio.

Представление чисел:
Например десятичное число 15 можно представить так:
0b00001111 - двоичное
017 - восьмеричное
0x0f - шестнадцатеричное

Математические оператры:
Сложение: +
Вычитание: -
Деление: /
Умножение: *
Остаток: %

Логические операции:

Логическое "И" (AND)&&Пример: <условие1> && <условие2> - возвращает истина(единица) в том случае, когда истинны оба условия 1 и 2, в противном случае возвращает ложь(ноль)
Логическое "ИЛИ" (OR)||Пример: <условие1> || <условие2> - возвращает ложь(ноль) в том случае, когда ложны оба условия 1 и 2, в противном случае возвращает истина(единица)
Логическое "НЕТ" (NOT)!Пример: int k=5; if (!k) {...} Оператор NOT инвертирует условие наоборот, вместо истины(единица) возвратит ложь(ноль) и наоборот. В примере есть переменная которой присвоено число 5, условие if будет выполнятся если переменная k будет равна чему угодно, но только не 5


Побитовые операции:

Отрицание-
Побитовое "И" (AND)&
Побитовое "ИЛИ" (OR)|
Побитовое "XOR"^
Сдвиг битов вправо(эквивалентно делению на 2)>>
Сдвиг битов влево(эквивалентно умножению на 2)<<



Управление портами ввода / вывода на микроконтроллерах AVR:
x-номер порта
DDRx (DDRA,DDRB,...) - Регистр направления передачи данных, конфигурирует контакты как вход(1) или выход(0)
PORTx (PORTA,PORTB,...) - Регистр вывода данных
PINx (PINA,PINB,...) - Регистр ввода данных, служит для чтения значения логического уровня на контактах(если они объявлены как вход)

Примеры манипуляций с двоичными числами с помощью логических операторов

Пример: мы хотим включить все контакты PORTB:
PORTB = 255;//в десятичной системе
PORTB = 0xff;//в шестнадцатеричной системе
PORTB = 0b11111111;//в двоичной системе(визуально более понятно какой контакт включен а какой выключен)

Пример: мы хотим установить высокий уровень на 0-3 контактах PORTB, нам нужно 4 младших бита установить в единицу, остальные биты будет с низким уровнем:
PORTB = 15;//в десятичной системе(трудно понятно, но коротко)
PORTB = 0xf;//в шестнадцатеричной системе(трудно понятно, но еще короче если большое число)
PORTB = 0b00001111;//в двоичной системе(визуально более понятно какой контакт включен а какой выключен)

Установление отдельных битов в единицу ,не затрагивая другие биты
Пример: PORTB = 0b00000010, необходимо на 4 контакт(всего битов 8, отсчет начинается с 0..7) PORTB установить высокий уровень, не изменяя при этом другие контакты, т.е. нужно чтобы в итоге остался высокий уровень на 2 и 4 контактах:
PORTB = 0b00000010; //Присвоим начальное значение 2-й бит = 1
PORTB = PORTB|0b00001000; //Присвоим 4-му биту единицу или подадим высокий уровень на контакт №4
или тоже самое но кратко:
PORTB |= 0b00001000; //Присвоим 4-му биту единицу или подадим высокий уровень на контакт №4

Установление отдельных битов в ноль, не затрагивая другие биты
Пример: PORTB = 0b11111101, необходимо на 4-й контакт PORTB установить низкий уровень, не изменяя при этом другие биты, т.е. нужно чтобы в итоге остался низкий уровень на 2 и 4 контактах:
PORTB = 0b11111101; //Присвоим начальное значение 2-й бит = 0, остальные биты с высоким уровнем
PORTB = PORTB &~ 0b00001000; //Присвоим 4-му биту единицу или подадим высокий уровень на контакт №4
или тоже самое но по другому:
PORTB = PORTB & 0b11110111; //Присвоим 4-му биту единицу или подадим высокий уровень на контакт №4
или тоже самое но кратко:
PORTB &= ~0b00001000; //Присвоим 4-му биту единицу или подадим высокий уровень на контакт №4
PORTB &= 0b11110111; //Присвоим 4-му биту единицу или подадим высокий уровень на контакт №4

Изменение отдельных битов на противоположное значение 1->0 или 0->1, не затрагивая другие биты
Пример: PORTB = 0b00000010, необходимо на 2 контакт PORTB установить низкий уровень, а потом высокий и т.д.:
PORTB ^= 0b00000010; //Результат: PORTB = 0b00000000, т.к. PORTB был равен 0b00000010
PORTB ^= 0b00000010; //Результат: PORTB = 0b00000010, т.к. PORTB был равен 0b00000000
PORTB ^= 0b00000010; //Результат: PORTB = 0b00000000, т.к. PORTB был равен 0b00000010
PORTB ^= 0b00000010; //Результат: PORTB = 0b00000010, т.к. PORTB был равен 0b00000000
и т.д., т.е. при каждом выполнении этой команды "PORTB ^= 0b00000010", изменяется только второй бит на противоположное значение, так можно сделать например мигание светодиодом.

Другие манипуляции с битами, каждое выражение не зависит от предыдущего, просто как примеры и результат этого выражения
PORTB = 0; //Результат: PORTB = 0b00000000, обнуляем
PORTB = 255; //Результат: PORTB = 0b11111111, установим все биты в единицу
PORTB = 0xff; //Результат: PORTB = 0b11111111, установим все биты в единицу

PORTB = 1; //Результат: PORTB = 0b00000001, просто присваиваем единицу
PORTB = 128; //Результат: PORTB = 0b10000000, просто присваиваем 128 в десятичной, а в двоичной будет такой результат
PORTB = 1<<1; //Результат: PORTB = 0b00000010, сдвигаем единицу на 1 позицию влево
PORTB = 1<<2; //Результат: PORTB = 0b00000100, сдвигаем единицу на 2 позиции влево
PORTB = 1<<7; //Результат: PORTB = 0b10000000, сдвигаем единицу на 7 позиций влево
PORTB = 128>>1; //Результат: PORTB = 0b01000000, сдвигаем десятичное число 128 на 1 позицию вправо
PORTB = 128>>2; //Результат: PORTB = 0b00100000, сдвигаем десятичное число 128 на 2 позиции вправо
PORTB = 128>>7; //Результат: PORTB = 0b00000001, сдвигаем десятичное число 128 на 7 позиций вправо

 

Источник: /engine/api/go.php?go=https://www.iprg.ru



Обсудить на форуме
serv-3

Комментарии

ошибка в описании команды DDRx
Добавить комментарий
    • bowtiesmilelaughingblushsmileyrelaxedsmirk
      heart_eyeskissing_heartkissing_closed_eyesflushedrelievedsatisfiedgrin
      winkstuck_out_tongue_winking_eyestuck_out_tongue_closed_eyesgrinningkissingstuck_out_tonguesleeping
      worriedfrowninganguishedopen_mouthgrimacingconfusedhushed
      expressionlessunamusedsweat_smilesweatdisappointed_relievedwearypensive
      disappointedconfoundedfearfulcold_sweatperseverecrysob
      joyastonishedscreamtired_faceangryragetriumph
      sleepyyummasksunglassesdizzy_faceimpsmiling_imp
      neutral_faceno_mouthinnocent

    Китайский ПЛК Wecon LX3V-0806MT-A2, часть 2: программирование

    С точки зрения программирования, ПЛК Wecon серии LX3V является клоном ПЛК Mitsubishi Melsec FX2N. Поэтому программировать LX3V можно как в родной среде программирования Wecon PLC Editor, так и в среде GX Works2 для

    Контроллер ПЛК160 Использование по назначению

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

    Аббревиатуры гармонизированных кабелей

    H - безгалогеновый ПВХ изоляция жилы/внешняя оболочка   SL - кабель контрольный Li - многожильный проводник по VDE

    Материалы по Siemens Step5

    Уходящая в прошлое линейка контроллеров Step5, продолжает все-таки кое где встречаться. Приведенные здесь материалы от автора ставшим классиком в написании мануалов по Сименсу - Ганса Бергера, помогут, при необходимости, разобраться с этим вопросом.

    Как перепрошить ЭБУ М73 / Январь 7.2+

    Работа с даными блоками управления осуществляется вкладкой MIKAS 11/M73A или J72+/M73I. MIKAS 11/M73A - только блоки управления M73 производства АВТЕЛ с ПО А308ХХХХ, А317ХХХХ, А373ХХХХ(далее ЭБУ M73A).

    Плата кабеля программирования Lovato LRXC00. Фото, схема

    Для загрузки программ в программируемое реле Lovato LRD20RD024  используется кабель программирования LRXC00 для COM-порта: