# EQ HID通信协议详细文档

## 1. 总体框架

### 1.1 协议概述
该协议使用HID (Human Interface Device) 协议进行主机与设备之间的通信。协议支持EQ参数设置、读取、模式切换等功能。

### 1.2 支持的指令列表
| 指令码 | 命令名称 | 功能 | 方向 | 描述 |
|--------|----------|------|------|------|
| 0x82 | SET_MIC_VOLUME | 设置麦克风增益级别 | 主机→设备 | 设置麦克风增益（0=静音, 1-48=0~24dB, 2级=1dB） |
| 0x83 | GET_MIC_VOLUME | 获取麦克风增益级别 | 主机→设备 | 读取当前麦克风增益级别（0=静音, 1-48=0~24dB, 2级=1dB） |
| 0x84 | FACTORY_RESET | 恢复出厂默认设置 | 主机→设备 | 删除Flash中所有已保存参数，设备重启后自动恢复出厂默认值 |
| 0x85 | SET_AI_NOISE_STRENGTH | 设置AI降噪强度 | 主机→设备 | 设置AI降噪强度（0=关闭，2-100偶数=强度级别，步进2；100对应最强-200dB） |
| 0x86 | GET_AI_NOISE_STRENGTH | 获取AI降噪强度 | 主机→设备 | 读取当前AI降噪强度；强度变化（含按键切换、开机初始值）时设备主动上报 |
| 0x87 | SET_MONITOR_SWITCH | 设置耳返开关 | 主机→设备 | 设置耳返（ADC→耳机监听）开关（0=关闭，1=开启），保存到Flash |
| 0x88 | GET_MONITOR_SWITCH | 获取耳返开关状态 | 主机→设备 | 读取当前耳返开关状态（0=关闭，1=开启） |
| 0x8A | SET_EQ_MODE | 切换EQ模式 | 主机→设备 | 切换EQ模式 |
| 0x8B | GET_EQ_MODE | 获取当前EQ模式信息 | 主机→设备 | 读取设备当前EQ模式和名称 |
| 0x8C | SET_MODE_GAIN_AND_NAME | 设置模式整体增益和名称 | 主机→设备 | 设置模式整体增益和名称 |
| 0x8D | SET_EQ_PARAMS | 发送EQ参数 | 主机→设备 | 发送单个滤波器的参数 |
| 0x8E | GET_EQ_PARAMS | 读取EQ参数 | 主机→设备 | 读取单个滤波器的参数 |
| 0x8F | GET_DEVICE_INFO | 获取设备信息 | 主机→设备 | 读取设备PID、VID、产品字符串等信息 |
| 0x90 | RESET_EQ_PARAMS | 复位EQ参数 | 主机→设备 | 删除Flash中的EQ参数并恢复头文件预设参数 |
| 0x91 | GET_EQ_MODE_COUNT | 获取EQ模式总数 | 主机→设备 | 返回预定义加用户模式的总数（不包含禁用模式） |
| 0x92 | SET_AND_SAVE_EQ_MODE | 设置并保存EQ模式 | 主机→设备 | 设置当前EQ模式(0-9)并保存到Flash，开机时自动恢复 |
| 0x93 | SET_VOLUME | 设置监听音量级别 | 主机→设备 | 设置设备监听音量级别（0=静音, 1-48按SY102dac对应表映射到-66dB~0dB） |
| 0x94 | GET_VOLUME | 获取监听音量级别 | 主机→设备 | 读取设备当前监听音量级别（0=静音, 1-48按SY102dac对应表映射） |
| 0x9D | SET_EQ_ENABLE | 设置EQ使能开关 | 主机→设备 | 设置EQ使能开关（ON/OFF），禁用时保存当前模式，启用时恢复之前模式 |
| 0x9E | GET_EQ_ENABLE | 获取EQ使能开关 | 主机→设备 | 读取EQ使能开关状态（ON/OFF） |
| 0x9F | GET_SAMPLE_FORMAT | 获取采样率和格式 | 主机→设备 | 读取当前采样率、DSD模式和DAC采样分辨率 |
| 0xA4 | SET_SOUND_EFFECT_MODE | 设置音效模式 | 主机→设备 | 设置音效模式（0=无音效，1=音乐模式，2=游戏模式，3=AI7.1模式） |
| 0xA5 | GET_SOUND_EFFECT_MODE | 获取音效模式 | 主机→设备 | 读取当前音效模式（0-3） |
| 0xA6 | GET_FIRMWARE_VERSION | 获取固件版本 | 主机→设备 | 读取设备固件版本号（BCD格式：主版本.次版本.修订版本） |
| 0xA7 | FIRMWARE_UPGRADE_START | 开始固件升级 | 主机→设备 |
| 0xA8 | FIRMWARE_UPGRADE_DATA | 传输固件数据块（固定57字节） | 主机→设备 |
| 0xA9 | FIRMWARE_UPGRADE_END | 结束固件升级，验证镜像 | 主机→设备 |
| 0xAA | FIRMWARE_UPGRADE_STATUS | 获取升级状态和进度 | 主机→设备 |
| 0xAB | FIRMWARE_UPGRADE_ABORT | 中止固件升级 | 主机→设备 |
| 0xAC | FIRMWARE_UPGRADE_ERASE | 擦除现有升级镜像 | 主机→设备 |
| 0xAE | DEVICE_REBOOT | 设备重启（通用命令） | 主机→设备 |
| 0xB0 | SET_EX3D_CMD | 发送EX3D命令 | 主机→设备 | 发送EX3D设置命令（封装所有EX3D SET命令） |
| 0xB1 | GET_EX3D_CMD | 读取EX3D命令 | 主机→设备 | 读取EX3D参数（封装所有EX3D GET命令） |

### 1.3 数据包格式
- **Report ID**: 0x01 (HID报告ID)
- **数据包大小**: 64字节 (1字节Report ID + 63字节数据)
- **同步头**: 0x77 (所有命令的第一个字节)
- **字节序**: 小端序 (Little Endian)

## 2. 详细指令说明

### 2.0 0x82 - SET_MIC_VOLUME (设置麦克风增益级别)
**功能**: 设置麦克风PGA增益级别
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x82 | 命令码
2        | 1    | uint8 | 增益级别 (0=静音, 1-48=0~24dB, 2级=1dB)
3-62     | 60   | 0x00 | 保留字节
```

**参数说明**:
- **增益级别范围：** 0-48（共49级）
- **对应硬件**：NAU88C22 ADC PGA增益寄存器（reg 0x007E）+ 输出放大器（reg 0x0035）
  - 0：静音（mute，同时清零 reg 0x007E 和 0x0035）
  - 1：约0.5dB（按2级=1dB映射）
  - 2：1dB
  - ...（2级=1dB）
  - 47：约23.5dB
  - 48：24dB（最大HID可设置增益）
- >48 为无效值，固件将拒绝设置

**设备端处理**:
- 设置后立即应用到ADC PGA硬件
- 同步更新前面板LED（L系列15个LED，反映当前增益级别）
- 保存到Flash（mic_vol路径），断电重启后自动恢复
- 设备端增益变化（含编码器旋转）会主动通过0x83格式上报

**返回值**:
无直接返回值。设备端增益变化会主动上报0x83格式数据包。

### 2.0b 0x83 - GET_MIC_VOLUME (获取麦克风增益级别)
**功能**: 读取设备当前麦克风PGA增益级别；设备端增益变化时也会主动上报
**方向**: 主机→设备（请求），设备→主机（响应/主动上报）
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x83 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**（含主动上报）:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x83 | 同步头2
3        | 1    | uint8 | 当前增益级别 (0=静音, 1-48=0~24dB, 2级=1dB)
4-62     | 59   | 0x00 | 保留字节
```

**主动上报说明**:
- 编码器旋转导致增益变化时，设备主动向主机上报当前增益（范围0~48）
- HID SET_MIC_VOLUME（0x82）命令成功执行后，设备也主动上报新增益

### 2.0c 0x84 - FACTORY_RESET (恢复出厂默认设置)
**功能**: 删除Flash中所有已保存的用户参数，设备重启后自动恢复出厂默认值
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x84 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**出厂默认参数**:
| 参数 | 出厂默认值 | 说明 |
|------|-----------|------|
| AI7.1音效模式 | 3 (AI7.1开启) | 音效模式 0=无音效, 1=音乐, 2=游戏, 3=AI7.1 |
| 脚步增强 | 12dB (全亮, 状态2) | LED全亮, 扩展增益12dB |
| 麦克风音量 | 44 (约22dB) | 49级中的44级，按2级=1dB映射 |
| 监听音量 | 30 (-14dB) | 49级中的30级，按SY102dac对应表映射 |
| EQ参数 | 头文件预设 | 删除所有用户EQ参数，恢复固件内置预设 |
| AI降噪 | 开启 | 每次上电默认开启（不保存到Flash） |
| 耳返开关 | 0 (关闭) | ADC→耳机监听通路默认关闭 |
| 麦克风静音 | 0 (未静音) | 麦克风静音状态默认关闭 |
| 监听静音 | 0 (未静音) | 耳机输出静音状态默认关闭 |

**设备端处理**:
1. 删除Flash中保存的以下参数文件：
   - `game_mode`（音效模式）
   - `mic_vol`（麦克风音量）
   - `dac_vol`（监听音量）
   - `footstep`（脚步增强状态）
   - `monitor_sw`（耳返开关）
   - `mic_mute`（麦克风静音状态）
   - `hp_mute`（耳机静音状态）
   - 所有EQ参数文件（调用eq_flash_clear_all）
2. 设置重启标志，约500ms后设备自动重启
3. 重启后自动加载出厂默认参数

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x84 | 同步头2
3        | 1    | uint8 | 状态码 (0x00=成功, 0x01=失败)
4-62     | 59   | 0x00 | 保留字节
```

**注意**:
- 执行后设备将在约500ms后自动重启，USB连接会短暂断开后重连
- 重启后所有参数将恢复为出厂默认值
- 此操作不可撤销

### 2.0d 0x85 - SET_AI_NOISE_STRENGTH (设置AI降噪强度)
**功能**: 设置AI降噪强度级别
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x85 | 命令码
2        | 1    | uint8 | 强度值 (0=关闭, 2/4/.../100=强度级别, 步进2)
3-62     | 60   | 0x00 | 保留字节
```

**参数说明**:
- **强度值范围**: 0、2、4、6、…、100（共51个有效值）
- **0**: 关闭AI降噪
- **2-100（步进2）**: 开启AI降噪，强度递增；内部dB映射：`dB = -(strength × 2)`
  - 2 → -4 dB（最轻微降噪）
  - 50 → -100 dB
  - 100 → -200 dB（最强降噪，出厂默认）
- **奇数或 >100** 为无效值，固件将拒绝（返回无响应）

**设备端处理**:
- 强度=0：关闭AI降噪算法，熄灭LED_ANC，flag_aidenoise_onoff=0
- 强度=2-100：开启AI降噪算法，点亮LED_ANC，flag_aidenoise_onoff=1，更新内部降噪深度
- 设置成功后设备主动上报当前强度（0x86格式）
- **不保存到Flash**；重启后AI降噪恢复为开启（强度=100，即-200dB最强）

**返回值**:
无直接返回，设置成功后设备通过0x86格式主动上报当前强度值。

### 2.0e 0x86 - GET_AI_NOISE_STRENGTH (获取AI降噪强度)
**功能**: 读取设备当前AI降噪强度；强度变化时设备主动上报
**方向**: 主机→设备（请求），设备→主机（响应/主动上报）
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x86 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**（含主动上报）:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x86 | 同步头2
3        | 1    | uint8 | 当前强度值 (0=关闭, 2-100=强度级别)
4-62     | 59   | 0x00 | 保留字节
```

**主动上报说明**:
- **开机时**：设备初始化完成后主动上报当前强度（出厂默认=100）
- **按键切换**：用户按下AI降噪按键时，设备主动上报新强度（关闭时上报0，开启时上报恢复的强度）
- **HID SET_AI_NOISE_STRENGTH（0x85）命令成功执行后**，设备主动上报新强度

### 2.0f 0x87 - SET_MONITOR_SWITCH (设置耳返开关)
**功能**: 设置耳返（ADC→耳机监听）开关，控制是否将麦克风输入实时路由到耳机输出
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x87 | 命令码
2        | 1    | uint8 | 开关值 (0=关闭, 1=开启)
3-62     | 60   | 0x00 | 保留字节
```

**参数说明**:
- **0**: 关闭耳返，ADC数据不路由到耳机输出（NAU88L21 reg 0x0035 = 0x0000）
- **1**: 开启耳返，ADC数据路由到耳机输出（NAU88L21 reg 0x0035 = 0xCFCF，0dB监听音量）
- **注意**: 耳返路由需要麦克风未静音（mic_mute=0）且麦克风增益有效（level≥2）方才生效

**设备端处理**:
- 立即更新 NAU88L21 reg 0x0035（耳返音量寄存器）
- 若麦克风当前处于静音状态，则无论耳返开关为何值，reg 0x0035保持0x0000
- 保存到Flash（`monitor_sw`路径），断电重启后自动恢复
- 设置成功后用0x88格式响应当前状态
- 出厂默认：关闭（0）

**返回值**:
设置成功后设备回复0x88格式响应。

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x88 | 同步头2
3        | 1    | uint8 | 当前耳返开关状态 (0=关闭, 1=开启)
4-62     | 59   | 0x00 | 保留字节
```

### 2.0g 0x88 - GET_MONITOR_SWITCH (获取耳返开关状态)
**功能**: 读取当前耳返开关状态
**方向**: 主机→设备（请求），设备→主机（响应）
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x88 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x88 | 同步头2
3        | 1    | uint8 | 当前耳返开关状态 (0=关闭, 1=开启)
4-62     | 59   | 0x00 | 保留字节
```

### 2.1 0x8A - SET_EQ_MODE (切换EQ模式)
**功能**: 切换当前EQ模式
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x8A | 命令码
2        | 1    | uint8  | 模式值 (0-9: 预设模式, 10-11: 用户模式)
3-62     | 60   | 0x00   | 保留字节
```


## 2.2 0x8B - GET_EQ_MODE (读取EQ模式信息)
**功能**: 读取EQ模式信息
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x8B | 命令码
2        | 1    | uint8 | 模式值 (0-11: 有效模式值, 0xFF: 获取当前模式信息)
3-62     | 60   | 0x00 | 保留字节
```

**设备端处理**:
- 如果mode值为0xFF，返回当前模式值、整体增益和模式名称
- 如果mode值为有效模式值(0-11)，返回指定模式值、整体增益和模式名称



**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x8B | 同步头2
3        | 1    | uint8  | 模式值 (当前模式或指定模式)
4-7      | 4    | int32  | 增益值 (范围0到-50dB，有符号整数)
8-23     | 16   | char   | 模式名称 (UTF-8编码，16字节)
24-62    | 39   | 0x00   | 保留字节
```

**使用说明**:
- 发送mode=0xFF时，返回当前激活的EQ模式信息
- 发送mode=0-11时，返回指定模式的增益和名称信息（不切换当前模式）

### 2.3 0x8C - SET_MODE_GAIN_AND_NAME (设置模式整体增益和名称)
**功能**: 设置EQ模式整体增益和名称
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x8C | 命令码
2        | 1    | uint8  | 模式值 (0-11)
3-6      | 4    | int32  | 增益值 (范围0到-50dB，有符号整数)
7-22     | 16   | char   | 模式名称 (UTF-8编码，16字节)
23-62    | 40   | 0x00   | 保留字节
```

**使用场景**:
- 需要为特定模式设置整体增益补偿和自定义名称
- 自动应用到所有采样率以确保一致性


### 2.4 0x8D - SET_EQ_PARAMS (发送EQ参数)
**功能**: 发送单个滤波器的参数
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x8D | 命令码
2        | 1    | uint8  | 模式值 (0-11)
3        | 1    | uint8  | 滤波器Band索引 (0-7)
4        | 1    | uint8  | 滤波器类型
5-8      | 4    | float  | 中心频率 (Hz)
9-12     | 4    | float  | Q值
13-16    | 4    | float  | 带宽 (Hz)
17-20    | 4    | float  | 增益 (dB)
21-62    | 42   | 0x00   | 保留字节
```

**滤波器类型码**:
| 类型码 | 滤波器类型 |
|--------|------------|
| 0x00   | bypass滤波器 |
| 0x01   | 全通滤波器 |
| 0x02   | 峰值滤波器 |
| 0x03   | 低通滤波器 |
| 0x04   | 高通滤波器 |
| 0x05   | 带通滤波器 |
| 0x06   | 带阻滤波器 |
| 0x07   | 陷波滤波器 |
| 0x08   | 恒定Q值滤波器 |
| 0x09   | 低架滤波器 |
| 0x0A   | 高架滤波器 |

### 2.5 0x8E - GET_EQ_PARAMS (读取EQ参数)
**功能**: 读取单个滤波器的参数
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x8E | 命令码
2        | 1    | uint8  | 模式值 (0-11)
3        | 1    | uint8  | EQ索引 (0-7)
4-62     | 59   | 0x00   | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x8E | 同步头2
3        | 1    | uint8  | 模式值 (0-11)
4        | 1    | uint8  | 滤波器Band索引 (0-7)
5        | 1    | uint8  | 滤波器类型
6-9      | 4    | float  | 中心频率 (Hz)
10-13    | 4    | float  | Q值
14-17    | 4    | float  | 带宽 (Hz)
18-21    | 4    | float  | 增益 (dB)
22-62    | 41   | 0x00   | 保留字节
```

### 2.6 0x8F - GET_DEVICE_INFO (获取设备信息)
**功能**: 获取设备基本信息
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x8F | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x8F | 同步头2
3-4      | 2    | uint16 | 产品ID (PID)
5-6      | 2    | uint16 | 厂商ID (VID)
7-22     | 16   | char   | 产品字符串 (UTF-8编码，16字节)
23-38    | 16   | char   | 厂商字符串 (UTF-8编码，16字节)
39-54    | 16   | char   | 序列号字符串 (UTF-8编码，16字节)
55-62    | 8    | 0x00   | 保留字节
```

### 2.7 0x90 - RESET_EQ_PARAMS (复位EQ参数)
**功能**: 删除客户定制EQ参数并恢复预设参数
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x90 | 命令码
2        | 1    | uint8 | 模式号 (0-11, 0xFF表示恢复所有包括EQ参数，总体增益，模式名称 )
3-62     | 60   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x90 | 同步头2
3        | 1    | uint8 | 状态码 (0x00=成功, 0x01=失败)
4-62     | 59   | 0x00 | 保留字节
```

### 2.8 0x91 - GET_EQ_MODE_COUNT (获取EQ模式总数)
**功能**: 获取预定义加用户模式的总数（不包含禁用模式）
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x91 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x91 | 同步头2
3        | 1    | uint8 | 模式总数 (当前为12，包含0-11共12个模式，不包含禁用模式)
4        | 1    | uint8 | 预定义模式数量 (当前为10，包含0-9共10个预设模式)
5-62     | 58   | 0x00 | 保留字节
```

### 2.9 0x92 - SET_AND_SAVE_EQ_MODE (设置并保存EQ模式)
**功能**: 设置当前EQ模式并保存到Flash，开机时自动恢复
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x92 | 命令码
2        | 1    | uint8 | 模式值 (0-11: 0-9预设模式, 10-11用户模式)
3-62     | 60   | 0x00 | 保留字节
```

**设备端处理**:
- 将模式值保存到Flash
- 开机时自动从Flash读取并恢复该模式

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x92 | 同步头2
3        | 1    | uint8 | 状态码 (0x00=成功, 0x01=失败)
4-62     | 59   | 0x00 | 保留字节
```

### 2.10 0x93 - SET_VOLUME (设置监听音量级别)
**功能**: 设置设备监听（耳机/DAC）音量级别
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x93 | 命令码
2        | 1    | uint8 | 音量级别 (0-48: 0=静音, 1=-66dB, ..., 48=0dB；按SY102dac对应表)
3-62     | 60   | 0x00 | 保留字节
```

**参数说明**:
- **音量级别范围：** 0-48（共49级）
- **说明：** 控制设备监听输出（DAC/耳机）音量级别
  - 0: 静音（mute，DAC完全静音）
  - 1: -66dB（最小有效音量）
  - 2: -64dB
  - ...（按 `SY102dac对应表.csv` 的非线性步进）
  - 46: -1dB
  - 47: -0.5dB
  - 48: 0dB（最大音量）
- **对应硬件**：NAU88C22 DAC音量寄存器（reg 0x0034），49级查表映射

**设备端处理**:
- 设置后立即应用到DAC硬件
- 同步更新前面板LED（D系列15个LED，反映当前音量级别，每2级对应1个LED）
- 保存到Flash（dac_vol路径），断电重启后自动恢复
- 如果参数超出范围（>48），固件将拒绝设置

**返回值**:
无直接返回值。如需确认音量是否设置成功，请使用GET_VOLUME命令读取当前音量。设备端音量变化（含编码器旋转引起的变化）会主动通过0x94格式上报。

### 2.11 0x94 - GET_VOLUME (获取监听音量级别)
**功能**: 读取设备当前监听音量级别；设备端音量变化时也会主动上报此格式
**方向**: 主机→设备（请求），设备→主机（响应/主动上报）
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x94 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**（含主动上报）:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x94 | 同步头2
3        | 1    | uint8 | 当前音量级别 (0-48: 0=静音, 1-48按SY102dac对应表映射到-66dB~0dB)
4-62     | 59   | 0x00 | 保留字节
```

**主动上报说明**:
- 当编码器旋转导致音量变化时，设备会主动向主机上报当前音量（使用相同的响应格式）
- 当HID SET_VOLUME（0x93）命令被成功执行后，设备也会主动上报新音量

### 2.20 0x9D - SET_EQ_ENABLE (设置EQ使能开关)
**功能**: 设置EQ使能开关（启用/禁用）
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x9D | 命令码
2        | 1    | uint8 | EQ使能开关 (0=OFF禁用, 1=ON启用)
3-62     | 60   | 0x00 | 保留字节
```

**设备端处理**:
- 只保存EQ使能状态到Flash（独立文件存储），不影响已保存的模式

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x9D | 同步头2
3        | 1    | uint8 | 状态码 (0x00=成功, 0x01=失败)
4        | 1    | uint8 | 当前EQ使能状态 (0=OFF, 1=ON)
5-62     | 58   | 0x00 | 保留字节
```

### 2.21 0x9E - GET_EQ_ENABLE (获取EQ使能开关)
**功能**: 读取EQ使能开关状态
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x9E | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x9E | 同步头2
3        | 1    | uint8 | EQ使能开关状态 (0=OFF禁用, 1=ON启用)
4-62     | 59   | 0x00 | 保留字节
```

**设备端处理**:
- 返回当前EQ使能开关状态（0=OFF, 1=ON）


### 2.22 0x9F - GET_SAMPLE_FORMAT (获取采样率和格式)
**功能**: 读取当前采样率和DSD模式
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0x9F | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x9F | 同步头2
3-6      | 4    | uint32 | 采样率 (samFreq，小端序，单位：Hz)
7        | 1    | uint8  | DSD模式 (dsdMode: 0=PCM, 1=DOP, 2=Native DSD)
8-62     | 55   | 0x00  | 保留字节
```

**设备端处理**:
- 返回当前采样率（32位无符号整数，小端序，单位：Hz）
- 返回DSD模式（0表示PCM格式，>0表示DSD格式）
- 设备会在采样率或DSD模式发生变化时自动上报此信息（通过HID状态报告）

**自动上报机制**:
- 设备中监控采样率和DSD模式的变化
- 当这些值发生变化时，设备会自动构建0x9F响应数据包并通过HID状态报告上报
- 主机可以通过HID GET_REPORT接收这些自动上报的状态变化

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0x9E | 同步头2
3        | 1    | uint8 | EQ使能开关状态 (0=OFF禁用, 1=ON启用)
4        | 1    | uint8 | 保存的模式值 (0-9，如果之前有保存，0xFF表示未保存)
5-62     | 58   | 0x00 | 保留字节
```

**设备端处理**:
- 返回当前EQ使能开关状态
- 返回之前保存的模式值（如果存在）

### 2.27 0xA4 - SET_SOUND_EFFECT_MODE (设置音效模式)
**功能**: 设置音效模式
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0xA4 | 命令码
2        | 1    | uint8 | 音效模式值 (0=无音效, 1=音乐模式, 2=游戏模式, 3=AI7.1模式)
3-62     | 60   | 0x00 | 保留字节
```

**参数说明**:
- **音效模式范围：** 0-3
- **说明：** 选择音效模式，与硬件按键效果相同
  - 0: 无音效 — 所有模式按键灯灭，EQ算法关闭，EX3D算法关闭
  - 1: 音乐模式 — 音乐键灯亮，EQ算法开启，EX3D算法关闭
  - 2: 游戏模式 — 游戏键灯亮，EQ算法开启，EX3D游戏声场(SF=0)开启
  - 3: AI7.1模式 — AI7.1键灯亮，EQ算法开启，EX3D AI7.1声场(SF=1)开启

**设备端处理**:
- 效果等同于按下相应的硬件模式按键
- 参数会通过现有的定时保存机制自动保存到Flash
- 如果参数超出范围（>3），固件将拒绝设置并返回false

**返回值**:
无直接返回值。设备端音效模式变化会主动通过0xA5格式上报。

### 2.28 0xA5 - GET_SOUND_EFFECT_MODE (获取音效模式)
**功能**: 读取设备当前音效模式；音效模式变化时设备主动上报
**方向**: 主机→设备（请求），设备→主机（响应/主动上报）
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0xA5 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0xA5 | 同步头2
3        | 1    | uint8 | 当前音效模式 (0=无音效, 1=音乐模式, 2=游戏模式, 3=AI7.1模式)
4-62     | 59   | 0x00 | 保留字节
```

**主动上报说明**:
- **开机时**：设备初始化完成后主动上报当前音效模式
- **按键切换**：用户按下Music/Game/AI7.1按键时，设备主动上报新音效模式
- **HID SET_SOUND_EFFECT_MODE（0xA4）命令成功执行后**，设备主动上报新音效模式
- 上报数据包格式与响应格式相同（0x01, 0x77, 0xA5, mode）

### 2.29 0xA6 - GET_FIRMWARE_VERSION (获取固件版本)
**功能**: 读取设备固件版本号
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0xA6 | 命令码
2-62     | 61   | 0x00 | 保留字节
```

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0xA6 | 同步头2
3        | 1    | uint8 | 主版本号 (BCD格式，如0x01表示1)
4        | 1    | uint8 | 次版本号 (BCD格式，如0x00表示0)
5        | 1    | uint8 | 修订版本号 (BCD格式，如0x0C表示12)
6-62     | 57   | 0x00 | 保留字节
```

**版本号格式说明**:
- 版本号采用BCD（Binary Coded Decimal）格式
- 3个字节分别表示：主版本号、次版本号、修订版本号
- 例如：0x01 0x00 0x0C 表示版本 1.0.12

### 2.30 0xB0 - SET_EX3D_CMD (发送EX3D命令)
**功能**: 发送EX3D设置命令，封装所有EX3D SET命令
**方向**: 主机→设备
**数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0xB0 | 命令码
2-5      | 4    | uint32 | EX3D命令码（包含SET标志，参考ex3d_protocol.md）
6-9      | 4    | uint32 | 参数1（根据EX3D命令不同而不同）
10-13    | 4    | uint32 | 参数2（根据EX3D命令不同而不同）
14-17    | 4    | uint32 | 参数3（根据EX3D命令不同而不同）
18-62    | 45   | 0x00 | 保留字节或扩展参数
```

**EX3D命令码说明**:
- 基础命令码范围: 0x80-0x94
- SET命令格式: `基础命令码 & ~0x0100`（清除第9位）
- 支持的SET命令：
  - 0x81: CMD_OPEN（打开EX3D）
  - 0x82: CMD_ONOFF（设置EX3D开关）
  - 0x83: CMD_ANGLE（设置角度）
  - 0x84: CMD_SOUND_FIELD（设置声场模式）
  - 0x85: CMD_MUTE（设置静音）
  - 0x86: CMD_ON_GAIN（设置开启增益）
  - 0x87: CMD_LMT_THRESHOLD（设置限制器阈值）
  - 0x88: CMD_UPMIX（设置上混）
  - 0x89: CMD_LFE（设置LFE增益）
  - 0x8A: CMD_OFF_GAIN（设置关闭增益）
  - 0x8E: CMD_LMT_ATTACKK_TIME（设置限制器攻击时间）
  - 0x8F: CMD_LMT_RELEASE_TIME（设置限制器释放时间）
  - 0x90: CMD_TEST_CANCEL（取消测试）
  - 0x91: CMD_TEST_STEP（测试步骤）
  - 0x92: CMD_TEST_ROTATE（测试旋转）
  - 0x93: CMD_EXPAND_GAIN（设置扩展增益）
  - 0x94: CMD_REDUCE_GAIN（设置减少增益）

**设备端处理**:
- 解析EX3D命令码，提取基础命令码和参数
- 调用相应的EX3D处理函数（hid_receive_task_in_c）
- 根据命令类型执行相应的设置操作

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0xB0 | 同步头2
3        | 1    | uint8 | 状态码 (0x00=成功, 0x01=失败)
4-7      | 4    | uint32 | EX3D命令码（回显）
8-11     | 4    | uint32 | 返回值（某些命令返回0xFFFFFFFF表示参数错误）
12-62    | 51   | 0x00 | 保留字节
```

**使用说明**:
- 该命令用于统一封装所有EX3D设置命令
- 参数格式与原始EX3D协议保持一致
- 详细的EX3D命令说明请参考ex3d_protocol.md文档

### 2.31 0xB1 - GET_EX3D_CMD (读取EX3D命令)
**功能**: 读取EX3D参数，封装所有EX3D GET命令
**方向**: 主机→设备
**请求数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x77 | 同步头1
1        | 1    | 0xB1 | 命令码
2-5      | 4    | uint32 | EX3D命令码（包含GET标志，参考ex3d_protocol.md）
6-9      | 4    | uint32 | 参数1（根据EX3D命令不同而不同，如通道号、索引等）
10-62    | 53   | 0x00 | 保留字节或扩展参数
```

**EX3D命令码说明**:
- 基础命令码范围: 0x80-0x94
- GET命令格式: `基础命令码 | 0x0100`（设置第9位）
- 支持的GET命令：
  - 0x180: CMD_CH_NUM（获取通道数量）
  - 0x182: CMD_ONOFF（获取EX3D开关）
  - 0x183: CMD_ANGLE（获取角度）
  - 0x184: CMD_SOUND_FIELD（获取声场模式）
  - 0x185: CMD_MUTE（获取静音）
  - 0x186: CMD_ON_GAIN（获取开启增益）
  - 0x187: CMD_LMT_THRESHOLD（获取限制器阈值）
  - 0x188: CMD_UPMIX（获取上混）
  - 0x189: CMD_LFE（获取LFE增益）
  - 0x18A: CMD_OFF_GAIN（获取关闭增益）
  - 0x18B: CMD_SOUND_FIELD_NUM（获取声场模式数量）
  - 0x18C: CMD_SOUND_FIELD_NAME（获取声场模式名称）
  - 0x18D: CMD_LEVEL（获取电平）
  - 0x18E: CMD_LMT_ATTACKK_TIME（获取限制器攻击时间）
  - 0x18F: CMD_LMT_RELEASE_TIME（获取限制器释放时间）
  - 0x193: CMD_EXPAND_GAIN（获取扩展增益）
  - 0x194: CMD_REDUCE_GAIN（获取减少增益）

**设备端处理**:
- 解析EX3D命令码，提取基础命令码和参数
- 调用相应的EX3D处理函数（hid_receive_task_in_c）
- 返回当前参数值

**响应数据包格式**:
```
字节位置 | 长度 | 内容 | 描述
---------|------|------|------
0        | 1    | 0x01 | Report ID
1        | 1    | 0x77 | 同步头1
2        | 1    | 0xB1 | 同步头2
3-6      | 4    | uint32 | EX3D命令码（回显）
7-10     | 4    | uint32 | 返回值1（根据命令不同而不同）
11-14    | 4    | uint32 | 返回值2（某些命令需要多个返回值，如角度、多通道数据等）
15-18    | 4    | uint32 | 返回值3（扩展返回值，如多通道数据）
...      | ...  | ...  | 其他返回值（最多可返回14个uint32值，总长度不超过63字节）
```

**返回值说明**:
- 返回值数量和格式取决于具体的EX3D命令
- 单值命令：返回1个uint32值
- 多值命令（如角度、多通道数据）：返回多个uint32值
- 字符串命令（如声场名称）：先返回长度(uint32)，然后返回字符串数据
- 详细的返回值格式请参考ex3d_protocol.md文档

**使用说明**:
- 该命令用于统一封装所有EX3D读取命令
- 参数格式与原始EX3D协议保持一致
- 详细的EX3D命令说明请参考ex3d_protocol.md文档


## 5. 关键特性

### 5.1 设备端系数计算
- 主机只发送参数 (fc, Q, bw, gain)
- 设备端根据参数实时计算滤波器系数

### 5.2 参数格式
- **浮点参数**: fc, Q, bw, gain 使用IEEE 754 float格式传输
- **字节序**: 所有多字节数据使用小端序

### 5.3 错误处理
- 数据包长度检查
- 同步头验证
- 参数范围检查
- 滤波器索引边界检查

### 5.4 模式管理
- 支持10个EQ模式 (0-9: 0-5预设模式, 6-8用户模式, 9: bypass)
- 支持禁用EQ模式 (10)
- 模式切换时自动清除滤波器状态

## 7. 注意事项

1. **时序要求**: 发送参数后需要等待设备处理完成再发送下一条命令
2. **数据完整性**: 所有8个滤波器的参数都需要发送，即使某些滤波器未使用
3. **模式同步**: 设置模式后需要调用读取模式确保数据同步
4. **错误恢复**: 通信失败时需要重新建立连接并重试
5. **参数验证**: 设备端会验证参数范围，超出范围的值会被限制

---

## 8. 固件升级命令 (0xA7–0xAE)

本节定义通过HID进行固件升级的命令。最大数据块57字节，Flash页256字节，字节序小端序。

### 8.1 固件升级命令列表

### 8.2 0xA7 - FIRMWARE_UPGRADE_START

**请求**:
```
字节 0: 0x77  同步头
字节 1: 0xA7  命令码
字节 2-5: uint32 固件大小（字节，小端序）
字节 6-62: 0x00 保留
```

**响应**（主动上报）:
```
字节 0: 0x77
字节 1: 0xA7
字节 2: 状态码 (0x00=成功, 0x01=失败, 0x03=大小无效)
字节 3-6: uint32 页对齐后的实际大小
字节 7-8: uint16 总块数
字节 9-62: 0x00
```

### 8.3 0xA8 - FIRMWARE_UPGRADE_DATA

**请求**（数据块固定57字节，不足补0）:
```
字节 0: 0x77
字节 1: 0xA8
字节 2-3: uint16 块序号（从0开始，小端序）
字节 4: uint8  数据长度（固定57）
字节 5-61: uint8[57] 固件数据
字节 62: uint8 Checksum（字节0-61累加 mod 256）
```

**响应**（主动上报）:
```
字节 0: 0x77
字节 1: 0xA8
字节 2: 状态码 (0x00=成功, 0x04=块号错误, 0x05=Checksum错误)
字节 3-4: uint16 已确认块序号
字节 5-62: 0x00
```

### 8.4 0xA9 - FIRMWARE_UPGRADE_END

**请求**:
```
字节 0: 0x77
字节 1: 0xA9
字节 2-5: uint32 固件总大小（用于验证）
字节 6-62: 0x00
```

**响应**（主动上报）:
```
字节 0: 0x77
字节 1: 0xA9
字节 2: 状态码 (0x00=成功, 0x01=失败)
字节 3-62: 0x00
```

### 8.5 0xAA - FIRMWARE_UPGRADE_STATUS

**请求**: 字节0=0x77, 字节1=0xAA, 其余0x00

**响应**（主动上报）:
```
字节 0: 0x77
字节 1: 0xAA
字节 2: 升级状态 (0=空闲, 1=准备中, 2=传输中, 3=完成中, 4=已完成, 5=错误, 6=已中止)
字节 3-4: uint16 已接收块数
字节 5-6: uint16 总块数
字节 7-8: uint16 已写页数
字节 9-10: uint16 总页数
字节 11-14: uint32 已传输字节数
字节 15-18: uint32 总字节数
字节 19: 错误码
字节 20-62: 0x00
```

### 8.6 0xAB - FIRMWARE_UPGRADE_ABORT

**请求**:
```
字节 0: 0x77
字节 1: 0xAB
字节 2: 清理标志 (0x00=保留数据, 0x01=擦除数据)
字节 3-62: 0x00
```

**响应**（主动上报）: 字节0=0x77, 字节1=0xAB, 字节2=状态码(0x00=成功)

### 8.7 0xAC - FIRMWARE_UPGRADE_ERASE

**请求**: 字节0=0x77, 字节1=0xAC, 其余0x00

**响应**（主动上报）: 字节0=0x77, 字节1=0xAC, 字节2=状态码(0x00=成功)

### 8.8 0xAE - DEVICE_REBOOT

**请求**: 字节0=0x77, 字节1=0xAE, 其余0x00

**响应**: 无响应，设备立即重启。

### 8.9 标准升级流程

```
1. (可选) ERASE  — 擦除现有upgrade image
2. START         — 设置固件大小，等待响应(SUCCESS)
3. 循环 DATA     — 逐块发送，每块等待响应确认
4. END           — 完成写入，等待响应(SUCCESS)
5. REBOOT        — 重启加载新固件
```

