PureBasic - форум

Информация о пользователе

Привет, Гость! Войдите или зарегистрируйтесь.


Вы здесь » PureBasic - форум » Программирование микроконтроллеров » STM32 - Простая программа - "мигалка" светодиодом


STM32 - Простая программа - "мигалка" светодиодом

Сообщений 1 страница 4 из 4

1

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

http://s3.uploads.ru/7kClx.jpg

Среда программирования EmBitz и предполагается что у вас она установлена.

Необходимо создать новый проект для разрабатываемой программы. Кликаем по кнопке "Создать новый проект" в окне программы.

http://sh.uploads.ru/j3enc.png

В появившемся окне выбираем тип проекта "STmicro-ARM" и кликаем по кнопке Go.

http://s8.uploads.ru/t/eM9OP.png

Дальше несколько раз кликаем по кнопке "Next" пока не попадаем в окно выбора имени проекта и места расположения на диске. Выбираем имя проекта (назовем его Blink) и папку куда сохраним его.

http://s2.uploads.ru/t/rMCpZ.png

Заполнять нужно два верхних поля (имя и путь), а нижние поля среда сама заполнит.

Кликаем кнопку "Next" и попадаем в окно выбора компилятора и конфигураций.

http://s2.uploads.ru/t/nJG5x.png

Компилятор оставляем тот что есть. Среда нам предлагает создать две конфигурации, а так же выбрать папки для объектного файла и прошивки.
Далее нужно выбрать микроконтроллер. Это делается в несколько этапов. Сначала нужно выбрать ядро. У нашего МК оно Cortex_M3.

http://s3.uploads.ru/t/MXBdV.png

Потом нужно выбрать модельный ряд. Т. к. МК STM32F103C8T6 выбираем STM32F10x.

http://sg.uploads.ru/t/n71Sh.png

Затем выбираем в списке микроконтроллер STM32F103C8.

http://s3.uploads.ru/t/IRnJy.png

После этого кликаем по кнопке Finish и проект будет создан и открыт в IDE. Так же появятся пара окон конфигурации отладчика. Закрываем их кликая по кнопке OK.

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

http://s7.uploads.ru/t/IDARu.png

Нужно кликнуть по файлу Main.c и он откроется в редакторе. Код из него.

Код:
#include "stm32f10x_conf.h"

int main(void)
{
  while(1)
  {

  }
}

Это функция main с которой программа начинает работать и цикл while. Если скомпилировать этот код ничего не изменяя в нем, то с максимальной оптимизацией размера, получим прошивку весящую 1048 байт. Кажется много, но не стоит забывать что модули STM32 более сложные и необходимо больше кода для их настройки, а так же что МК 32 битный, а значит адресация 4-ех байтная. Все это требует больше памяти чем в 8-ми битных МК...

Теперь добавим код мигающий светодиодом находящийся на плате (подключен к GPIOC.13). Для этого добавим перед циклом код настройки порта GPIOC.13.

Код:
	GPIO_InitTypeDef GPIO_InitStructure;

	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE);

	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;

	GPIO_Init(GPIOC, &GPIO_InitStructure);

О том как это работает можно прочитать в статье http://easyelectronics.ru/rabota-s-stm3 … brary.html
Когда порт настроен, можно светодиодом помигать.

Код:
    while(1)
    {
        GPIO_SetBits(GPIOC, GPIO_Pin_13);
        Delay(2000000);
        GPIO_ResetBits(GPIOC, GPIO_Pin_13);
        Delay(2000000);
    }

Думаю этот участок понятен без объяснений.

Теперь программу можно скомпилировать, прошить МК и наблюдать как светодиод находящийся на плате мигает несколько раз в секунду.
Проект. http://pure-basic.narod.ru/forum_files/stm32/Blink.zip

0

2

Выше была использована библиотека StdPeriph. Сейчас же сделаем программу с той же функциональностью ("мигалка" светодиодом), но с использованием библиотеки HAL.
Запускаем EmBitz и создаем проект как написано выше. Назовем его Blink_2. Так как при создании проекта в него была автоматически добавлена библиотека StdPeriph, а нужна HAL, то необходимо удалить все файлы проекта.

http://s8.uploads.ru/j2P9k.png

Появится окно в котором находится список удаляемых файлов. Выбираем все и нажимаем кнопку ok. Затем нужно сохранить проект.
Теперь открываем папку с проектом и удаем из нее все папки (cmsis, inc, SPL и src) и запускаем программу STM32CubeMX (у кого ее нет, качаем (ссылка на скачивание в самом низу страницы, после надписи "Get Software"), устанавливаем и запускаем).
Эта программа является визуальным конструктором программы, в котором можно быстро настроить ядро и периферию МК как нам нужно. Небольшая статья, рассказывающая о ней. https://habrahabr.ru/post/213561/
В программе создаем новый проект. В появившемся окне в списках, выбираем МК STM32F103C8Tx.

http://s2.uploads.ru/ZsgaW.png

Нажимаем на кнопку ok. Проект будет создан и увидим такое окно (по умолчанию, активна вкладка Pinout).

http://s6.uploads.ru/t/nuZdv.png

В левой части окна можно конфигурировать модули МК, а в правой, показан МК и какие функции назначены выводам.
Так как светодиод на плате подключен к выводу GpioC.13, то его нужно настроить на вывод. Ищем в окне этот вывод (он находится слева вверху, рядом с выводом VBAT) и кликаем по нему левой кнопкой мышки и выбираем GPIO_Output.

http://sa.uploads.ru/H0iLZ.png

Теперь перейдем на вкладку "Configuration", где можно настроить модули.

http://s6.uploads.ru/t/qoRfg.png

В области System нажимаем на кнопку GPIO. Откроется окно где можно настроить параметры порта, например, такие как начальный логический уровень, тип (полноценный выход, или выход с открытым истоком) и т. д.

http://s7.uploads.ru/t/5cN8p.png

Далее открываем настройки проекта (меню Project пункт Setting).

http://s7.uploads.ru/t/SYVgq.png

Нужно выбрать название проекта и путь куда сохранить его. Путь должен быть таким же как у проекта EmBitz чтобы файлы оказались той же папке, а так же выбрать IDE TrueSTUDIO.
После этого в меню Project кликаем по пункту "Generate Code" и ждем завершения генерации кода.
Теперь можно закрыть программу STM32CubeMX и открыть ранее созданный проект в программе EmBitz.
Добавляем файлы в проект, выбрав в меню пункт "Добавить файлы рекурсивно".

http://s9.uploads.ru/U5dz7.png

Последовательно появятся несколько окон. Во всех жмем кнопку ok.
Будут добавлены файлы, которые были сгенерированы программой STM32CubeMX. Открываем файл "main.c".

http://s8.uploads.ru/J3hWt.png

Если сейчас попытаться скомпилировать программу, то появится множество ошибок... Все потому что сгенерированные файлы не для EmBitz, а для TrueSTUDIO. Проблема в том что компилятор не знает под какой МК ему создавать прошивку. Нужно ему об этом сообщить. Открываем опции компиляции (меню "Проект" пункт "Build Options") и на вкладке "Compiler setting" в "#defines" вводим "STM32F103xB" (без кавычек). Это нужно сделать для конфигрураций "Debug" и "Release".

http://sf.uploads.ru/t/ny4Zl.png

Теперь программа компилируется без ошибок.

Далее в файле "main.c" находим функцию main в ее цикле while, пишем код мигания светодиодом.

Код:
 while (1)
  {
  /* USER CODE END WHILE */

  /* USER CODE BEGIN 3 */

  HAL_GPIO_TogglePin(GPIOC, GPIO_PIN_13); // Инвертирование состояния выхода.
  HAL_Delay(500);                         // Пауза 500 миллисекунд.

  }
  /* USER CODE END 3 */

Собственно все. Компилируем программу, берем прошивку в папке bin\Debug или bin\Release в зависимости от активной конфигурации на момент компиляции и прошиваем МК, подаем на него питание и смотрим как мигает светодиод. :)  :D

Прошивка имеет размер примерно в три раза больше (почти 4 КБ) чем аналогичная с использованием библиотеки StdPeriph в первом сообщении, но думаю что это не из-за библиотеки, а из-за не совсем оптимального кода, генерируемого программой STM32CubeMX.

Файлы. http://pure-basic.narod.ru/forum_files/ … link_2.zip

Продолжение темы - STM32 - Отладка программы

0

3

Пётр написал(а):

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

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

Код:
#include "stm32f10x.h"

#define StackTop  ((uint32_t)(0x20000000 + 20*1024))

static void Reset_Handler(void);

__attribute__((used,section(".isr_vector")))
void (*const g_pfnVectors[])(void) =
{
  (void*)StackTop, // Указатель на начало стека.
  Reset_Handler    // Функция выполняемая при сбросе МК.
};

static void Reset_Handler(void)
{
    RCC->APB2ENR = RCC_APB2ENR_IOPCEN; // Вкл. тактирование порта GPIOC.
    GPIOC->CRH = GPIO_CRH_MODE13;      // Настройка вывода PC13 как выхода.

    while(1)
    {
        GPIOC->ODR ^= (1<<13);         // Инвертирование состояния вывода PC13.
        for (uint32_t i=0; i<1000000; i++);
    }
}

Собственно это весь код, который выполняется в МК. В массиве g_pfnVectors находится начало таблицы векторов, без которых нельзя обойтись. Это адрес начала стека и адрес функции выполняемой при старте (сбросе) МК. Массив занимает 8 байт прошивки.
Функция Reset_Handler выполняется при старте (сбросе) МК и в ней включается тактирование порта GPIOC, а затем его 13 вывод настраивается на работу выходом. После, в цикле инвертируется выход PC13 к которому подключен светодиод и циклом for создается небольшая пауза чтобы было видно как мигает светодиод.
Этот код скомпилировался в прошивку размером 48 байт.

Код:
Program size (bytes):      48
Data size    (bytes):       0
BSS size     (bytes):       0

Total size   (bytes):      48   (R/W Memory: 0)

Ассемблерный листинг с привязкой к коду.

Скриншот

http://sd.uploads.ru/9vetC.png

Видно что функция начинается с адреса 0x08000008 и заканчивается на адресе 0x08000028, т. е. размер кода составляет 32 байта.
Программа работает - светодиод мигает, но для максимального уменьшения размера, пришлось отказаться от таблицы векторов прерываний (кроме двух первых, где располагается адрес стека и адрес функции старта), а также от настройки тактирования (МК работает с настройками по умолчанию, т. е. от RC генератора с частотой 8 МГц) и код написан так как обычно его не пишут. В нем для уменьшения размера применены приемы, которые являются неправильными. К примеру эта строка.

Код:
RCC->APB2ENR = RCC_APB2ENR_IOPCEN;

Должна быть такой.

Код:
RCC->APB2ENR |= RCC_APB2ENR_IOPCEN;

Кроме того, компилятор gcc 5.4 (входит в дистрибутив EmBitz 1.11) не выбросил цикл for, но должен был это сделать. gcc 7 выбрасывает его, т. е. для компиляции нужен gcc 5.4.

Файлы. http://pure-basic.narod.ru/forum_files/ … _bytes.zip

0

4

Текущая версия STM32CubeMX кроме HAL поддерживают другую библиотеку - LL (Low Layer). В проекте можно использовать их обе. Выбор производится в настройках проекта на вкладке Advanced Setting.

Свернутый текст

http://sh.uploads.ru/xMVPX.png

На скриншоте видно что для RCC и GPIO выбрана библиотека LL.
Генерация кода и добавление файлов в проект EmBitz производится также как написано в 2 сообщении. В опциях проекта на вкладке "Compiler setting" в "#defines" нужно ввести кроме "STM32F103xB", также и USE_FULL_LL_DRIVER.

Свернутый текст

http://s3.uploads.ru/uPz6t.png

Имена функций библиотеки отличаются от тех что в HAL.

Код:
    while (1)
    {

        /* USER CODE END WHILE */

        /* USER CODE BEGIN 3 */
        LL_GPIO_TogglePin(GPIOC, LL_GPIO_PIN_13);
        LL_mDelay(500);
    }
    /* USER CODE END 3 */

При компиляции используя GCC 5.4 из дистрибутива EmBitz 1.11, размер прошивки 1248 байт.

Код:
Program size (bytes):    1240
Data size    (bytes):       8
BSS size     (bytes):      28

Total size   (bytes):    1276   (R/W Memory: 36)

=== Сборка закончена: 0 errors, 0 warnings (0 minutes, 1 seconds) ===

GCC 7 код лучше оптимизирует и прошивка имеет меньший размер.

Код:
Program size (bytes):    1164
Data size    (bytes):       8
BSS size     (bytes):      28

Total size   (bytes):    1200   (R/W Memory: 36)

=== Сборка закончена: 0 errors, 0 warnings (0 minutes, 1 seconds) ===

Размер кода примерно соответствует библиотеке SPL. По сравнению с HAL, результат намного лучше.

Файлы. http://pure-basic.narod.ru/forum_files/ … ink_LL.zip

0


Вы здесь » PureBasic - форум » Программирование микроконтроллеров » STM32 - Простая программа - "мигалка" светодиодом