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

добрый день

 

подскажите кто пользуется эклипсом возможно ли нормально отлаживать задачку с scmrtos

 

у меня в коде на с++ точки остановки криво устанавливаются - остановка происходит не в тех местах где где в эклипсе установлены брекпойнты, при пошаговом исполнении какие то непонятные скачки по коду, при этом в частях написанных на чистом с в этой же задачке отладка проходит нормально

 

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

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


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

Полагаю, проблема в оптимизации. Ось компилируется с достаточно высокой степенью оптимизации и связь между исходником и ассемблерным кодом становится далеко не однозначной. Сишный же код наверняка компилится вообще без оптимизации, поэтому никаких неоднозначностей не возникает. Остается выбрать: если мы хотим писать большие медленные программы, то надо отключить оптимизацию и при компиляции C++. Если же мы хотим писать маленькие быстрые программы, то надо открывать рядом окно дизассемблера и отлаживаться в нем. Вариант "отключать оптимизацию на время отладки" - это вообще не вариант, ибо

а) будет отлаживаться фактически другая программа

б) не факт что она вообще соберется (без оптимизациии отключается встраивание)

в) после включения оптимизации в якобы отлаженной программе она может перестать работать и горе-программист окажется в той же ситуации, что и в начале - программа не работает, а отлаживать оптимизированный код он не умеет.

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


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

проблема не в оси а в системе отладки еклипса плюсов похоже

 

никто не знает в кокосе дело точно так же обстоит?

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


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

Не вижу у себя таких проблем с отладкой. Да, он скачет по сишным/плюсплюсным строкам, но только лишь потому, что благодаря объединению одинаковых участков кода один и тот же код ассемблера соответствует нескольким разным строкам исходника. Поставьте оптимизацию -O1 и увидите прекрасную отладку.

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


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

да я посмотрел код дизасемблера, там все перемешано из-за оптимизации, потому видимо так все скачет

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


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

добрый день, подскажите как правильно использовать init_stack_frame() и stack_slack(), если можно на примере, что то у меня не получается с этими функциями программу скомпилировать - ошибки такого плана

 

cannot call member function 'size_t OS::TBaseProcess::stack_slack() const' without object	main.cpp	
no matching function for call to 'OS::process<(OS::TPriority)1u, 300u>::init_stack_frame()'	main.cpp

 

вот в таком вот коде

 

template <>
OS_PROCESS void TProc4::exec()
{init_stack_frame();
for(;;)
	{res_table.uregs[104]=stack_slack();
		GreenLED::On();
		sleep(50);
		GreenLED::Off();
		sleep(950);
	}
}

 

что я не так делаю?

 

кажется разобрался...

 

init_stack_frame(); вызывается самой ос

а stack_slack(); следует вызывать таким образом Proc4.stack_slack();

верно? то есть в итоге делать так

 

template <>
OS_PROCESS void TProc4::exec()
{//init_stack_frame();
for(;;)
	{res_table.uregs[104]=Proc4.stack_slack();
		GreenLED::On();
		sleep(50);
		GreenLED::Off();
		sleep(950);
	}
}

Изменено пользователем сарматъ

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


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

продолжаю тему начатую тут

 

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

 

в одной из задач есть мигание светодиодом, эта задачка никого не ждет никаких ресурсов, вот ее код

 

template <>
OS_PROCESS void TProc4::exec()
{//init_stack_frame();
    for(;;)
        {res_table.uregs[104]=stack_slack();
            GreenLED::On();
            sleep(50);
            GreenLED::Off();
            sleep(950);
        }
}

но светодиодик моргать перестает

 

подскажите какие места в ос посмотреть отладчиком какие переменные чтобы понять отчего перестали переключаться задачки?

Изменено пользователем сарматъ

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


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

Здесь я вижу только три возможные проблемы:

1) Перестают генериться прерывания системного таймера. Это можно проверить, останавливая и запуская программу и смотря на переменную Kernel.SysTickCount. Если она меняется - значит прерывания генерятся и обработчик вызывается.

2) Из-за переполнения стека в переменную Timeout этого процесса заносится ноль и ожидание этого процесса становится бесконечным, либо заносится какое-то огромное число и вы просто не дожидаетесь окончания задержки sleep(). Опять же отлавливается отладчиком наблюдая за этой переменной - тикает ли и дотикивает ли до нуля.

3) Какой-то из более высокоприоритетных процессов крутится в цикле не отдавая управление (не впадая в ожидание в каком-либо из системных сервисов). Или же более высокоприоритетные процессы не успевают выполнить свою работу и до низкоприоритетных очередь просто не доходит. Это отлавливается наблюдая за тем, где крутится программа - если в IdleTask, то все нормально, если в каком-то из процессов - разбираться, почему он не отдает управление.

 

Есть еще одна возможная причина -

4) во время выполнения этой задачи происходит перепланировка, которая по какой-то неведомой причине удаляет эту задачу из карты активных задач. Это можно проверить, поставив точку останова в IdleTask и посмотрев на переменную Timeout этого процесса и на карту активных процессов Kernel.ReadyProcessMap. Либо ReadyProcessMap должен содержать единичку в бите этого процесса, либо Timeout должен быть ненулевым.

Ни вторая, ни четвертая не объясняют, почему останавливаются и другие задачи тоже. Ну разве что кто-то обнуляет ReadyProcessMap, останавливая все процессы.

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


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

да в этом месте

void OS::TKernel::system_timer()
{
    SYS_TIMER_CRIT_SECT();
#if scmRTOS_SYSTEM_TICKS_ENABLE == 1
    SysTickCount++;
#endif

точки останова не срабатывают, Kernel.SysTickCount не увеличивается, но я не понимаю изза чего, подскажите куда копать дальше?

 

в задачке есть прерывания - они работают, в том смысле что прерывания разрешены... в TIdleProc::exec() тоже ос попадает

Изменено пользователем сарматъ

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


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

точки останова не срабатывают, Kernel.SysTickCount не увеличивается, но я не понимаю изза чего, подскажите куда копать дальше?
Смотреть, тикает ли таймер. Если тикает - то почему не вызываются прерывания - может кто-то их запретил. А может таймер кто-то остановил.

 

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


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

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

 

0xE000E010 - 0х00010007 - прерывания разрешены (не понял пока назначение 16-го бита пробовал его сбрасывать с помощью mww команды, этот бит все равно устанавливается в единицу)

0хЕ000Е014 - 0х0002903f - значение регистра перезагрузки

0хЕ000Е018 - все время разные значения - таймер тикает

 

это прерывание не вызывается

extern "C" OS_INTERRUPT void Default_SystemTimer_ISR()
{
   scmRTOS_ISRW_TYPE ISR;

#if scmRTOS_SYSTIMER_HOOK_ENABLE == 1
   system_timer_user_hook();
#endif

   Kernel.system_timer();

#if scmRTOS_SYSTIMER_NEST_INTS_ENABLE == 0
   DISABLE_NESTED_INTERRUPTS();
#endif
}

 

нашел разницу между работающей и нерабочей системой

 

в работающей системе регистр 0xe000ed04 равен 0

когда система залипла то значение 1400e84d выходит что pendsv, равно как и систик отложены поэтому прерывание систик больше не генерируется, так? и что с этим делать?

Изменено пользователем сарматъ

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


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

в работающей системе регистр 0xe000ed04 равен 0

когда система залипла то значение 1400e84d выходит что pendsv, равно как и систик отложены поэтому прерывание систик больше не генерируется, так? и что с этим делать?

Вот честно - совершенно не хочется лопатить документацию ST чтобы найти, что за регистр живет по адресу 0xe000ed04.

 

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


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

Тогда, если я ничего не путаю, 4D в младших битах указывает, что ваша программа осталась в прерывании OTG_FS. Вероятно, вы вызвали из этого прерывания какой-то сервис, который выполнил перепланировку.

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


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

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

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

Гость
Ответить в этой теме...

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

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

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

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

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

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