当前位置: 首页 > ops >正文

openjdk底层汇编指令调用(一)——汇编指令及指令编码基础

汇编指令

计算机在执行过程时只识别代表0或者1的电信号。因此为了让计算机能够执行则须向计算机输入一系列01构成的指令。
例如在x64平台下,0x53,二进制为01010011,表示将rbx寄存器中的值压栈。
但是,对于程序员而言,如果每个操作都用二进制数来表示(早期的程序员确实是这样)则会带来2个问题。

  1. 容易出错
  2. 不方便记忆
    为了避免上述的错误,各厂商定义了一系列由英文关键字用来表示二进制指令,这些关键字构成的指令称为汇编指令,或者汇编语言。
    例如,上述0x53在x64下的汇编指令为
push %rbx

如果将上述汇编指令写入汇编文件(.s),经过编译器(gcc)编译后,形成了可被执行的二进制文件,该文件中的对应位置将push %rbx转换为0x53
此时,如果CPU中执行上述指令时,则会将rbx的值压栈。

总而言之,push %rbx一定会转为唯一的二进制指令让CPU执行。

指令编码

上述的汇编指令由英文构成,其中开始部分的关键字称为助记符(mnemonic),后面的被操作对象称为操作数。编译器将根据助记符和操作数按照一定的规则将其翻译成唯一的二进制数供CPU执行。
每个厂商由于其指令集的区别(CISC:复杂指令集;RISC:精简指令集)而有各自的编码规则。
根据x64的手册,其push %rbx的编码规则如下
在这里插入图片描述
push代表0x50
reg64由%rbx代替,而rbx寄存器中x64架构下的编码为0x3,因此,将二者相加后最终的编码结果为0x53

汇编转换规则

根据上述描述可发现,汇编指令转二进制指令根据的是助记符和操作码的值进行编制。首先需确定助记符的值,该值在二进制指令中被称为操作码,后面紧跟的值是操作数。每个厂商编制了各自的编码规则。
例如,假设一个寄存器加法指令。将一个寄存器(源寄存器)内的值与另一个寄存器(源寄存器)相加,将结果放入寄存器(目的寄存器)中。我们看看在x64指令下是如何编码的。
在这里插入图片描述
假设加法指令如下

add %rbx, %rax

则翻译的机器码为

48 01 D8

其翻译规则如下

Byte(s)Meaning
48REX prefix: 64-bit operand size (REX.W = 1)|
01Opcode: ADD r/m64, r64 (adds second register to the first)
D8ModR/M byte: specifies registers → rbx to rax

关于x86的编码规则,可参见我另一篇文章

AArch64ARM v8架构。其指令属于RISC指令集。嵌入式系统,苹果M系列芯片以及国产飞腾,鲲鹏等服务器芯片等采用该架构的指令集。如果是在AArch64下实现上述加法, 其写法如下

add x0, x1, x2

由于AArch64指令与x86不是同一指令集,因此寄存器定义也不一致,只是厂商在定义加法指令时都采用了add助记符。上述指令的意思是将x1寄存器内的值加上x2寄存器内的值之后的结果放入x0寄存器。

AArch64针对上述指令的编码如下
在这里插入图片描述
由于AArch64的编码规则较x86简单,这里以AArch64为例进行说明。
根据手册上的描述可以看出,对于64位机器,31位是1,Rm是x2,Rn是x1, Rd是x0的编码。即2,1和0,其他位置按照规范不变,option和imm3规定了其他的行为,这里是单纯的寄存器赋值,按照手册全部为0

因此机器码为

#二进制
10001011000 00010 000000 00001 00000#十六进制
0x8B020020
#小端编码需要反转
0x2000028B
http://www.xdnf.cn/news/5292.html

相关文章:

  • 通过 Azure DevOps 探索 Helm 和 Azure AKS
  • Spark 中RDD、Job,stage,task的关系
  • ActiveMQ 生产环境问题排查与调优指南(一)
  • 编程日志5.3
  • 智能语音助手的未来:从交互到融合
  • 实战项目3(04)
  • 画立方体软件开发笔记 js-pytorch xlsx 导出 excel pnpm安装
  • uni-app学习笔记(二)--vue页面代码的构成和新建页面
  • Pandas学习笔记(四)
  • 嵌入式硬件篇---UART
  • 外网访问内网海康威视监控视频的方案:WebRTC + Coturn 搭建
  • Python OpenCV性能优化与部署实战指南
  • python 实现文件批量重命名
  • “frame stacking”---帮助强化学习稳定提升和收敛技巧
  • Nipype 简单使用教程
  • 5 从众效应
  • Spring Boot 集成 Flink CDC 实现 MySQL 到 Kafka 实时同步
  • RabbitMQ--进阶篇
  • React+Springboot项目部署ESC服务器
  • 三维空间中的组织行为映射:MATLAB 数据插值可视化技术
  • 【网络】:传输层协议 —— UDP、TCP协议
  • 兔子队列?RabbitMQ详解(1)
  • 数字化转型-4A架构之技术架构
  • Mac下Robotframework + Python3环境搭建
  • 《智能网联汽车 自动驾驶系统设计运行条件》 GB/T 45312-2025——解读
  • 无锁秒杀系统设计:基于Java的高效实现
  • 补补表面粗糙度的相关知识(一)
  • leetcode 15. 三数之和
  • Java 原生异步编程与Spring 异步编程 详解
  • 比亚迪全栈自研生态的底层逻辑