Kernel 5.10 SD卡专属探测、上电与注册流程分析 (Detect -> Power Up -> Add)

总体控制流:Host 中断 -> 扫描频率 -> SD专属协议握手 -> 加网注册

第一阶段:探测流 (Detect Phase)

  1. 热插拔触发 (mmc_rescan) : 大部分 SD 卡槽带有 Card Detect (CD) 引脚。当物理插入动作发生时,底层主机控制器(如 sdhci)产生中断,唤醒系统工作队列 host->detect 执行 mmc_rescan 函数。
  2. 安全初始环境准备 : 在 mmc_rescan 中,主机控制器会首先给 SD 卡加电并以较低的频率启动轮询。因为所有的 SD 卡在刚插入时强制要求以规范定义的低速进入。它调用 mmc_rescan_try_freq(host, freq),通常以 400KHz 开始盲探。
  3. SD专属协议试探 (mmc_attach_sd) : 在 mmc_rescan_try_freq 内部:
    • 先发送 CMD0 (GO_IDLE_STATE) 让所有卡软复位。
    • 跳过 SDIO 探测(如果 CMD5 无响应)。
    • SD 卡的关键试探 :紧接着发送 CMD8 (SEND_IF_COND) 测试电压兼容性(识别 SD 2.0+ 标志)。
    • 身份最终确认 :由探测转入实质依附过程,调用 mmc_attach_sd(host)

第二阶段:上电协商与初始化 (Power Up & Init Phase)

在 SD 卡的体系中,上电不再是一次性的拉高电平就结束了,而是涉及到复杂的 UHS-I 超高速卡 1.8V 降压切换以及调谐(Tuning)。这是 Kernel 5.10 中 SD 驱动最精华的部分。

  1. 操作条件查询与初始供电 (mmc_send_app_op_cond / mmc_power_up) : 在 mmc_attach_sd 起始阶段,系统发送 CMD55 + ACMD41 (APP_SEND_OP_COND) 命令不断轮询。这不仅仅是检测,同时也在查询卡的可用电压窗口(OCR,Operation Conditions Register)。 只要卡在这个环节宣告 Ready,主机就会依据返回的 OCR 锁定工作电压,通过 mmc_power_up(host, ocr) 调用底层的寄存器(set_ios)把芯片对应的 VDD 管脚真正上电稳定。

  2. 核心状态机拉升 (mmc_sd_init_card): 由于电压稳了,系统真正开始解析 SD 卡,进行一系列经典的协议流动作:

    • CMD2 (ALL_SEND_CID):获取这小板子的出厂身份码,比如闪迪还是金士顿、生产年月。
    • CMD3 (SEND_RELATIVE_ADDR):SD卡与 eMMC 不同,系统会要求 SD 卡自己汇报一个相对地址 (RCA)。之后所有通信基于此地址进行。
    • CMD9 (SEND_CSD):获取卡的核心特征,最主要的是算出这卡到底有多少 GB 容量。
    • CMD7 (SELECT_CARD):拿着刚才得到的 RCA 地址,正式选中这张卡。至此,SD 卡从"待机态(Standby)"完全进入了"传输态(Transfer State)"。
    • CMD8 (APP_SEND_SCR):读取配置寄存器,获知卡支持的特性配置。
  3. UHS-I 电压切换与调谐 (Voltage Switch & Tuning): 如果是高速 SD 卡(如 U1, U3 规格):

    • 主机通过 CMD11 (VOLTAGE_SWITCH) 提示卡。
    • 随即底层控制器把 VCCQ 引脚由 3.3V "热切换" 降维至 1.8V(这是保证高频运转不发热不失真的硬件门槛)。
    • 若进入 SDR50 / SDR104 高速模式,还会调用 mmc_execute_tuning() 连续发送特制波形来测算当前温度和电路阻抗下的最佳时钟采样延时点。

第三阶段:注册投轨向 Linux 报到 (Add Card Phase)

当所有的初始化和降压提速动作跑完后,代码流返回到了最上层的业务归口。

  1. 实体建立 (mmc_add_card) : 执行 err = mmc_add_card(host->card);。在 core/bus.c 中,把前面各种繁杂步骤获得的信息(CID,容量,速率,只读状态等)打包,以此为蓝本作为一个 struct device 实体注入到庞大的 Linux 设备树字典中。
  2. 通报 Block 层 : 随着 device_add 的内部广播,一直监视着 MMC 总线的虚拟块设备驱动 block.c 闻风而动。
  3. 暴露存储空间 (mmc_blk_probe) : 由于前面的协商结果毫无瑕疵,块驱动终于放心地执行 alloc_disk() 并创建 /dev/mmcblkX。 紧接着内核的通用分区代码会自动去读这张卡的第 0 扇区(也就是 MBR / GPT 所在处),识别到 FAT32/ext4 等文件系统布局并抛出如 /dev/mmcblkXp1 等设备接口,最终 udev 层面可借此自动挂载您的 SD 卡卷标至 /mnt/media 内。

关键代码追踪锚点总结

如果在 Kernel 5.10 排查 SD 卡挂载失败的问题,可以顺着以下锚点顺藤摸瓜:

  1. 卡槽没反应 :查中断触发、GPIO配置、或 host.cmmc_rescan 延时队列是否被屏蔽。
  2. 提示超时或电压不匹配 -EINVAL :在 mmc_attach_sd()ACMD41 阶段出问题了,重点看核心板的供电引脚实际电压输出能力与设备树描述是否一致(即 Regulator 稳压器设错了)。
  3. -EILSEQ (信号调谐失败) 或者降速警告 :重点看 mmc_sd_init_card() 中段的电压切换 CMD11 和之后的 mmc_execute_tuning() 过程。
  4. 出现写保护 / 不能读 :查看 slot-gpio.c 中对卡槽旁边的物理 WP (Write Protect) 小拨钮管脚映射。
相关推荐
艾莉丝努力练剑2 小时前
【Linux信号】Linux进程信号(下):可重入函数、Volatile关键字、SIGCHLD信号
linux·运维·服务器·c++·人工智能·后端·学习
si莉亚2 小时前
2026.3.31成功安装Ubuntu22.04+ROS2记录
linux·c++·开源
蓝凌y2 小时前
51单片机之按键扫描
单片机·嵌入式硬件·51单片机
RrEeSsEeTt2 小时前
【HackTheBox】- Monteverde 靶机学习
linux·网络安全·渗透测试·kali·红队·hackthebox·ad域
果果燕2 小时前
ARM嵌入式学习(三)---汇编应用:LED点亮
arm开发·单片机·嵌入式硬件
美式请加冰2 小时前
Linux权限的概念
linux·运维·服务器
两年半的个人练习生^_^3 小时前
List集合的使用和源码
linux·windows·list
蓝天居士3 小时前
认识libcurl(2)
linux·libcurl
Jonathan Star3 小时前
在 Claude Code 中重新加载插件,最常用的是 **`/reload-plugins` 热重载**,也
linux·运维·服务器