microblaze 串口学习·2

举报
心殁花满楼 发表于 2022/06/30 13:51:00 2022/06/30
【摘要】 microblaze 串口学习·2 串口初始化函数1int XUartLite_Initialize(XUartLite *InstancePtr, u16 DeviceId)int XUartLite_Initialize(XUartLite *InstancePtr, u16 DeviceId){ XUartLite_Config *ConfigPtr; Xil_AssertNonvo...

microblaze 串口学习·2

串口初始化函数1int XUartLite_Initialize(XUartLite *InstancePtr, u16 DeviceId)

int XUartLite_Initialize(XUartLite *InstancePtr, u16 DeviceId)
{
	XUartLite_Config *ConfigPtr;
	Xil_AssertNonvoid(InstancePtr != NULL);
	ConfigPtr = XUartLite_LookupConfig(DeviceId);

	if (ConfigPtr == (XUartLite_Config *)NULL) {
		return XST_DEVICE_NOT_FOUND;
	}
	return XUartLite_CfgInitialize(InstancePtr, ConfigPtr,
					ConfigPtr->RegBaseAddr);
}

##1 串口初始化 XUartLite_Config *ConfigPtr;

typedef struct {
	u16 DeviceId;		/**< Unique ID  of device */
	UINTPTR RegBaseAddr;	/**< Register base address */
	u32 BaudRate;		/**< Fixed baud rate */
	u8  UseParity;		/**< Parity generator enabled when TRUE */
	u8  ParityOdd;		/**< Parity generated is odd when TRUE, even
					when FALSE */
	u8  DataBits;		/**< Fixed data bits */
} XUartLite_Config;

ConfigPtr是一个指向结构体的指针,这个结构体中包含了串口配置的一些参数,需要注意的是。MDM串口的一些参数无法在寄存器级别进行修改。因此需要在硬件工程例化的时候。进行设置

2 Xil_AssertNonvoid(InstancePtr != NULL);

xlinx的断言函数,用于检测参数输入的合法性,猜测是重定向了assert的输出,这个以后再研究。不影响整体的逻辑实现。

3 ConfigPtr = XUartLite_LookupConfig(DeviceId);

XUartLite_Config *XUartLite_LookupConfig(u16 DeviceId)
{
	XUartLite_Config *CfgPtr = NULL;
	u32 Index;

	for (Index=0; Index < XPAR_XUARTLITE_NUM_INSTANCES; Index++) {
		if (XUartLite_ConfigTable[Index].DeviceId == DeviceId) {
			CfgPtr = &XUartLite_ConfigTable[Index];
			break;
		}
	}

	return CfgPtr;
}

控制向量在这个函数中被赋值。
首先初始化空指针,然后检查外设ID,然后通过IC查询,将XUartLite_ConfigTable中的参数传递给XUartLite_Configptr。XUartLite_ConfigTable的结构和CfgPtr的结构完全一致。XUartLite_ConfigTable是由vitis自动生成的参数配置文件,XUartLite_ConfigTable本质是一个结构体常量,内部全都是用宏来定义参数,具体的参数被保存在xparameter中。
如果输入的DeviceID不合法,那么函数就会返回空指针,导致配置失败。

4 return XUartLite_CfgInitialize(InstancePtr, ConfigPtr,ConfigPtr->RegBaseAddr);

int XUartLite_CfgInitialize(XUartLite *InstancePtr, XUartLite_Config *Config,
				UINTPTR EffectiveAddr)
{
	(void) Config;
	/*
	 * Assert validates the input arguments
	 */
	Xil_AssertNonvoid(InstancePtr != NULL);

	/*
	 * Set some default values, including setting the callback
	 * handlers to stubs.
	 */
	InstancePtr->SendBuffer.NextBytePtr = NULL;
	InstancePtr->SendBuffer.RemainingBytes = 0;
	InstancePtr->SendBuffer.RequestedBytes = 0;

	InstancePtr->ReceiveBuffer.NextBytePtr = NULL;
	InstancePtr->ReceiveBuffer.RemainingBytes = 0;
	InstancePtr->ReceiveBuffer.RequestedBytes = 0;

	InstancePtr->IsReady = XIL_COMPONENT_IS_READY;

#if (XPAR_XUARTLITE_USE_DCR_BRIDGE != 0)
	InstancePtr->RegBaseAddress = ((EffectiveAddr >> 2)) & 0xFFF;
#else
	InstancePtr->RegBaseAddress = EffectiveAddr;
#endif

	InstancePtr->RecvHandler = StubHandler;
	InstancePtr->SendHandler = StubHandler;

	/* Write to the control register to disable the interrupts, don't
	 * reset the FIFOs are the user may want the data that's present
	 */
	XUartLite_WriteReg(InstancePtr->RegBaseAddress,
				XUL_CONTROL_REG_OFFSET, 0);

	/*
	 * Clear the statistics for this driver
	 */
	XUartLite_ClearStats(InstancePtr);

	return XST_SUCCESS;
}

传入的参数是外设指针,外设配置参数指针,外设寄存器起始地址。首先将传入的Config结构体指针强制转换成无类型(这里没理解上去,为什么要这么转换?)

对外设结构体中的一些变量赋初值
对于 XPAR_XUARTLITE_USE_DCR_BRIDGE 这个的理解我找到了Xlinx的一篇文档

图片.png

On-Chip Periphaeral Bus (OPB)

**device control register (DCR) **

可以看到对于外设寄存器的访问有很多不同的方式,文章中就提到了一种CPU-OPB的桥路。
这个地方先挖个坑,以后再研究实现细节和区别。

5 XUartLite_WriteReg(BaseAddress, RegOffset, Data)

#define XUartLite_WriteReg(BaseAddress, RegOffset, Data)
XUartLite_Out32((BaseAddress) + (RegOffset), (u32)(Data))
然后按照配置,写入地址+地址偏移+数据

然后清空外设的Stats reg标志,至此初始化完成。

【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。