Pull to refresh

Дебаггинг в реальном времени через JTAG/SWJ-DP для микроконтроллеров на ядре ARM Cortex-M

Reading time4 min
Views39K

С некоторых пор фирма Segger предлагает технологию Real Time Terminal (RTT) для своих JTAG адаптеров J-Link. Суть ее в том, что программа на микроконтроллере может выводить и принимать отладочную информацию из JTAG/SWJ-DP порта, как это обычно делается через UART. И тогда нам больше не нужен реальный отладочный UART. Далее чуть подробнее о возможностях этой технологии.

Возможность выводить программой отладочную информацию в порт JTAG/SWJ-DP была реализована, как только у микроконтроллеров появился сам этот порт. Для этого есть два пути: использовать технику semihosting или технику Serial Wire Output (SWO).

Использование semihosting приводит к подмене каналов ввода-вывода стандартных файловых операций языка С-и. Это не всегда приемлемо, поскольку файловые операции в приложении могут уже использоваться по другому назначению. Также semihosting необходимо явно отключать и перекомпилировать проект при выпуске релизной версии.

Вдобавок ко всему semihosting обеспечивает самую медленную передачу данных из рассматриваемых здесь технологий.

Использование Serial Wire Output проще чем semihosting, однако требует использования дополнительного сигнала SWO порта JTAG/SWJ-DP, и также вызывает необходимость в перекомпиляции при переходе на релизную версию, т.е. версию без подключения отладчика. Функции вывода SWO синхронные, т.е. ожидают готовности порта и не обладают необходимым детерминизмом.

Технология Real Time Terminal от Segger еще более упрощает вывод отладочной информации через SWJ-DP и предоставляет следующие удобства:
• Достаточно только двух внешних линий– это SW CLK и SW DIO.
• Весь дополнительный код в микроконтроллере занимает не более 500 байт, если не использовать ввод, то даже 300 байт.
• Не требуется перекомпиляция для релизной версии, функции отладочного вывода асинхронные и практически не занимают процессорного времени и не оказывают никакого влияния на ход выполнения программы при отсутствии подключения отладочного адаптера.
• Скорость отладочного ввода-вывода очень высока.
• Отладочный ввод-вывод можно перенаправить в любую стороннюю программу эмулятор терминала поддерживающую протокол telnet.
• Segger предоставляет бесплатные утилиты эмулятора терминала, логгера и telnet клиента для подключения к микроконтроллеру через отладочный адаптер без необходимости запуска сторонних IDE с отладчиками.



Пример использования RTT.


На рисунке выше плата контроллера на базе чипа STM32F745VET6. Внешний кварц 16 МГц. Частота ядра 168 МГц.
Отладка потребовалась для начального загрузчика по шине CAN. Последовательный порт RS232 подключенный к UART есть, но тоже используется для загрузчика. Выводить в него отладочную информацию означало бы сильно видоизменить отладочную версию программы по сравнению с релизной. При дефиците времени это крайне нежелательно.

Для подключения RTT были выполнены следующие шаги:
  1. Взяты исходники RTT (http://download.segger.com/J-Link/RTT/RTT_Implementation_141217.zip)
  2. Исходники распакованы и скопированы в директорию проекта названную RTT. Сам проект выполнялся в среде Keil MDK ARM
  3. Исходники подключены к проекту. В общий список заголовочных файлов проекта добавлены файлы SEGGER_RTT.h и SEGGER_RTT_Conf.h
  4. В файле SEGGER_RTT_Conf.h выполнены дополнительные настройки: значение BUFFER_SIZE_UP увеличено до 2048, значение SEGGER_RTT_PRINTF_BUFFER_SIZE увеличено до 512. Параметры изменялись на самом деле итерационно, пока не перестали происходить переполнения указанных буферов.
  5. Редактирование исходников загрузчика. Во все интересующие места были вставлены вызовы функции SEGGER_RTT_printf с необходимыми сообщениями. Использовал эту функцию как самую удобную, хотя она и вносит значительное потребление стека и определенную задержку преобразования данных. Но в моем случае это было приемлемо.
  6. Поскольку нужна была отладка даже во время программирования внутренней Flash, то перенес код RTT в RAM микроконтроллера. Для этого во всех 2-х файлах исходников RTT ввел директиву
    #pragma arm section code = «CODE_IN_RAM»,

    а в файле линкера .sct определил эту область следующим образом:
    RW_IRAM1 0x20000000 0x00010000
    {
    .ANY (+RW +ZI)
    *(CODE_IN_RAM)
    }
  7. Определил для структуры SEGGER_RTT_CB абсолютный адрес размещения директивой
    static SEGGER_RTT_CB _SEGGER_RTT __attribute__((at(0x20000000)))
  8. Скомпилировал проект. После компиляции выяснилось, что код RTT в RAM занял 400 байт при нулевой оптимизации.
  9. Вставил в инструментальное меню IDE Keil вызов утилиты JLinkRTTViewer.exe
  10. Поскольку предпочитаю в качестве эмулятора термина использовать TeraTerm, то вставил в меню вызов и его. Строка вызова при этом такая:
    ”C:/Program Files (x86)/teraterm/ttermpro.exe” /T=1 telnet://localhost:19021 /X=0 /Y=0 /W=»J-Link RTT"


Пропускная способность


Показалось интересным с какой же скоростью выводится информация в эмулятор терминала через отладочный адаптер с применением RTT. Были сняты осциллограммы с сигналов SW SLK и SW DIO.

Оказалось, что в J-Link используется поллинг с периодичностью около 40 мс. Для передачи данных используется не более 50% этого периода. В блоке данных передаваемых за период пакеты несущие полезные данные занимают тоже не более 50% времени. Пакеты переносят не более 3-х байт полезных данных. Три байта полезных данных в пакете также занимают не более 50% его длины. Итого получаем: 0.5*0.5*0.5 = 0.125 т.е. 12.5 % пропускной способности канала SW используется для передачи отладочного вывода.

Частоту канала выше 4 МГц в J-Link поднять не удалось ни при каких настройках. Это значит, что максимально мы имеем скорость передачи 4 Мбит/с. Из них только 4*0.125= 0.5 т.е. 500 Кбит/с в лучшем случае можно использовать для отладочного вывода. Это, конечно, немного, по сравнению с реальным отладочным UART, которые могут передавать на скоростях в несколько Мбит/с, но все имеет свою цену.
Tags:
Hubs:
Total votes 25: ↑24 and ↓1+23
Comments1

Articles