2.10、uboot源码分析6-uboot的硬件驱动部分(2021-5-10)


2.10.1、uboot与linux驱动

2.10.1.1、uboot本身是裸机程序

在这里插入图片描述

2.10.1.2、uboot的虚拟地址对硬件操作的影响

在这里插入图片描述

2.10.1.3、uboot借用(移植)了linux驱动

在这里插入图片描述


2.10.2、iNand/SD驱动解析1

2.10.2.1、从start_armboot开始

在这里插入图片描述

//Board.c
#if defined(CONFIG_GENERIC_MMC)
		puts ("SD/MMC:  ");            //打印:SD/MMC:  
		mmc_exist = mmc_initialize(gd->bd);
		if (mmc_exist != 0)
		{
			puts ("0 MB\n");
		}
	#endif

2.10.2.2、mmc_initialize

在这里插入图片描述

//Mmc.c
//mmc_devices为一个结构体,其里面存放前一个结点指针和后一个结点指针
static struct list_head mmc_devices;     //链表全局变量

//List.h
//定义一个链表结点指针结构体,其里面为结点指针,指向自己的前一个结点和后一个结点
struct list_head {
	struct list_head *next, *prev;
};

//List.h
//定义一个链表结点指针,其前后指针均指向自己
#define INIT_LIST_HEAD(ptr) do { \
	(ptr)->next = (ptr); (ptr)->prev = (ptr); \
} while (0)

//Mmc.c
/*
 * CPU and board-specific MMC initializations.  Aliased function
 * signals caller to move on
 * 特定于CPU和主板的MMC初始化。别名函数向调用者发出继续前进的信号
 */
static int __def_mmc_init(bd_t *bis)
{
	return -1;
}
//alias:别名
//用__attribute__的方式给__def_mmc_init()函数起了一个别名,叫board_mmc_init()
int cpu_mmc_init(bd_t *bis) __attribute__((weak, alias("__def_mmc_init")));
int board_mmc_init(bd_t *bis) __attribute__((weak, alias("__def_mmc_init")));

//Mmc.c
//初始化开发板上MMC系统。
//SoC里的MMC控制器初始化(MMC系统时钟的初始化、SFR初始化)
//SoC里MMC相关的GPIO的初始化、SD卡/iNand芯片的初始化。
int mmc_initialize(bd_t *bis)      //MMC初始化
{
	struct mmc *mmc;                 //定义了一个结构体指针,其指向了一个结构体
	int err;                         //错误返回值

	//mmc_devices链表全局变量,用来记录系统中所有已经注册的SD/iNand设备。
	INIT_LIST_HEAD(&mmc_devices);      //初始化链表,初始化全局变量
	cur_dev_num = 0;                   //定义的静态全局变量,用来标识指向了哪一个设备;指向第0个设备

	if (board_mmc_init(bis) < 0)       //调用board_mmc_init()函数,肯定成立
		cpu_mmc_init(bis);             //调用cpu_mmc_init()函数

#if defined(DEBUG_S3C_HSMMC)
	print_mmc_devices(',');
#endif

#ifdef CONFIG_CHECK_X210CV3
	mmc = find_mmc_device(1);//lqm
#else
	mmc = find_mmc_device(0);
#endif
	if (mmc) {
		err = mmc_init(mmc);
		if (err)
			err = mmc_init(mmc);
		if (err) {
			printf("Card init fail!\n");
			return err;
		}
	}
	printf("%ldMB\n", (mmc->capacity/(1024*1024/(1<<9))));
	return 0;
}

2.10.2.3、cpu_mmc_init

在这里插入图片描述

/*
 * Initializes on-chip MMC controllers.
 * to override, implement board_mmc_init()
 * 初始化片内MMC控制器
 * 若要覆盖,请实现board_mmc_init()
 */
int cpu_mmc_init(bd_t *bis)
{
#ifdef CONFIG_S3C_HSMMC                //CONFIG_S3C_HSMMC定义
	setup_hsmmc_clock();               //初始化SoC中MMC控制器中的时钟部分的。
	setup_hsmmc_cfg_gpio();           //配置SoC中MMC控制器相关的GPIO的。
	return smdk_s3c_hsmmc_init();     //调用
#else
	return 0;
#endif
}

在这里插入图片描述

void setup_hsmmc_clock(void)
{
	u32 tmp;
	u32 clock;
	u32 i;

	/* MMC0 clock src = SCLKMPLL */
	tmp = CLK_SRC4_REG & ~(0x0000000f);
	CLK_SRC4_REG = tmp | 0x00000006;

	/* MMC0 clock div */
	tmp = CLK_DIV4_REG & ~(0x0000000f);
	clock = get_MPLL_CLK()/1000000;
	for(i=0; i<0xf; i++)               //自动计算
	{
		if((clock / (i+1)) <= 50) {   //不能超过50M
			CLK_DIV4_REG = tmp | i<<0;
			break;
		}
	}

在这里插入图片描述








评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值