汇编基础知识

这是1.4中探讨variable的scope和lifetime的代码,这里我将用它来做基础的汇编知识学习

global fun声明fun函数为全局符号,意味着它在其他文件中也可以被引用。

type fun, @function: 指定fun的类型为函数。

fun:: 函数fun的开始。

LFBO:: 标签,通常用于调试信息。

cfi_startproc: 调用帧信息的开始。

pushq %rbp: 将基指针rbp压入栈。

.cfi_def_cfa_offset 16: 定义了调用帧的偏移量为16字节。

.cfi_offset 6, -16: 将寄存器6(rbp)的偏移设置为-16字节。

movq %rsp, %rbp: 将堆栈指针rsp的值移动到基指针rbp。

.cfi_def_cfa_register 6: 定义了调用帧寄存器为rbp。

movl %edi, -20(%rbp): 将edi寄存器的值移动到rbp地址减去20字节的位置。

addl $1, -20(%rbp): 将1加到rbp-20处的值上。

movl -20(%rbp), %eax: 将rbp-20处的值移动到eax寄存器。

movl %eax, -4(%rbp): 将eax寄存器的值移动到rbp地址减去4字节的位置。

nop: 无操作指令,可能用于调试或对齐。

popq %rbp: 将栈顶部的值弹出到rbp寄存器。

.cfi_def_cfa: 调用帧信息的结束。

ret: 返回指令,从函数返回。(return)

.LFEO:: 标签,表示函数的结束。

.size fun, -fun: 定义fun函数的大小,从fun标签到.LFEO标签的距离。

main:: 函数main的开始。

.LFB1:: 标签,表示main函数的开始。

.cfi_startproc: 调用帧信息的开始。

pushq %rbp: 将基指针rbp压入堆栈。

.cfi_def_cfa_offset 16: 定义了调用帧的偏移量为16字节。

.cfi_offset 6, -16: 将寄存器6(rbp)的偏移设置为-16字节。

movq %rsp, %rbp: 将堆栈指针rsp的值移动到基指针rbp。

.cfi_def_cfa_register 6: 定义了调用帧寄存器为rbp。

subq $16, %rsp: 从堆栈指针rsp减去16字节,为局部变量分配空间。

movl $1, -4(%rbp): 将立即数1移动到rbp-4的位置。

movl -4(%rbp), %eax: 将rbp-4处的值移动到eax寄存器。

movl %eax, %edi: 将eax寄存器的值移动到edi寄存器。

call fun: 调用fun函数。

movl $0, %eax: 将立即数0移动到eax寄存器,通常用于表示函数返回值。

leave: 清理堆栈帧,将rbp的值移动到rsp,然后弹出rbp。

.cfi_def_cfa 7,8: 这行代码似乎不完整或有误,可能是.cfi_def_cfa_offset 8的缩写或错误。

ret: 返回指令,从函数返回。

.cfi_endproc: 调用帧信息的结束。

.LFE1:: 标签,表示main函数的结束。

.size main, .-main: 定义main函数的大小,从main标签到.LFE1标签的距离。

.ident "GCC: (Ubuntu 7.5.0-3ubuntu1~1ubuntu1)": 编译器标识信息。

.section .note.GNU-stack, One: 指定了GNU栈的注释部分。

注:使用.comm声明的变量可以在程序的任何部分访问,类似于C语言中的全局变量。

.comm symbol, size, alignment

由于我在声明globalOne时用的是int,所以系统自动开辟4个B的空间预留

那如果我用double声明呢?那应该开辟8B空间吧

尝试一下·:果然如此,但是为什么alignment也是8呢?

数据宽度

例如:

movl:l表示long word --32b

pushq,popq:q表示quad 即 quadword 即64b

寄存器

%表示Register

%rbp(基指针)、%rsp(栈指针)、%eax、%esi 和 %edi 等。

%rbp(基指针)

RegisterBasePointer

%rsp(栈指针)

RegisterStackPointer

%rip(指令指针

RegisterInstruction Pointer

%eax

%esi

%edi

%esp

Extended Stack Pointer

%ebp

Extended Base Pointer

##(%esp)

指令

功能:告诉 CPU 执行特定操作的命令。

movl(移动长整型数据)

pushq(压栈)

popq(出栈)

call(调用函数)。

leaq

leaq address, register

address:是要加载的内存地址或内存地址表达式。

register:是目标寄存器,用于存储计算出的地址。

incl(increment longword

用于将操作数(通常是寄存器或内存位置)的值增加1。如果操作数是32位的,incl 就是增加32位操作数的值;如果是16位的,就是增加16位操作数的值。

incl register ; 增加指定寄存器的值

incl memory ; 增加内存地址中的值

incl %eax ; 将eax寄存器的值增加1

incl 4(%rbx) ; 将rbx寄存器地址加4的内存位置的值增加1

标签

功能:用于标识代码段或位置的名称,如 fun、.LFBO 和 main。

.LFBO

立即数:直接跟在指令后面的数值,如 movl $200, %esi 中的 200

栈操作:使用 pushq 和 popq 进行的栈操作,栈是用于存储临时数据的数据结构,如函数调用时的参数和返回地址。

注:此文章为长期更新

相关推荐
我在人间贩卖青春4 天前
汇编之伪指令
汇编·伪指令
我在人间贩卖青春5 天前
汇编之伪操作
汇编·伪操作
济6175 天前
FreeRTOS基础--堆栈概念与汇编指令实战解析
汇编·嵌入式·freertos
myloveasuka5 天前
汇编TEST指令
汇编
我在人间贩卖青春5 天前
汇编编程驱动LED
汇编·点亮led
我在人间贩卖青春5 天前
汇编和C编程相互调用
汇编·混合编程
myloveasuka5 天前
寻址方式笔记
汇编·笔记·计算机组成原理
请输入蚊子6 天前
《操作系统真象还原》 第六章 完善内核
linux·汇编·操作系统·bochs·操作系统真像还原
myloveasuka6 天前
指令格式举例
汇编·笔记·计算机组成原理
我在人间贩卖青春6 天前
汇编之分支跳转指令
汇编·arm·分支跳转