可见core文件夹下有针对总线的服務bus.c,针对主控制器的服务host.c针对SD卡的服务sd.c, sd_ops.c等等。
其中最为核心的一个函数便是之前提到的位于core.c的mmc_rescan,概括来讲主要完成两项任务,即
扫描SD总线插入SD卡
扫描SD总线,拔出SD卡
如果上电成功则返回0,即执行if()里的mmc_attach_sd()进行总线与SD卡的绑定
如果上电失败,则返回非0值跳过if(),尝试其怹上电的方法
这里的指令SD_APP_OP_COND只有SD2.0的协议支持,也就是说只有普通SD卡支持,所以也只有普通SD卡能够成功上电
如果上电成功,就开始进行總线与SD卡的绑定通过mmc_attach_sd(),绑定过程可分为四步
启动SD卡 - 根据协议,完成SD卡启动的各个步骤
二、注册总线上的操作函数
这里的mmc_sd_detect和mmc_sd_remove就是拔出SD卡所需要用到的函数下文将详细讨论。这里需要注意的是插入SD卡的时候,并不执行mmc_sd_detect和mmc_sd_remove这两个函数但是会注册它们,也就是说这两个函数的功能已经实现,将来可以使用
从这里可以体会到回调函数的精髓:协议层里利用回调函数为所有满足该协议的设备提供统一的接ロ,而具体实现由底层不同的设备驱动各自完成注意到,之所以要定义一些放之四海而皆准的公用的类比如struct mmc_host,就是需要通过struct mmc_host *host指针作为形参传到协议层所提供的接口函数中从而得以调用。
其他操作比如切换到高速模式初始化card
1) SD卡的启动过程
-> 发送指令并得到寄存器的值
card->raw_cid),請求得到SD卡CID寄存器的值当主控制器发送cmd完成后,芯片产生一个内部中断处理结束cmd的中断函数,之后得到来自SD卡的response即CID寄存器的值,存放于host->cmd->resp[i]中关于内部中断处理,参看上文的中断一节里的 mmc_wait_for_cmd()
-> 解析寄存器的值
为了方便得到具体某一个信息,协议层为我们解析了寄存器里的域并赋给card->cid,比如厂商名称就可以通过card->cid.manfid直接读取到。
五、 注册SD卡设备驱动这里的mmc_bus_get/put()为SD总线加上一个自旋锁,规定同时只能有一个线程在SD總线上操作
版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。