# Отладка программ

Разберем (поверхностно) способы отладки программ на примере проекта из пердыдущего раздела (светодиод с ШИМ).

## Дебагер CubeIDE

Дебагер, в первом приближении, умеет делать три полезные вещи:

1. Ставить программу на паузу в точках остановки и показывать состояние локальных переменных
2. Идти по программе по шагам (также с информацией о всех локальных переменных)
3. Следить за значениями глобальных переменных

### Точки остановки (breakpoints)

Добавим точку остановки на строке `HAL_Delay(0.05);` Для этого, можно нажать на свободное место справа от номера строки или нажать правой кнопкой на строку -> `Toggle Breakpoint`.

Далее, надо нажать на кнопку ![](/files/qMMTUKTtTsWycHou18jE). Это пересоберет программу, зальет ее, и подключитя дебаггером. После этого, программа **встанет на паузу**. Нажмем ![](/files/uVevWg9j1ftdDTjoeth1) - это скажет программе выполняться до точки остановки, после чего опять встать на паузу.

Программа должна была остановиться тут - ![](/files/XoiGTSzJyKZqYogMMaFb) . Теперь, справа есть меню дебагера. Первая вкладка в нем (`variables`) показывает локальные переменные в данной точке программы. На данный момент, это только `x`.

<figure><img src="/files/ueaC829eknagAY5IbhjT" alt=""><figcaption><p>Обзор переменных</p></figcaption></figure>

Еще раз нажмем  ![](/files/uVevWg9j1ftdDTjoeth1) - так как точка остановки находится в бесконечном цикле, мы попадем на эту же строку на следующей итерации. Теперь, значение переменной `x` должно быть `0.001`.

### Пошаговый дебаггинг

Теперь попробуем из этого же места посмотреть, что делает наша программа по шагам. Для этого у нас есть три кнопки.

1. Step Into (![](/files/TYBrxXFcL52iROk1fZWd)) - если на строке, на которой находится в данный момент дебаггер, вызывается какая либо функция, эта кнопка позволит нам "провалиться" внутрь, и посмотреть что конкретно происходит при вызове
2. Step Over (![](/files/mpcs8Q8hlYubkXkaF5Eh)) - *самая часть используемая*. Переход к следующей инструкции.
3. Step Return (![](/files/EzvXFbTMT7LwQLB4w43Y)) - если до этого вы делали "Step Into", нажатие на эту кнопку выполнит текущую функию до конца и "вытолкнет" вас наверх, к следующей после нажатия "Step Into" инструкции

Тут нам понадобится только Step Over. Несколько раз нажав на нее, мы можем дойти до конца цикла `while`, и увидеть, что значение `x` стало `0.002`.

В такой простой программе как это большой пользы такой метод не принесет, но при отладке сложных алгоритмов он крайне полезен.

### Глобальные переменные

Уберем точку остановки (также, как и ставили), и будем следить за изменением `x` без остановки программы. Для этого, рассмотрим второй по популярности раздел панели дебагера - `Live Ex`. Откроем его, нажмем "*Add new expression*", впишем просто `x`, и тут же увидим "*Failed to evaluate expression*". Дело в том, что следить мы можем только за глобальными переменными. Ось X можно также для синусоиды назвать осью времени, поэтому заведем глобальную переменную `double time;` и в цикле сразу перед `if(...)` добавим `time = x;`. Конечно, тут это пример крайне натянутый, но поможет понять как пользоваться этим инструментом.

Теперь, вместо `х` впишем `time`. Тут мы сразу видим правильно значение. Теперь, так как мы убрали точку остановки, если нажать ![](/files/uVevWg9j1ftdDTjoeth1), то программа просто будет работать, а изменение `time` мы будем видеть в реальном времени.

## STM32CubeMonitor

{% hint style="info" %}
Предполагается, что программу CubeMonitor вы уже установили ([ссылка](https://www.st.com/en/development-tools/stm32cubemonitor.html))
{% endhint %}

Открым программу, нас встретит вот такое окно:

<figure><img src="/files/miZyNRPxJMxUnI0CHssP" alt=""><figcaption></figcaption></figure>

Это диаграмма процесса сбора данных с контроллера, и в большинстве случаев, такого простого варианта вполне достаточно. Рассмотрим, как настроить его для нашего проекта.

#### Probe\_Out / Probe\_In

Нажмем на ![](/files/pFgVdBJ5s0bXcLmrDH9p)

В открывшемся менем выберем **Probe Config -> Добавить новый probe ->** ![](/files/b5tSThmNDS1LGr5tF9a1). Тут: **Probe name ->select a probe -> ST-Link ... -> Добавить**. Таким образом, мы добавили настройки для программатора.

Открыв ![](/files/KEzYBlMbQ77H5BeOCJDh), в **Probe Config** надо просто выбрать настроенный только что ST-Link.

#### myVariables

&#x20;Тут нам надо выбрать проект и переменные в нем, за которыми будем следить.

Нажмем ![](/files/g6rOpiJqrlh7emlR1vw0). **Executable -> добавить новый exe-config ->** ![](/files/b5tSThmNDS1LGr5tF9a1). **Folder** - папка вашего проекта *и в ней папка с названием билда* (обычно Debug). **File -> Select a File -> \*.elf**. Далее назначаем ему любое имя и нажимаем "**Добавить**".

Допустим, нам хотелось бы увидеть синусоиду, по которой меняется яркость светодиода. Но следить мы можем только за значениями глобальных перменных. Поэтому заведем еще одну глобальную переменную `double y;`, в которую будем в нашем цикле записывать текущее значение регистра CCR: `y = __HAL_TIM_GET_COMPARE(&htim2, TIM_CHANNEL_1);`&#x20;

Откроем опять myVariables и нажмем на "карандаш" рядом с названием нашего файла. В открывшемся окне есть списко всех глобальных переменных - ставим галочки рядом с `time` и `y`. Жмем "**Обновить**".

Все что осталось - нажать ![](/files/aFOnn7idcxZ1Xqic9Pod)(в случае каких либо проблем на этом ээтапе помогает вынуть-вставить программатор). Теперь - ![](/files/v9384fyaUJq8HDBhY8xI).

Думаю, название кнопок в открывшемся окне говорит само за себя. Жмем **Start Acquisition** и если программа на микроконтроллере работает и все прошло успешно, наблюдаем за красивой синусоидой. Если поставить галочку у ![](/files/zctKtdNwFU27c3qoH0Wf), то наведясь мышкой на график можно видеть значения всех переменных в выбранный момент времени:

<figure><img src="/files/cg9bVTGKLH1NPbERmNBN" alt=""><figcaption><p>Графики переменных</p></figcaption></figure>


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://voltbro.gitbook.io/vbcores/tutorials/stm32-cube-ide/otladka-programm.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
