您当前的位置: 首页 > 
  • 2浏览

    0关注

    483博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

ROS + UDEV管理开源小车rikirobot的USB设备

高精度计算机视觉 发布时间:2022-03-12 10:56:09 ,浏览量:2

在弄清楚udev的规则后(可参考我的前一篇博文),我们来看一下rikirobot的设备管理。

rikirobot的源码大家可以去github.com上搜索下载,有很多热心的网友已经将其打包上传,包括我们下面要讨论的setup文件,例如,

https://github.com/ykevin/rikirobot_setup

项目使用usb接口(包括USB串口)进行通讯时,我们都希望有个固定的设备名供程序调用。由于usb为即插即用设备,udev又是动态随机命名,所以,很难保证每次设备的名称都不变;因此,我们需要编写一些名称映射规则文件,对usb设备进行设置。

规则文件以.rules作为扩展名,规则配置路径一般在:

/etc/udev/rules.d/*

由于这些文件有优先级,所以一般在名称前面加上一个数字,系统加载时会按照数字进行排序,数字小的排前面(优先级别相对较高)。

规则格式示例: KERNEL=="ttyUSB*", ATTRS{idVendor}=="xxxx", ATTRS{idProduct}=="xxxx", MODE:="0777",  SYMLINK+="device_name" 其中 ATTRS{idVendor}=="xxxx" ATTRS{idProduct}=="xxxx"

从查询到的结果里进行配置。

下面我以我自己的通过ch340控制ROS小车进行通迅的实际配置为例进行说明。

通过查询命令

$ ls -l  /dev |grep USB crw-rw---- 1 root dialout 188,   0 Jan 10 04:56 ttyUSB0 $ ls -l  /dev |grep serial drwxr-xr-x 4 root root          80 Jan 10 04:56 serial

可以找到我们的串口设备;

$ lsusb Bus 003 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 002 Device 001: ID 1d6b:0003 Linux Foundation 3.0 root hub Bus 001 Device 004: ID 1a86:7523 QinHeng Electronics HL-340 USB-Serial adapter Bus 001 Device 003: ID 248a:8367 Maxxter USB2.0 Hub Bus 001 Device 002: ID 2109:3431 VIA Labs, Inc. Hub Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub

再细看一下,

$lsusb  -v

可以查到所有的usb设备的详细信息,其中包括要找的ch340,内容如下

Bus 001 Device 004: ID 1a86:7523 QinHeng Electronics HL-340 USB-Serial adapter
Couldn't open device, some information will be missing
Device Descriptor:
  bLength                18
  bDescriptorType         1
  bcdUSB               1.10
  bDeviceClass          255 Vendor Specific Class
  bDeviceSubClass         0 
  bDeviceProtocol         0 
  bMaxPacketSize0         8
  idVendor           0x1a86 QinHeng Electronics
  idProduct          0x7523 HL-340 USB-Serial adapter
  bcdDevice            2.64
  iManufacturer           0 
  iProduct                2 
  iSerial                 0 
  bNumConfigurations      1
  Configuration Descriptor:
    bLength                 9
    bDescriptorType         2
    wTotalLength       0x0027
    bNumInterfaces          1
    bConfigurationValue     1
    iConfiguration          0 
    bmAttributes         0x80
      (Bus Powered)
    MaxPower               98mA
    Interface Descriptor:
      bLength                 9
      bDescriptorType         4
      bInterfaceNumber        0
      bAlternateSetting       0
      bNumEndpoints           3
      bInterfaceClass       255 Vendor Specific Class
      bInterfaceSubClass      1 
      bInterfaceProtocol      2 
      iInterface              0 
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x82  EP 2 IN
        bmAttributes            2
          Transfer Type            Bulk
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0020  1x 32 bytes
        bInterval               0
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x02  EP 2 OUT
        bmAttributes            2
          Transfer Type            Bulk
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0020  1x 32 bytes
        bInterval               0
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x81  EP 1 IN
        bmAttributes            3
          Transfer Type            Interrupt
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0008  1x 8 bytes
        bInterval               1

熟悉usb的朋友一下子就可以看出,这个usb的通信协议是bulk,其中endpoint为0x8?为IN,0x0?的为Out,例如,用户的通迅是EP2-0x82(IN)/0x02(out),还有一个中断传输端口EP1-0x81(IN)。具体想了解usb规范的可以到这里去看一下,

USB 2.0 Specification | USB-IF

设备的idVendor和idProduct分别为,

idVendor           0x1a86 QinHeng Electronics idProduct          0x7523 HL-340 USB-Serial adapter

我们就可以建立一个规则,文件名称为 /etc/udev/rules.d/58-riki.rules

与ch340相对应的规则为内容为 KERNEL=="ttyUSB?", SUBSYSTEM=="tty", ATTRS{idVendor}=="1a86", ATTRS{idProduct}=="7523", MODE="0777" SYMLINK+="rikibase"

规则文件配置完成后,执行命令 service udev reload service udev restart 然后就可以在/dev下找到我们想看的rikibase了(如果不行的话,就重启吧), ls /dev/rikibase

然后在ros相应的launch文件中,配置的参数就可以固定为 /dev/rikibase了。ros的launch文件 serial_port参数定义为/dev/rikibase可以实现对相应硬件的调用设置,而不必插拔usb后在查看到底是那个端口号反复修改launch文件。

全部开源riki底盘树莓派中系统使用的规则配置示例及说明:

58-riki.rules
KERNEL=="ttyACM?", SUBSYSTEM=="tty", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="0483", MODE="0777" SYMLINK+="rikibase"
KERNEL=="ttyACM?", SUBSYSTEM=="tty", ATTRS{idVendor}=="0483", ATTRS{idProduct}=="5740", MODE="0777" SYMLINK+="rikiarm_left"
KERNEL=="ttyACM?", SUBSYSTEM=="tty", ATTRS{idVendor}=="2341", ATTRS{idProduct}=="0046", MODE="0777" SYMLINK+="rikiarm_right"
KERNEL=="ttyUSB?", SUBSYSTEM=="tty", ATTRS{idVendor}=="10c4", ATTRS{idProduct}=="ea60", ATTRS{serial}=="0001", MODE="0777" SYMLINK+="rikilidar"
KERNEL=="ttyUSB?", SUBSYSTEM=="tty", ATTRS{idVendor}=="1a86", ATTRS{idProduct}=="7523", MODE="0777" SYMLINK+="rikibase"
KERNEL=="ttyUSB?", SUBSYSTEM=="tty", ATTRS{idVendor}=="0403", ATTRS{idProduct}=="6001", MODE="0777" SYMLINK+="rikibase"
KERNEL=="ttyUSB?", SUBSYSTEM=="tty", ATTRS{idVendor}=="067b", ATTRS{idProduct}=="2303", MODE="0777" SYMLINK+="rikilidar"
558-orbbec-usb.rules
# Make primesense device mount with writing permissions (default is read only for unknown devices)
SUBSYSTEM=="usb", ATTR{idProduct}=="0401", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0402", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0403", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0404", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0405", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0406", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0407", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0408", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="0409", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
SUBSYSTEM=="usb", ATTR{idProduct}=="040a", ATTR{idVendor}=="2bc5", MODE:="0666", OWNER:="ubuntu", GROUP:="video"
49-teensy.rules
ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789B]?", ENV{ID_MM_DEVICE_IGNORE}="1"
ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789A]?", ENV{MTP_NO_PROBE}="1"
SUBSYSTEMS=="usb", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789ABCD]?", MODE:="0666"
KERNEL=="ttyACM*", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789B]?", MODE:="0666"
10-local-rpi.rules
SUBSYSTEM=="vchiq", GROUP="video", MODE="0660"

解释:

vchiq是个什么子系统?

VCHIQ is a command interface between the running Linux kernel and peripherals (among other things) in the VideoCore silicon. /dev/vchiq provides generic userspace access to those commands for use by (at minimum) the camera and audio subsystems as well. It's a decently dangerous interface to expose to random programs, hence the somewhat restrictive permissions by default.

40-scratch.rules
ATTRS{idVendor}=="0694", ATTRS{idProduct}=="0003", SUBSYSTEMS=="usb", ACTION=="add", MODE="0666", GROUP="plugdev"


99-com.rules
SUBSYSTEM=="input", GROUP="input", MODE="0660"
SUBSYSTEM=="i2c-dev", GROUP="i2c", MODE="0660"
SUBSYSTEM=="spidev", GROUP="spi", MODE="0660"
SUBSYSTEM=="bcm2835-gpiomem", GROUP="gpio", MODE="0660"

SUBSYSTEM=="gpio*", PROGRAM="/bin/sh -c '\
        chown -R root:gpio /sys/class/gpio && chmod -R 770 /sys/class/gpio;\
        chown -R root:gpio /sys/devices/virtual/gpio && chmod -R 770 /sys/devices/virtual/gpio;\
        chown -R root:gpio /sys$devpath && chmod -R 770 /sys$devpath\
'"

KERNEL=="ttyAMA[01]", PROGRAM="/bin/sh -c '\
        ALIASES=/proc/device-tree/aliases; \
        if cmp -s $ALIASES/uart0 $ALIASES/serial0; then \
                echo 0;\
        elif cmp -s $ALIASES/uart0 $ALIASES/serial1; then \
                echo 1; \
        else \
                exit 1; \
        fi\
'", SYMLINK+="serial%c"

本文结束

关注
打赏
1661664439
查看更多评论
立即登录/注册

微信扫码登录

0.0433s