第 28 章。USB 设备模式 / USB OTG

28.1. 概述

本章涵盖了在 FreeBSD 中使用 USB 设备模式和 USB On The Go (USB OTG)。这包括虚拟串行控制台、虚拟网络接口和虚拟 USB 驱动器。

在支持 USB 设备模式或 USB OTG 的硬件上运行时,例如许多嵌入式板中内置的硬件,FreeBSD USB 堆栈可以在设备模式下运行。设备模式使计算机可以将自身呈现为不同类型的 USB 设备类,包括串行端口、网络适配器和海量存储设备,或它们的组合。像笔记本电脑或台式电脑这样的 USB 主机能够像访问物理 USB 设备一样访问它们。设备模式有时被称为“USB 小工具模式”。

硬件可以通过两种基本方式提供设备模式功能:使用单独的“客户端端口”,该端口只支持设备模式,以及使用 USB OTG 端口,该端口可以提供设备模式和主机模式。对于 USB OTG 端口,USB 堆栈会根据连接到端口的内容自动在主机端和设备端之间切换。将 USB 设备(如存储棒)连接到端口会导致 FreeBSD 切换到主机模式。将 USB 主机(如电脑)连接到端口会导致 FreeBSD 切换到设备模式。单用途“客户端端口”始终在设备模式下工作。

FreeBSD 向 USB 主机呈现的内容取决于hw.usb.template sysctl。一些模板提供单个设备,例如串行终端;另一些模板提供多个设备,这些设备可以同时使用。例如,模板 10 提供了一个海量存储设备、一个串行控制台和一个网络接口。请参阅usb_template(4)以获取可用值的列表。

请注意,在某些情况下,根据硬件和主机操作系统的不同,主机需要物理断开连接并重新连接才能注意到配置更改,或者需要以系统特定的方式强制重新扫描 USB 总线。当 FreeBSD 在主机上运行时,可以使用usbconfig(8)reset。如果 USB 主机已经连接到 USBOTG 插座,则也必须在加载usb_template.ko后执行此操作。

阅读完本章后,您将了解

  • 如何在 FreeBSD 上设置 USB 设备模式功能。

  • 如何在 FreeBSD 上配置虚拟串行端口。

  • 如何从各种操作系统连接到虚拟串行端口。

  • 如何配置 FreeBSD 以提供虚拟 USB 网络接口。

  • 如何配置 FreeBSD 以提供虚拟 USB 存储设备。

28.2. USB 虚拟串行端口

28.2.1. 配置 USB 设备模式串行端口

虚拟串行端口支持由模板编号 3、8 和 10 提供。请注意,模板 3 在 Microsoft Windows 10 上使用无需特殊驱动程序和 INF 文件。其他主机操作系统与所有三种模板一起使用。必须加载usb_template(4)umodem(4)内核模块。

要启用 USB 设备模式串行端口,请将这些行添加到/etc/ttys

ttyU0	"/usr/libexec/getty 3wire"	vt100	onifconsole secure
ttyU1	"/usr/libexec/getty 3wire"	vt100	onifconsole secure

然后将这些行添加到/etc/devd.conf

notify 100 {
	match "system"		"DEVFS";
	match "subsystem"	"CDEV";
	match "type"		"CREATE";
	match "cdev"		"ttyU[0-9]+";
	action "/sbin/init q";
};

如果devd(8)已经在运行,请重新加载配置

# service devd restart

通过将这些行添加到/boot/loader.conf(如果该文件不存在,则创建它)来确保在启动时加载必要的模块并设置正确的模板

umodem_load="YES"
hw.usb.template=3

要加载模块并设置模板而不重启,请使用

# kldload umodem
# sysctl hw.usb.template=3

28.2.2. 从 FreeBSD 连接到 USB 设备模式串行端口

要连接到配置为提供 USB 设备模式串行端口的板,请将 USB 主机(例如笔记本电脑)连接到板的 USB OTG 或 USB 客户端端口。在主机上使用pstat -t列出终端线路。在列表的末尾,您应该看到一个 USB 串行端口,例如“ttyU0”。要打开连接,请使用

# cu -l /dev/ttyU0

在按下Enter键几次后,您将看到一个登录提示。

28.2.3. 从 macOS 连接到 USB 设备模式串行端口

要连接到配置为提供 USB 设备模式串行端口的板,请将 USB 主机(例如笔记本电脑)连接到板的 USB OTG 或 USB 客户端端口。要打开连接,请使用

# cu -l /dev/cu.usbmodemFreeBSD1

28.2.4. 从 Linux 连接到 USB 设备模式串行端口

要连接到配置为提供 USB 设备模式串行端口的板,请将 USB 主机(例如笔记本电脑)连接到板的 USB OTG 或 USB 客户端端口。要打开连接,请使用

# minicom -D /dev/ttyACM0

28.2.5. 从 Microsoft Windows 10 连接到 USB 设备模式串行端口

要连接到配置为提供 USB 设备模式串行端口的板,请将 USB 主机(例如笔记本电脑)连接到板的 USB OTG 或 USB 客户端端口。要打开连接,您将需要一个串行终端程序,例如 PuTTY。要检查 Windows 使用的 COM 端口名称,请运行设备管理器,展开“端口(COM 和 LPT)”。您将看到一个类似于“USB 串行设备(COM4)”的名称。运行您选择的串行终端程序,例如 PuTTY。在 PuTTY 对话框中,将“连接类型”设置为“串行”,在“串行线路”对话框中键入从设备管理器获得的 COMx,然后单击打开。

28.3. USB 设备模式网络接口

虚拟网络接口支持由模板编号 1、8 和 10 提供。请注意,它们都不适用于 Microsoft Windows。其他主机操作系统与所有三种模板一起使用。必须加载usb_template(4)if_cdce(4)内核模块。

通过将这些行添加到/boot/loader.conf(如果该文件不存在,则创建它)来确保在启动时加载必要的模块并设置正确的模板

if_cdce_load="YES"
hw.usb.template=1

要加载模块并设置模板而不重启,请使用

# kldload if_cdce
# sysctl hw.usb.template=1

28.4. USB 虚拟存储设备

cfumass(4)驱动程序是 USB 设备模式驱动程序,最早在 FreeBSD 12.0 中提供。

海量存储目标由模板 0 和 10 提供。必须加载usb_template(4)cfumass(4)内核模块。cfumass(4)与 CTL 子系统接口,该子系统用于 iSCSI 或光纤通道目标。在主机端,USB 海量存储启动器只能访问单个 LUN,即 LUN 0。

28.4.1. 使用 cfumass 启动脚本配置 USB 海量存储目标

设置只读 USB 存储目标的最简单方法是使用cfumass rc 脚本。要通过这种方式配置它,请将要呈现给 USB 主机计算机的文件复制到/var/cfumass目录中,并将此行添加到/etc/rc.conf

cfumass_enable="YES"

要配置目标而不重启,请运行以下命令

# service cfumass start

与串行和网络功能不同,模板不应在/boot/loader.conf中设置为 0 或 10。这是因为必须在设置模板之前设置 LUN。cfumass 启动脚本在启动时会自动设置正确的模板号。

28.4.2. 使用其他方法配置 USB 海量存储

本章的其余部分详细描述了设置目标而不使用 cfumass rc 文件的方法。如果例如要提供可写 LUN,则需要这样做。

USB 海量存储不需要ctld(8)守护进程运行,尽管如果需要,可以使用它。这与 iSCSI 不同。因此,有两种方法可以配置目标:ctladm(8)ctld(8)。两者都需要加载cfumass.ko内核模块。可以手动加载模块

# kldload cfumass

如果cfumass.ko尚未构建到内核中,则可以将/boot/loader.conf设置为在启动时加载模块

cfumass_load="YES"

可以在没有ctld(8)守护进程的情况下创建 LUN

# ctladm create -b block -o file=/data/target0

这将向 USB 主机呈现图像文件/data/target0的内容作为 LUN。该文件必须在执行命令之前存在。要配置系统启动时的 LUN,请将命令添加到/etc/rc.local中。

ctld(8)也可以用来管理 LUN。创建/etc/ctl.conf,在/etc/rc.conf中添加一行以确保ctld(8)在启动时自动启动,然后启动守护进程。

这是一个简单的/etc/ctl.conf配置文件示例。有关选项的完整描述,请参阅ctl.conf(5)

target naa.50015178f369f092 {
	lun 0 {
		path /data/target0
		size 4G
	}
}

该示例创建一个包含单个 LUN 的单个目标。naa.50015178f369f092是一个设备标识符,由 32 个随机十六进制数字组成。path行定义支持 LUN 的文件或 zvol 的完整路径。该文件必须在启动ctld(8)之前存在。第二行是可选的,它指定 LUN 的大小。

要确保ctld(8)守护进程在启动时启动,请将此行添加到/etc/rc.conf

ctld_enable="YES"

要立即启动ctld(8),请运行以下命令

# service ctld start

ctld(8)守护进程启动时,它会读取/etc/ctl.conf。如果在守护进程启动后编辑了此文件,请重新加载更改,以便它们立即生效

# service ctld reload

上次修改时间:2024 年 3 月 9 日,作者 Danilo G. Baio