现代汇编语言


本篇文章介绍汇编,链接等常识,同时介绍了x86-64和armv8-a的一些指令语法

现代汇编学习

之前学的80x86汇编太古老了,甚至连第一版linux kernel代码都看不懂,现在整理一下一些汇编知识,主要是针对x86armv8-a架构的,但是本文并不会教具体的指令长什么样,也不会阐述怎么写一个通用汇编代码。学习汇编本身不是我们的终极目的。我们的目的是为了更好开发软件或者高性能库,因此会介绍一下编译,链接的原理和流程。

汇编语言类型

  • AT&T

    • 是这个实验室提出的一种语法,注意它和指令集是没关系的,仅仅是一种语法而已。
    • 对于x86处理器,立即数由$,寄存器由%引用。
    • 对于arm处理器,直接使用arm官方的语言格式。
  • intel

    • 本科会学到的一种语言格式,x86汇编
    • 简单,易用
  • 汇编器的作用是把汇编语言翻译成机器语言,所以不同的汇编语言可能会使用不同的汇编器。他们的机器语言即指令。

  • GAS 汇编器可以汇编x86的汇编语言,也可以汇编arm。

  • Intel assembler 只能汇编 intel的汇编语言,就像icc。

汇编器

汇编器列表

  • AT&T assembler - as
  • Borland’s Turbo Assembler - TASM
  • GNU assembler - gas,GCC默认使用这个
  • Intel Assembler
  • Microsoft Assembler - MASM
  • Netwide Assembler - NASM
  • Yet Another Assembler - YASM

x86 gas语法

汇编器简短比较

汇编器都干了什么

  • 汇编器负责把当前源文件的所有变量,常量,宏,label解析等等并且生成相应的符号表(这时候的解析是初步的,符号表是不完整的,后续工作链接器会接手),所谓解析就是确定他们的地址。这些地址都是基于本模块计算出来的相对地址,绝对地址的计算需要到链接阶段才能做。

  • 汇编器的输出是目标文件

Assembling:
- Assembling converts source program into object program if syntactically correct and
generates an intermediate .obj file or module.
- It calculates the offset address for every data item in data segment and every
instruction in code segment.
- A header is created which contains the incomplete address in front of the generated obj
module during the assembling.
- Assembler complains about the syntax error if any and does not generate the object
module.
- Assembler creates .obj .lst and .crf files and last two are optional files that can be
created at run time.
- For short programs, assembling can be done manually where the programmer translates
each mnemonic into the machine language using lookup table.
- Assembler reads each assembly instruction of a program as ASCII character and
translates them into respective machine code.
  • 符号表实际上就是用于链接器定位每个目标文件的变量和函数信息比如汇编中重要的三个节.bss .data .text

  • 在汇编语言源代码可以调用外部文件的函数,就像C语言调用库函数一样。汇编器对这些函数或者变量无法进行地址计算。这些活由链接器干。

  • c 语言中 加了static的函数不会出现在 global section

  • 目标文件的三种类型(来自CSAPP:chapter 7)

    • Relocatable object file. Contains binary code and data in a form that can be combined with other relocatable object files at compile time to create an executable object file.
    • Executable object file. Contains binary code and data in a form that can be copied directly into memory and executed.
    • Shared object file. A special type of relocatable object file that can be loaded into memory and linked dynamically, at either load time or run time.
  • nm工具可以查看某个目标文件的符号(readelf和objdump都可以看符号表)

    • nm -gD yourLib.so
      
      objdump -TC 也可以(C用于c++)
      
      readelf -Ws
      
  • 一个简单的例子:

...
int x = 0;
int y = -1;
y = x;
...

上面这个片段定义了两个全局标号x y,这两个标号实际上是一个地址,但是我们在C语言引用的时候实际上是引用值而不是地址。只有y = &x这个语句的含义才是将x这个标号的值(即x的地址)赋给y
y = x这个语句实际上会被编译成

mov eax,[x]
mov dword[y],eax

链接器

  • 链接器负责进一步解析所有的符号,函数名,(根据每个目标文件的符号表)把所有的目标文件链接成一个最终的可执行文件。链接器收集所有目标文件的符号表信息,合并同类的段(比如不同目标文件的代码段,数据段)等工作。最终可执行文件的符号表是完整的。
    • 比如两个.o文件都定义了函数void foo(),这时候链接器需要判断哪个是需要被采用的
    • 在.o文件中没有在global中的函数是无法被其他.o文件调用的,实际上在汇编阶段不会出现在符号表,因此链接器也无法使用。(这些函数就是在c中加了static修饰符的变量)
This involves the converting of .OBJ module into .EXE(executable) module i.e.
executable machine code.
- It completes the address left by the assembler. 
Microprocessors lecture 5: Programming with 8086 Microprocessor
- It combines separately assembled object files.
- Linking creates .EXE, .LIB, .MAP files among which last two are optional files. 

链接器负责把全部的符号解析成最终的地址。它负责解析所有的符号。

  • ld即一个链接器

  • 命令readelf很有用

  • 链接

    • static linking

    • dynamic linking

    • runtime linking

    参考1

    quaro参考

  • 更详细的参考另外的md文件

ld(链接器)

  • 如果希望兼容32位的elf输出,这里需要使用-m选项

    ld -m elf_i386 -s -o file file.o
    

linker script

链接脚本是链接器使用的。脚本中会指定某些默认行为,比默认链接的一些标准库,比如可执行文件的入口地址。

加载器

  • loader通常由shell进程负责唤起,它将可执行文件的代码加载到内存。
It Loads the program in memory for execution.
- It resolves remaining address.
- This process creates the program segment prefix (PSP) before loading.
- It executes to generate the result. 

可执行文件格式

  • 常用的有ELF:executable and linkable format

    		bin       flat-form binary files (e.g. DOS .COM, .SYS)
        ith       Intel hex
        srec      Motorola S-records
        aout      Linux a.out object files
        aoutb     NetBSD/FreeBSD a.out object files
        coff      COFF (i386) object files (e.g. DJGPP for DOS)
        elf32     ELF32 (i386) object files (e.g. Linux)
        elf64     ELF64 (x86_64) object files (e.g. Linux)
        elfx32    ELFX32 (x86_64) object files (e.g. Linux)
        as86      Linux as86 (bin86 version 0.3) object files
        obj       MS-DOS 16-bit/32-bit OMF object files
        win32     Microsoft Win32 (i386) object files
        win64     Microsoft Win64 (x86-64) object files
        rdf       Relocatable Dynamic Object File Format v2.0
        ieee      IEEE-695 (LADsoft variant) object file format
        macho32   NeXTstep/OpenStep/Rhapsody/Darwin/MacOS X (i386) object files
        macho64   NeXTstep/OpenStep/Rhapsody/Darwin/MacOS X (x86_64) object files
        dbg       Trace of all info passed to output stage
        elf       ELF (short name for ELF32)
        macho     MACHO (short name for MACHO32)
        win       WIN (short name for WIN32)
    

objconv 工具


  • objconv -fnasm main.o把目标文件反汇编成指定格式的汇编语言

x86汇编

  • .set symbol,expression,把符号设为具体的值

AT&T语法

  • 指令可能会加后缀表示操作数的宽度
    • “byte” refers to a one-byte integer (suffix b)
    • “word” refers to a two-byte integer (suffix w),
    • “doubleword” refers to a four-byte integer (suffix l), and
    • “quadword” refers to an eight-byte value (suffix q).
  • MOV:movl,movw,movb,movq.(32,16,8,64)一般如果没有后缀那就是默认的长度。
mov 基本指令
如果用到扩展,mov还会有s(signed),z(zero)的后缀,
movzbl %al,%ebx 表示对al寄存器(8-bit)进行zero扩展放到ebx(64-bit)
mov 内存寻址方式segment:displacement(base register, index register, scale factor)
即segment:[base register + displacement + index register * scale factor]

movzwl (%rdx,%rax,2),%edx  

函数定义

  • .type start, @function表示将符号start定义成一个函数标号

AVX,SSE指令

指令参考1

x64 寄存器

在这里插入图片描述

  • There are sixteen 64-bit registers in x86-64: %rax, %rbx, %rcx, %rdx, %rdi, %rsi, %rbp, %
  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值