Магия отладки

Приветствую!
Итак, попалась мне в руки железяка на ARM Cortex-M3, точнее даже отладочная плата, с чипом от Texas Instruments.
Поставил их IDE Code Composer Studio, SDK и принялся за код.
Но в какой-то момент потребовалась отладка. Отлаживаемое ПО перестает отзываться при попытке создания потока. Ставлю брекпоинты, прога останавливается в нужном месте (стр. 169).
Сейчас посмотрим, что там не так.
image
Нажимаю Step Over и оказываюсь… в стр 168!
image
Снова Step Over и снова на стр 169.
Переменная retc, которая имела значение 1, после этого становится равной нулю.
Как? Как в результате логического ИЛИ с ненулевым значением получился 0?
Почему идет перескок на предыдущую строку?
Как вообще такое отлаживать?
Или я чего-то не понимаю в ARM?

Создание потока, указание размера и выбор приоритета разделяются условиями.
Пример потоковой мигалки

P. S.
Пояснение почему поток очищается \ переполняется

Если тут еще просто один поток, то похоже на какие-то проблемы с отладчиком или отладочной инфой от компилятора.
Может стоит пожаловаться на форуме этой CCS https://e2e.ti.com/support/tools/ccs/f/code-composer-studio-forum

Лучше давать ссылку на оригинал c - proper way to create multiple forked threads - Stack Overflow

Просто данный вариант кода – пример не работающей демонстрационной демки:
RTOS/CC2640R2F: How to create pthread in TIRTOS

Не видел данную тему, потому и привел ту ссылку. Что нагуглил то и показал ))

Переменная у вас лежит на стеки. Если указатель полетел, то при вызове функции. Она может затереть ваш стек. Как следствие не только обнуление переменной. Так как стеке лежит адреса возврата из функции, поэтому затертый стек также приводит к скачкам отладчика.
Ищите утечки, проверяйте указатели, ссылки, размеры структур. Указатели и размеры переменных в структурах.

Спасибо. Добавил

if (... != 0) {while(1);}

Стало вести себя более предсказуемо.

Про стэк то я и забыл.
Вот что бывает, когда копипастишь код из примера из SDK :slight_smile:

А где еще найдешь такие перлы:

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

Так эти примеры. в принципе как примеры для пиара какого то нового борда. И не более того.
P. S.
бесконечный while(1) неотъемлемая часть тактирования ARM.
Нельзя задать ряд инструкций, а потом где то-там обработать.
Последовательность: инструкция – выполнение.
Как в жостком языке C

Т.е. это нечто вроде барьера памяти, только для инструкций?

Не много не так.
Это нечто как в армии.
Есть размер стека заданный рармером ОЗУ конкретного контроллера. И необходимо вписаться в эти рамки.
Контроллер выполняет инструкции последовательно, ООП к нему прилепить не получится, как ни старайся.
Вот по этой причине необходимо в коде продумывать: конструкторы, деструкторы, и слипы конструктров для энергосбережения.
Emdedder – должность сложная.

Так там и в оригинале

more often you would create a timer thread, and park it until it is needed

что вроде бы не является общепринятым термином )

Так а ПК/сервер как их выполняет? :thinking:

ООП и С++ там ж не берут скорее просто потому что они там не особо нужны, цель сделать как можно более просто, заоптимизировать всё и т.д.

Но судя по гуглу и туда оно проникает (тут правда еще дело в том, что ембедед много чего называют).

Ну и ООП это не обязательно про “язык с классами”, сами идеи и в С можно применять.
Тут вон вроде чему-то на эту тему и учат ембедеров Embedded Programming Video Course Shows How OOP Works Under the Hood - Miro Samek

Видимо, тот кто отвечал, тоже воспользовался автопереводом)

Вот, кстати, ядро ОС (Winedows, Linux) - хороший пример реализации ООП парадигмы на С.
А вот обвязки, обычно характерные для ОО-языка (автоматический вызов конструкторов, деструкторов, RTTI и т.д.) там действительно не используются.
Была Numega Driver Studio для разработки драйверов под Win. Там, насколько я помню, можно было на плюсах писать. Но они там были “урезанные”.

1 лайк