赞助论坛
  • 32245阅读
  • 0回复

从海尔机boot的一点小秘密,到hi2023(e)与51单片机指令分析。 [复制链接]

楼层直达

发帖
58
精华
11
金币
882
威望
105
贡献
113
好评
41
注册
2010-01-05
楼主    quicktime 发表于: 2010-03-20 20:31:45 
[quote][b]这是3/20的标题,新增较多内容,改之[/b]
把海尔机改称8051单片机学习机及海尔机boot的一点小秘密。
[/quote]

一直在猜海尔方案的刷机程序中boot2运行是什么意思。
俺猜测,鸡顶盒flash内有一段代码叫boot1, 开机后先运行boot1, 当发现有刷机程序时,刷机程序把boot2发送到鸡顶盒,然后加载boot2。最后进入刷机就绪状态,等待刷机程序发出指令,刷机或读bin。
万一flash中的boot1损坏,就无法加载boot2,完成刷机。这时短接bootloader针脚,从芯片内部的ROM启动boot1,完成加载boot2的任务。

找到免费的一个串口通信监控程序,AccessPort, 监控了一下abs_flash的刷机过程。部分证实了上述猜想。
刷机过程,果然抓到的boot2的代码,就是abs_flash的cmd\2023\boot2.bin。

假如这个boot2.bin是自己写的51指令代码,那么就能用这个方法让鸡顶盒运行自己的代码,变成8051单片机学习机,呵呵。当然又能力的高手们也许能做更多的事。
俺有点小期待,就是高手们移植一个俄罗斯方块进取..............

于是搞了一个自己的boot加载器,可以把自己的代码发送到鸡顶盒。程序及源代码见附件,C#写的。
[color=darkred]运行需要微软的.NET Framework 3.5,如不能运行,请到微软网站下载。[/color]
更绝妙的是,发现原版的boot2.bin头几个字节是发送数据到串口的代码。以汇编语言表示就是:

0000:   74 3B MOV   A,#3BH
0002:   C2 C1 CLR   C1H
0004:   F5 C1 MOV   0C1H,A
0006: 30 C1 FD JNB   C1H,$

把其中的MOV A, #3BH改称你想要的数据,就可以发送到串口。呵呵,连输出的方法都有了。

自己写了一个boot2.bin, 可以输出四个字符0。[color=darkred]见下图.[/color]

[quote][b]这是3/20的内容,可跳过看3/22的更新[/b]
另外写了一个,原本想把鸡顶盒运行时的代码空间的0000~FFFF的数据导出,这样可以得到运行时的内存映像。
不过总取不到64K数据,差几个字节。而且取出的数据中居然不包含myboot23.bin的代码。

俺对单片机开发一窍不通,现学了几条51指令,才疏学浅,望高手指教。
下面是这个bin的源代码:

  MOV   DPTR, #0000H
LOOP:
  MOV   A, #00H
  MOVC   A,@A+DPTR

  CLR   0C1H
  MOV   0C1H,A
WAIT:  
  JNB   0C1H,WAIT

  INC DPTR;
  MOV A, DPH
  ORL A, DPL
  JNZ LOOP
 
ENDPROG:  
  SJMP ENDPROG
END
[/quote]

[color=darkred]========以下3/22的更新===========[/color]
感谢byzx提供的hi2023指令的分析信息。对代码进行了修改,成功抓到运行时的代码空间的内存映像。
因目前找不到合适的hi2023编译器,所以使用标准51编译器编译后,再手工修改。hi2023的DPTR是24位的,所以必须手工增加一个字节。

证实了3个问题:
1. hi2023确实对地址指针作了扩充,把16位地址指针扩充到24位。
2. Boot2.bin被加载到0F0000。
3. boot同时把flash中的代码加载入代码空间。但是APP区的代码在boot1运行时的加载还没有解压。估计要等到starter运行后才会解压。

附上最新的myboot23.bin。使用方法可参考HaierBoot2Loader使用说明。可以抓取系统开机boot后的代码映像,其中0F0000处是myboot23.bin的代码数据。全部抓完需要比较长间。

[color=darkred]=======以下是2010/3/23更新======[/color]
修正3/22日的一个错误,boot2.bin其实是被加载到0F0000,看花眼,以致走了许多弯路。
另3/22提供的myboot23.bin的源代码,改成附件方式下载。

[color=red][b]3/23对Hi2023的24位寻址指令进行了分析和验证![/b][/color]

1. 24位的DPTR寄存器
hi2023(e)的DPTR寄存器是24位的,标准51的指令:
[color=blue]
MOV DPTR, #XXXX
对应的16进制的指令为:
90 XX XX
[/color]
被扩展成:
[color=blue]
MOV DPTR, #XXXXXX
对应的16进制的指令为:
90 XX XX XX
[/color]
不存在byzx大虾发布的海尔国芯反汇编V1.5测试版,中出现的90 0F特殊指令。这个规则通过MOVC A,@A+DPTR指令,取内存数据验证。

2. 24位地址编码的LJMP和LCALL
hi2023的代码空间寻址能力也是24位的。以LJMP为例,
标准51的指令:
[color=blue]
LJMP XXXX
对应的16进制的指令为:
02 XX XX
[/color]
被扩展成:
[color=blue]
LJMP XXXXXX
对应的16进制的指令为:
02 XX XX XX
[/color]
不存在byzx大虾发布的海尔国芯反汇编V1.5测试版,中出现的02 0F特殊指令。这个规则通过附件jumptest.bin验证。

3. 19位地址编码的AJMP和ACALL
标准51指令AJMP和ACALL为2字节指令,hi2023(e)扩展成3字节。AJMP的指令格式说起来比较繁琐,请参考byzx大侠提供的51标准指令。

这个规则通过附件jumptest.bin验证。

jumptest.bin是先通过标准51编译器编译后,再手工修改的16进制机器码。通过HaierBoot2Loader加载运行。经过多次跳转后,按期望输出"OKOK"。测试通过。

4. 考虑到海尔鸡顶盒bin的头3个字节
[color=blue]
02 10 00
[/color]
译成LJMP 100H比较合理。推测hi2023(e)中有特殊状态控制位,指示cpu使用16位地址还是使用24位地址。由cpu加电后初始化,设置该位。

5. 目前DPTR的最高八位放在哪个寄存器,还不太清楚。不过已经解决了关键的指针问题,及程序入口问题。
等byzx大侠完整反编译工具,hi2023的指令集分析的理论和工具准备可以告一段落了。

这几天折腾鸡顶盒占用不少业余时间,已向家人承诺,早睡早起身体好!呵呵....

byzx大侠的[url=http://bbs.lcdhome.net/read-htm-tid-42323.html]海尔/国芯反汇编程序1.5测试版[/url]
本帖最近评分记录: 11 条评分