Giter Club home page Giter Club logo

microscope-controller's Introduction

Программа управления микроскопом: Modbus TCP/RTU конвертер и web-интерфейс на базе Raspberry Pi.

Содержание

  1. Первое включение и установка wi-fi соединения
  2. Пользовательский интерфейс управления
  3. Настройка устройства и конфигурационные файлы
    1. Конфигурация TCP/RTU конвертера
    2. Конфигурация сервера микроскопа
  4. Информация для разработчиков
    1. Команды, поддерживаемые камерой при запуске без сервера микроскопа
    2. Запуск и отображение стрима
    3. Как посмотреть логи сервисов?
    4. Какие пины UART доступны для использования на RPI4?
    5. Как пересобирать и обновлять код?
    6. Что было установлено в образе?

Первое включение и установка wi-fi соединения

По дефолту устройство при загрузке пытается подключиться к следующей wi-fi сети:

SSID: Issaya
PASS: <мобильный заказчика>

Чтобы настроить свою сеть и подключить устройство к другой сети wi-fi, необходимо временно поднять точку доступа с вышеуказанными параметрами, дождаться пока плата подключится к ней и узнать IP-адрес. Например, посмотреть его на web-странице роутера или с помощью nmap на Linux системах.

Помните, что на плате RPI есть единственный и дефолтный пользователь в системе:

User: pi
Password: \\

Далее нужно залогиниться по SSH на плату.

ssh pi@<ip-addr>

И выполнить следующие команды для установки нового wi-fi соединения

nmcli device wifi connect YOUR-SSID password "YOUR-PASSWORD"
nmcli device set wlan0 autoconnect yes
sudo reboot

После этого устройство всегда будет подключаться к вашей сети автоматически.

Пользовательский интерфейс управления

После успешного подключения устройства к сети необходимо узнать его ip-адрес, если он ещё вам неизвестен. Например, это будет 192.168.1.55. Веб-интерфейс управления доступен на порту 5000. То есть, чтобы открыть UI, нужно в браузере зайти на страницу: http://192.168.1.55:5000/.

UI с устройств Mac/Windows/Linux с использованием Google Chrome (Firefox аналогично)



UI с устройства Android с использованием Google Chrome (Firefox аналогично)


Настройка устройства и конфигурационные файлы

Как только плата стала "онлайн", на ней автоматически запускается два systemd-сервиса:

  1. Сервис, реализующий логику преобразования протокола Modbus TCP в Modbus RTU, для взаимодействия с микроконтроллером, подключенным в к плате RPI. Сервис называется modbus_converter.

  2. Сервис, реализующий HTTP-сервер и непосредственный стриминг видео, для взаимодейтсвия с устройстром через браузер. Сервис называется microscope_server.

Оба этих сервиса можно настраивать с помощью конфигурационных файлов. Все нужные конфиги и все исполняемые файлы находятся по пути - /home/pi/.microscope. (обратите внимание, что в названии есть точка).

Конфигурация TCP/RTU конвертера

Конфигурационный файл сервиса modbus_converter - это /home/pi/.microscope/modbus_converter.conf. Формат файла - JSON. Этот конфиг считается низкоуровневым и служит для настройки пинов и скорости UART на плате RPI, к которому подключён нижестоящий микроконтроллер. Дефолтный конфиг выглядит так:

{
    "uart_device": "/dev/ttyAMA5",
    "uart_baud": "9600",
    "uart_parity": "N",
    "uart_data_bit": "8",
    "uart_stop_bit": "1",

    "modbus_port": "1502",
    "modbus_number_of_tcp_connections": "1",
    "modbus_connected_microcontroller_slave_addr": "1",
    "modbus_camera_slave_addr": "2",
    "modbus_loss_connection_timeout_ms": "1000"
}

modbus_port - порт, на котором сервис modbus_converter откроет TCP соединение.

modbus_number_of_tcp_connections - количество возможных TCP соединений. Это для будущего использования. На данный момент поддерживается только одно соединение. Если изменить этот параметр, то сервис выдаст в лог информацию о том, что это пока не поддерживается и всё равно будет создавать только одно соединение.

modbus_connected_microcontroller_slave_addr - slave-адресс нижестоящего микроконтроллера. Можно установить какой угодно, так как любые присланные данные будут переданы устройству uart_device, но важно, чтобы это значение не совпадало c slave-адресом камеры.

modbus_camera_slave_addr - slave-адрес, на который будет реагировать камера. Это используется, если хотите получать и управлять видеостримом БЕЗ web-сервера. Например, это может быть полезно для написания собственного UI, в котором будет управление потоком.

modbus_loss_connection_timeout_ms - время ожидания ответа (в милисекундах) от нижестоящего микроконтроллера. Если в течении этого промежутка времени нет ответа от устройства uart_device, то сервис просто начинает заново ожидать указаний по TCP.

!!! Важно !!!

Если какой-либо из параметров был изменён, то НЕОБХОДИМО ПЕРЕЗАПУСТИТЬ сервис, чтобы настройки вступили в силу:

sudo systemctl stop modbus_converter
sudo systemctl start modbus_converter

Или просто перезагрузить устройство:

sudo reboot

Конфигурация сервера микроскопа

Конфигурационный файл сервиса microscope_server - это /home/pi/.microscope/microscope_server.conf. Формат файла - JSON. Этот конфиг считается высокоуровневым и используется для задания количества шагов двигателей при работе с устройством. Дефолтный конфиг выглядит так:

{
    "home_steps_cnt_focus_stepper": "-32766",
    "home_steps_cnt_updown_stepper": "-32766",
    "home_steps_cnt_leftright_stepper": "-32766",

    "swap_updown_and_leftright_logic": "yes",

    "work_steps_cnt_focus_stepper": "-300",
    "work_steps_cnt_updown_stepper": "-111",
    "work_steps_cnt_leftright_stepper": "-112",

    "retention_step_size_focus_stepper": "1",
    "retention_step_size_updown_stepper": "1",
    "retention_step_size_leftright_stepper": "1",

    "modbus_repeat_cmd_period_ms": "100",
    "modbus_soc_polling_period_ms": "60000",
    "modbus_led_max_pwm_percentage": "20",
    "modbus_debug_mode": "Off"
}

home_steps_* - это количество шагов, которые будут посылаться сервисом в нижестоящий микроконтроллер, когда пользователь нажимает кнопку HOME в интерфейсе управления. Соответственно при дефолтной конфигурации сервер пошлёт в микроконтроллер следующие данные:

  1. -32766 шагов на мотор, отвечающий за фокусировки камеры
  2. -32766 шагов на мотор, отвечающий за движение ввер-вниз
  3. -32766 шагов на мотор, отвечающий за движение вправо-влево

В этот параметр можно устанавливать как положительные числа(то есть без явного указания знака), так и отрательные (то есть явно пишут знак "-", как в дефолтном конфиге). Либо можно установить значение "0". Это будет означать, что сервер не будет посылать ничего на тот мотор, где указано это значение.

swap_updown_and_leftright_logic - если указано "yes", то моторы up-down и "left-right" инвертированы. То есть вы нажимаете ехать, например, кнопки влево/вправо, а по факту команда пошлётся для моторов вверх/вниз.

work_steps_* - это количество шагов, которые будут посылаться сервисом в нижестоящий микроконтроллер, когда пользователь нажимает кнопку WORK в интерфейсе управления. Тут также можно устанавливать либо положительные числа, либо отрицательные, либо ноль.

retention_step_size_* - это количество шагов, которые будут посылаться сервисом в нижестоящий микроконтроллер, когда пользователь удерживает кнопки +/- или up/down/left/right. То есть при однократном нажатии пошлётся точно 1 шаг. А при удержании будет переодически посылаться кол-во шагов, указанное тут.

modbus_repeat_cmd_period_ms - период в милисекундах, с которым браузер будет повторять команды при удержании кнопок.

modbus_soc_polling_period_ms - период в милисекундах, с которым браузер будет опрашивать заряд уст-ва.

modbus_led_max_pwm_percentage - максимальное значение яркости светодиодов в процентах от максимума ШИМ.

!!!Важно!!! При обновлении какого либо параметра в этом конфиге достаточно просто ОБНОВИТЬ страницу в браузере, чтобы сервер считал новые данные

Информация для разработчиков

Команды, поддерживаемые камерой при запуске без сервера микроскопа

Запуском стрима можно управлять напримую по Modbus TCP без участия сервера. НО для этого нужно зайти на RPI и остановить работу сервера:

sudo systemctl stop microscope_server

Камера будет реагировать на тот адрес slave-устройства, что указали в конфиг-файле. Команды для всех остальных адресов будут пересылаться нижестоящему микроконтроллеру. На данный момент камера поддерживает только одну команду (один Modbus function code) - MODBUS_FC_WRITE_SINGLE_REGISTER=0x06 Это команда на запись аналогового вывода. Была выбрана именно эта команда, так как в будущем можно сделать, чтобы 16-битные регистры Modbus отвечали за настройки камеры. Например, настройка зума, баланса белого и тд.

На данный момент поддерживается только один регистр у этой команды - CAMERA_API_LAUNCH_VIDEO_REG_ADDR=0x01 Этот регистр отвечает за состояние видеопотока. Значения этого регистра могут быть следующие:

typedef enum {
    CAMERA_API_LAUNCH_VIDEO_4K_VALUE = 0x00,
    CAMERA_API_LAUNCH_VIDEO_1080P_VALUE = 0x01,
    CAMERA_API_LAUNCH_VIDEO_STOP_VALUE = 0x02,
} camera_api_supported_cmd_values_t;

Примеры Modbus-команд для камеры:

0x02 0x06 0x00 0x01 0x00 0x00 <crc16> - запустить 4к видео стрим на ip адресс хоста.
0x02 0x06 0x00 0x01 0x00 0x01 <crc16> - запустить 1080p видео стрим на ip адресс хоста.
0x02 0x06 0x00 0x01 0x00 0x02 <crc16> - остановить вообще видеопоток. (Использовалось для отладки).

Если камера получила неподдерживаемые значения fucntion code, регистра или значений регистров, то сервис modbus_converter вернёт соответствующие коды ошибок вышестоящей программе, приславшей неверную команду. В данном случае - программе Modbus Poll.

Запуск и отображение стрима

Как только к сервису modbus_converter присоединился по TCP какой-то клиент, то сервис самостоятельно определяет IP адрес этого хоста и записывает его в соответствующий конфиг-файл. Далее, как только конвертер получил команду для камеры, то он запускает соответствующий скрипт на RPI. Если запросили 4к, то запускает 4к. Если 1080p, то 1080p. Предварительно будет считан конфиг-файл с адресом хоста. И именно на этот адрес будет посылать видеострим с помощью gstreamer.

Как установить gstreamer на любую платформу? На плате RPI он уже установлен:

Если вы хотите запустить стрим в каком-либо разрешении, то нужно просто послать соответствующую Modbus-команду на запуск стрима. Предварительно посылать команду "стоп" не нужно. Конвертер сам остановит старый стрим и запустит новый, если это необходимо.

Но на хосте нужно запускать соответствующие скрипты для отображения стрима руками. Скрипты для хоста лежат в этом репозистории в директории scripts/. Файлы с префиксом host_ в названии - это скрипты для запуска на хосте для отображения видеопотока. Все остальные скрипты в этой директории не обязательны для пользователя. Они либо уже есть в образе, либо используются системой сборки для компиляции/установки.

 Для стрима 1080p
   На хосте запустить ./host_show_mjpg_1080p_stream_with_fps

 Для стрима 4к
    На хосте запустить ./host_show_h264_stream_with_fps

То есть сценарий запуска такой:

  • Сначала посылается соответствующая команда для камеры по Modbus TCP
  • Затем на хост-машине запускается соответствующий скрипт. При этом, если ранее на хосте уже был запущен какой-либо из скриптов, то его нужно остановить и только потом запускать новый.

Это нужно делать руками только лишь потому, что стримы посылаются в разных кодировках. Для 4к используется H264. Для 1080p - MJPG. Поэтому на хосте требуется запускать разные декодеры.

Как посмотреть логи сервисов?

# Просмотр логов сервиса modbus_converter в режиме tail -f, показав последние 50 строк лога
sudo journalctl -a -f -n 50 -u modbus_converter

# Просмотр логов сервиса modbus_converter с момента последней загрузки системы
sudo journalctl -b -u modbus_converter

По дефолту сервис скомпилирован с параметром MODBUS_CONVERTER_DEBUG=0 (см. Makefile), поэтому логов будет не очень много. Логироваться будут только ошибки и немного теоретически полезной информации о состоянии программы. Если нужен подробный лог происходящего, то нужно пересобрать и перезапустить сервис с установленным этим дефайном в значение 1.

# Просмотр логов сервиса microscope_server в режиме tail -f, показав последние 50 строк лога
sudo journalctl -a -f -n 50 -u microscope_server

# Просмотр логов сервиса microscope_server с момента последней загрузки системы
sudo journalctl -b -u microscope_server

Какие пины UART доступны для использования на RPI4?

https://raspberrypi.stackexchange.com/questions/45570/how-do-i-make-serial-work-on-the-raspberry-pi3-pizerow-pi4-or-later-models/107780#107780

В образе включены 3 разных uart, которые можно использовать для подключения к ним uart от нижестоящего микроконтроллера. Здесь пины - это номер пина на 40-ко пиновой гребёнке.

# /dev/ttyAMA3 - UART3.
  PIN7 - TX
  PIN29 - RX

# /dev/ttyAMA4 - UART4.
  PIN24 - TX
  PIN21 - RX

# /dev/ttyAMA5 - UART5. <--- дефолт
  PIN32 - TX
  PIN33 - RX

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

Если в код были внесены изменения, то все они будут закомичены тут, в этот репозиторий. Чтобы применить изменения на стороне заказчика необходимо сделать следующее:

Залогиниться по ssh на RPI и далее:

1. cd Microscope-controller
2. ./update.sh

После этого можно вновь пользоваться устройством как ранее.

Что было установлено в образе?

Сам образ представляет из себя дефолтный образ для RPI4 без графического интерфейса.

  • Далее были включены девайсы последовательных портов. Для этого в device tree были добавлены overlays. Они включены с помощью записи следующих строк в файл /boot/config.txt
enable_uart=1
dtoverlay=uart3
dtoverlay=uart4
dtoverlay=uart5

Они загружаются во время boot-time, поэтому команда dtoverlay -l не покажет их.

Также в образе включен bootlog uart. Можно подсоединить к гребенке на PIN8(tx0) и на PIN10(rx0) uart-usb преобразватель и пользоваться этим uart, как консолью для управления платой RPI без подключения платы к wifi и без SSH.

Посмотреть текущую конфигурацию пинов можно с помощью следующих команд:

$ pinctrl

либо

$ raspi-gpio get

Обе команды выводят информацию о текущих настройках пина. В этом случае в выводе каоманд GPIO-N - это номер gpio на процессоре. То есть НЕ на 40-ко пиновой гребёнке.

  • В файл ~/.bashrc добавлены эти строки:
export LC_ALL="en_US.UTF-8"
export LANG="en_US.UTF-8"
alias ll="ls -l"
alias myip='curl ipinfo.io/ip; echo'
  • Пользоваьель pi добавлен в sudouser
sudo adduser pi sudo
  • Ограничен размер логов до 100Mb и выключен бродкастинг в journalctl
sudo nano /etc/systemd/journald.conf
SystemMaxUse=100M
ForwardToWall=no 
sudo systemctl restart systemd-journald
  • Отключено логирование PAM-сессий в journal
sudo nano /etc/sudoers
Defaults !syslog, !pam_session
  • Далее были доустановлены в образ следующие программы:

gstreamer

sudo apt-get install libgstreamer1.0-dev libgstreamer-plugins-base1.0-dev libgstreamer-plugins-bad1.0-dev gstreamer1.0-plugins-base gstreamer1.0-plugins-good gstreamer1.0-plugins-bad gstreamer1.0-plugins-ugly gstreamer1.0-libav gstreamer1.0-tools gstreamer1.0-x gstreamer1.0-alsa gstreamer1.0-gl gstreamer1.0-gtk3 gstreamer1.0-qt5 gstreamer1.0-pulseaudio

Программы для компиляции библиотек и конвертера

sudo apt-get install git autoconf libtool

libmodbus

git clone https://github.com/stephane/libmodbus.git
cd ~/Microscope-controller/modbus_tcp_rtu_converter/patches
scp * [email protected]:/home/pi/libmodbus/
cd ~/libmodbus
git apply libmodbus_tid.patch
git apply libmodbus_msglen.patch
sudo ./autogen.sh
sudo ./configure --prefix=/usr/local/
sudo make
sudo make install

libsystemd для Python-обёртки

sudo apt-get install libsystemd-dev
sudo apt-get install python3-dev

lsof

sudo apt-get install lsof

v4l

sudo apt-get install v4l-conf

Flask

# Install Flask itself
cd ~
python3 -m venv .venv
. .venv/bin/activate

cd /home/pi/Microscope-controller/web_server
pip install -r requirements.txt
deactivate

# Run server at <ip>:5000
. .venv/bin/activate
cd /home/pi/Microscope-controller/web_server
flask run --host=0.0.0.0 --debug --app microscope_server.py

microscope-controller's People

Contributors

anisyanka avatar

Watchers

 avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.