Pull to refresh

Свой task switch logging за один день

Reading time3 min
Views2K
Еще на заре своей карьеры мне довелось поработать с RTOS VxWorks и средой разработки Tornado. Впечатления остались крайне положительные (тем более что сейчас есть с чем сравнивать), но пост не об этом. Составной частью системы тогда была система сбора и визуализации информации о переключении задач в реальном времени. Сразу скажу, что вещь крайне полезная, не зря ведь говорят, что лучше один раз увидеть. Скажем, если у вас в системе есть хотя бы два десятка задач, то с уверенностью в 99% можно сказать, что вы сильно удивитесь, когда увидите визуализацию переключения задач — она будет совсем не такой, какой вы ее себе представляли.

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

Но что же делать, если приходится работать с RTOS и окружением, где такого удобного механизма нет? Конечно же, сделать его самому!



Часть первая, сбор статистики.

Тут все просто — нам понадобится точный таймер (микросекунды или еще точне) и немного свободного места в памяти. В памяти выделяем место под массив под данные (из расчета «одно переключение — taskId + time»), «вешаемся» на событие OC «переключение задач» (и на вход-выход в/из прерывания, если хотим отслеживать и их тоже), и сохраняем данные (ID активизирующейся задачи и значение таймера) в массив (который используется как циклический буфер).

Можно также реализовать «User-defined events» — написать функцию, которая при ее вызове будет заносить в этот массив значения, чтобы увидеть, когда точно случается то или иное событие в коде.

Реализуем возможность запуска-остановки логирования по требованию (CLI, вызов функции...) и возможность непрерывного логирования (чтобы отследить, например, последние моменты перед сбоем — ведь после перезагрузки сохраненные данные отлично сохранятся в памяти, если конечно память не очищается принудительно).

И, в зависимости от embedded системы, реализуем какой-нибудь способ передачи этого массива с embedded устройства на PC, где и будем его будем визуализировать. Если на embedded есть файловая система — это может быть запись в файл, если нет — то какой-нибудь другой вариант — отправка по сети, например. Я использовал RS232, используемый в системе для отладки.

Осталось визуализировать собранную информацию. И здесь нам даже писать ничего не придется (ну или почти ничего). Можно использовать бесплатный пакет Octave, который умеет рисовать 2D графики функций и отлично реализует zoom-in — zoom-out (даже если вы соберете данные всего лишь за пару секунд, учитывая то, что обычно квант времени задачи — это 1 миллисекунда, без зума вам не обойтись).

Все, что нужно сделать — преобразовать собранные данные в формат Octave:

y = [time1, time2, …, timeN];
x = [task1, task2, …, taskN];
plot(x, y)
grid on

Здесь timeX — время (в любых единицах, удобнее использовать, например, микро- или миллисекунды, и сделать так, чтобы time1 было равно 0), а taskX — ID задачи (в принципе любое число, но удобнее, опять же, отсортировать задачи по приоритетам и нормировать их так, чтобы их ID были 1, 2, 3..., запомнив, какое значение у какой задачи). При наличии прерываний и пользовательских событий тоже можно что-нибудь придумать, например, нумеруя пользовательские события отрицательными числами.

Как сделать это преобразование — каждый может выбрать сам (именно здесь и придется немного написать своего кода).

В результате получится что-то вроде такого. Вот так выглядела система в незагруженном (idle) состоянии:



А вот так — полностью загруженная:

"

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

Профессионально сделанное решение от WindRiver было, конечно, покрасивее, показывало имена задач, а не абстрактные ID, точками на графике показывало интересные моменты… Но если его нет, то лучше иметь свое, хоть и более простое, чем не иметь его вообще.
Tags:
Hubs:
Total votes 4: ↑4 and ↓0+4
Comments6

Articles