admin管理员组

文章数量:1026989

80C51和ARM的Intel hex解析

 

更改说明

版本号

日期

作者

描述

1.0

2020-11-20

靴子丢了的猫

第一个版本

1.1

2020-11-21

靴子丢了的猫

添加ARM汇编和intel hex对应关系

 

  1. 创建开发环境得到汇编代码
    1. 创建开发环境

由于新换了电脑所以需要装C51的开发环境,下了几个版本都是ARM的开发环境,不过最终还是找到了C51版本的keil,版本信息如下:

然后创建了一个工程,添加了测试代码以后测试如下:

    1. 编译得到汇编

编译以后选择模拟调试:

 

点击开始调试:

 

然后得到汇编代码如下:

    1. 整理汇编文件和Intel hex
      1. 汇编文件整理

上面已经展示的汇编由于参杂了注释需要进一步整理分析:

需要参考工程请下载: 资源文件方便您查看

 

详情请看aa工程中的asm.asm

// 0x0000地址存放跳转指令跳转到080F

C:0x0000    02080F   LJMP     STARTUP1(C:080F)  

 

   6: int main(){

   7:         int a=0;

C:0x0800    E4       CLR      A

C:0x0801    F508     MOV      0x08,A

C:0x0803    F509     MOV      0x09,A

     8:         delay(100);

C:0x0805    7F64     MOV      R7,#0x64

C:0x0807    FE       MOV      R6,A

C:0x0808    12081B   LCALL    delay(C:081B)

     9:         return 0;

    10:         

C:0x080B    E4       CLR      A

C:0x080C    FE       MOV      R6,A

C:0x080D    FF       MOV      R7,A

    11: }

C:0x080E    22       RET     

   133:                 MOV     R0,#IDATALEN - 1

 

*************************************************************

STARTUP.A51的内容

 

C:0x080F    787F     MOV      R0,#0x7F

   134:                 CLR     A

C:0x0811    E4       CLR      A

   135: IDATALOOP:      MOV     @R0,A

C:0x0812    F6       MOV      @R0,A

   136:                 DJNZ    R0,IDATALOOP

C:0x0813    D8FD     DJNZ     R0,IDATALOOP(C:0812)

C:0x0815    758109   MOV      SP(0x81),#0x09

   196:                 LJMP    ?C_START

C:0x0818    020800   LJMP     main(C:0800)

*************************************************************

 

     3: void delay(int t){

     4:         while(t--);

C:0x081B    EF       MOV      A,R7

C:0x081C    1F       DEC      R7

C:0x081D    AC06     MOV      R4,0x06

C:0x081F    7001     JNZ      C:0822

C:0x0821    1E       DEC      R6

C:0x0822    4C       ORL      A,R4

C:0x0823    70F6     JNZ      delay(C:081B)

     5: }

C:0x0825    22       RET     

C:0x0826    00       NOP     

      1. Intel hex

然后是Intel hex的内容:参考aa工程下的aa.hex

:0300000002080FE4

:0C080F00787FE4F6D8FD7581090208002E

:0B081B00EF1FAC0670011E4C70F622AF

:0E080000E4F508F5097F64FE12081BE4FEFF14

:01080E0022C7

:00000001FF

  1. 解析intel hex与汇编对应
    1. Intel hex格式

由于以前只是稍稍看了一下hex的文件结构,没有深究参考这篇文章:

参考博客得到信息如下:

有一条intel hex语句如下(用我们上面的整理的语句吧)

:0300000002080FE4

得到了这两个文件以后需要确定的是如何解析intel hex并且让其与汇编对应。这也就是接下来要做的工作

:0300000002080FE4

这条语句可以拆分成如下的本部分:

   :                     03          0000           00       02080F         E4

起始标志    数据长度   地址        记录类型      数据          检验和

 

了解了这个以后需要明确的是这些数据分别对应了汇编中的什么东西,由于我是使用的notepad查看所以分离了数据以后首先观察到的就是02080F这个数据对应了LJMP     STARTUP1这样一条语句:

然后我将上面的那些语句前面的十六进制进行了整理

02080F 787F E4 F6 D8FD 758109 020800 E4 F508 F509 7F64 FE 12081B E4 FE FF  EF 1F AC06 7001 1E 4C 70F6 22

同时对intel hex进行了分割:

:03 0000 00 02080F E4

:0C 080F 00 787F E4 F6 D8FD 758109 020800 2E

:0B 081B 00 EF 1F AC06 7001 1E 4C 70F6 22 AF

:0E 0800 00 E4 F508 F509 7F64 FE 12081B E4 FE FF 14

:01 080E 00 22 C7

:00 0000 01 FF

然后就发现数据段的部分和我分离出的十六进制顺序是一致整理后展示如下:

Intel hex地址就对应了在单片机ROM中的储存位置,后面的数据段就分别对应了不同的指令和数据,由于在ROM中储存的位置不一样,所以上面Intel hex就在不同的行,连续的指令数据是在统一行的。

以上就找到了intel hex和实际机器指令的关系的关系,那么下一步就需要找到指令和汇编代码之间的关系。

 

    1. 机器码与对应的汇编

我对比了比较长的时间去对比MOV汇编指令看看有没有对应关系:

结果发现这些MOV指令不是同一条照我的理解每一条MOV指令应该是这样的结构:

 

MOV指令(八位根据数据不同而不同)+数据…… 

 

然后查阅相关资料得到如下的博客内容:指令集参考博文

我对比了下面这样一条指令和博客所给出的结果如下:

发现我猜想的确实是如此,MOV指令不同的情况下机器码不一样,所以找起来没有头绪,不过有这样一张表对应着就刚好能够找出所有的对应的规则。

至此intel hex和汇编的对应关系就建立起来了,如果想要整理出整套的编译规则那么顺应着上面介绍的内容就可以了。

  1. ARM汇编和intel hex

依照着上述的步骤在keil for arm的环境下创建工程展示如下:

然后得到汇编代码展示如下:

 

编译产生的hex文件如下图所示:

 

由于我测试的编译工程较大找对应关系还是同找51汇编和产生的额intel hex关系一样,由于我只是复制出部分的汇编代码所以需要找到地址对应的代码部分最终找到一部分对应的:

    红色标记的部分是地址,蓝色标记的部分intel hex的数据段对应了汇编部分,你会看到高八位和低八位是反着的这就是大小字节序的问题,这个对应关系和51汇编对应的方式是一样的,最后当然是机器码和汇编的对应部分了,当然这部分比较复杂,如果您想了解具体的ARM机器指令请参考图书:《ARM体系结构与编程》杜春雷。

 

版权声明:博客内提及的内容仅作为学习使用。本文刊载的所有内容为本人自主创作,访问者可将本文提供的内容或服务用于个人学习、研究或以及其他非商业性或非盈利性用途。如需作商业用途需要请求作者意见,同时应遵守著作权法及其他相关法律的规定,不得侵犯本文及作者的合法权利。

80C51和ARM的Intel hex解析

 

更改说明

版本号

日期

作者

描述

1.0

2020-11-20

靴子丢了的猫

第一个版本

1.1

2020-11-21

靴子丢了的猫

添加ARM汇编和intel hex对应关系

 

  1. 创建开发环境得到汇编代码
    1. 创建开发环境

由于新换了电脑所以需要装C51的开发环境,下了几个版本都是ARM的开发环境,不过最终还是找到了C51版本的keil,版本信息如下:

然后创建了一个工程,添加了测试代码以后测试如下:

    1. 编译得到汇编

编译以后选择模拟调试:

 

点击开始调试:

 

然后得到汇编代码如下:

    1. 整理汇编文件和Intel hex
      1. 汇编文件整理

上面已经展示的汇编由于参杂了注释需要进一步整理分析:

需要参考工程请下载: 资源文件方便您查看

 

详情请看aa工程中的asm.asm

// 0x0000地址存放跳转指令跳转到080F

C:0x0000    02080F   LJMP     STARTUP1(C:080F)  

 

   6: int main(){

   7:         int a=0;

C:0x0800    E4       CLR      A

C:0x0801    F508     MOV      0x08,A

C:0x0803    F509     MOV      0x09,A

     8:         delay(100);

C:0x0805    7F64     MOV      R7,#0x64

C:0x0807    FE       MOV      R6,A

C:0x0808    12081B   LCALL    delay(C:081B)

     9:         return 0;

    10:         

C:0x080B    E4       CLR      A

C:0x080C    FE       MOV      R6,A

C:0x080D    FF       MOV      R7,A

    11: }

C:0x080E    22       RET     

   133:                 MOV     R0,#IDATALEN - 1

 

*************************************************************

STARTUP.A51的内容

 

C:0x080F    787F     MOV      R0,#0x7F

   134:                 CLR     A

C:0x0811    E4       CLR      A

   135: IDATALOOP:      MOV     @R0,A

C:0x0812    F6       MOV      @R0,A

   136:                 DJNZ    R0,IDATALOOP

C:0x0813    D8FD     DJNZ     R0,IDATALOOP(C:0812)

C:0x0815    758109   MOV      SP(0x81),#0x09

   196:                 LJMP    ?C_START

C:0x0818    020800   LJMP     main(C:0800)

*************************************************************

 

     3: void delay(int t){

     4:         while(t--);

C:0x081B    EF       MOV      A,R7

C:0x081C    1F       DEC      R7

C:0x081D    AC06     MOV      R4,0x06

C:0x081F    7001     JNZ      C:0822

C:0x0821    1E       DEC      R6

C:0x0822    4C       ORL      A,R4

C:0x0823    70F6     JNZ      delay(C:081B)

     5: }

C:0x0825    22       RET     

C:0x0826    00       NOP     

      1. Intel hex

然后是Intel hex的内容:参考aa工程下的aa.hex

:0300000002080FE4

:0C080F00787FE4F6D8FD7581090208002E

:0B081B00EF1FAC0670011E4C70F622AF

:0E080000E4F508F5097F64FE12081BE4FEFF14

:01080E0022C7

:00000001FF

  1. 解析intel hex与汇编对应
    1. Intel hex格式

由于以前只是稍稍看了一下hex的文件结构,没有深究参考这篇文章:

参考博客得到信息如下:

有一条intel hex语句如下(用我们上面的整理的语句吧)

:0300000002080FE4

得到了这两个文件以后需要确定的是如何解析intel hex并且让其与汇编对应。这也就是接下来要做的工作

:0300000002080FE4

这条语句可以拆分成如下的本部分:

   :                     03          0000           00       02080F         E4

起始标志    数据长度   地址        记录类型      数据          检验和

 

了解了这个以后需要明确的是这些数据分别对应了汇编中的什么东西,由于我是使用的notepad查看所以分离了数据以后首先观察到的就是02080F这个数据对应了LJMP     STARTUP1这样一条语句:

然后我将上面的那些语句前面的十六进制进行了整理

02080F 787F E4 F6 D8FD 758109 020800 E4 F508 F509 7F64 FE 12081B E4 FE FF  EF 1F AC06 7001 1E 4C 70F6 22

同时对intel hex进行了分割:

:03 0000 00 02080F E4

:0C 080F 00 787F E4 F6 D8FD 758109 020800 2E

:0B 081B 00 EF 1F AC06 7001 1E 4C 70F6 22 AF

:0E 0800 00 E4 F508 F509 7F64 FE 12081B E4 FE FF 14

:01 080E 00 22 C7

:00 0000 01 FF

然后就发现数据段的部分和我分离出的十六进制顺序是一致整理后展示如下:

Intel hex地址就对应了在单片机ROM中的储存位置,后面的数据段就分别对应了不同的指令和数据,由于在ROM中储存的位置不一样,所以上面Intel hex就在不同的行,连续的指令数据是在统一行的。

以上就找到了intel hex和实际机器指令的关系的关系,那么下一步就需要找到指令和汇编代码之间的关系。

 

    1. 机器码与对应的汇编

我对比了比较长的时间去对比MOV汇编指令看看有没有对应关系:

结果发现这些MOV指令不是同一条照我的理解每一条MOV指令应该是这样的结构:

 

MOV指令(八位根据数据不同而不同)+数据…… 

 

然后查阅相关资料得到如下的博客内容:指令集参考博文

我对比了下面这样一条指令和博客所给出的结果如下:

发现我猜想的确实是如此,MOV指令不同的情况下机器码不一样,所以找起来没有头绪,不过有这样一张表对应着就刚好能够找出所有的对应的规则。

至此intel hex和汇编的对应关系就建立起来了,如果想要整理出整套的编译规则那么顺应着上面介绍的内容就可以了。

  1. ARM汇编和intel hex

依照着上述的步骤在keil for arm的环境下创建工程展示如下:

然后得到汇编代码展示如下:

 

编译产生的hex文件如下图所示:

 

由于我测试的编译工程较大找对应关系还是同找51汇编和产生的额intel hex关系一样,由于我只是复制出部分的汇编代码所以需要找到地址对应的代码部分最终找到一部分对应的:

    红色标记的部分是地址,蓝色标记的部分intel hex的数据段对应了汇编部分,你会看到高八位和低八位是反着的这就是大小字节序的问题,这个对应关系和51汇编对应的方式是一样的,最后当然是机器码和汇编的对应部分了,当然这部分比较复杂,如果您想了解具体的ARM机器指令请参考图书:《ARM体系结构与编程》杜春雷。

 

版权声明:博客内提及的内容仅作为学习使用。本文刊载的所有内容为本人自主创作,访问者可将本文提供的内容或服务用于个人学习、研究或以及其他非商业性或非盈利性用途。如需作商业用途需要请求作者意见,同时应遵守著作权法及其他相关法律的规定,不得侵犯本文及作者的合法权利。

本文标签: 80C51和ARM的Intel hex解析