C语言如何转换成计算机底层的二进制语言(MIPS)

文章开头我只想问一个问题:写了很多代码,你不好奇代码在计算机底层是什么样的吗?

下面将一步一步探索这个过程。首先,大家要有个初步的认识,一次从左到右进行编译汇编。 

高级语言(C语言) 

int add(int a,int b){  
    int c;   
    c = a + b; 
    return c;

}

-->编译

汇编语言

 add: 
    add   $a2,$a0,$a1  //c=a+b  
    add $v0,$a2,$zero   
    return c; 

-->汇编

二进制机器语言

00000000100001010011000000100000   // add   $a2,$a0,$a1
00000000110000000001000000100000  // add $v0,$a2,$zero       
00000011111000000000000000001000   //  return c; 

 

关于 $a2,$ra等寄存器,大家可以看看这篇博主的文章总结 MIPS 通用寄存器 。

首先大家要了解计算机的一个概念--过程意思是根据提供的参数执行一定任务的存储的子程序。说白了,就是上述C语言add函数里面的逻辑在CPU执行的过程。MIPS在为过程调用分配32个寄存器是遵循以下约定:

  • $a0~$a3:用于传递参数的4个参数寄存器。如上述的 $a0 即为 a,$a1即为b,由于参数寄存器还足够,因此 $a2即为c。
  • $v0~$v1:用于返回值的两个寄存器。
  • $ra:用于返回起始点的返回地址寄存器。如上述的 jr  $ra,意思是无条件跳转到寄存器所制定的地址。通俗地说,$ra是存储调用过程前的指令地址,执行完过程后,跳转到调用过程前的指令地址,继续做后续的计算。int a1 = add(1,2),执行完过程add的逻辑后, jr  $ra由回到a1继续计算。因为过程是可能由程序中多个点调用。即 int a2 = add(3,4);执行完 jr  $ra后回到a2继续计算。代码可以如下:

#include <stdio.h>

int add(int a,int b){
    int c;
    c = a + b;
    return c;
}

void main(){
    int a1 = add(1,2);
    int a2 = add(3,4);
}

综上所述,大家应该知道为啥$a0 即为 a,$a1即为b,$a2即为c了。接下来,我们继续,汇编语言怎么转换成二进制程序语言。想必大家都了解到,无论什么程序,最后在计算机底层都是 0 1 存在的。

接下来我们继续,相比大家都想知道汇编语言是怎么转成二进制机器语言。以下是MIPS指令各字段的命名以及含义。分为I型以及R型两类指令格式。

R型:用于寄存器,进行逻辑运算,如加减操作。

oprsrtrdshamtfunct
6位5位5位5位5位6位
  •  op:指令的基本操作,通常称为操作码(opcode)。
  • rs:第一个源操作数寄存器。
  • rt:第二个源操数寄存器。
  • rd:用于存放操作结果的目的寄存器。
  • shamt:位移量。
  • funct:功能码(function code)。

I型:用于立即数,即立即数与数据传输指令,如sw,lw等操作。

oprsrtconstant and adress
6位5位5位16位

 下面列出MPIS常用指令的值给到大家看下:

 指令

格式

op

rs

rt

rd

shumt

hinct

address

add

R

0

reg

reg

reg

0

32

n. a.

Iw (load word)

I

35

reg

n. a

n. an. an. aaddress

在上表中,“reg”代表寄存器的标号(从0 ~31), “address”表示16位地址, “na.” (not applicable)表示这个字段在该指令格式中不出现。注意,add指令在硬件是根据hmct字段的值来决定所进行的操作:add (32)或substract (34)

因此针对上面转换,可以得到:

    汇编语言                                             

 add: 

  add  $a2,$a0,$a1  //c=a+b                    
  add  $v0,$a2,$zero              
  jr      $ra        
}

op

rsrtrdaddress/shumthinct
0$a0$a1$a20add
0$v0$a2$zero0add 
0$ra000jr

 转换到对应数字后:

op

rs

rt

rd

address/shumt

hinct

0

4

5

6

0

32

6

0

2032
0310008

转换为二进制:

op

rs

rt

rd

address/shumt

hinct

000000

00100

00101

00110

00000

100000 

000000 

00110

00000

0001000000100000
00000011111000000000000000001000

到这里,相必大家都有点感觉了,实际一个程序的指令是涉及很多指令计算的。远远超过以上三条,因此大家需要去强化学习,加深对计算机的理解。 

参考文献:

[1]计算机组成与设计:硬件/软件接口(原书第5版).北京:机械工业出版社,2015.

  • 2
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值