**`libcomposite`** 是 Linux 内核中的一个框架,主要用于创建 **USB Gadget**(虚拟 USB 设备)。它允许用户配置和组合多种功能,将 Linux 系统模拟成各种 USB 设备,如存储设备、网络适配器、摄像头(通过 UVC)、串行设备等。`libcomposite` 为开发者提供了高度灵活的 USB gadget 开发工具,可以通过配置多个不同的功能,将它们组合成一个 USB 设备。
### **libcomposite 的核心概念**
1. **USB Gadget**:
**USB gadget** 是嵌入式设备或计算机模拟的 USB 外设设备,如 USB 存储设备、USB 摄像头等。`libcomposite` 是用来管理这些 gadget 的框架。2. **Function (功能)**:
USB 设备通常可以有不同的功能模块,称为 **function**。例如,一个设备可以同时有 **存储功能** 和 **串行功能**,这些模块可以通过 `libcomposite` 进行组合。常见的 function 有:
- **Mass Storage**: 模拟 USB 存储设备。
- **UVC (USB Video Class)**: 模拟 USB 摄像头。
- **CDC ECM**: 模拟 USB 网络适配器。
- **Serial**: 模拟串口设备。3. **Configuration (配置)**:
一个 USB gadget 可以有多种 **configuration**,每个 configuration 可以包含多个功能。设备可以通过不同的 configuration 告诉主机支持不同的功能组合。4. **UDC (USB Device Controller)**:
USB Device Controller (UDC) 是硬件层面的 USB 控制器,用于处理 USB 数据的传输。`libcomposite` 负责将 gadget 绑定到 UDC,使得 gadget 可以与主机通信。### **libcomposite 的工作流程**
当你想要通过 `libcomposite` 创建一个 USB gadget 时,大致的工作流程如下:1. **加载 `libcomposite` 模块**:
```bash
modprobe libcomposite
```
这将加载 `libcomposite` 框架。2. **创建 USB gadget 目录**:
在 `/sys/kernel/config/usb_gadget` 下创建一个目录来定义 gadget 设备。
```bash
mkdir /sys/kernel/config/usb_gadget/g1
cd /sys/kernel/config/usb_gadget/g1
```3. **设置设备描述符**:
设备描述符是 USB 设备向主机报告自身信息的方式。设置 **Vendor ID**、**Product ID** 等描述符:
```bash
echo 0x1d6b > idVendor # Vendor ID
echo 0x0104 > idProduct # Product ID
echo 0x0100 > bcdDevice # Device version
echo 0x0200 > bcdUSB # USB 2.0
```4. **配置语言、制造商和产品字符串**:
```bash
mkdir strings/0x409 # 0x409 表示英语
echo "1234567890" > strings/0x409/serialnumber
echo "Linux Foundation" > strings/0x409/manufacturer
echo "Composite Gadget" > strings/0x409/product
```5. **定义功能**:
添加 gadget 的功能,比如 UVC(USB 摄像头功能)、串行设备、存储设备等。下面的例子是添加一个存储设备功能:
```bash
mkdir functions/mass_storage.0
echo /dev/sda > functions/mass_storage.0/lun.0/file
```6. **配置设备**:
创建并配置 USB gadget 的配置:
```bash
mkdir configs/c.1
echo 120 > configs/c.1/MaxPower # 最大供电 120mA
ln -s functions/mass_storage.0 configs/c.1/
```7. **绑定到 UDC**:
最后,使用硬件控制器启动 gadget 设备。
```bash
echo $(ls /sys/class/udc) > UDC
```完成后,主机将识别这个 gadget 设备。
### **libcomposite 的常用功能**
1. **Mass Storage**: 模拟 USB 存储设备。
```bash
mkdir functions/mass_storage.0
echo /dev/sda > functions/mass_storage.0/lun.0/file
```2. **USB 视频设备 (UVC)**: 用于模拟 USB 摄像头。
```bash
mkdir functions/uvc.usb0
echo 1024 > functions/uvc.usb0/streaming_maxpacket
```3. **串行设备 (Serial)**: 用于模拟串行控制设备。
```bash
mkdir functions/acm.usb0
ln -s functions/acm.usb0 configs/c.1/
```4. **网络设备**: 模拟 USB 网络适配器。
```bash
mkdir functions/ecm.usb0
echo "02:00:00:00:00:00" > functions/ecm.usb0/dev_addr
echo "02:00:00:00:00:01" > functions/ecm.usb0/host_addr
ln -s functions/ecm.usb0 configs/c.1/
```### **示例程序**
这是一个将树莓派配置为 **USB 组合设备**(存储设备 + 串口)的示例脚本:```bash
#!/bin/bash
# Load the composite gadget module
modprobe libcomposite# Create the gadget
mkdir /sys/kernel/config/usb_gadget/g1
cd /sys/kernel/config/usb_gadget/g1# Set device descriptor
echo 0x1d6b > idVendor # Linux Foundation
echo 0x0104 > idProduct # Product ID
echo 0x0100 > bcdDevice # Device version
echo 0x0200 > bcdUSB # USB 2.0# Set English strings
mkdir strings/0x409
echo "1234567890" > strings/0x409/serialnumber
echo "Linux Foundation" > strings/0x409/manufacturer
echo "Composite Gadget" > strings/0x409/product# Create a configuration
mkdir configs/c.1
echo 120 > configs/c.1/MaxPower# Add mass storage function
mkdir functions/mass_storage.0
echo /dev/sda > functions/mass_storage.0/lun.0/file
ln -s functions/mass_storage.0 configs/c.1/# Add serial (ACM) function
mkdir functions/acm.usb0
ln -s functions/acm.usb0 configs/c.1/# Bind to USB controller
echo $(ls /sys/class/udc) > UDC
```### **总结**
`libcomposite` 提供了一个灵活、可扩展的框架,用于 Linux 设备模拟成多种 USB 功能。通过 `libcomposite`,开发者可以轻松组合和管理多种 USB 功能,如 UVC、存储、串行等。