CAN и GPS адаптер для RaceChrono
CAN и GPS адаптер для RaceChrono

В любительском и не очень профессиональном сегменте авто-мото спорта многие используют приложение RaceChrono для записи телеметрии и хронометража. Если кратко, то RaceChrono позволяет решить 2 задачи:

  1. Хронометраж. Отсечка времени по кругам или по линии старта и финиша. Приложение позволяет в "онлайне", прямо во время движения, видеть опережение или отставание от лучшего времени. Прямо как в компьютерной игре.

  2. Запись телеметрии (траектории движения, параметров работы автомобиля) и последующий их просмотр для анализа. Так же можно наложить отображение нужных параметров на видео.

Как правило, для решения этих задач используют 2 отдельных устройства: внешний GPS приемник и CAN-адаптер. И то и другое выпускается промышленно и доступно для покупки.

Я сделал небольшое устройство, которое сочетает в себе сразу всё необходимое: GPS на 25 Гц и CAN интерфейс.

Железо

Выбор GPS приемника.

Внешний GPS приемник нужен для более высокой частоты обновления позиции. В мобильном телефоне уже есть GPS приемник, только его частота обновления 1 Гц, он выдает координаты 1 раз в секунду. Если автомобиль движется со скорость 100 км/ч, за 1 секунду он проходит 27 метров. Хотелось бы получать траекторию движения более точно.

Большинство доступных для покупки bluetooth GPS приемников имеют частоту обновления 10 Гц.

Я использовал модуль Ublox M9N, который, согласно его описанию, при использовании GPS+GLO+GAL выдает координаты 25 раз в секунду. Модуль относительно не дорогой и его можно приобрести. Документация у Ublox вполне хороша, есть и hardware integration manual и описание протокола. Кроме стандартного NMEA приемники Ublox работают по собственному бинарному протоколу, который значительно удобнее разбирать со стороны микроконтроллера.

Выбор микроконтроллера

Поддержка "самоделок" в RaceChrono была реализована достаточно давно. Используя классический Bluetooth можно было слать сообщения в формате RC2 и RC3. Набор параметров там ограничен, но это лучше, чем ничего.

Относительно недавно автор добавил новый способ подключения "самоделок", через BLE. Новый API рассчитан в первую очередь на подключение GPS приемников и CAN адаптеров. Есть так же возможность наоборот, получать данные из RaceChrono к себе в устройство, для создания каких-то мониторов.

Поскольку нужна была работа с BLE, выбор микроконтроллеров был не очень широким. Я предпочитаю STM32, но контроллеров с поддержкой BLE в количестве нескольких штук было не купить. Поэтому был выбран nRF52840.

Документация у Nordic похуже чем у ST, но в целом вполне достаточно. Чтобы немного облегчить себе жизнь, я решил использовать не голый МК, а в виде готового модуля Ebyte E73-2G4M08S1C. Больше всего мне не хотелось заниматься расчетом и разводкой радио части. Модуль не сильно больше по размерам чем голый МК + обвязка и купить его можно без проблем.

Выбор CAN интерфейса

К сожалению у nRF52840 нет CAN интерфейса. Поэтому пришлось использовать внешний. Выбрал самый популярный и легко доступный, mcp2515. Отдельно микросхем или в наличии не было или стоимость была неадекватной, поэтому проще оказалось купить на али готовые модули и снять с них микросхему и заодно кварц. На модуле используется 5 вольтовый трансивер, на нем сэкономить не получилось, использовал SN65HVD230.

Схема

Основная схема
Основная схема
Питание
Питание
GPS модуль
GPS модуль

Схема устройства и весь проект в KiCad, а также список комплектующих и файлы для производства лежат на GitHub.

Программная часть

Для своих МК Nordic предоставляет SDK. Я использовал сборку при помощи GCC через Makefile. В целом, вполне понятный HAL.

Для упрощения себе жизни, я использовал в проекте FreeRTOS. Сама RTOS уже есть в SDK, поэтому можно сказать всё было готово для использования "из коробки".

С BLE я раньше не сталкивался. Протокол оказался достаточно обширным. Кроме того, сам стек BLE у Nordic закрыт. Он прошивается во флеш отдельно и основная прошивка вызывает нужные функции по заранее определенным адресам. Это называется softdevice. Для "пользователя" это достаточно прозрачно, надо лишь помнить, что часть аппаратных ресурсов (таймеры, прерывания) используется внутри softdevice.

Работа с BLE сделана по примеру от Nordic - nRF52 Bluetooth Course.

Некоторые сложности возникли только, как ни странно, с UART. Вроде не сложный блок периферии, но завести удалось совсем не сразу. В SDK есть несколько драйверов для UART. Я сначала пробовал те, что попроще, но при скорости обмена выше 33600 начинались переполнения приемного буфера и мусор в принимаемых данных. В какой-то момент я решил вообще отказаться от использования HAL нордика и сделать свою реализацию. Тут оказалось, что ничего похожего на reference manual от ST, где описаны все регистры, все режимы работы и все последовательности инициализации у Nordic нет. Есть описание регистров, но без особых подробностей. Наиболее наглядным было изучение внутренностей HAL. В итоге, использовал драйвер libuarte из SDK и все заработало без ошибок на 115200.

С SPI и mcp2515 никаких проблем не возникло. В драйвере mcp2515 я реализовал только тот минимум, который был нужен мне. Прием работает по прерыванию с ноги INT.

API RaceChrono предполагает, что пересылаться будут напрямую CAN пакеты. Причем зарезервированы места даже для Extended ID, которых в живую я ни разу не видел. Предполагается следующая схема работы: устройство получает CAN пакет, пересылает его через BLE, а уже приложение RaceChrono на мобильном устройстве извлекает из данных пакета нужные параметры.

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

Я реализовал разбор 2 CAN протоколов. Во-первых это протокол adlm для блоков управления "Абит М11 Корвет". У производителя есть подробное описание протокола.

Во-вторых, это очень базовая реализация протокола ODBII. Дело в том, что заниматься отладкой на спортивном автомобиле и дорого и неудобно. Поэтому отлаживал я на повседневном автомобиле. Реализовано получение лишь нескольких базовых параметров (обороты, температура, дроссель).

Прошивка также доступна на GitHub.

Тестовый образец выглядит вот так:

Для тестов использовал самую дешевую gps антенну с али. Крепится на магните на крышу автомобиля. Корпус сделан на 3D принтере с расчетом под отладку (есть доступ к SWD разъему). Кабель для подключения к ODB разъему (используется 12В, GND, CAN-Hi, CAN-Low).

Ну и пример работы:

На видео в параметре "Частота обновления" два значения. Верхнее это обновление GPS данных (постоянно 25 Гц), нижнее это обновление данных из CAN. Частота CAN немного плавает около 18-20 Гц, но думаю это решаемо программно. Само приложение RaceChrono запущенно на телефоне, который на стекло прилеплен.

Что не реализовано.

Можно было бы реализовать поддержку K-Line. На мотоциклах (в частности у Honda) используется протокол аналогичный KWP2000. Можно собирать данные с K-линии, складывать в CAN пакет и отправлять в RaceChrono. Я не уверен, насколько это вообще кому-то нужно, поэтому поленился делать.

Комментарии (8)


  1. igor_suhorukov
    30.08.2023 14:40
    +1

    Прямо как в компьютерной игре!


  1. mrsnowin
    30.08.2023 14:40

    Прекрасная работа! Приятно видеть качественный и информативный онборд.

    Какой скорости удалось добиться на OBD протоколе?

    У меня хонды 2000х годов, CAN шины там нет, есть только OBD. С помощью дешёвых OBD Bluetooth адаптеров удается читать 5гц на все каналы суммарно, как заявляет RaceChrono, но судя по графику их там нет даже близко, скорее 1гц даже если читать только обороты двигателя.

    Переплатил интернеты и заказал OBDLink MX+, везде заявляют максимально возможную скорость, но что то мне подсказывает что она будет сильно ограничена возможностями ЭБУ старой хонды :)


    1. mrsnowin
      30.08.2023 14:40

      Конечно перелопатил, а не переплатил, хотя, судя по его цене, первый вариант тоже подходит.


    1. Sergey78 Автор
      30.08.2023 14:40

      Под OBD протоколом я подразумевал стандартный протокол по CAN который есть во всех современных автомобилях. Вот тут подробности https://en.wikipedia.org/wiki/OBD-II_PIDs Работает это по схеме "запрос-ответ". Мой форд отвечает с некоторой задержкой и частота в результате получается около 10Гц. В каждом запросе только один параметр, в итоге чем больше параметров тем ниже частота. У меня вроде было около 10Гц при запросе 3 параметров (обороты, дроссель, температура). Если вопрос принципиальный, могу проверить. Но ограничено там всё именно блоком управления, он с задержкой отвечает.

      Если нужно получать быстрее, надо смотреть на сообщения на шине конкретного производителя. У того же форда на шине около 2000 сообщений в секунду летит. Но никакого доступного описания нет, надо самостоятельно искать ID и разбирать пакеты.

      То, что вы подразумеваете под OBD без CAN-шины, это скорее всего как раз обмен по K-Line. Я экспериментировал с этим на мотоцикле (honda cb-600). Структура обмена там достаточно типовая, похожа на KWP2000. Работает тоже по схеме "запрос-ответ" и есть установленные протоколом задержки между посылками. В итоге частота тоже была небольшая, до 10Гц суммарно. Только описания что где лежит нормального нет и пришлось лог. анализатором смотреть обмен и вычислять параметры.

      OBD это же OnBoard Diagnostic, оно для других целей, поэтому и больших скоростей обмена там нет.

      У того же Абита, например, протокол по CAN построен иначе. Это блок специально для спорта и ничего запрашивать там не нужно. Блок сам шлет все параметры с заданной частотой. Те же обороты, например, идут с частотой 100Гц.


      1. mrsnowin
        30.08.2023 14:40

        https://www.youtube.com/watch?v=enP3at7eHrU < Вот тут я читаю из OBD только педаль газа и обороты. В целом даже на видео хорошо видно с какой большой задержкой это происходит... В итоге отказался вообще от этих показаний на онбордах и графиках, потому что они только дезинформируют. RaceChrono на эти два канала показывает в графиках 5гц, но визуально это вообще так не выглядит, слишком рваный график, между точками оборотов может быть спокойно 2000+rpm.

        Наверняка при чтении через дешевый Bluetooth OBD накладывается много лишних действий, что сильно замедляет процесс обмена данными. По идее температуру и подобные параметры можно запрашивать реже (такое и сейчас реализовано в RaceChrono), а вот дроссель и обороты по идее как раз максимально быстро.

        Было бы интересно попробовать ускорить чтение этих данных из обычного OBD.

        Абит и другие спортивные ЭБУ мне, к сожалению, нельзя по регламенту.


        1. Sergey78 Автор
          30.08.2023 14:40

          На 2:20 на переключении газ не отпускали, или это пропуск получения данных?


          1. mrsnowin
            30.08.2023 14:40

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


  1. melodictsk
    30.08.2023 14:40

    Делал аналогичное устройство. У меня через ble была задержка порядка секунды. Обычный блютус реагирует почти мгновенно. Наверное от модуля зависит.