数莓派Simple Bootloader设计相关知识点

目的:

学习数莓派裸机编程需要不断的插拔sd卡,即不方便也加快了磨损,所以设计这个简单的bootloader方便调试。

简介:

bootloader包括置于sd卡中的镜像和电脑端的下载软件,通过串口可以将新的测试kernel镜像下载到内存中。(minicom功能暂时没有)有下载hex格式和binary方式。

设计细节:

思路是将bootloader部分放到2M地址处,重启数莓派后进入bootloader等待,上位机发送数据,bootloader接到后放到指定的内存地址(此处是0)。img文件直接从0地址存,hex可以根据其指定的地址存。

 hex方式

hex格式:以行为单位,每行以冒号开头,内容全部为16进制码(以ASCII码形式显示)。

每一行由六个部分组成:

 :数据个数 数据地址 类型 数据 校验和

每个域长度:

    1 2 1 n 1,单位byte,实际是两个ascii表示一个字节,需要转换一下

类型域:

00数 据 记录(Data Record)
01文件结 束 记录(End of FileRecord)
02扩展段地址 记录(ExtendedSegment Address Record)
03开始段地址 记录(Start Segment Address Record)
04扩展 线 性地址 记录(Extended Linear Address Record)
05

开始线性地址 记录(Extended Segment Address Record)

数据域的数据是小端存储的。文件的结尾一般都是:00000001FF。

数据包格式:start+len+~len+type+seq+res+res+res+...payload...+end+checksum

上位机设计思路:判断输入参数;打开文件和串口;解析hex文件;打包地址和数据发送;接收返回包;发送执行命令。

下位机设计思路:等待start;接收数据;发送返回包;存储数据到内存;跳转运行

img方式:

img格式与bin格式都是binary格式,是可以直接在内存运行的。

设计上有点不同,这种方式对操作没有限制,先运行脚本或者先重启数莓派都可以。

上位机发送起始数据头(start),等待下位机的响应,如果接不到会隔一段时间再发,如果接到了就开始发送数据。代码参考:

https://github.com/gcrisis/raspberry-pi-os/tree/master/exercises/lesson01/2/gcrisis/uart-boot

使用下面的代码判断是否接到了指定的头信息,h是头字符串,hlen是字符串长度。

void check_head(char *h,int hlen)
{
    uint8_t index=0;
    while(1)
	{
		char c=uart_recv();
		if(c==h[index])
		{
			index++;
		}
		else
		{
			if(c==h[0])
				index=1;
			else
				index=0;
		}
		if(index==hlen)
			break;
	}
	uart_send_string("OK");
}

遇到的问题:

在发送了头之后也收到了返回,但是之后下位机接到的数据错误,原因是串口采用nonblock模式,发送了数据后下位机的返回数据还没发上来,所以上位机的read没有读到就退出了,这段时间有一个延时,这时下位机的数据发上来了,存到了缓冲区,下位机准备接收新信息,但是第二次循环的时候又发了一次head,所以下位机接到了错误的信息,上位机这次才接到下位机发上来的响应数据,跳出循环。

针对这个问题,要不就是发送完等待一会或者轮寻接收,超时后再重发;要不就发送每段数据都设置对应的同步信息,即构造数据包。

注意:

1、Linux的printf必须加'\n'才能显示出来,否则就在缓冲中显示不到终端;

2、c语言的局部变量初值是不确定的,所以要显示初始化;

3、

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值