jmtpfs
当我将 GoPro 插入计算机时,我尝试使用它来安装它来传输文件。
我有一个可以在 udev 规则之外运行的脚本。但是,当在 udev 规则内运行时,该脚本会失败并断开我的 USB 设备。
这里给出了一个最小的工作示例:
脚本
#!/usr/bin/env bash
jmtpfs /media/GoPro > /tmp/gopro.log 2> /tmp/gopro.err
udev 规则
SUBSYSTEM=="usb", ATTR{idVendor}=="2672", ATTR{idProduct}=="004b", ACTION=="add", RUN+="/bin/bash -c /home/matt/Projects/GoProScraping/scripts/grab_go_pro_files.sh"
该文件的输出/tmp/gopro.err
是:
Device 0 (VID=2672 and PID=004b) is UNKNOWN in libmtp v1.1.19.
Please report this VID/PID and the device model to the libmtp development team
fusermount: mount failed: Operation not permitted
的输出journalctl -f
为:
Sep 29 09:45:31 nina kernel: usb 1-4: new high-speed USB device number 16 using xhci_hcd
Sep 29 09:45:31 nina kernel: usb 1-4: New USB device found, idVendor=2672, idProduct=004b, bcdDevice= 0.01
Sep 29 09:45:31 nina kernel: usb 1-4: New USB device strings: Mfr=1, Product=2, SerialNumber=3
Sep 29 09:45:31 nina kernel: usb 1-4: Product: GoPro MAX
Sep 29 09:45:31 nina kernel: usb 1-4: Manufacturer: GoPro
Sep 29 09:45:31 nina kernel: usb 1-4: SerialNumber: C3351325091705
Sep 29 09:45:31 nina sudo[1455]: root : PWD=/ ; USER=root ; COMMAND=/usr/bin/jmtpfs /media/GoPro
Sep 29 09:45:31 nina sudo[1455]: pam_unix(sudo:session): session opened for user root(uid=0) by (uid=0)
Sep 29 09:45:34 nina sudo[1455]: pam_unix(sudo:session): session closed for user root
Sep 29 09:45:34 nina kernel: usb 1-4: USB disconnect, device number 16
Sep 29 09:45:34 nina systemd-udevd[1453]: 1-4: Process '/bin/bash -c /home/matt/Projects/GoProScraping/scripts/grab_go_pro_files.sh' failed with exit code 1.
看起来我插入了 GoPro,udev 发现它已连接,然后出现权限错误,该错误导致 USB 断开连接,然后 udev 再次将其连接起来。
jmtpfs /media/GoPro
但是,如果我尝试以 root 用户身份运行该命令:它会很好地安装并且我可以手动访问文件。
我以为 udev 规则以 root 身份运行,我遗漏了什么?
您可能正在尝试遵循过时的建议。以前可以从 udev 规则运行任意事物,但后来发现了一个安全漏洞,并应用了一些限制。现在
systemd-udevd
服务进程通常是沙盒化的,这限制了它的直接操作基本上只是创建、探测和删除设备节点。但它仍然可以告诉systemd
启动其他事物。RUN
在现代系统中,有关关键字的章节man udev
说道:因此,首先创建一个服务文件,例如
/etc/systemd/system/gopro-jmtpfs.service
,其内容如下:这定义了一个静态单元,无法手动启动。它将稍后由 udev 规则触发。
还有另一项针对文件抓取脚本的服务,例如
/etc/systemd/system/gopro-grabfiles.service
:创建服务文件后,记得运行
systemctl daemon-reload
才能生效。然后为你的 GoPro 创建一个 udev 规则,如下所示:
现在,
gopro-jmtpfs.service
当插入 GoPro 时应该自动启动,并且gopro-grabfiles.service
应该在第一个服务开始运行后触发。用 标记 udev 规则
TAG+="systemd"
应该会导致systemd
识别相关设备,从而*.device
自动为其创建一个单元。如果您愿意,您可以使用它进行进一步的systemd
基于 的自动化。默认情况下,设备单元的名称将是一个长而笨拙的
sys-devices-pci...-usb....device
字符串,但您可以将其添加ENV{SYSTEMD_ALIAS}="/sys/subsystem/usb/somename"
到 udev 规则中以获取更易于管理的设备单元名称。