Перейти к содержанию
    

Отследить переменные на стеке.

40 минут назад, jenya7 сказал:

это не мой случай. или если произойдёт прерывание между функциями это может затереть переменную?

Правильно написанный обработчик прерывания не нарушает контекст, поэтому переменные он затереть не должен.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/4/2023 at 11:43 AM, makc said:

Правильно написанный обработчик прерывания не нарушает контекст, поэтому переменные он затереть не должен.

я сделал буфер глобальным, т.е убрал со стека, это наводит на мысль что происходит какая то коллизия именно на стеке. 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

1 час назад, jenya7 сказал:

это не мой случай. или если произойдёт прерывание между функциями это может затереть переменную?

В кривой программе может случаться что угодно. Вплоть до аннигиляции содержимого переменных.

 

А стек прерываний у вас где? Знаете?  :mosking:

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Стек прерываний находится там же, где и стек вызовов функций, располагается выше по движению (назад по адресам), над стеком последней активной функции на момент прерывания. Всё, что вызывается из прерываний, располагается там же, выше по стеку.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/4/2023 at 12:40 PM, jcxz said:

В кривой программе может случаться что угодно. Вплоть до аннигиляции содержимого переменных.

 

А стек прерываний у вас где? Знаете?  :mosking:

единственное периодическое прерывание это systick. другие никак нельзя привязать к периодичному багу.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

11 минут назад, Variant99 сказал:

Стек прерываний находится там же, где и стек вызовов функций, располагается выше по движению (назад по адресам), над стеком последней активной функции на момент прерывания. Всё, что вызывается из прерываний, располагается там же, выше по стеку.

Это на каком основании сделан такой вывод?? Почему именно "выше", а не "ниже"?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

На основании практических наблюдений. 

Хорошо, а где он должен быть по вашему разумению? 🙂 Может, в сферическом вакууме?

3 часа назад, jenya7 сказал:
uint16_t check_new_message(void)
{
    uint16_t l_uiDataBuffer[32];

Достаточно было написать static uint16_t l_uiDataBeffer[32] и этот массив разместился бы в другой области памяти, а не в стеке и имел бы постоянную "прописку" (адрес) и они сразу были бы = 0. А когда просто объявилили локальный нестатический массив, он содержит случайные числа, они не обнуляются, если их явно не обнулить в момент создания.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/4/2023 at 1:34 PM, Variant99 said:

Достаточно было написать static uint16_t l_uiDataBeffer[32] и этот массив разместился бы в другой области памяти, а не в стеке и имел бы постоянную "прописку" (адрес) и они сразу были бы = 0. А когда просто объявилили локальный нестатический массив, он содержит случайные числа, они не обнуляются, если их явно не обнулить в момент создания.

а теперь надо объяснить почему это решило проблему. без объяснений новую версию не принимают.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

36 минут назад, Variant99 сказал:

На основании практических наблюдений. 

Вывод, что Земля плоская и покоится на 3-х слонах, тоже делали "на основании практических наблюдений". Ваши того же качества.

Советую читать документацию на ARM-ядрА. Чтобы узнать где может находиться стек и как он работает. И последнюю букву я выделил не зря.

36 минут назад, Variant99 сказал:

Хорошо, а где он должен быть по вашему разумению? 🙂 Может, в сферическом вакууме?

В любом месте памяти. Никак не зависимом от стека обсуждаемых функций.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

jcxzне думайте, что я глупее вас. Документацию я читал. И не затевайте в очередной раз спор ради спора просто лишь бы поспорить. 

В любом месте памяти он быть не может, иначе он позатрет всё что нужно и что не нужно. Он располагается там, где было указано. Есть два указателя стека MSP и PSP. И наврядли тут разговор идет о втором указателе и навряд ли используется RTOS. По крайней мере, автор не упоминал про это. 

40 minutes ago, jenya7 said:

а теперь надо объяснить почему это решило проблему. без объяснений новую версию не принимают.

Лучше всего это проследить в отладчике так, как я показывал выше на скринах. Там сразу видно, где лежат переменные, какое они имеют содержимое на каждом шаге.

Поскольку мы тут не видим окружения и наполнения функций buffcpy_cont() и save_data(), не знаем, используется ли RTOS, то конечно не можем угадать, что у вас произошло. Например, при использовании RTOS объяснение будет простое - переполнился стек задачи из-за очень большого локального буфера.
Так же, при объявлении uint16_t l_uiDataBuffer[32]; без инициализации содержимое его будет случайным, а не нулевым. Чтобы там были нули, их надо явно занулить uint16_t l_uiDataBuffer[32] = {0,0,0 ...<32_штуки>};
Вы там проверяете только один, последний элемент на равенство 0. А надо бы все элементы.

Ну и еще раз повторюсь - используйте отладчик, чтобы посмотреть "вживую" что и где лежит.
 

Изменено пользователем haker_fox
Нарушение правил 2.1.а

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Модератор: коллеги, прошу высказываться более аргументированно, например - давать ссылку на документацию и раздел. Дабы тема не ушла в сторону "оффтопика" или флейма.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/4/2023 at 2:37 PM, Variant99 said:

jcxzне думайте, что я глупее вас. Документацию я читал. И не затевайте в очередной раз спор ради спора просто лишь бы поспорить. 

В любом месте памяти он быть не может, иначе он позатрет всё что нужно и что не нужно. Он располагается там, где было указано. Есть два указателя стека MSP и PSP. И наврядли тут разговор идет о втором указателе и навряд ли используется RTOS. По крайней мере, автор не упоминал про это. 

Лучше всего это проследить в отладчике так, как я показывал выше на скринах. Там сразу видно, где лежат переменные, какое они имеют содержимое на каждом шаге.

Поскольку мы тут не видим окружения и наполнения функций buffcpy_cont() и save_data(), не знаем, используется ли RTOS, то конечно не можем угадать, что у вас произошло. Например, при использовании RTOS объяснение будет простое - переполнился стек задачи из-за очень большого локального буфера.
Так же, при объявлении uint16_t l_uiDataBuffer[32]; без инициализации содержимое его будет случайным, а не нулевым. Чтобы там были нули, их надо явно занулить uint16_t l_uiDataBuffer[32] = {0,0,0 ...<32_штуки>};
Вы там проверяете только один, последний элемент на равенство 0. А надо бы все элементы.

Ну и еще раз повторюсь - используйте отладчик, чтобы посмотреть "вживую" что и где лежит.
 

 

RTOS есть но бежит только мейн таск. кроме того я не попадаю в эксепшн

 

void FRTOS1_vApplicationStackOverflowHook(TaskHandle_t pxTask, char *pcTaskName)
{
  /* This will get called if a stack overflow is detected during the context
     switch.  Set configCHECK_FOR_STACK_OVERFLOWS to 2 to also check for stack
     problems within nested interrupts, but only do this for debug purposes as
     it will increase the context switch time. */
  (void)pxTask;
  (void)pcTaskName;
  taskDISABLE_INTERRUPTS();
  /* Write your code here ... */
  for(;;) {}
}

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

6 minutes ago, jenya7 said:

RTOS есть но бежит только мейн таск. кроме того я не попадаю в эксепшн

Как я понимаю, у Вас - FreeRTOS. Там для Cortex-Mx только программная ловушка переполнения стека. В руководстве написано, что гарантий, что она сработает в случае переполнения - никаких. Для более надёжного обнаружения нарушения границ памяти на архитектурах Cortex-M3 и выше используется модуль MPU, если он есть в конкретном микроконтроллере.

Кстати, у Вас ещё idle-задача есть. Создаётся средствами самой ОСРВ.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

5 минут назад, jenya7 сказал:

RTOS есть

Оооо, нуууу воооот, вот. Хехе, вот вам и объяснение. Размер стека задачи, в которой записаны эти функции с массивом, он какой?

И кстати, коль уж работает RTOS, то используйте её инструменты - очереди (Queue), отправку в очередь и прием из очереди для перемещения данных.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/4/2023 at 3:01 PM, haker_fox said:

Как я понимаю, у Вас - FreeRTOS. Там для Cortex-Mx только программная ловушка переполнения стека. В руководстве написано, что гарантий, что она сработает в случае переполнения - никаких.

Кстати, у Вас ещё idle-задача есть. Создаётся средствами самой ОСРВ.

а если не сработает?  стек перегрузиться и таск будет работать дальше?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
К сожалению, ваш контент содержит запрещённые слова. Пожалуйста, отредактируйте контент, чтобы удалить выделенные ниже слова.
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...