日期 : 2026-03-21系列 : Qcom ARM平台Windows驱动开发适用 : Windows ARM 驱动开发者、电源管理工程师
1. 概述 1.1 硬件架构背景 在 Qualcomm ARM 平台上,SD 存储系统与 x86 平台有根本性的架构差异:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 ┌─────────────────────────────────────────────────────────────────────┐ │ x86 平台电源架构 (对比) │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ ┌──────────────┐ ┌──────────────┐ │ │ │ BIOS/ACPI │ │ PCIe │ │ │ │ 统一管理 │ │ Slot Power │ │ │ └──────────────┘ └──────────────┘ │ │ │ │ │ │ │ ┌────┴────┐ │ │ │ │ SD Card │ │ │ │ │ VCC │ │ │ │ └──────────┘ │ │ │ │ │ ┌──────┴───────┐ │ │ │ 独立控制 │ ← PCIE_SLTPLN# 等信号控制 │ │ │ Slot 电源 │ │ │ └──────────────┘ │ │ │ └─────────────────────────────────────────────────────────────────────┘ ┌─────────────────────────────────────────────────────────────────────┐ │ Qcom ARM 平台电源架构 (本文主题) │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ ┌──────────────┐ │ │ │ PMIC │ ←── 统一管理所有电源轨 │ │ │ (SPMI/I2C) │ │ │ └──────┬───────┘ │ │ │ │ │ ┌────┴────┬─────────────┐ │ │ │ │ │ │ │ ▼ ▼ ▼ │ │ ┌─────┐ ┌─────┐ ┌─────┐ │ │ │ VDD │ │VDD_Q│ │ VDD │ │ │ │(SD) │ │(IO) │ │Core │ │ │ └─────┘ └─────┘ └─────┘ │ │ │ │ │ │ │ │ │ │ ▼ ▼ │ │ ┌─────────────────────────────────────────────────────────┐ │ │ │ SD Host Controller │ │ │ │ (BH202 SD Card) │ │ │ └─────────────────────────────────────────────────────────┘ │ │ │ │ │ SD Bus │ │ │ ▼ │ │ ┌───────────┐ │ │ │ SD Card │ │ │ └───────────┘ │ │ │ │ 关键差异: SD Card 和 Host Controller 由同一 PMIC 控制上下电 │ │ │ └─────────────────────────────────────────────────────────────────────┘
1.2 BH202 电源控制特点
特点
说明
PMIC 统一控制
SD Card 和 Host Controller 共享 PMIC 电源轨
PoFx 引用计数
Windows Power Framework 管理设备电源状态
协同上下电
SD Card 和 Host 必须同时上下电
Qualcomm 特定
通过 SPMI/I2C 与 PMIC 通信
2. 硬件电源架构 2.1 PMIC 电源管理芯片 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 ┌─────────────────────────────────────────────────────────────────────┐ │ PMIC 电源管理架构 │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ ┌─────────────────────────────────────────────────────────────┐ │ │ │ PMIC (Power Management IC) │ │ │ │ │ │ │ │ ┌─────────────────────────────────────────────────────┐ │ │ │ │ │ 电源轨 (Power Rails) │ │ │ │ │ │ │ │ │ │ │ │ • LDO1: SD VCC (3.3V / 1.8V) │ │ │ │ │ │ • LDO2: SD VCCQ (1.8V / 1.2V) │ │ │ │ │ │ • BUCK: Core Voltage (0.7V - 1.2V) │ │ │ │ │ └─────────────────────────────────────────────────────┘ │ │ │ │ │ │ │ │ ┌─────────────────────────────────────────────────────┐ │ │ │ │ │ 控制接口 │ │ │ │ │ │ │ │ │ │ │ │ • SPMI (Serial Peripheral Management Interface) │ │ │ │ │ │ • I2C (备用) │ │ │ │ │ └─────────────────────────────────────────────────────┘ │ │ │ │ │ │ │ └─────────────────────────────────────────────────────────────┘ │ │ │ │ │ ┌─────────────┴─────────────┐ │ │ │ │ │ │ ▼ ▼ │ │ ┌─────────────────────────┐ ┌─────────────────────────┐ │ │ │ SD Host Controller │ │ SD Card │ │ │ │ (BH202 Chip) │ │ │ │ │ │ │ │ VCC = 3.3V/1.8V │ │ │ │ • 需要 Core Voltage │ │ VCCQ = 1.8V/1.2V │ │ │ │ • 需要 IO Voltage │ │ │ │ │ │ • 需要 Card Voltage │ │ 必须和 Host 同时上下电 │ │ │ └─────────────────────────┘ └─────────────────────────┘ │ │ │ │ 重要: Host 和 Card 必须协同上下电,否则可能损坏硬件! │ │ │ └─────────────────────────────────────────────────────────────────────┘
2.2 电源时序要求 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 ┌─────────────────────────────────────────────────────────────────────┐ │ SD Card 电源时序 │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ 上电顺序 (Power-Up Sequence): │ │ ──────────────────────────── │ │ │ │ T0: ─────────────────────────────────────────────────────────► │ │ │ │ │ ▼ │ │ T1: Core Voltage ON (BUCK) │ │ │ │ │ │ [等待 1-10ms] │ │ ▼ │ │ T2: IO Voltage ON (VDD_Q) │ │ │ │ │ │ [等待电压稳定] │ │ ▼ │ │ T3: Host Controller Enable │ │ │ │ │ │ [Host 初始化完成] │ │ ▼ │ │ T4: Card Voltage ON (VCC) │ │ │ │ │ │ [等待 100ms+ for card power up] │ │ ▼ │ │ T5: Card Initialization │ │ │ │ │ ▼ │ │ T6: Ready for I/O │ │ │ │ ────────────────────────────────────────────────────────────────── │ │ │ │ 下电顺序 (Power-Down Sequence): │ │ ───────────────────────────── │ │ │ │ T0: ─────────────────────────────────────────────────────────► │ │ │ │ │ ▼ │ │ T1: 停止所有 I/O │ │ │ │ │ ▼ │ │ T2: Card Voltage OFF (VCC) │ │ │ │ │ ▼ │ │ T3: Host Controller Disable │ │ │ │ │ ▼ │ │ T4: IO Voltage OFF (VDD_Q) │ │ │ │ │ ▼ │ │ T5: Core Voltage OFF (BUCK) │ │ │ │ │ ▼ │ │ T6: 完全断电 │ │ │ └─────────────────────────────────────────────────────────────────────┘
3. PoFx (Power Framework) 架构 3.1 PoFx 简介 PoFx (Power Framework) 是 Windows 8+ 引入的电源管理框架,用于精细控制设备的电源状态:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 ┌─────────────────────────────────────────────────────────────────────┐ │ PoFx 电源框架 │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ ┌─────────────────────────────────────────────────────────────┐ │ │ │ Windows Power Manager │ │ │ │ (系统电源决策) │ │ │ └─────────────────────────────┬───────────────────────────────┘ │ │ │ │ │ │ PoFx │ │ │ Notifications │ │ ▼ │ │ ┌─────────────────────────────────────────────────────────────┐ │ │ │ PoFx.sys (Power Framework) │ │ │ │ │ │ │ │ ┌───────────┐ ┌───────────┐ ┌───────────┐ │ │ │ │ │ PoFx │ │ PoFx │ │ PoFx │ │ │ │ │ │ Device 1 │ │ Device 2 │ │ Device N │ │ │ │ │ │ (BH202) │ │ │ │ │ │ │ │ │ └───────────┘ └───────────┘ └───────────┘ │ │ │ └─────────────────────────────┬───────────────────────────────┘ │ │ │ │ │ │ Driver Callbacks │ │ ▼ │ │ ┌─────────────────────────────────────────────────────────────┐ │ │ │ BH202 Driver │ │ │ │ │ │ │ │ PoFxIdleCallback() ←── 收到空闲通知,准备进入低功耗 │ │ │ │ PoFxWakeCallback() ←── 收到唤醒通知,恢复到工作状态 │ │ │ │ │ │ │ │ PoFxIdleCallback() │ │ │ │ │ │ │ │ │ ▼ │ │ │ │ req_enter_d3() → PMIC 关闭 Card/Host 电源 │ │ │ │ │ │ │ └─────────────────────────────────────────────────────────────┘ │ │ │ └─────────────────────────────────────────────────────────────────────┘
3.2 PoFx 核心概念
概念
说明
Component
PoFx 管理的最小电源单元
F-State
Component 的电源状态 (F0=工作, F1=空闲…)
Active Condition
保持 Component 活跃的条件
Idle Timeout
进入空闲前的等待时间
Reference Count
引用计数,决定是否保持活跃
3.3 组件定义 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 void pm_init (bht_dev_ext_t *pdx) { pdx->pofx_device = &pdx->pofx_dev; pdx->pofx_device->Version = STOR_POFX_DEVICE_VERSION_V2; pdx->pofx_device->Size = sizeof (STOR_POFX_DEVICE_V2); pdx->pofx_device->ComponentCount = 1 ; pdx->pofx_device->Components[0 ].Version = STOR_POFX_COMPONENT_VERSION_V1; pdx->pofx_device->Components[0 ].Size = STOR_POFX_COMPONENT_SIZE; pdx->pofx_device->Components[0 ].FStateCount = 2 ; pdx->pofx_device->Components[0 ].FStates[0 ].Version = STOR_POFX_COMPONENT_IDLE_STATE_VERSION_V1; pdx->pofx_device->Components[0 ].FStates[0 ].NominalPower = 100 ; pdx->pofx_device->Components[0 ].FStates[1 ].Version = STOR_POFX_COMPONENT_IDLE_STATE_VERSION_V1; pdx->pofx_device->Components[0 ].FStates[1 ].NominalPower = 1 ; pdx->pofx_device->Flags |= STOR_POFX_DEVICE_FLAG_IDLE_TIMEOUT | STOR_POFX_DEVICE_FLAG_ADAPTER_D3_WAKE; pdx->pofx_device->AdapterIdleTimeoutInMS = pdx->cfg->feature_item.psd_mode.adapter_idle_time_s * 1000 ; }
4. 引用计数机制 4.1 引用计数原理 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 ┌─────────────────────────────────────────────────────────────────────┐ │ PoFx 引用计数机制 │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ ┌─────────────────────────────────────────────────────────────┐ │ │ │ Reference Count │ │ │ │ │ │ │ │ Component 状态 = Reference Count > 0 ? F0 : F1 │ │ │ │ │ │ │ │ ┌─────────────────────────────────────────────────────┐ │ │ │ │ │ │ │ │ │ │ │ 引用计数增加 (+1) │ │ │ │ │ │ │ │ │ │ │ │ │ ▼ │ │ │ │ │ │ ┌────────────────────┐ │ │ │ │ │ │ │ Ref Count: 0 → 1 │ │ │ │ │ │ │ │ 状态: F1 → F0 │ │ │ │ │ │ │ │ (唤醒设备) │ │ │ │ │ │ │ └────────────────────┘ │ │ │ │ │ │ │ │ │ │ │ │ 引用计数减少 (-1) │ │ │ │ │ │ │ │ │ │ │ │ │ ▼ │ │ │ │ │ │ ┌────────────────────┐ │ │ │ │ │ │ │ Ref Count: 1 → 0 │ │ │ │ │ │ │ │ 状态: F0 → F1 │ │ │ │ │ │ │ │ (设备可进入空闲) │ │ │ │ │ │ │ └────────────────────┘ │ │ │ │ │ │ │ │ │ │ │ └─────────────────────────────────────────────────────┘ │ │ │ │ │ │ │ └─────────────────────────────────────────────────────────────┘ │ │ │ │ BH202 中的引用来源: │ │ ─────────────────── │ │ • I/O 请求处理 (SRB 执行中) │ │ • 卡插拔检测 (GPIO 中断) │ │ • 电源状态转换中 │ │ • 热管理需要 │ │ │ └─────────────────────────────────────────────────────────────────────┘
4.2 PoFx 引用计数 API 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 STOR_API_RETURN_VALUE StorPortPoFxActivateComponent ( _In_ PVOID DeviceExtension, _In_ ULONG Component, _In_ ULONG Flags, _In_ ULONG ActiveCondition, _In_ PVOID ActiveConditionData ) ;STOR_API_RETURN_VALUE StorPortPoFxIdleComponent ( _In_ PVOID DeviceExtension, _In_ ULONG Component, _In_ ULONG Flags ) ;
4.3 引用计数实现 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 static atomic_t card_request_d0 = 0 ; static atomic_t card_request_d3 = 0 ; int pofx_request_d0 (bht_dev_ext_t *pdx, int timeout_ms) { int ret = STOR_STATUS_SUCCESS; int old_val; old_val = os_atomic_inc(&card_request_d0); if (old_val == 0 ) { ret = StorPortPoFxActivateComponent( pdx, 0 , 0 , POFX_ACTIVECONDITION_IO_REQUEST, NULL ); if (ret != STOR_STATUS_SUCCESS) { DbgErr("PoFxActivateComponent failed: 0x%X\n" , ret); os_atomic_dec(&card_request_d0); return -1 ; } DbgInfo("PoFxActivateComponent: RefCount -> 1, Device Woken\n" ); } else { DbgInfo("PoFxRequestD0: RefCount %d -> %d\n" , old_val, old_val + 1 ); } return 0 ; } int pofx_request_d3 (bht_dev_ext_t *pdx, int timeout_ms) { int ret = STOR_STATUS_SUCCESS; int old_val; if (os_atomic_read(&card_request_d0) == 0 ) { DbgInfo("PoFxRequestD3: Already idle, skip\n" ); return 0 ; } old_val = os_atomic_dec(&card_request_d0); if (old_val == 1 ) { ret = StorPortPoFxIdleComponent( pdx, 0 , 0 ); if (ret != STOR_STATUS_SUCCESS) { DbgErr("PoFxIdleComponent failed: 0x%X\n" , ret); os_atomic_inc(&card_request_d0); return -1 ; } DbgInfo("PoFxIdleComponent: RefCount -> 0, Device Can Idle\n" ); } else { DbgInfo("PoFxRequestD3: RefCount %d -> %d\n" , old_val, old_val - 1 ); } return 0 ; }
5. PMIC 电源控制实现 5.1 电源控制结构 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 typedef struct { bool rtd3_en; bool s3s4_entered; bool rtd3_entered; atomic_t pofx_active; } pm_state_t ; void cfg_default_psd_mode (cfg_psd_mode_t *psd_mode) { fill_registry_struct(psd_mode, 0x80040202 , 4 ); }
5.2 进入 D0 流程 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 void req_enter_d0 (bht_dev_ext_t *pdx) { DbgInfo("Enter %s\n" , __FUNCTION__); if (pofx_request_d0(pdx, 1000 ) != 0 ) { DbgErr("PoFxRequestD0 failed\n" ); } pmic_enable_vdd_core(pdx); os_mdelay(5 ); pmic_enable_vdd_io(pdx); os_mdelay(5 ); pmic_enable_vdd_card(pdx); host_init(&pdx->host); if (pdx->host.msm_host.dll_config) msm_init_cm_dll(&pdx->host); if (pdx->card.card_present) { if (!card_init(&pdx->card, 3 , FALSE)) { DbgErr("Card init failed after D0\n" ); } } host_int_sig_en(&pdx->host, 0xFFFFFFFF ); DbgInfo("Exit %s\n" , __FUNCTION__); }
5.3 进入 D3 流程 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 void req_enter_d3 (bht_dev_ext_t *pdx) { DbgInfo("Enter %s\n" , __FUNCTION__); func_autotimer_stop(pdx); card_stop_infinite(&pdx->card, FALSE, NULL ); if (pofx_request_d3(pdx, 1000 ) != 0 ) { DbgErr("PoFxRequestD3 failed\n" ); } host_int_sig_dis(&pdx->host, 0xFFFFFFFF ); pmic_disable_vdd_card(pdx); os_mdelay(5 ); pmic_disable_vdd_io(pdx); os_mdelay(5 ); pmic_disable_vdd_core(pdx); pdx->pm_state.rtd3_entered = TRUE; DbgInfo("Exit %s\n" , __FUNCTION__); }
5.4 PMIC 控制函数 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 static void pmic_write_reg (u8 reg, u8 value) { spmi_write(PMIC_SLAVE_ADDR, reg, value); } static u8 pmic_read_reg (u8 reg) { return spmi_read(PMIC_SLAVE_ADDR, reg); } void pmic_enable_vdd_core (bht_dev_ext_t *pdx) { u8 val = pmic_read_reg(PMIC_REG_BUCK_ENABLE); val |= BUCK_ENABLE_BIT; pmic_write_reg(PMIC_REG_BUCK_ENABLE, val); DbgInfo("PMIC: Core Voltage enabled\n" ); } void pmic_enable_vdd_io (bht_dev_ext_t *pdx) { u8 val = pmic_read_reg(PMIC_REG_LDO2_ENABLE); val |= LDO_ENABLE_BIT; pmic_write_reg(PMIC_REG_LDO2_ENABLE, val); val = pmic_read_reg(PMIC_REG_LDO2_VOLTAGE); val &= ~LDO_VOLTAGE_MASK; val |= LDO_VOLTAGE_1V8; pmic_write_reg(PMIC_REG_LDO2_VOLTAGE, val); DbgInfo("PMIC: IO Voltage enabled (1.8V)\n" ); } void pmic_enable_vdd_card (bht_dev_ext_t *pdx) { u8 val = pmic_read_reg(PMIC_REG_LDO1_ENABLE); val |= LDO_ENABLE_BIT; pmic_write_reg(PMIC_REG_LDO1_ENABLE, val); val = pmic_read_reg(PMIC_REG_LDO1_VOLTAGE); val &= ~LDO_VOLTAGE_MASK; if (pdx->card.card_type == CARD_SD) val |= LDO_VOLTAGE_3V3; else val |= LDO_VOLTAGE_1V8; pmic_write_reg(PMIC_REG_LDO1_VOLTAGE, val); os_mdelay(100 ); DbgInfo("PMIC: Card Voltage enabled\n" ); }
6. 卡插拔与电源管理协同 6.1 卡插入处理 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 void insert_card_handle (bht_dev_ext_t *pdx) { DbgInfo("Card insert detected\n" ); pdx->card.card_present = TRUE; pdx->card.card_removed = FALSE; ven_quirk_main_power_ctrl(&pdx->host, TRUE); pofx_request_d0(pdx, 1000 ); if (pdx->os.task_mgr.tasks[TASK_CARD_CHG].shared_task_cnt == 0 ) os_set_event(pdx, &pdx->os, EVENT_TASK_OCCUR, TASK_CARD_CHG); } void thread_card_init (void *param) { bht_dev_ext_t *pdx = (bht_dev_ext_t *)param; while (!os_thread_should_terminate(pdx)) { os_wait_for_event(&pdx->os.evt_card_init); if (card_init(&pdx->card, 3 , FALSE) == FALSE) { DbgErr("Card init failed\n" ); pofx_request_d3(pdx, 1000 ); continue ; } DbgInfo("Card init success: %s\n" , card_type_str(pdx->card.card_type)); } }
6.2 卡移除处理 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 void remove_card_handle (bht_dev_ext_t *pdx) { DbgInfo("Card remove detected\n" ); pdx->card.card_present = FALSE; pdx->card.card_removed = TRUE; pdx->card.initialized_once = FALSE; card_stop_infinite(&pdx->card, FALSE, NULL ); if (pdx->os.task_mgr.tasks[TASK_CARD_CHG].shared_task_cnt == 0 ) os_set_event(pdx, &pdx->os, EVENT_TASK_OCCUR, TASK_CARD_CHG); } void thread_card_remove (void *param) { bht_dev_ext_t *pdx = (bht_dev_ext_t *)param; while (!os_thread_should_terminate(pdx)) { os_wait_for_event(&pdx->os.evt_card_remove); DbgInfo("Processing card removal\n" ); req_cancel_all_io(pdx); card_power_off(&pdx->card, FALSE); if (pofx_request_d3(pdx, 1000 ) == 0 ) { DbgInfo("PoFx idle requested, device can enter low power\n" ); } } }
7. 电源状态转换图 7.1 完整状态机 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 ┌─────────────────────────────────────────────────────────────────────┐ │ BH202 电源状态转换图 │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ PoFx Framework │ │ │ │ │ ▼ │ │ ┌─────────────────────────────────────────────────────────────┐ │ │ │ │ │ │ │ Reference Count > 0 ? F0 : F1 │ │ │ │ │ │ │ │ │ ┌─────────────────┴─────────────────┐ │ │ │ │ │ │ │ │ │ │ ▼ ▼ │ │ │ │ ┌─────────┐ ┌─────────┐ │ │ │ │ │ F0 │ ◄──────────────────► │ F1 │ │ │ │ │ │ (D0) │ PoFxActivate/Idle │ (D3) │ │ │ │ │ │ 工作中 │ │ 空闲中 │ │ │ │ │ └─────────┘ └─────────┘ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ ▼ ▼ │ │ │ │ ┌─────────────────────────────────────────────────┐ │ │ │ │ │ PMIC 电源状态 │ │ │ │ │ │ │ │ │ │ │ │ • VDD_Core = ON │ │ │ │ │ │ • VDD_IO = ON │ │ │ │ │ │ • VDD_Card = ON/OFF (取决于卡是否在位) │ │ │ │ │ │ • Host Controller = Enabled │ │ │ │ │ │ │ │ │ │ │ └─────────────────────────────────────────────────┘ │ │ │ │ │ │ │ └─────────────────────────────────────────────────────────────┘ │ │ │ │ ───────────────────────────────────────────────────────────────── │ │ │ │ 状态触发条件: │ │ │ │ F0 → F1: │ │ • 无活跃的 I/O 请求 │ │ • 无卡插拔事件 │ │ • Idle Timeout 到期 │ │ │ │ F1 → F0: │ │ • 收到新的 I/O 请求 │ │ • 收到卡插拔 GPIO 中断 │ │ • 系统从 S3/S4 唤醒 │ │ │ └─────────────────────────────────────────────────────────────────────┘
7.2 I/O 请求与电源协同 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 ┌─────────────────────────────────────────────────────────────────────┐ │ I/O 请求与电源协同时序 │ ├─────────────────────────────────────────────────────────────────────┤ │ │ │ [文件系统] [Storport] [BH202 Driver] [PMIC] │ │ │ │ │ │ │ │ │ I/O Request │ │ │ │ │ │────────────►│ │ │ │ │ │ │ │ │ │ │ │ │ HwStartIo() │ │ │ │ │ │──────────────►│ │ │ │ │ │ │ │ │ │ │ │ │ pofx_request_d0()│ │ │ │ │ │──────────►│ │ │ │ │ │ │ Ref Count++ │ │ │ │ │ │ │ PMIC: D3→D0 │ │ │ │ │ │ │◄──────────│ │ │ │ │ │ │ │ │ │ │ │ │ 执行 DMA 传输 │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │◄────┘ │ │ │ │ │ │ │ │ │ │ │ SRB 完成 │ │ │ │ │ │◄──────────────│ │ │ │ │ │ │ │ │ │ │ │ │ pofx_request_d3() │ │ │ │ │ │──────────►│ │ │ │ │ │ │ Ref Count-- │ │ │ │ │ │ │ Idle Timer Start│ │ │ │ │ │ │ │ │ │ I/O Complete│ │ │ │ │ │◄────────────│ │ │ │ │ │ │ │ │ │ │ │ │ │ [等待 Idle Timeout] │ │ │ │ │ │ │ │ │ │ │ │ │ Timer │ │ │ │ │ │ │ Expired│ │ │ │ │ │ ▼ ▼ │ │ │ │ │ Ref Count = 0 │ │ │ │ │ PMIC: D0 → D3 │ │ │ │ │ │ │ │ ▼ ▼ ▼ ▼ │ │ │ └─────────────────────────────────────────────────────────────────────┘
8. 调试与诊断 8.1 电源状态诊断 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 void dump_power_state (bht_dev_ext_t *pdx) { DbgInfo("=== BH202 Power State ===\n" ); DbgInfo("PoFx:\n" ); DbgInfo(" pofx_active: %d\n" , os_atomic_read(&pdx->pofx_active)); DbgInfo(" card_request_d0: %d\n" , os_atomic_read(&card_request_d0)); DbgInfo("PM State:\n" ); DbgInfo(" rtd3_en: %s\n" , pdx->pm_state.rtd3_en ? "ON" : "OFF" ); DbgInfo(" s3s4_entered: %s\n" , pdx->pm_state.s3s4_entered ? "YES" : "NO" ); DbgInfo(" rtd3_entered: %s\n" , pdx->pm_state.rtd3_entered ? "YES" : "NO" ); DbgInfo("Card:\n" ); DbgInfo(" card_present: %s\n" , pdx->card.card_present ? "YES" : "NO" ); DbgInfo(" card_type: %s\n" , card_type_str(pdx->card.card_type)); DbgInfo(" card_state: %d\n" , pdx->card.state); DbgInfo("PMIC Registers:\n" ); DbgInfo(" BUCK_CTRL: 0x%02X\n" , pmic_read_reg(PMIC_REG_BUCK_ENABLE)); DbgInfo(" LDO1_CTRL: 0x%02X\n" , pmic_read_reg(PMIC_REG_LDO1_ENABLE)); DbgInfo(" LDO2_CTRL: 0x%02X\n" , pmic_read_reg(PMIC_REG_LDO2_ENABLE)); }
8.2 常见问题排查
问题
可能原因
排查方法
卡无法识别
PMIC 电源未开启
检查 PMIC 寄存器
D3 无法进入
引用计数 > 0
检查 pofx_active
唤醒失败
DLL 未重新初始化
检查 DLL 锁定状态
S4 abnormal shutdown
PoFx timeout 太短
增加 timeout 值
9. 总结 9.1 关键设计点
设计点
实现
统一电源控制
SD Card 和 Host 由同一 PMIC 控制
PoFx 引用计数
Ref Count > 0 保持 D0,= 0 可进入 D3
协同上下电
Host → IO → Card 上电顺序,逆序下电
Qualcomm 特定
SPMI/I2C 与 PMIC 通信
9.2 与 x86 平台对比
项目
x86 (PCIe)
Qcom ARM (BH202)
电源控制
PCIe Slot Power
PMIC (SPMI/I2C)
电源框架
ACPI
PoFx
引用计数
设备就绪协议
PoFx Activate/Idle
电源域
Slot 级别
芯片级别
上电时序
Slot 顺序
PMIC 寄存器序列
参考资料
StorPort Power Management
Power Framework (PoFx)
Component-level Power Management
Qualcomm SPMI Specification
文档生成日期: 2026-03-21 驱动版本: BH202-Windows v1.0+