Самый недорогой программатор/отладчик ST-Link V2 на примере STM32F103CBT6.

Обязательно меняем провода на короткие
Итак первым делом меняем провода для соединения ST-LINK V2 с STM32F103C8T6 на короткие 10см.
Используем для соединения с STM32F103C8T6 только 4 провода (SWD интерфейс):
3.3V — 3.3V
GRD — GRD
SWDIO- DIO
SWCLK- CLK
Нет SWO трассировки
То есть не выведен отдельный провод PB3 SWO из программатора наружу.
Но в принципе программно SWO реализован внутри программатора. Только воспользоваться им нельзя. Белый провод это он и есть, а как подпаятся к ножке микросхемы программатора вопрос ?..

Как обновить внутреннее ПО
через программу ST-LINK Utility
Проверяем сначала связь с контроллером программой ST-LINK Utility:
Обе перемычки на STM32F103C8T6 в положении 0
запускаем, жмем Connect и все определяется ОК
щелкаем Settings и видим, что устройство определяется автоматически корректно (см.скриншот) , port = SWD, target Voltage=3.2V и т.д.
Обновление внутреннего ПО
Чтобы сделать Firmware Update в программе ST-LINK Utility надо установить перемычку в положение 1 (режим DFU). В результате должно получится примерно так, кнопка Yes активна:

Иногда , почему-то не удается сделать Firmware Update. Но помогает — закрытие всех программ, перезагрузка ПК (танцы с бубном).
По-видимому надо разобраться что устанавливать? — Hardware Reset (при SoftWare Reset у меня не срабатывает).

Важно! — в ST-Link V2 после прошивки (через Stm32-Link Utility) сохраняются старые настройки Mode (Normal|Hot Plug|Connect Undr Reset) и Reset Mode (Software System Reset|Core Reset|Hardware Reset).
Если не работает ничего — пытаемся разобраться с дополнительными настройками
Mode : Connect Under Reset можно выставить только с Reset Mode : Hardware Reset (Похоже по смыслу , что это тот самый режим когда надо ручками кнопку Reset нажимать и перемычка в 1 д/б).
The “Connect Under Reset” option allows to connect to the target using a reset vector catch before executing any instruction. This is useful in many cases like when the target contains a code that disables the JTAG/SWD pins.
Т.е. это похоже когда программа в начале своего исполнения отключает SWD возможности. Понятно отладка тут не будет возможна.
Mode : Normal возможен с Reset Mode : (Software System Reset|Core Reset|Hardware Reset) .
With “Normal” connection mode, the target is rest then halted. The type of reset is selected using the “reset Mode” option.
Mode : Hot Plug возможен с Reset Mode : (Software System Reset|Core Reset|Hardware Reset)
The “Hot Plug” option allows to connect to the target without halt or reset. This is useful to update the RAM addresses or the IP registers while the application is running.
И мы понимаем, что Hot Plug — пока этот режим нам не нужен никак.
Итак режим (Mode) и Reset Mode настраивается именно в ST-Link V2 через Stm32-Link Utility.
В Keil надо соответственно этому указать настройки.
Предисловие
Самой распространенной модель отладчика-программатора STLINK V2 стал миниатюрный свисток. И хоть многие на него жалуются, но у меня они работали очень даже неплохо и не один не вышел из строя. Но в свете последних событие (роста цен) можно задуматься над покупкой более стационарного и «надежного» решения в виде оригинального обмылка, ведь его стоимость около 10?.
В комплекте будет входить белый USB-кабель, при первой прошивке нужно будет обновить (выскочит окно).
Купить на Aliexpress
?️ ST-LINK/V2 ST-LINK V2(CN) (10.8?): https://ali.ski/1AVNB
?️ Debugger ST-LINK V2 (11.41?): https://ali.ski/aAHtrn
?️ ST-LINK/V2 miniUSB (16.04?): https://ali.ski/8kkGhG
Назначение выводов
В комплекте идут несколько проводов с разъемами, один из них для JTAG, резать его не обязательно, достаточно сделать переходник из обычных штырей.
Прошивка через SWD (Serial Wire Debug)
Определяется хорошо, если дрова установлены (должны подхватиться, на всякий случай можно скачать STSW-LINK009.zip):
Во время работы прикольно красиво и достаточно ярко мигает, что хорошо заметно и дает понять, что всё идет хорошо:
Через STM32CubeProgrammer отлично работает:
Использование SWO (Serial Wire Output)
Существеннейшим достоинством именно такого программатора является наличие выхода для отправки отладочных данных:
Через STM32CubeIDE отлично работает:
Разборка в высоком разрешении
Чтобы разобрать нужно отклеить наклейку сзади и открутить два самореза, далее части корпуса легко разъединяются:
Под капотом всё по-простому, почти как у обычного USB-свистка, ремонтопригодность хорошая:
Микроконтроллер всем известный, теперь дефицитный STM32F103C8T6 (если что можно выдрать отсюда 
На плате остается куча свободного места, не удивительно почему это чудо такое огромное:
Можно попытаться в будущем переделать это чудо на USB-C, но пока пусть так работает.
ST-Link/V2 специальное устройство разработанное компанией ST для отладки и программирования микроконтроллеров серии STM8 и STM32. Про сам прибор можно прочитать на сайте компании ST.
Основные его возможности:
-
Выход 5В для питания устройства
-
USB 2.0 высокоскоростной интерфейс
-
SWIM, JTAG/serial wire debugging (SWD) интерфейсы
-
SWIM поддержка низкоскоростного и высокоскоростного режимов
-
SWD and serial wire viewer (SWV)
-
Возможность Обновление прошивки
Так как микроконтроллеры STM32 построены на ядре ARM Cortex, которое имеет интерфейс отладки SWD, то ST-Link позволяет программировать и отлаживать и другие 32-битные микроконтроллеры на базе ARM-Cortex.
Это, можно сказать, единственный программатор микроконтроллеров STM8. Для программирования STM32 существуют и другие универсальные программаторы.
Где можно купить программатор STM8 STM32 ST-Link
На текущий момент интерес к микроконтроллерам ST очень большой. Поэтому программатор ST link довольно широко распространен на рынке. Существует несколько версий, отличающихся по цене.
Оригинальный ST Link от компании ST, как всегда, самый дорогой вариант. Стоит больше 2 000 руб.
Мини ST link (очень похож на наш вариант этого программатора) стоит около 600 руб. Купить его можно у крупных поставщиков электроники — Компэл, Терра электроника и другие.
Ali express (Китай) — тут предлагается большое количество самых простых вариантов Программатора, но в общем, они все рабочие, ими вполе можно пользоваться. Как правило они годятся для программирования STM8 и STM32. Единственное, они не имеют SWO выхода, но он нужен не так часто. Пожалуй, единственный минус тут, это ожидание покупки. Стоимость около 150-200 руб.
Если вам не нужен программатор STM8, а нужна только серия STM32, то хорошим вариантом будут платы Discovery от ST, они имеют на бору и программатор ST link. Однако, как правило, разъем для программирования STM8 там не разведен.
Ну и конечно, можно просто купить детали и сделать данное устройство самостоятельно. В основе лежит не самый дешевый микроконтроллер STM32, да и купить детали дешево не так просто, так что, стоимость будет от 300 до 400 рублей. В данной статье мы будем рассказывать, как собрать данный прибор самостоятельно из набора необходимых SMD компонент. Конечно же мы рекомендуем пойти этим путем. Только так вы сможете научится трассировке плат, их изготовлению и паянию.
{product id=30}
Как изготовить программатор ST-LINK V2
1. Прочитать эту статью внимательно и до конца!
2. Подготовить или приобрести необходимые инструменты: все для пайки, USB UART адаптер (будет нужен для программирования МК)
3. Внимательно прочитать статьи из раздела Обязательная теория.
4. Скачать необходимые файлы по данному прибору с github.
5. Изготовить плату для прибора самостоятельно (это совсем несложно, в нашей инструкции все подробно описано).
6. Приобрести все необходимые комплектующие можно в нашем магазине за 300 руб.
7. Запаять все компоненты на плату, смотри наше видео.
ПРИБОР ГОТОВ, можно пользоваться!
Поиск схемы для ST Link программатора, отладчика
Сама компания ST не дает нам схему данного прибора, однако есть схемы ее ознакомительных плат серии DISCOVERY, в которых приводится и схема отладчика. Например документ UM0919. Но она не полная, там присутсвует только SWD интерфейс. В основе микроконтроллер STM32F103C8T6.

Вторая схема, которая есть в документе UM1670, содержит выводы SWIM выходов, но это уже версия V2.2 на другом микроконтролере STM32F103CBT6.

Также в интернет удалось найти схему ST-LINK v2, восстановленную по оригинальному прибору:
Вот из этих трех схем нам надо разработать схему для нашего устройства. Но сначала давайте составим основные требования к прибору, который мы будем делать.
Требования к нашему ST-LINK
Мы будем делать приборы на базе STM8, а также STM32, процессоров NUVOTON Cortex-M0, ATMEL. Все они будут питаться от 3.3В или 5В. Так что, нам не нужна возможность работать с микроконтроллерами на напряжении 1.8В. Но сама возможность программировать STM8 нужна обязательно.
Мы делаем прибор для своих задач, поэтому у нас нет необходимости в стандартных разъемах SWIM и JTAG. Будет делать такой разъем, который удобнее для трассировки платы.
Версия 2.2 на микроконтролере STM32F103CBT6 добавляет второе USB устройство — COM порт UART, но он уже у нас есть, так что, нет смысла переплачивать, микроконтроллер там дороже. Правда у него есть хорошая возможность — прошивка через интерфейс DFU, то есть микроконтроллер видится как флешка при подключении по USB, и прошивку просто надо скопировать на диск. Но прошить надо будет один раз, и для этого у нас есть USB UART адаптер, прошивать первый раз будет через него. Дальнейшее обновление прошивки идет уже через программу от ST по USB. Мы будем делать версию 2.0 на базе STM32F103C8T6.
Оригинальная версия ST-Link содержит микросхему преобразования уровней, что удобно для отладки и прошивки готового устройства, и необходимо для работы с напряжением ниже 3.3В. У нас таких не будет, а для работы с 5В и 3.3В — преобразование уровней не нужно.
Прибор будем делать в формате USB dongle, соответсвенно будет использоваться разъем USB-A male.
На защите выходов можно сэкономить, так что не будем использовать защитные диоды. Достаточно будет сопротивлений на всех выходах разъемов на случай, если вдруг мы их подключим на 5В или землю. Надо обязательно иметь в виду, что пользоваться данным прибором надо аккуратно! Все выходы при подключении проверять несколько раз! Выход 3.3В больше защищен, он идет через регулятор напряжения, защищающий от КЗ. Так что, лучше питать тестовые схемы от него!
Теперь можно составить финальную схему нашего ST-Link.
В интернет предложено много готовых плат и схем данного прибора, но в целях обучения мы специально строим схему и делаем плату сами, основываясь на DATASHEET, выложенных проиводителем. Если вы копируете схему с какого либо другого сайта вы должны в ней разобраться, что и как там сделано, почему выкинули или добавили какие-то элементы.
Финальная схема
Саму схему вы можете посмотреть в файлах данного прибора. Здесь же приведем ее для комментирования основных узлов.
Основная часть:

Питание и разъемы:
Небольшие комментарии.
В качестве регулятора питания на 3.3в используем NCP603 — очень хороший LDO, выдает ток до 300ма с падением 300mv и точностью +-3%. Светодиоды индикации — обычные smd светодиоды двух цветов. Для программирования по UART необходимо вывод BOOT0 соединить с +3В, для этого выведем его на разъем. Также необходимо вывести сам UART — ножки RX TX. Все остальные выводы без защиты выведем на разъем. Пользуюсь этим программатором уже больше года, и кз были и помехи — ничего не сгорело ни разу.
В некоторых схемах ставится самовостанавливающийся предохранитель на питание от USB для защиты самого порта. Современные компьютеры имеют защиту на портах USB, в том числе предохранители и токовые ограничивающие ключи, так что он не нужен. Но лучше конечно не проверять это, и не ошибаться! Напряжение 3.3в идет с нашего LDO, который имеет защиту от КЗ и от перегрева, и не выдает больше 600ма, там тоже защищать нечего.
Очень удобно подключать STM8 для программирования с помощью ST-Link, нужно всего 3 провода — питание, земля и SWIM выход. Это так же удобно при разводке плат, можно разводить только SWIM выход, землю и питание всегда можно найти на плате.
Трассировка платы в Kicad с помощью автотрассировщика Topor
В приборе USB UART адаптер мы уже тренировались трассировать плату в Kicad вручную. Данный прибор чуть сложнее. На нем можно поучиться разводить плату в автотрассировщике TOPOR. Весь процесс лучше просмотреть на видео в конце статьи, здесь будут лишь небольшие комментарии к видео.
Подготовка платы к автотрассировке
Для того, чтобы работать с Topor, надо сначала подготовить плату в Kicad. Необходимо определить границы платы, импортировать все компоненты и предварительно их расположить. У нас нет требований к разъемам, поэтому на первом этапе лучше сам разъем удалить с платы. Так как каждый вывод разъема соединен через резистор, то резисторы и будут ориентиром выводов разъема. Также для расстановки компонент можно удалить все конденсаторы питания, кварцы, микросхемы питания (их лучше располагать на обратной стороне — там обычно много места) — это все можно расставить потом.
Теперь необходимо определить сторону кажого копонента. И примерно расположить их как необходимо, разъемы расположить у края. И на этом этапе можно все это перебросить в Topor и там продолжить размещение копонентов. USB разъем, светодиоды сразу располагаем на обратной стороне, все остальное на лицевой.
Размещение компонентов с помощью Topor
Теперь переносим это все в Topor и продолжаем там. Чем хорош Topor? Тем, что каждый раз, подвигав компоненты, можно перепроложить все трассы автоматически и посмотреть стало лучше или хуже. Также Topor умеет переворачивать простые компоненты — резисторы, конденсаторы. Нам важно понять как удобнее расположить выводы разъемов, и основные компоненты.
Покрутив и подвигав компоненты в Topor мы пришли к такому расположению:

Теперь необходимо этот результат перекинуть в Kicad обратно и добавить остальные компоненты. Перед финальной трассировкой необходимо:
-
расположить микросхемы питания
-
развести вручную цепи питания
-
распложить и подключить кварц, и конденсаторы питания
-
переопределить выводы разъема на схеме.
Автотрассировка
Перебрасываем нашу полутрассировку в Topor.
Необходимо сразу установить правила трассировки — ширину зазоров, дорожек, размеры переходных отверстий. При первом импорте из Kicad надо выделить все компоненты и зафиксировать их, чтобы можно было легко удалить кнопкой del и заново перепроложить трассировку, оставляя наш полуручной вариант. В параметрах автотрассировки обязательно необходимо установить галку «Использовать имеющуюся разводку в качестве начального варианта», иначе наши ручные трассы будут перепроложены (Сам процесс работы в Topor смотри на видео).
После автотрассировки перебрасываем все обратно и доводим до финального варианта — добавляем земляные полигоны, выравниваем где необходимо дорожки. Плата готова.
Финальный вариант платы
Лицевая сторона

Обратная сторона
Прошивка ST Link, установка драйверов
Плата готова, делаем ее методом холодного переноса тонера ацетоном (или любым другим), травим, собираем прибор. Перед первым включением, обязательно проверьте любым мультиметром, что между 5В и GND сопртивления нет (бесконечно велико) — это будет гарантировать, что нет короткого замыкания. Также надо проверить сопротивление между 3.3В и GND.
Для работы с нашим устройством необходимо установить драйвера, прошить его первый раз по UART стартовой прошивкой и потом обновить прошивку до последней версии специальной программой от ST.
Все микроконтроллеры STM32 имеют bootloader и прошиваются по UART. Для прошивки необходимо:
-
скачать с сайта ST программу «STM32 Flash loader demonstrator» по ссылке (необходимо зарегистрироваться у них на сайте).
-
установить ее, все как обычно — далее далее далее — готово.
-
подключить наш ST link для программирования временными проводками:
-
Соединяем выводы программирования PROG_RX и PROG_TX (см. схему в Kickad на github) и USB/UART модуль — наш RX на TX модуля, наш TX на RX модуля.
-
В USB ST Link не включаем, подключаем 5В с UART модуля и GND на любой наш разъем (например на разъеме SWIM есть 5В и GND) — то есть запитаем от нашего модуля (если у вас свой модуль без питания, то можно сразу подключить ST-Link в USB разъем, тогда надо будет только соединить TX и RX, только не забудьте на вашем модуле необходимо выбрать 3.3в)
-
Подключем BOOT0 на выход 3.3В (можно просто держать проводок при подключении питания) — это необходимо для перехода в bootloader
-
-
включаем USB/UART модуль в компьютер, указываем в программе Flash Loader наш COM порт, жмем далее — программа должна найти наш микроконтроллер, далее, выбираем download и загружаем прошивку STLinkV2.J16.S4.bin, выложенную на github прибора. Вот такие это выглядит в картинках:
Тут выбираем 64К.
а тут ставим переключатель на download и выбираем файл прошивки (маска файлов на *.bin)
Теперь у нас есть ST LINK, но со старой прошивкой. Убираем все провода. Скачиваем с сайта ST программу обновления прошивки STSW-LINK007 и драйвера STSW-LINK009 для windows. Вставляем новоиспеченный ST-Link в USB порт компьютера, и запускаем программу обновления прошивки, в ней жмем CONNECT и потом обновить прошивку до последней версии. Прибор ГОТОВ! Теперь у вас есть программатор-отладчик и можно перейти к программированию.
Готовое устройство
Самостоятельная работа
Потренируйтесь разводить плату. Сделайте это вручную, с помощью программы Topor и без. Вы должны уметь быстро делать любую несложную плату.
Привет, Хабр!
Зачастую среди большинства любителей и даже профессионалов в сфере программирования микроконтроллеров STM32 очень часто возникает один и тот же вопрос, сочетающий в себе одновременно открытие новых горизонтов, душевную боль (особенно для чайников) и множество скептицизма:
А какой программатор вы используете?
Разумеется данный вопрос коснулся и Автора статьи. Сначала, сидя на табуретке, держа в одной руке стипендию, а в другой желание программировать железку, хочется начать изучение «по уму», однако жизненные факторы на раннем этапе развития заставляют себя ограничивать… Поэтому идеальный вариант — дешёвый китайский программатор ST-Link V2… Был…
Введение
В данной статье речь пойдёт о самодельном программаторе ST-Link V2.1.
Всё дело в том, что со временем приходит усталость от пользования дешёвыми китайскими программаторами ST-Link V2. У них нет поддержки SWO (Serial Wire Output), VCO (Virtual COM Port) и MSC (Mass Storage Class). Покупать оригинальный программатор ST-Link V2 совсем не тянет, тратить в 10 раз больше практически за те же возможности, что у китайского программатора, тоже не вариант.
Сущетсвует также ST-Link V3, он сомещает все те функции, которых лишён ST-Link V2. но цена его просто космос.
Подробнее см. Сравнение с аналогами.
Поэтому со временем возможно каждому приходит потребность как-то выкручиваться и делать себе модифицированный программатор. Кто-то делает ST-Link V2.1 из китайского «свистка» путём разрезания дорожек и напаивания дополнительных проводов и подтягивающего резистора, кто-то делает j-link программатор из BluePill и т.д. Можно конечно ещё себе купить DISCOVERY или NUCLEO с встроенным ST-Link V2-1 и вообще горя не знать. Это и программатор почти со всеми возможностями, и универсальная плата для разных семейств STM32. Однако снова же, цена…
Ссылки на другие статьи Хабр по модификации ST-Link V2 в версию V2.1
В связи с вышеизложенным было принято решение сделать себе полноценный, практичный и надёжный программатор ST-Link V2.1. Особенности: интерфейс SWD, функция виртуального COM-порта, поддержка SWO, функция MSC (mass storage class), низкая цена (4-5$ за плату).
Нюанс стоимости
Конечно, в реальности делать платы, это где-то 15$ за 10 штук + компоненты где-то 30-35$ на все платы, если нужно кому-то отослать по почте — ещё сверху стоимость упаковки и отправки. Если всё сложить и высчитать примерную стоимость отправки кому-нибудь в любую точку Земного шара по почте, затем разделить на 10 (кол-во плат) получим среднюю стоимость платы: 5$ с учётом того, что паять придётся самому, при желании можно отправить уже запаянную, но это дороже.
Краткий обзор оригинального ST-Link V2-1 в платах NUCLEO
Прежде чем разбирать самодельный ST-Link V2.1, взглянем на оригинальную схему принципиальную данного программатора входящего в состав платы NUCLEO и DISCOVERY:
Рассматривать схему здесь может быть неудобно, все материалы есть на GitHub.
Рассмотрим основные моменты:
-
Собран на базе STM32F103CBT6. Версия «CB» использована потому, что у всем привычного «С8» не хватит памяти для загрузки прошивки «STM32+MSD+VCP». В дешёвый «С8» хорошо вмещается прошивка «STM32+STM8», чем успешно пользуются китайцы, делая свои дешёвые «свистки»;
-
Интерфейс программирования: SWD;
-
Подтяжка к +D (DP) шины USB делается через транзистор. Это сделано для возможности аппаратного переподключения программатора через USB. Это обычный кусок в схеме, но китайцы им не пользуются.
-
Использован бедный разъём micro-USB без защиты от статического напряжения (об этом позже).
В целом всё, ничего особенного за исключением отсутствия возможности отладки по SWO.
Обзор самодельного ST-Link V2.1
1. Анализ схемы электрической принципиальной
За основу схемы электрической принципиальной был взят строенный в NUCLEO ST-Link. Что-то было скопировано, что-то добавлено или модифицировано:
Рассматривать схему здесь может быть неудобно, все материалы есть на GitHub.
Рассмотрим отличные особенности самодельного ST-Link V2.1:
-
Разъём USB Type C с защитой от статического напряжения (вещь маленькая и копеечная, но стоит того);
-
Есть поддержка VCP и добавлена индикация передачи данных по линии RX, TX;
-
Добавлены диоды Шоттки на линию +5В и +3.3В для защиты от переполюсовки. Если нужно исключить диоды и падение напряжение, параллельно им добавлены перемычки;
-
Имеется вывод SWO на краевом разъёме (printf теперь реальность);
-
Имеется кнопка отключения программатора от ПК по линии USB.
Сравнение с аналогами
1. Достоинства и недостатки китайского ST-Link V2
Достоинства китайского ST-Link V2:
-
Подходит для программирования STM32 и STM8;
-
Дешёвый и легко доступный;
-
И всё, прикиньте.
Недостатки китайского ST-Link V2:
-
Отсутствие вывода SWO (Serial Wire Output). Любителей использовать внутренний терминал и функцию printf() увы данный программатор сильно разочарует, а у новичков нередко данный факт вызывал желение забросить изучение такой замечательной сфере деятельности.
-
Отсутствие выводов под UART (Universal Asynchronous Receiver Transmitter): RX и TX. Отсюда следует, что Вам не доступен VCO (Virtual COM Port) и это на самом деле крик души, ибо это надёжный и удобный способ ввода/вывода информации. Тем более, особенно когда начинающие смотрят примеры в интернете, скорее пример кода написан на HAL с использованием функции HAL_UART_Transmit() для вывода информации в терминал. Увы…
-
Очень неудобен в использовании: программатор нужно сразу втыкать в разъём компьютера (или придётся обзавестить хорошим экранированным USB-USB удлинителем). Далее ведём китайские проводки к микроконтроллеру, по пути 100500 раз их перекрещивая, поскольку выводы на программаторе растрассированы таким образом, что нельзя взять 4 провода и провести их эстетично напрямую к отладочной плате BluePill или BlackPill, или иной другой. Почему бы китайцам не установить разъём USB Type-C на программатор, чтобы можно было подключиться через длинный уже универсальный кабель, а также сделать нормальнную трассировку своего программатора.
«C’mon, you sell thousands of st-links from AliExpress to all over the world and you can’t develop new better version? This will take about 2 hours at all, guys!»
Random User
-
Не оригинальный камень STM32 в 95% программаторах. Часто могут возникать проблемы с отказом ПК определить данный программатор по USB. Кроме этого китайцы часто отправляют уже бракованный программатор, не убедившись в его исправности перед отправкой. Более того, пайка и сборка корпуса данного программатора зачастую оставляет желать лучшего: может быть плохо запаен USB разъём, из-за чего при снятии металлического корпуса разъём будет болтаться, пока не оторвутся контактные площадки с дорожками.
2. Достоинства и недостатки оригинального ST-Link V2
Достоинства:
-
Подходит для программирования STM32 и STM8;
-
Доступно два интерфейса программирования: SWD и JTAG;
-
Можно подключить через кабель mini-USB Type B к ПК.
Недостатки:
-
Высокая цена (от 20$);
-
Нет VSP, MSD и SWO.
-
Разъём подключения mini-USB Type B без защиты от статического напряжения.
3. Достоинства и недостатки оригинального ST-Link V3
Достоинства:
-
Подходит для программирования STM32 и STM8;
-
Можно подключить через кабель micro-USB к ПК;
-
Доступно два интерфейса программирования: SWD и JTAG;
-
Доступен VCP.
Недостатки:
-
Высокая цена (от 50$);
-
Нет поддержки SWO;
-
Разъём подключения micro-USB Type B без защиты от статического напряжения.
На запрос «Купить ST-Link V3 недорого» выбивиает это:
Смотреть другие источники не имеет смысла, на чип дип цена от 100$ до 200$ в других магазинах не лучше.
Прошивка программатора
На GitHub есть бутлоадер, скачиваете его и заливаете в камень через любой имеющийся ST-Link под рукой. Обновление программатора делаем по типу уже имеющихся статей на Хабр:
https://habr.com/ru/articles/442290/
Подведение итогов
В целом всё, все материалы есть на GitHub: схема принципиальная, гербер файлы, бутлоадер, драйвера и установочник ST-Link Utility v4.3, по схеме и фотографиям видны элементы, которые нужно установить.
Я не стал забивать статью кучей разной информацией, поскольку тема не является сложной, а по материлам на GitHub понятны особенности программатора, методика изготовления и отладки. Кроме всего я добавил файл корпуса для печати на 3Д принтере. Выглядит он так:
Существует более свежая версия данного программатора от того же автора, я лично ей не пользовался, она ничем не отличается от этой, краевым разъёмом. На мой взгляд описываемая версия будет удобнее своим краевым разъёмом. Вот ссылка для сравнения.
Если вам чего-то не хватает в данной статье, пишите комментарии я дополню её дополнительными главами при необходимости.
P.S. Данная статья не вышла бы, если бы не просьба моих читателей. Спасибо за вашу активность!
Только зарегистрированные пользователи могут участвовать в опросе. Войдите, пожалуйста.
Каким программатором пользуетесь Вы?
20%
Оригинальный ST-Link V2
26
60.77%
Китайский ST-Link V2
79
24.62%
Используете плату NUCLEO или DISCOVERY с встроенным ST-Link
32
10.77%
Прошиваете через USB в режиме DFU
14
12.31%
Прошиваете через UART
16
10%
Собираюсь сделать себе описываемый программатор в статье
13
Проголосовали 130 пользователей.
Воздержались 11 пользователей.
St link v2 — это программатор и отладочный интерфейс для микроконтроллеров семейства STM32. Он позволяет прошивать и отлаживать микроконтроллеры, а также подключаться к ним через интерфейсы JTAG или SWD. St link v2 является одним из наиболее популярных и доступных программаторов для работы с микроконтроллерами STM32.
Для работы с St link v2 необходимо установить соответствующие драйверы и обновления. Вы можете скачать их с официального сайта производителя. Драйверы обычно предоставляются в виде исполняемого файла, который нужно запустить и следовать инструкциям на экране для установки. Обновления также рекомендуется скачивать и устанавливать с официального сайта, чтобы быть уверенным в их правильности и совместимости с вашей версией St link v2.
Важно отметить, что перед установкой драйверов и обновлений, рекомендуется отключить St link v2 от компьютера. Подключайте его только после завершения процесса установки.
После установки драйверов и обновлений, можно приступить к настройке и использованию St link v2. Подключите программатор к компьютеру с помощью USB-кабеля и к микроконтроллеру с помощью интерфейсов JTAG или SWD. Затем запустите программу-отладчик для работы с STM32 и выберите St link v2 в качестве интерфейса. В программе вы сможете прошивать микроконтроллер, устанавливать точки останова, отлаживать код и многое другое.
В заключение, St link v2 — это мощный и универсальный инструмент для разработки и отладки микроконтроллеров STM32. Установка драйверов и обновлений обеспечивает его корректную работу. Не забывайте также проверять официальный сайт производителя для получения последних версий драйверов и обновлений.
Содержание
- ST Link V2 прошивка STM32: скачать драйверы и обновления
- Установка и обновление драйверов
- Настройка и использование ST Link V2
ST Link V2 прошивка STM32: скачать драйверы и обновления
ST Link V2 — это программатор/отладчик, разработанный компанией STMicroelectronics для работы с микроконтроллерами STM32. Для его использования требуется правильная прошивка и установка драйверов.
Драйверы ST Link V2 можно скачать с официального сайта компании STMicroelectronics. На сайте доступны драйверы для различных операционных систем, таких как Windows, Linux и MacOS. Для загрузки драйверов необходимо перейти на страницу поддержки продукта на сайте компании и выбрать соответствующую операционную систему.
После загрузки драйверов следует установить их на компьютер. Для этого запустите загруженный файл и следуйте инструкциям установщика.
После установки драйверов можно приступить к прошивке ST Link V2. Для этого необходимо загрузить последнюю версию прошивки с официального сайта STMicroelectronics. Обновления прошивки рекомендуется устанавливать для улучшения функциональности и исправления ошибок.
Процесс прошивки ST Link V2 довольно простой, но требует некоторых навыков работы с компьютером. Важно следовать инструкциям, предоставляемым вместе с прошивкой, чтобы избежать возможных проблем.
После успешной прошивки ST Link V2 готов к использованию с микроконтроллерами STM32. Он может быть подключен к компьютеру через USB и использован для программирования и отладки микроконтроллеров. Для работы с ST Link V2 также может понадобиться специальное программное обеспечение, такое как IDE или инструменты разработки STM32Cube.
В заключение, для использования ST Link V2 с микроконтроллерами STM32 необходимо правильно прошить программатор, установить драйверы и использовать соответствующее программное обеспечение. Следование инструкциям и обновление прошивки и драйверов поможет обеспечить стабильную и надежную работу.
Установка и обновление драйверов
Для использования ST Link V2 необходимо установить драйверы на ваш компьютер. Драйверы позволяют установить соединение между ST Link V2 и вашим микроконтроллером STM32.
Шаги по установке драйверов ST Link V2 на Ваш компьютер:
- Скачайте драйверы для ST Link V2 . Вы можете скачать их с официального сайта производителя либо с других доверенных ресурсов. Убедитесь, что вы загрузили драйверы, соответствующие операционной системе вашего компьютера.
- Распакуйте скачанный файл драйверов, если он упакован в архив. Проверьте содержимое папки и убедитесь, что все необходимые файлы присутствуют.
- Подключите ST Link V2 к своему компьютеру с помощью USB-кабеля. Ваш компьютер должен автоматически обнаружить новое устройство, но не сможет найти для него драйверы.
- Откройти Диспетчер устройств на вашем компьютере. Вы можете найти его в Панели управления или в Поиске.
- Найдите раздел «Порты (COM и LPT)» в Диспетчере устройств. Вы увидите ST Link V2, отмеченное восклицательным знаком или другим символом, что свидетельствует об отсутствии драйверов.
- Щелкните правой кнопкой мыши по ST Link V2 и выберите «Обновить драйвер».
- Выберите «Обновление драйвера программного обеспечения» и выберите папку с распакованными драйверами.
- Дождитесь завершения процесса установки драйверов. В ходе установки могут появиться предупреждения безопасности — подтвердите установку драйверов, если они появятся.
- После завершения установки драйверов перезагрузите ваш компьютер. После перезагрузки драйверы должны быть успешно установлены и готовы к использованию.
Теперь, после установки драйверов, вы можете использовать ST Link V2 для прошивки и отладки микроконтроллеров STM32. Убедитесь, что ваша среда разработки настроена на использование ST Link V2 как основного инструмента.
Настройка и использование ST Link V2
ST Link V2 — это программатор-отладчик, который используется для программирования и отладки микроконтроллеров STM32. Данное устройство позволяет прошивать микроконтроллеры и периферийные устройства, а также отлаживать код и мониторить работу программы на уровне регистров и переменных.
Для начала использования ST Link V2 вам понадобятся драйверы. Вы можете скачать последнюю версию драйверов с официального сайта производителя или использовать пакет установки STM32CubeProg, который уже содержит необходимые драйверы.
После установки драйверов подключите ST Link V2 к компьютеру с помощью USB-кабеля. Убедитесь, что устройство правильно распознано операционной системой и отображается в списке подключенных устройств.
Для начала работы с ST Link V2 вам понадобится программа-клиент для управления программатором. Один из самых популярных инструментов — это стандартная программа STM32CubeProg, которая предоставляется производителем. Вы можете скачать ее с официального сайта.
После установки STM32CubeProg запустите программу. В верхней части окна вы увидите список доступных устройств. Если ваш ST Link V2 правильно подключен, он должен быть виден в списке. Если его не видно, проверьте правильность подключения и установленные драйверы.
Для настройки ST Link V2 выберите его в списке устройств и нажмите на кнопку «Настройка». В открывшемся окне вы сможете выбрать различные настройки программатора, такие как скорость передачи данных, целевую платформу и другие параметры. Вы можете оставить настройки по умолчанию или изменить их по своему усмотрению.
После настройки ST Link V2 вы готовы к использованию. Вы можете открыть проект STM32Cube в программе STM32CubeProg и начать прошивку или отладку вашего кода. Программа предоставляет широкие возможности для работы с микроконтроллером: прошивка различных файлов, чтение и запись памяти, отладка с помощью точек останова и многое другое.
ST Link V2 также поддерживает интеграцию с другими IDE, такими как Keil, IAR Embedded Workbench и другие. Вы можете использовать ST Link V2 вместе с вашей любимой средой разработки, настроив ее для работы с программатором.
В заключение, ST Link V2 — это мощный инструмент для программирования и отладки микроконтроллеров STM32. Он обладает широкими возможностями, прост в использовании и поддерживается производителем. С его помощью вы сможете эффективно разрабатывать и отлаживать свои проекты на базе STM32.
разделы: STM32 , STM32duino , среда разработки , дата: 14 октября 2016г.
рекомендуется к прочтению
Архитектуру STM32 можно мысленно разделить на две части. Первая часть, это ядро Cortex-M3, которое спроектировали в ARM и которое примерно одинаковое для всех. «Примерно», потому что, содержит опциональные модули которые могут быть у одного производителя и отсутствовать у другого. Вторая часть, это периферия знакомая по STM8, с тем отличием, что был добавлен USB2.0 интерфейс, хотя точнее было бы сказать, что этот интерфейс был «откручен» от STM8(такая у STM политика: хочешь аппаратный USB, используй STM32).
-
Справочники и руководства которые нужны для работы c STM32F103x8/STM32F103xB:
-
Справочное руководство по 32-битным микроконтроллерам серий STM32F10x Reference Manual. STM32F101xx, STM32F102xx, STM32F103xx, STM32F105xx and STM32F107xx advanced ARM®-based 32-bit MCUs
или RM 0008 - Руководство на чипы STM32F103x8/STM32F103xB STM32F103x8 STM32F103xB Medium-density performance line ARM®-based 32-bit MCU with 64 or 128 KB Flash, USB, CAN, 7 timers, 2 ADCs, 9 com. interfaces
- Ядро Cortex — МЗ компании ARM. Полное руководство. Книга не обязательная, но на мой взгляд очень полезная.
- Небльшой ликбез по ARM и Cortex-M3 в частности:
- Cortex-M3 основан на архитектуре ARMv7 и является усеченным вариантом архитектуры ARMv7 специально для микроконтроллеров. По сравнению с полноценным ЦПУ Cortex-A, здесь отсутствует кеш и 32-битный альтернативный набор команд ARM. Также могут отсутствовать некоторые модули, такие как модуль зашиты памяти — MPU (Memory Protect Unit).
- Cortex-M3 включает в себя 16-битный набор команд, оптимизированный для систем с малым объемом памяти, Thumb и 32-битный дополнительный набор Thumb-2. Здесь 16-битная команда означает, что ее двоичное представление будет занимать в памяти 16-бит, т.е. она более компактная. Программный код может состоять из произвольного набора 16-битных команд Thumb и 32-битных Thumb 2.
- В Cortex-M3 имеется аппаратное деление и умножение. Урезанная, удешевленная версия Cortex-M0 базируется на архитектуре ARMv6 и таких инструкций не имеет. ARMv6 отличается от ARMv7 отсутствием набора инструкций Thumb-2. Cortex-M4, напротив, дополнен DSP модулем, а Cortex-M4F также включает в себя FPU модуль, т.е. он аппаратно поддерживает числа с плавающей запятой.
- Номера процессоров ARM никак не согласованы с версиями архитектур. Процессоры ARM11 имеют архитектуру ARMv6, а ARM9 имели архитектуру ARMv4.
- Cortex-M3 имеет единую адресную 32-битную шину, которая может адресовать 4Гб памяти. Процессор построен по гарвардской архитектуре и имеет отдельные шины для памяти данных SRAM и памяти программ Flash. Программа может быть запущена из SRAM, тогда будет задействована только одна шина и код будет выполняться медленнее.
- Cortex-M3 имеет шестнадцать 32-битных РОН (регистров общего назначения) R0-R15. Команды из набора инструкций Thumb могут обращаться только к регистрам R0-R7. Команды из набора Thumb-2 могут обращаться ко всем регистрам. При этом, регистр r13 — это указатель стека, r14 — регистр связи(хранит адрес возврата из подпрограммы), r15 — счетчик команд.
Немного о STM32:
Выпускаемые линейки микроконтроллеров изображены на следующей картинке:
Это не полный перечень, но представление давать должен. Кроме линеек, микроконтроллеры делятся по размерам flash-памяти. Чем больше flash-пямять, тем больше остальной периферии. Для 103-й линейки это выглядит так:

Блок-схема устройства STM32F103 представлена на картинке ниже:

Во всем этом хозяйстве нас будет больше всего интересовать периферия подключенная к периферийным шинам APB1 и APB2. Также полезно будет запомнить внутреннюю шину AHB.
Имеющаяся в чипах периферия перечислена в следующей табличке:

Выбор «железа»
Чип который у меня оказался под рукой — STM32F103CBT6 запаянный в плату Maple Mini:

Заказав его год назад на Али, я ради интереса загрузил в него несколько скетчей, и набалововшись бросил на полку. За этот год проект Leaf Maple накрылся медным тазом, сайт поменял содержимое, а поддержку железа передали на следующий форум: STM32 for Arduino. Я особо не расстроился, т.к. не питал особых надежд на этот проект, и планировал плату использовать для Си-программирования.
Кстати, на упомянутом выше сайте есть хороший классификатор с образчиками результатов работы китайской промышленности, содержащих чипы STM32F103, очень рекомендую ознакомится: STM32F103 boards
Если у кого-то имеется под рукой «Blue Pill», то это не беда, там установлен чип STM32F103C8T6 который от STM32F103CBT6 отличается только уменьшенным до 64кБ размером flash-памяти. Еще там светодиод подключен на PC13, в то время как на MapleMini он на PB1, и кроме этого у Maple Mini имеется кнопка на PB8.

Зато на «Blue Pill» имеется штыревой разъем для подключения программатора ST-LINK, в то время как Maple Mini нужно устанавливать в макетку что бы прошить по SWD. Прозвонкой чипа было выяснено, что на Mapple Mini SWDIO контакт «висит» на 22-pin, а SWCLK на 21-м. Но заставить работать ST-LINK с Maple Mini оказалось не просто.
Прошивка чипов через программатор ST-LINK v2
STM32 можно прошить либо через UART встроенным загрузчиком, либо через SWD-интерфейс программатором ST-LINK. Меня интересовал второй вариант, т.к. был скромным владельцем клона ST-LINK v2.

В Windows прошить STM32 через ST-LINK можно воспользовавшись фирменной утилитой «STM32 ST-LINK Utility», или непосредственно из среды разработки IAR for ARM. В Linux можно воспользоваться консольной утилитой sy-flash.
Если у вас «Blue Pill» или еще какая-либо плата отличная от Leaf Maple, то никаких проблем не будет, их можно сразу прошивать. Моя же Maple Mini никак не хотела видеться программатором, пока я не догадался во время загрузки программы из IAR в чип, несколько раз нажать на кнопку Reset на плате. После чего Maple Mini начала свободно прошиваться, но родной USB-загрузчик был на этом этапе потерт. Но это мелочи.
Ок. Посмотрим как чипы прошиваются в Windows. Войдя на сайт http://my.st.com и залогинившись, введем в строку поиска «st-link». На выходе получим такую табличку:

Щелкнув мышкой по второй строчке и промотав открывшуюся страницу книзу, увидим список предлагаемого ПО для программатора:

STSW-LINK004 — это утилита для прошивки STM32 чипов. STSW-LINK007 утилита для обновления прошивки программатора, STSW-LINK009 — драйвера для различных версий Windows. Немного выше предлагаются свежие прошивки для самого программатора. ST-LINK v2.
Как установить драйвер для ST-LINK v2 я рассказывал здесь: STM8 + IAR + ST-LINK2: программирование, прошивка и отладка из под Windows, поэтому далее будем считать, что драйвер уже установлен.
После установки и запуска «STM32 ST-LINK Utility» следует подключить ST-LINK v2 к компьютеру или виртуальной машине(мой случай), а к ST-LINK в свою очередь, должен быть подключен чип который следует прошить:

После чего следует пройти по меню: «меню-> Target — > Settings…» и должно появится такое окно:

Во-первых, сам программатор ST-LINK V2 должен быть опознан программой, показана версия его прошивки. Во-вторых должен быть опознан чип подключенный к программатору. В третьих, рабочий протокол должен быть установлен как SWD, а не JTAG.
Когда я впервые воткнул ST-LINK полученный год назад с Али, мне вместо номера прошивки показывало что-то вроде «Old firmware», поэтому мне пришлось воспользоваться утилитой обновления прошивки ST-LINK, что бы флешеры нормально работали с моим клоном ST-LINK. К сожалению у меня не сохранились скрины.

Здесь у меня изначальная версия прошивки(цифра после буквы J) была то ли 20, то ли 21. В итоге меня обновили то текущей версии. Кстати, из под виртуальной машины обновляется прошивка без проблем.
Вернемся к STM32 ST-LINK Utility. После нажатия кнопки «Ок» в окне «Settings», появится рабочее окно программы:

Следует запомнить, что стартовый адрес флеш-памяти начинается с 0x08000000. Встроенная оперативка начинается c 0x20000000. Чтобы программа стартовала с оперативки, контакты boot0 и boot1 должны быть сконфигурированы специальным образом.
Щелкнув по вкладке «binary file» можно выбрать файл с прошивкой, затем пройдя по «меню->Target->Program…» эту прошивку можно прошить в микроконтроллер:

Наряду со знакомым форматом прошивок HEX, в stm32 широко используется бинарный raw-формат «*.bin».
Через меню «File->Save As» можно сохранить прошивку чипа в файл:

Если честно, слить пошивку с чипа и потом залить ее обратно так, чтобы она работала, мне не удалось. Нужно будет разбираться.
Еше интересной штукой являются Option Bytes знакомые по STM8:

Пока не будем их трогать.
Теперь, что касается st-flash для Linux, то там с одной стороны все проще, а с другой — сложнее. Сложнее, потому что глючит. Может к этим глюкам как-то можно привыкнуть, но я пока не сумел.
darkstar:~: st-flash
invalid command line
stlinkv1 command line: ./st-flash [--debug] [--reset] [--format ] {read|write} /dev/sgX
stlinkv1 command line: ./st-flash [--debug] /dev/sgX erase
stlinkv2 command line: ./st-flash [--debug] [--reset] [--serial ] [--format ] {read|write}
stlinkv2 command line: ./st-flash [--debug] [--serial ] erase
Use hex format for addr, and .
Format may be 'binary' (default) or 'ihex', although must be specified for binary format only.
удачная прошивка:
st-flash write ./blink.bin 0x08000000 2016-10-11T09:02:47 INFO /home/flanker/mydev/tools/stlink/src/common.c: Loading device parameters.... 2016-10-11T09:02:47 INFO /home/flanker/mydev/tools/stlink/src/common.c: Device connected is: F1 Medium-density device, id 0x20036410 2016-10-11T09:02:47 INFO /home/flanker/mydev/tools/stlink/src/common.c: SRAM size: 0x5000 bytes (20 KiB), Flash: 0x20000 bytes (128 KiB) in pages of 1024 bytes 2016-10-11T09:02:47 INFO /home/flanker/mydev/tools/stlink/src/common.c: Attempting to write 5832 (0x16c8) bytes to stm32 address: 134217728 (0x8000000) Flash page at addr: 0x08001400 erased 2016-10-11T09:02:48 INFO /home/flanker/mydev/tools/stlink/src/common.c: Finished erasing 6 pages of 1024 (0x400) bytes 2016-10-11T09:02:48 INFO /home/flanker/mydev/tools/stlink/src/common.c: Starting Flash write for VL/F0/F3 core id 2016-10-11T09:02:48 INFO /home/flanker/mydev/tools/stlink/src/flash_loader.c: Successfully loaded flash loader in sram 5/5 pages written 2016-10-11T09:02:49 INFO /home/flanker/mydev/tools/stlink/src/common.c: Starting verification of write complete 2016-10-11T09:02:49 INFO /home/flanker/mydev/tools/stlink/src/common.c: Flash written and verified! jolly good!
неудачная прошивка:
st-flash write ./blink.bin 0x08000000 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Loading device parameters.... 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Device connected is: F1 Medium-density device, id 0x20036410 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: SRAM size: 0x5000 bytes (20 KiB), Flash: 0x20000 bytes (128 KiB) in pages of 1024 bytes 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Attempting to write 5832 (0x16c8) bytes to stm32 address: 134217728 (0x8000000) Flash page at addr: 0x08001400 erased 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Finished erasing 6 pages of 1024 (0x400) bytes 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Starting Flash write for VL/F0/F3 core id 2016-10-11T09:05:50 INFO /home/flanker/mydev/tools/stlink/src/flash_loader.c: Successfully loaded flash loader in sram 2016-10-11T09:06:56 ERROR /home/flanker/mydev/tools/stlink/src/flash_loader.c: flash loader run error 2016-10-11T09:06:56 ERROR /home/flanker/mydev/tools/stlink/src/common.c: stlink_flash_loader_run(0x8000000) failed! == -1 stlink_fwrite_flash() == -1
Пока я обнаружил такую закономерность, команда очистки флеш-памяти «st-flash erase» помогает избавиться от глюков:

Программирование STM32 с помощью IAR и SPL в Windows
Если на сайте http://my.st.com ввести в строку поиска «stm32f10x standard peripheral library» то нам предложат скачать SPL для чипов STM32F10x:

В отличии от SPL для STM8, библиотека разделена на CMSIS и саму SPL. CMSIS (Cortex® Microcontroller Software Interface Standard) — это стандарт описания периферии микроконтроллера, то что в STM8 размещалось в файлах stm8s.h/stm8l.h
Подключить SPL к IAR достаточно просто, в сети множество видео и пошаговых инструкций. Я лично делал по этому видео:
STM32 Discovery IAR and StdPeriph Lib настройка и загрузка проекта
Исходник Blink:
#include "stm32f10x.h" void dummy_loop(uint32_t count){ while(--count); } int main() { RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); GPIO_InitTypeDef GPIO_InitStructure; GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOB, &GPIO_InitStructure); for(;;){ GPIO_SetBits(GPIOB,GPIO_Pin_1); dummy_loop(600000); GPIO_ResetBits(GPIOB,GPIO_Pin_1); dummy_loop(600000); }
Проект компилируется и заливается в чип, после чего успешно работает. Наверное больше и не надо, но я предлагаю забрать результирующий объектный файл с расширением *.out и перенести его в Linux, для внимательного изучения:

Программирование STM32 с помощью Eclipse и SPL в Linux
В Linux попробуем посмотреть, что за файл генерирует на выходе IAR:
$ file ./first_project.out ./first_project.out: ELF 32-bit LSB executable, ARM, EABI5 version 1 (SYSV), statically linked, not stripped
Как видим, это обыкновенный эльф. Смотрим дальше:
$ arm-none-eabi-readelf ./first_project.out -A Attribute Section: aeabi File Attributes Tag_conformance: "2.10" Tag_CPU_arch: v7 Tag_CPU_arch_profile: Microcontroller Tag_THUMB_ISA_use: Thumb-2 Tag_PCS_config: Bare platform Tag_ABI_align_needed: 8-byte Tag_ABI_align_preserved: 8-byte, except leaf SP Tag_ABI_enum_size: small Tag_ABI_VFP_args: compatible Tag_CPU_unaligned_access: v6 Tag_DIV_use: Not allowed
Из «эльфа» мы всегда можем получить файл прошивки в HEX формате:
arm-none-eabi-objcopy ./first_project.out -O ihex ./first_project.hex
или бинарный файл:
arm-none-eabi-objcopy ./first_project.out -O binary ./first_project.bin
Также можно посмотреть ассемблерный код:
$ arm-none-eabi-objdump ./first_project.out -S > ./first_project.asm
показать ассемблерный код
./first_project.out: file format elf32-littlearm
Disassembly of section A0 rw:
08000000 <__vector_table>:
8000000: 00 08 00 20 d9 01 00 08 a7 01 00 08 a9 01 00 08 ... ............
8000010: ab 01 00 08 ad 01 00 08 af 01 00 08 00 00 00 00 ................
...
800002c: b1 01 00 08 b3 01 00 08 00 00 00 00 b5 01 00 08 ................
800003c: b7 01 00 08 ....
Disassembly of section P1 ro:
08000040 <GPIO_Init>:
8000040: b470 push {r4, r5, r6}
8000042: 2200 movs r2, #0
8000044: 2500 movs r5, #0
8000046: 2300 movs r3, #0
8000048: 2600 movs r6, #0
800004a: 2400 movs r4, #0
800004c: 2500 movs r5, #0
800004e: 78ca ldrb r2, [r1, #3]
8000050: f012 020f ands.w r2, r2, #15
8000054: 78cb ldrb r3, [r1, #3]
8000056: 06db lsls r3, r3, #27
8000058: d501 bpl.n 800005e <GPIO_Init+0x1e>
800005a: 788b ldrb r3, [r1, #2]
800005c: 431a orrs r2, r3
800005e: 780b ldrb r3, [r1, #0]
8000060: 061b lsls r3, r3, #24
8000062: d021 beq.n 80000a8 <GPIO_Init+0x68>
8000064: 6804 ldr r4, [r0, #0]
8000066: 2300 movs r3, #0
8000068: e006 b.n 8000078 <GPIO_Init+0x38>
800006a: 78cd ldrb r5, [r1, #3]
800006c: 2d48 cmp r5, #72 ; 0x48
800006e: d102 bne.n 8000076 <GPIO_Init+0x36>
8000070: 2501 movs r5, #1
8000072: 409d lsls r5, r3
8000074: 6105 str r5, [r0, #16]
8000076: 1c5b adds r3, r3, #1
8000078: 2b08 cmp r3, #8
800007a: d214 bcs.n 80000a6 <GPIO_Init+0x66>
800007c: 2501 movs r5, #1
800007e: fa15 f603 lsls.w r6, r5, r3
8000082: 880d ldrh r5, [r1, #0]
8000084: 4035 ands r5, r6
8000086: 42b5 cmp r5, r6
8000088: d1f5 bne.n 8000076 <GPIO_Init+0x36>
800008a: 009e lsls r6, r3, #2
800008c: 250f movs r5, #15
800008e: 40b5 lsls r5, r6
8000090: 43ac bics r4, r5
8000092: fa12 f506 lsls.w r5, r2, r6
8000096: 432c orrs r4, r5
8000098: 78cd ldrb r5, [r1, #3]
800009a: 2d28 cmp r5, #40 ; 0x28
800009c: d1e5 bne.n 800006a <GPIO_Init+0x2a>
800009e: 2501 movs r5, #1
80000a0: 409d lsls r5, r3
80000a2: 6145 str r5, [r0, #20]
80000a4: e7e7 b.n 8000076 <GPIO_Init+0x36>
80000a6: 6004 str r4, [r0, #0]
80000a8: 880b ldrh r3, [r1, #0]
80000aa: 2bff cmp r3, #255 ; 0xff
80000ac: dd26 ble.n 80000fc <GPIO_Init+0xbc>
80000ae: 6844 ldr r4, [r0, #4]
80000b0: 2300 movs r3, #0
80000b2: e020 b.n 80000f6 <GPIO_Init+0xb6>
80000b4: 2501 movs r5, #1
80000b6: f113 0608 adds.w r6, r3, #8
80000ba: fa15 f606 lsls.w r6, r5, r6
80000be: 880d ldrh r5, [r1, #0]
80000c0: 4035 ands r5, r6
80000c2: 42b5 cmp r5, r6
80000c4: d116 bne.n 80000f4 <GPIO_Init+0xb4>
80000c6: 009e lsls r6, r3, #2
80000c8: 250f movs r5, #15
80000ca: 40b5 lsls r5, r6
80000cc: 43ac bics r4, r5
80000ce: fa12 f506 lsls.w r5, r2, r6
80000d2: 432c orrs r4, r5
80000d4: 78cd ldrb r5, [r1, #3]
80000d6: 2d28 cmp r5, #40 ; 0x28
80000d8: d104 bne.n 80000e4 <GPIO_Init+0xa4>
80000da: 2501 movs r5, #1
80000dc: f113 0608 adds.w r6, r3, #8
80000e0: 40b5 lsls r5, r6
80000e2: 6145 str r5, [r0, #20]
80000e4: 78cd ldrb r5, [r1, #3]
80000e6: 2d48 cmp r5, #72 ; 0x48
80000e8: d104 bne.n 80000f4 <GPIO_Init+0xb4>
80000ea: 2501 movs r5, #1
80000ec: f113 0608 adds.w r6, r3, #8
80000f0: 40b5 lsls r5, r6
80000f2: 6105 str r5, [r0, #16]
80000f4: 1c5b adds r3, r3, #1
80000f6: 2b08 cmp r3, #8
80000f8: d3dc bcc.n 80000b4 <GPIO_Init+0x74>
80000fa: 6044 str r4, [r0, #4]
80000fc: bc70 pop {r4, r5, r6}
80000fe: 4770 bx lr
08000100 <GPIO_SetBits>:
8000100: b289 uxth r1, r1
8000102: 6101 str r1, [r0, #16]
8000104: 4770 bx lr
08000106 <GPIO_ResetBits>:
8000106: b289 uxth r1, r1
8000108: 6141 str r1, [r0, #20]
800010a: 4770 bx lr
0800010c <dummy_loop>:
800010c: 1e40 subs r0, r0, #1
800010e: 2800 cmp r0, #0
8000110: d1fc bne.n 800010c <dummy_loop>
8000112: 4770 bx lr
08000114 <main>:
8000114: b580 push {r7, lr}
8000116: 2101 movs r1, #1
8000118: 2008 movs r0, #8
800011a: f000 f821 bl 8000160 <RCC_APB2PeriphClockCmd>
800011e: 2002 movs r0, #2
8000120: f8ad 0000 strh.w r0, [sp]
8000124: 2003 movs r0, #3
8000126: f88d 0002 strb.w r0, [sp, #2]
800012a: 2010 movs r0, #16
800012c: f88d 0003 strb.w r0, [sp, #3]
8000130: 4669 mov r1, sp
8000132: 480a ldr r0, [pc, #40] ; (800015c <.text_4>)
8000134: f7ff ff84 bl 8000040 <GPIO_Init>
8000138: 2102 movs r1, #2
800013a: 4808 ldr r0, [pc, #32] ; (800015c <.text_4>)
800013c: f7ff ffe0 bl 8000100 <GPIO_SetBits>
8000140: f64e 2060 movw r0, #60000 ; 0xea60
8000144: f7ff ffe2 bl 800010c <dummy_loop>
8000148: 2102 movs r1, #2
800014a: 4804 ldr r0, [pc, #16] ; (800015c <.text_4>)
800014c: f7ff ffdb bl 8000106 <GPIO_ResetBits>
8000150: f64e 2060 movw r0, #60000 ; 0xea60
8000154: f7ff ffda bl 800010c <dummy_loop>
8000158: e7ee b.n 8000138 <main+0x24>
...
0800015c <.text_4>:
800015c: 40010c00 .word 0x40010c00
08000160 <RCC_APB2PeriphClockCmd>:
8000160: b2c9 uxtb r1, r1
8000162: 2900 cmp r1, #0
8000164: d005 beq.n 8000172 <RCC_APB2PeriphClockCmd+0x12>
8000166: 4906 ldr r1, [pc, #24] ; (8000180 <.text_53>)
8000168: 6809 ldr r1, [r1, #0]
800016a: 4308 orrs r0, r1
800016c: 4904 ldr r1, [pc, #16] ; (8000180 <.text_53>)
800016e: 6008 str r0, [r1, #0]
8000170: e005 b.n 800017e <RCC_APB2PeriphClockCmd+0x1e>
8000172: 4903 ldr r1, [pc, #12] ; (8000180 <.text_53>)
8000174: 6809 ldr r1, [r1, #0]
8000176: ea31 0000 bics.w r0, r1, r0
800017a: 4901 ldr r1, [pc, #4] ; (8000180 <.text_53>)
800017c: 6008 str r0, [r1, #0]
800017e: 4770 bx lr
08000180 <.text_53>:
8000180: 40021018 .word 0x40021018
08000184 <?main>:
8000184: f000 f80b bl 800019e <__low_level_init>
8000188: 2800 cmp r0, #0
800018a: d001 beq.n 8000190 <_call_main>
800018c: f3af 8000 nop.w
08000190 <_call_main>:
8000190: 2000 movs r0, #0
8000192: f3af 8000 nop.w
8000196: f7ff ffbd bl 8000114 <main>
0800019a <_main>:
800019a: f000 f802 bl 80001a2 <exit>
0800019e <__low_level_init>:
800019e: 2001 movs r0, #1
80001a0: 4770 bx lr
080001a2 <exit>:
80001a2: f000 b809 b.w 80001b8 <_exit>
080001a6 <NMI_Handler>:
80001a6: 4770 bx lr
080001a8 <HardFault_Handler>:
80001a8: e7fe b.n 80001a8 <HardFault_Handler>
080001aa <MemManage_Handler>:
80001aa: e7fe b.n 80001aa <MemManage_Handler>
080001ac <BusFault_Handler>:
80001ac: e7fe b.n 80001ac <BusFault_Handler>
080001ae <UsageFault_Handler>:
80001ae: e7fe b.n 80001ae <UsageFault_Handler>
080001b0 <SVC_Handler>:
80001b0: 4770 bx lr
080001b2 <DebugMon_Handler>:
80001b2: 4770 bx lr
080001b4 <PendSV_Handler>:
80001b4: 4770 bx lr
080001b6 <SysTick_Handler>:
80001b6: 4770 bx lr
080001b8 <_exit>:
80001b8: 4607 mov r7, r0
080001ba <.text_4>:
80001ba: 4638 mov r0, r7
80001bc: f000 f802 bl 80001c4 <__exit>
80001c0: e7fb b.n 80001ba <.text_4>
...
080001c4 <__exit>:
80001c4: b580 push {r7, lr}
80001c6: f3af 8000 nop.w
80001ca: 4a02 ldr r2, [pc, #8] ; (80001d4 <__exit+0x10>)
80001cc: 0011 movs r1, r2
80001ce: 2018 movs r0, #24
80001d0: beab bkpt 0x00ab
80001d2: e7fb b.n 80001cc <__exit+0x8>
80001d4: 00020026 .word 0x00020026
080001d8 <__iar_program_start>:
80001d8: f3af 8000 nop.w
80001dc: f3af 8000 nop.w
80001e0: f7ff ffd0 bl 8000184 <?main>
Даже можно попытаться загрузить на чип в режиме отладки. Для этого понадобиться сервер st-util который входит в набор утилит st-flash и сам отладчик gdb.
Запускаем сервер:
$ st-util 2016-10-12T03:33:50 INFO /home/flanker/mydev/tools/stlink/src/usb.c: -- exit_dfu_mode 2016-10-12T03:33:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Loading device parameters.... 2016-10-12T03:33:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Device connected is: F1 Medium-density device, id 0x20036410 2016-10-12T03:33:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: SRAM size: 0x5000 bytes (20 KiB), Flash: 0x20000 bytes (128 KiB) in pages of 1024 bytes 2016-10-12T03:33:50 INFO /home/flanker/mydev/tools/stlink/src/gdbserver/gdb-server.c: Chip ID is 00000410, Core ID is 1ba01477. 2016-10-12T03:33:50 INFO /home/flanker/mydev/tools/stlink/src/gdbserver/gdb-server.c: Listening at *:4242...
Запускаем отладчик:
$ arm-none-eabi-gdb ./first_project.out GNU gdb (GNU Tools for ARM Embedded Processors) 7.10.1.20160616-cvs Copyright (C) 2015 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Type "show copying" and "show warranty" for details. This GDB was configured as "--host=i686-linux-gnu --target=arm-none-eabi". Type "show configuration" for configuration details. For bug reporting instructions, please see: . Find the GDB manual and other documentation resources online at: . For help, type "help". Type "apropos word" to search for commands related to "word"... Reading symbols from ./first_project.out...done. (gdb)
Подключаемся к ранее запущенному серверу:
(gdb) target remote localhost:4242 Remote debugging using localhost:4242 0x08000220 in ?? () (gdb)
Загружаем прошивку:
(gdb) load Loading section A0 rw, size 0x40 lma 0x8000000 Loading section P1 ro, size 0x1a4 lma 0x8000040 Start address 0x80001d8, load size 484 Transfer rate: 1 KB/sec, 242 bytes/write. (gdb)
Ставим точку останова и запускаем на исполнение:
(gdb) break main Breakpoint 1 at 0x8000116: file C:\Program Files\IAR Systems\project/main.c, line 8. (gdb) continue Continuing. Note: automatically using hardware breakpoints for read-only addresses. Breakpoint 1, main () at C:\Program Files\IAR Systems\project/main.c:8 8 C:\Program Files\IAR Systems\project/main.c: Нет такого файла или каталога. (gdb)
Но при попытке распечатать исходный листинг программы выдаст сообщение об ошибке:
(gdb) list 3 in C:\Program Files\IAR Systems\project/main.c (gdb)
кое-что сделать конечно можно
(gdb) info breakpoint
Num Type Disp Enb Address What
1 breakpoint keep y 0x08000116 in main at C:\Program Files\IAR Systems\project/main.c:8
breakpoint already hit 1 time
(gdb) info registers
r0 0x0 0
r1 0x8000400 134218752
r2 0x0 0
r3 0x23 35
r4 0x40022000 1073881088
r5 0x0 0
r6 0xf484929a 4102328986
r7 0xe03acba1 3761949601
r8 0xfffeef9d 4294897565
r9 0xffffffff 4294967295
r10 0x9ae315e4 2598573540
r11 0xc2eae1f4 3270173172
r12 0xffff7fdf 4294934495
sp 0x200007f8 0x200007f8
lr 0x800019b 134218139
pc 0x8000116 0x8000116
cpsr 0x61000000 1627389952
(gdb) disass
Dump of assembler code for function main:
0x08000114 <+0>: push {r7, lr}
=> 0x08000116 <+2>: movs r1, #1
0x08000118 <+4>: movs r0, #8
0x0800011a <+6>: bl 0x8000160
0x0800011e <+10>: movs r0, #2
0x08000120 <+12>: strh.w r0, [sp]
0x08000124 <+16>: movs r0, #3
0x08000126 <+18>: strb.w r0, [sp, #2]
0x0800012a <+22>: movs r0, #16
0x0800012c <+24>: strb.w r0, [sp, #3]
0x08000130 <+28>: mov r1, sp
0x08000132 <+30>: ldr r0, [pc, #40] ; (0x800015c <.text_4>)
0x08000134 <+32>: bl 0x8000040
0x08000138 <+36>: movs r1, #2
0x0800013a <+38>: ldr r0, [pc, #32] ; (0x800015c <.text_4>)
0x0800013c <+40>: bl 0x8000100
0x08000140 <+44>: movw r0, #60000 ; 0xea60
0x08000144 <+48>: bl 0x800010c
0x08000148 <+52>: movs r1, #2
0x0800014a <+54>: ldr r0, [pc, #16] ; (0x800015c <.text_4>)
0x0800014c <+56>: bl 0x8000106
0x08000150 <+60>: movw r0, #60000 ; 0xea60
0x08000154 <+64>: bl 0x800010c
0x08000158 <+68>: b.n 0x8000138
End of assembler dump.
(gdb) n
13 in C:\Program Files\IAR Systems\project/main.c
(gdb) info registers pc
pc 0x800011e 0x800011e
(gdb)
На этом этапе думаю лучше оставить прошивку с IAR в сторону, и попытаться скомпилировать нормальный объектный файл в Linux.
некоторые не ищут легких путей…
Проблема в том, что нельзя вот так просто взять компилятор, исходный текст и скомпилировать прошивку для stm32. Почему? Потому что в опциях gcc компилятора можно указать только тип архитектуры «cortex-m3», а чипов на этой архитектуре выпускаются различными фирмами — тьма тьмущая. И у всех них разные карты памяти и периферия. Как минимум понадобиться скрипт линкера для вашего чипа.
О масштабах проблемы можно почитать например тут: ARM-ы для самых маленьких: тонкости компиляции и компоновщик. Более-менее толковый самопальный Makefile который мне удалось найти можно взять тут: Еще один шаблон проекта под STM32 на gcc.
После некоторых размышлений я решил взять в качестве основы сборочные файлы из какого-нибудь IDE. Традиционным IDE для ARM в Linux стал Eclipse, который ненавидят наверно все linux-пользователи за глючность и тормознутость. Справедливости ради, должен упомянуть, что генерации проектов существует специальная фирменная утилита STM32CubeMX. Но может ли она генерировать проекты для gcc или нет, я не знаю.
Поддержка ARM в Eclipse ставится через плагин: GNU ARM Eclipse
На странице установки предлагается несколько способов установки ARM плагина. Но, например, на LinuxMint мне этот плагин установить не удалось. В репозитории какая-то древняя версия Eclipse 3.8, это версия от 2012(!) года. И установка плагина заканчивается фейлом:

Поэтому пришлось вспомнить про старую добрую Slackware GNU/Linux. В этом году вышла новая версия 14.2.
Для начала нужно будет скачать ARM toolchain c сайта ARM:

Скачанный архив я распаковал в /usr/local
Теперь чтобы скачать Eclipse, зайдем в репозиторий и введем в строку поиска «eclipse-cpp»:

После чего попадаем на страницу с пакетом:

Т.к. уменя Слакваръ 64-битная, то для установки выполняем следующие манипуляции:
darkstar:~: su Пароль:
darkstar:/home/flanker# cd /tmp
darkstar:/tmp# curl https://slackbuilds.org/slackbuilds/14.2/development/eclipse-cpp.tar.gz|tar xvz
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 6964 100 6964 0 0 8246 0 --:--:-- --:--:-- --:--:-- 8451
eclipse-cpp/
eclipse-cpp/doinst.sh
eclipse-cpp/README
eclipse-cpp/eclipse-cpp.png
eclipse-cpp/eclipse-cpp.info
eclipse-cpp/slack-desc
eclipse-cpp/eclipse-cpp.SlackBuild
eclipse-cpp/eclipse-cpp.desktop
darkstar:/tmp# cd eclipse-cpp/
darkstar:/tmp/eclipse-cpp# wget http://download.eclipse.org/technology/epp/downloads/release/mars/2/eclipse-cpp-mars-2-linux-gtk-x86_64.tar.gz --2016-10-12 14:53:25-- http://download.eclipse.org/technology/epp/downloads/release/mars/2/eclipse-cpp-mars-2-linux-gtk-x86_64.tar.gz Resolving download.eclipse.org (download.eclipse.org)... 198.41.30.199 Connecting to download.eclipse.org (download.eclipse.org)|198.41.30.199|:80... connected. HTTP request sent, awaiting response... 200 OK Length: 191591158 (183M) [application/x-gzip] Saving to: ‘eclipse-cpp-mars-2-linux-gtk-x86_64.tar.gz’ eclipse-cpp-mars-2-linux-gtk-x86_64.tar 100%[=============================================================================>] 182.71M 91.1KB/s in 26m 42s 2016-10-12 15:20:08 (117 KB/s) - ‘eclipse-cpp-mars-2-linux-gtk-x86_64.tar.gz’ saved [191591158/191591158]
darkstar:/tmp/eclipse-cpp# sh ./eclipse-cpp.SlackBuild
darkstar:/tmp/eclipse-cpp# installpkg /tmp/eclipse-cpp-4.5.2-x86_64-1_SBo.tgz Verifying package eclipse-cpp-4.5.2-x86_64-1_SBo.tgz. Installing package eclipse-cpp-4.5.2-x86_64-1_SBo.tgz: PACKAGE DESCRIPTION: # eclipse-cpp (Eclipse IDE for C/C++ Developers) # # The CDT is Eclipse's C/C++ Development Tooling project. # It is an industrial-strength C/C++ IDE that also serves # as a platform for others to provide value-added tooling # for C/C++ developers. # # # Homepage: http://www.eclipse.org/cdt # Executing install script for eclipse-cpp-4.5.2-x86_64-1_SBo.tgz. Package eclipse-cpp-4.5.2-x86_64-1_SBo.tgz installed.
Поставив Eclipse мы сделали полдела. Еще нужно поставить jdk. C 6-й и 8-й версии JDK Eclipse отказывался работать и вылетал. С 7-й тоже глючит, но кое-как работает. В гугл вбиваем «java jdk 7 download» попадем на страницу: Java SE Development Kit 7 Downloads

darkstar:/tmp/eclipse-cpp# cd /tmp
darkstar:/tmp# lftp http://mirror.yandex.ru/slackware/slackware64-14.2/extra/ cd ok, cwd=/slackware/slackware64-14.2/extra lftp mirror.yandex.ru:/slackware/slackware64-14.2/extra> mirror java Total: 1 directory, 8 files, 0 symlinks New: 8 files, 0 symlinks 8563 bytes transferred lftp mirror.yandex.ru:/slackware/slackware64-14.2/extra> bye
darkstar:/tmp# cd java
darkstar:/tmp/java# cp /home/flanker/mydev/down/jdk-7u79-linux-x64.tar.gz ./
darkstar:/tmp/java# sh ./java.SlackBuil
darkstar:/tmp/java# installpkg /tmp/jdk-7u79-x86_64-1.txz Verifying package jdk-7u79-x86_64-1.txz. Installing package jdk-7u79-x86_64-1.txz: PACKAGE DESCRIPTION: # Java(TM) 2 Platform Standard Edition Development Kit. # # The Java 2 SDK software includes tools for developing, testing, and # running programs written in the Java programming language. This # package contains everything you need to run Java(TM). # # For additional information, refer to this web page: # http://java.com/ # Executing install script for jdk-7u79-x86_64-1.txz. Package jdk-7u79-x86_64-1.txz installed.
Последий штрих:
darkstar:/tmp/java# ln -s /usr/lib64/java/bin/java /usr/bin/java
Теперь можно запускать Eclipse:


Жмем OK, это будет рабочий каталог проектов:

Далее открываем Marketplace:

В строку поиска вводим ARM:

и щелкаем по «install»

жмем «Confirm»

Перед установкой нужно будет принять условия лицензии:


Если погода на Марсе будет солнечной, то в конце установки предложат перезагрузить Eclipse:

После перезапуска Eclipse создаем новый проект:

В открывшийся форме нужно будет заполнить имя нового проекта и выбрать его тип:

В следующей форме необходимо выбрать параметры чипа. Замечу, что по дефолту(поле Content) предлагается не пустой проект, а проект с blink’ом:

Следующую форму можно оставить как есть:

Аналогично:

Здесь нужно указать путь к папке toolchain’ом:

Осталось закрыть окно «Welcome»

И перед нами открывается окно проекта:

Это совсем не тот простенький Blink который был в IAR. Здесь задержки формируются по таймеру и кроме этого используется модуль трассировки. Задать номер pin’а к которому подключен светодиод, можно в файле Blinky.h
2014 #ifndef BLINKLED_H_ #define BLINKLED_H_ #include "stm32f10x.h" 0123456 #define BLINK_PORT_NUMBER (2) #define BLINK_PIN_NUMBER (12) #define BLINK_ACTIVE_LOW (1) #define BLINK_GPIOx(_N) ((GPIO_TypeDef *)(GPIOA_BASE + (GPIOB_BASE-GPIOA_BASE)*(_N))) #define BLINK_PIN_MASK(_N) (1 << (_N)) #define BLINK_RCC_MASKx(_N) (RCC_APB2Periph_GPIOA << (_N)) extern void blink_led_init(void); inline void blink_led_on(void); inline void blink_led_off(void); inline void __attribute__((always_inline)) blink_led_on(void) { #if (BLINK_ACTIVE_LOW) GPIO_ResetBits(BLINK_GPIOx(BLINK_PORT_NUMBER), BLINK_PIN_MASK(BLINK_PIN_NUMBER)); #else GPIO_SetBits(BLINK_GPIOx(BLINK_PORT_NUMBER), BLINK_PIN_MASK(BLINK_PIN_NUMBER)); #endif } inline void __attribute__((always_inline)) blink_led_off(void) { #if (BLINK_ACTIVE_LOW) GPIO_SetBits(BLINK_GPIOx(BLINK_PORT_NUMBER), BLINK_PIN_MASK(BLINK_PIN_NUMBER)); #else GPIO_ResetBits(BLINK_GPIOx(BLINK_PORT_NUMBER), BLINK_PIN_MASK(BLINK_PIN_NUMBER)); #endif } #endif
Чтобы задать светодиод на PB1 нужно константы BLINK_PORT_NUMBER и BLINK_PIN_NUMBER установить в единицы. После чего можно скомпилировать проект:

Если все прошло удачно, то можно закрыть проект и перейти в консоли в папку проекта:
$ cd ~/workspace/myBlink/Debug/
Там будет объектный файл прошивки. Получаем бинарный файл:
darkstar:~/workspace/myBlink/Debug: arm-none-eabi-objcopy ./myBlink.elf -O binary ./myBlink.bin
Прошиваем:
darkstar:~/workspace/myBlink/Debug: st-flash write ./myBlink.bin 0x08000000 2016-10-12T17:50:49 INFO /home/flanker/mydev/tools/stlink/src/usb.c: -- exit_dfu_mode 2016-10-12T17:50:49 INFO /home/flanker/mydev/tools/stlink/src/common.c: Loading device parameters.... 2016-10-12T17:50:49 INFO /home/flanker/mydev/tools/stlink/src/common.c: Device connected is: F1 Medium-density device, id 0x20036410 2016-10-12T17:50:49 INFO /home/flanker/mydev/tools/stlink/src/common.c: SRAM size: 0x5000 bytes (20 KiB), Flash: 0x20000 bytes (128 KiB) in pages of 1024 bytes 2016-10-12T17:50:49 INFO /home/flanker/mydev/tools/stlink/src/common.c: Attempting to write 5832 (0x16c8) bytes to stm32 address: 134217728 (0x8000000) Flash page at addr: 0x08001400 erased 2016-10-12T17:50:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Finished erasing 6 pages of 1024 (0x400) bytes 2016-10-12T17:50:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Starting Flash write for VL/F0/F3 core id 2016-10-12T17:50:50 INFO /home/flanker/mydev/tools/stlink/src/flash_loader.c: Successfully loaded flash loader in sram 5/5 pages written 2016-10-12T17:50:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Starting verification of write complete 2016-10-12T17:50:50 INFO /home/flanker/mydev/tools/stlink/src/common.c: Flash written and verified! jolly good!
Если, опять же все нормально, то светодиод начнет мигать с интервалом в одну секунду. Заливать прошивку можно и из Eclipse, но эта IDE меня интересует только как генератор проектов.
Попробуем взглянуть на makefile файл который лежит в этой же папке:
-include ../makefile.init RM := rm -rf -include sources.mk -include system/src/stm32f1-stdperiph/subdir.mk -include system/src/newlib/subdir.mk -include system/src/diag/subdir.mk -include system/src/cortexm/subdir.mk -include system/src/cmsis/subdir.mk -include src/subdir.mk -include subdir.mk -include objects.mk ifneq ($(MAKECMDGOALS),clean) ifneq ($(strip $(C++_DEPS)),) -include $(C++_DEPS) endif ifneq ($(strip $(C_DEPS)),) -include $(C_DEPS) endif ifneq ($(strip $(ASM_DEPS)),) -include $(ASM_DEPS) endif ifneq ($(strip $(CC_DEPS)),) -include $(CC_DEPS) endif ifneq ($(strip $(CPP_DEPS)),) -include $(CPP_DEPS) endif ifneq ($(strip $(CXX_DEPS)),) -include $(CXX_DEPS) endif ifneq ($(strip $(C_UPPER_DEPS)),) -include $(C_UPPER_DEPS) endif ifneq ($(strip $(S_UPPER_DEPS)),) -include $(S_UPPER_DEPS) endif endif -include ../makefile.defs SECONDARY_FLASH += \ myBlink.hex \ SECONDARY_SIZE += \ myBlink.siz \ all: myBlink.elf secondary-outputs myBlink.elf: $(OBJS) $(USER_OBJS) @echo 'Building target: $@' @echo 'Invoking: Cross ARM C++ Linker' arm-none-eabi-g++ -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -T mem.ld -T libs.ld -T sections.ld -nostartfiles -Xlinker --gc-sections -L"../ldscripts" -Wl,-Map,"myBlink.map" --specs=nano.specs -o "myBlink.elf" $(OBJS) $(USER_OBJS) $(LIBS) @echo 'Finished building target: $@' @echo ' ' myBlink.hex: myBlink.elf @echo 'Invoking: Cross ARM GNU Create Flash Image' arm-none-eabi-objcopy -O ihex "myBlink.elf" "myBlink.hex" @echo 'Finished building: $@' @echo ' ' myBlink.siz: myBlink.elf @echo 'Invoking: Cross ARM GNU Print Size' arm-none-eabi-size --format=berkeley "myBlink.elf" @echo 'Finished building: $@' @echo ' ' clean: -$(RM) $(SECONDARY_SIZE)$(C++_DEPS)$(OBJS)$(C_DEPS)$(ASM_DEPS)$(CC_DEPS)$(SECONDARY_FLASH)$(CPP_DEPS)$(CXX_DEPS)$(C_UPPER_DEPS)$(S_UPPER_DEPS) myBlink.elf -@echo ' ' secondary-outputs: $(SECONDARY_FLASH) $(SECONDARY_SIZE) .PHONY: all clean dependents .SECONDARY: -include ../makefile.targets
Очищаем проект:
darkstar:~/workspace/myBlink/Debug: make clean rm -rf myBlink.siz ./system/src/stm32f1-stdperiph/misc.o ./system/src/stm32f1-stdperiph/stm32f10x_gpio.o ./system/src/stm32f1-stdperiph/stm32f10x_rcc.o ./system/src/newlib/_cxx.o ./system/src/newlib/_exit.o ./system/src/newlib/_sbrk.o ./system/src/newlib/_startup.o ./system/src/newlib/_syscalls.o ./system/src/newlib/assert.o ./system/src/diag/Trace.o ./system/src/diag/trace_impl.o ./system/src/cortexm/_initialize_hardware.o ./system/src/cortexm/_reset_hardware.o ./system/src/cortexm/exception_handlers.o ./system/src/cmsis/system_stm32f10x.o ./system/src/cmsis/vectors_stm32f10x.o ./src/BlinkLed.o ./src/Timer.o ./src/_write.o ./src/main.o ./system/src/stm32f1-stdperiph/misc.d ./system/src/stm32f1-stdperiph/stm32f10x_gpio.d ./system/src/stm32f1-stdperiph/stm32f10x_rcc.d ./system/src/newlib/_exit.d ./system/src/newlib/_sbrk.d ./system/src/newlib/_startup.d ./system/src/newlib/_syscalls.d ./system/src/newlib/assert.d ./system/src/diag/Trace.d ./system/src/diag/trace_impl.d ./system/src/cortexm/_initialize_hardware.d ./system/src/cortexm/_reset_hardware.d ./system/src/cortexm/exception_handlers.d ./system/src/cmsis/system_stm32f10x.d ./system/src/cmsis/vectors_stm32f10x.d ./src/BlinkLed.d ./src/Timer.d ./src/_write.d ./src/main.d myBlink.hex ./system/src/newlib/_cxx.d myBlink.elf
Собираем заново:
darkstar:~/workspace/myBlink/Debug: make all Building file: ../system/src/stm32f1-stdperiph/misc.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/stm32f1-stdperiph/misc.d" -MT"system/src/stm32f1-stdperiph/misc.o" -c -o "system/src/stm32f1-stdperiph/misc.o" "../system/src/stm32f1-stdperiph/misc.c" Finished building: ../system/src/stm32f1-stdperiph/misc.c Building file: ../system/src/stm32f1-stdperiph/stm32f10x_gpio.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/stm32f1-stdperiph/stm32f10x_gpio.d" -MT"system/src/stm32f1-stdperiph/stm32f10x_gpio.o" -c -o "system/src/stm32f1-stdperiph/stm32f10x_gpio.o" "../system/src/stm32f1-stdperiph/stm32f10x_gpio.c" Finished building: ../system/src/stm32f1-stdperiph/stm32f10x_gpio.c Building file: ../system/src/stm32f1-stdperiph/stm32f10x_rcc.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/stm32f1-stdperiph/stm32f10x_rcc.d" -MT"system/src/stm32f1-stdperiph/stm32f10x_rcc.o" -c -o "system/src/stm32f1-stdperiph/stm32f10x_rcc.o" "../system/src/stm32f1-stdperiph/stm32f10x_rcc.c" Finished building: ../system/src/stm32f1-stdperiph/stm32f10x_rcc.c Building file: ../system/src/newlib/_cxx.cpp Invoking: Cross ARM C++ Compiler arm-none-eabi-g++ -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu++11 -fabi-version=0 -fno-exceptions -fno-rtti -fno-use-cxa-atexit -fno-threadsafe-statics -MMD -MP -MF"system/src/newlib/_cxx.d" -MT"system/src/newlib/_cxx.o" -c -o "system/src/newlib/_cxx.o" "../system/src/newlib/_cxx.cpp" Finished building: ../system/src/newlib/_cxx.cpp Building file: ../system/src/newlib/_exit.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/newlib/_exit.d" -MT"system/src/newlib/_exit.o" -c -o "system/src/newlib/_exit.o" "../system/src/newlib/_exit.c" Finished building: ../system/src/newlib/_exit.c Building file: ../system/src/newlib/_sbrk.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/newlib/_sbrk.d" -MT"system/src/newlib/_sbrk.o" -c -o "system/src/newlib/_sbrk.o" "../system/src/newlib/_sbrk.c" Finished building: ../system/src/newlib/_sbrk.c Building file: ../system/src/newlib/_startup.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/newlib/_startup.d" -MT"system/src/newlib/_startup.o" -c -o "system/src/newlib/_startup.o" "../system/src/newlib/_startup.c" Finished building: ../system/src/newlib/_startup.c Building file: ../system/src/newlib/_syscalls.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/newlib/_syscalls.d" -MT"system/src/newlib/_syscalls.o" -c -o "system/src/newlib/_syscalls.o" "../system/src/newlib/_syscalls.c" Finished building: ../system/src/newlib/_syscalls.c Building file: ../system/src/newlib/assert.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/newlib/assert.d" -MT"system/src/newlib/assert.o" -c -o "system/src/newlib/assert.o" "../system/src/newlib/assert.c" Finished building: ../system/src/newlib/assert.c Building file: ../system/src/diag/Trace.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/diag/Trace.d" -MT"system/src/diag/Trace.o" -c -o "system/src/diag/Trace.o" "../system/src/diag/Trace.c" Finished building: ../system/src/diag/Trace.c Building file: ../system/src/diag/trace_impl.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/diag/trace_impl.d" -MT"system/src/diag/trace_impl.o" -c -o "system/src/diag/trace_impl.o" "../system/src/diag/trace_impl.c" Finished building: ../system/src/diag/trace_impl.c Building file: ../system/src/cortexm/_initialize_hardware.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/cortexm/_initialize_hardware.d" -MT"system/src/cortexm/_initialize_hardware.o" -c -o "system/src/cortexm/_initialize_hardware.o" "../system/src/cortexm/_initialize_hardware.c" Finished building: ../system/src/cortexm/_initialize_hardware.c Building file: ../system/src/cortexm/_reset_hardware.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/cortexm/_reset_hardware.d" -MT"system/src/cortexm/_reset_hardware.o" -c -o "system/src/cortexm/_reset_hardware.o" "../system/src/cortexm/_reset_hardware.c" Finished building: ../system/src/cortexm/_reset_hardware.c Building file: ../system/src/cortexm/exception_handlers.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/cortexm/exception_handlers.d" -MT"system/src/cortexm/exception_handlers.o" -c -o "system/src/cortexm/exception_handlers.o" "../system/src/cortexm/exception_handlers.c" Finished building: ../system/src/cortexm/exception_handlers.c Building file: ../system/src/cmsis/system_stm32f10x.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/cmsis/system_stm32f10x.d" -MT"system/src/cmsis/system_stm32f10x.o" -c -o "system/src/cmsis/system_stm32f10x.o" "../system/src/cmsis/system_stm32f10x.c" Finished building: ../system/src/cmsis/system_stm32f10x.c Building file: ../system/src/cmsis/vectors_stm32f10x.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"system/src/cmsis/vectors_stm32f10x.d" -MT"system/src/cmsis/vectors_stm32f10x.o" -c -o "system/src/cmsis/vectors_stm32f10x.o" "../system/src/cmsis/vectors_stm32f10x.c" Finished building: ../system/src/cmsis/vectors_stm32f10x.c Building file: ../src/BlinkLed.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"src/BlinkLed.d" -MT"src/BlinkLed.o" -c -o "src/BlinkLed.o" "../src/BlinkLed.c" Finished building: ../src/BlinkLed.c Building file: ../src/Timer.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"src/Timer.d" -MT"src/Timer.o" -c -o "src/Timer.o" "../src/Timer.c" Finished building: ../src/Timer.c Building file: ../src/_write.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"src/_write.d" -MT"src/_write.o" -c -o "src/_write.o" "../src/_write.c" Finished building: ../src/_write.c Building file: ../src/main.c Invoking: Cross ARM C Compiler arm-none-eabi-gcc -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -DDEBUG -DUSE_FULL_ASSERT -DTRACE -DOS_USE_TRACE_SEMIHOSTING_DEBUG -DSTM32F10X_MD -DUSE_STDPERIPH_DRIVER -DHSE_VALUE=8000000 -I"../include" -I"../system/include" -I"../system/include/cmsis" -I"../system/include/stm32f1-stdperiph" -std=gnu11 -MMD -MP -MF"src/main.d" -MT"src/main.o" -c -o "src/main.o" "../src/main.c" Finished building: ../src/main.c Building target: myBlink.elf Invoking: Cross ARM C++ Linker arm-none-eabi-g++ -mcpu=cortex-m3 -mthumb -Og -fmessage-length=0 -fsigned-char -ffunction-sections -fdata-sections -ffreestanding -fno-move-loop-invariants -Wall -Wextra -g3 -T mem.ld -T libs.ld -T sections.ld -nostartfiles -Xlinker --gc-sections -L"../ldscripts" -Wl,-Map,"myBlink.map" --specs=nano.specs -o "myBlink.elf" ./system/src/stm32f1-stdperiph/misc.o ./system/src/stm32f1-stdperiph/stm32f10x_gpio.o ./system/src/stm32f1-stdperiph/stm32f10x_rcc.o ./system/src/newlib/_cxx.o ./system/src/newlib/_exit.o ./system/src/newlib/_sbrk.o ./system/src/newlib/_startup.o ./system/src/newlib/_syscalls.o ./system/src/newlib/assert.o ./system/src/diag/Trace.o ./system/src/diag/trace_impl.o ./system/src/cortexm/_initialize_hardware.o ./system/src/cortexm/_reset_hardware.o ./system/src/cortexm/exception_handlers.o ./system/src/cmsis/system_stm32f10x.o ./system/src/cmsis/vectors_stm32f10x.o ./src/BlinkLed.o ./src/Timer.o ./src/_write.o ./src/main.o Finished building target: myBlink.elf Invoking: Cross ARM GNU Create Flash Image arm-none-eabi-objcopy -O ihex "myBlink.elf" "myBlink.hex" Finished building: myBlink.hex Invoking: Cross ARM GNU Print Size arm-none-eabi-size --format=berkeley "myBlink.elf" text data bss dec hex filename 5653 176 416 6245 1865 myBlink.elf Finished building: myBlink.siz
некоторые вещи бывает сложно объяснить
Пробуем еще раз загрузить полученный файл в отлдачик. Запускаем сервер:
darkstar:~/workspace: st-util 2016-10-13T03:20:05 INFO /home/flanker/mydev/tools/stlink/src/usb.c: -- exit_dfu_mode 2016-10-13T03:20:05 INFO /home/flanker/mydev/tools/stlink/src/common.c: Loading device parameters.... 2016-10-13T03:20:05 INFO /home/flanker/mydev/tools/stlink/src/common.c: Device connected is: F1 Medium-density device, id 0x20036410 2016-10-13T03:20:05 INFO /home/flanker/mydev/tools/stlink/src/common.c: SRAM size: 0x5000 bytes (20 KiB), Flash: 0x20000 bytes (128 KiB) in pages of 1024 bytes 2016-10-13T03:20:05 INFO /home/flanker/mydev/tools/stlink/src/gdbserver/gdb-server.c: Chip ID is 00000410, Core ID is 1ba01477. 2016-10-13T03:20:05 INFO /home/flanker/mydev/tools/stlink/src/gdbserver/gdb-server.c: Listening at *:4242...
загружаем отладчик:
darkstar:~/workspace/myBlink/Debug: arm-none-eabi-gdb ./myBlink.elf GNU gdb (GNU Tools for ARM Embedded Processors) 7.10.1.20160616-cvs Copyright (C) 2015 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Type "show copying" and "show warranty" for details. This GDB was configured as "--host=i686-linux-gnu --target=arm-none-eabi". Type "show configuration" for configuration details. For bug reporting instructions, please see: . Find the GDB manual and other documentation resources online at: . For help, type "help". Type "apropos word" to search for commands related to "word"... Reading symbols from ./myBlink.elf...done. (gdb)
подключаемся к серверу:
(gdb) target remote localhost:4242
Remote debugging using localhost:4242
Reset_Handler () at ../system/src/cortexm/exception_handlers.c:31
31 {
(gdb)
загружаем прошивку:
(gdb) load Loading section .isr_vector, size 0x354 lma 0x8000000 Loading section .inits, size 0x28 lma 0x8000354 Loading section .text, size 0x12c1 lma 0x800037c Loading section .data, size 0x88 lma 0x8001640 Start address 0x800010c, load size 5829 Transfer rate: 3 KB/sec, 1457 bytes/write. (gdb)
ставим точку останова:
(gdb) break main Breakpoint 1 at 0x8000a70: file ../src/main.c, line 60. (gdb)
Запускаем на выполнение:
(gdb) continue
Continuing.
Note: automatically using hardware breakpoints for read-only addresses.
Breakpoint 1, main (argc=1, argv=0x20000004 ) at ../src/main.c:60
60 {
(gdb)
Выполнение программы приостонавливается на точке останова. Смотрим листинг:
(gdb) list
55 #pragma GCC diagnostic ignored "-Wmissing-declarations"
56 #pragma GCC diagnostic ignored "-Wreturn-type"
57
58 int
59 main(int argc, char* argv[])
60 {
61 // Send a greeting to the trace device (skipped on Release).
62 trace_puts("Hello ARM World!");
63
64 // At this stage the system clock should have already been configured
(gdb)
В этот раз все в прорядке. Однако если мы еще раз дадим команду continue, то будет возможно, неожиданный эффект:
(gdb) continue
Continuing.
Program received signal SIGTRAP, Trace/breakpoint trap.
0x08000694 in call_host (arg=0x4, reason=4) at ../system/include/arm/semihosting.h:80
80 asm volatile (
(gdb) list
75 static inline int
76 __attribute__ ((always_inline))
77 call_host (int reason, void* arg)
78 {
79 int value;
80 asm volatile (
81
82 " mov r0, %[rsn] \n"
83 " mov r1, %[arg] \n"
84 #if defined(OS_DEBUG_SEMIHOSTING_FAULTS)
Программа останавливается по сигналу SIGTRAP и дальше ни в какую не идет.
Проблема кроется в отладочном интерфейсе semihosting, которого как понимаю, в чипе просто нет, но который позволяет выводить отладочные сообщения через функцию trace_printf().
Чтобы решить эту проблему, нужно в Eclipce через меню->project->proporties, открыть вкладку Settings в «C/C++ Build»:

В настройке препроцессора следует удалить макроопределение OS_USE_TRACE_SEMIHOSTING_DEBUG. После чего пересобрать проект. и полученный объектный файл заново загрузить в отладчик:
(gdb) n
62 trace_puts("Hello ARM World!");
(gdb) n
66 trace_printf("System clock: %u Hz\n", SystemCoreClock);
(gdb)
Посмотрим что нам пытаются вывести:
(gdb) p SystemCoreClock $1 = 72000000
здесь вроде все нормально
(gdb) n 68 timer_start(); (gdb) n 70 blink_led_init(); (gdb) n 72 uint32_t seconds = 0; (gdb) n 77 blink_led_on(); (gdb) n 78 timer_sleep(seconds == 0 ? TIMER_FREQUENCY_HZ : BLINK_ON_TICKS); (gdb)
Посмотрим значение переменной seconds:
(gdb) p seconds $2 = 0
идем дальше:
(gdb) n
80 blink_led_off();
(gdb) n
81 timer_sleep(BLINK_OFF_TICKS);
(gdb) n
83 ++seconds;
(gdb) n
86 trace_printf("Second %u\n", seconds);
(gdb) n
87 }
(gdb)
Почему то у меня после blink_on() светодиод гаснет, а после blink_off() наоборот загорается
(gdb) break main.c:83 if seconds = 100 Breakpoint 2 at 0x8000a02: file ../src/main.c, line 83. (gdb) continue Continuing. Breakpoint 2, main (argc=, argv=) at ../src/main.c:83 83 ++seconds; (gdb) print seconds $3 = 100 (gdb)
Думаю, что здесь все понятно.






































