IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> C++知识库 -> GCC编译工具集 -> 正文阅读

[C++知识库]GCC编译工具集

GCC不是一个人在战斗,GCC背后其实有一堆战友。

?

目录

一、GCC的合作伙伴?

二、GCC编译具体过程

2.1 简单编译

2.2 实际编译?

①预处理?

?②编译为汇编代码

?③汇编

?④连接

三、分析ELF文件

3.1 ELF文件的段

?3.2 反汇编ELF


一、GCC的合作伙伴?

以下介绍部分gcc二进制程序处理工具

 工具           作用
addr2line用来将程序地址转换成其所对应的程序源文件及所对应的代码行,也可以得到所对应的函数。该工具将帮助调试器在调试的过程中定位对应的源代码位置
as主要用于汇编
ld主要用于链接
ar?主要用于创建静态库
ldd可以用于查看一个可执行程序依赖的共享库
objcopy将一种对象文件翻译成另一种格式,譬如将.bin 转换成.elf、或者将.elf 转换成.bin 等
objdump主要的作用是反汇编
readelf显示有关ELF文件的信息
size列出可执行文件每个部分的尺寸和总尺寸,代码段、数据段、总大小等

二、GCC编译具体过程

示例程序如下

#include<stdio.h>
int main(void)
{
	printf("Hello World!\n");
	return 0;
}

2.1 简单编译

?gcc test.c -o test

2.2 实际编译?

实质上,上述编译过程是分为四个阶段进行的,即预处理(也称预编译,Preprocessing)、编译(Compilation)、汇编(Assembly)和连接(Linking)。

①预处理?

?执行命令gcc -E test.c -o test.i 或gcc -E test.c,生成test.i文件

test.i部分代码:

?②编译为汇编代码

执行命令gcc -S test.i -o test.s,生成test.s文件

test.s部分代码:

?③汇编

?执行命令gcc -c test.s -o test.o,生成test.o文件

?④连接

执行命令gcc test.o -o test,生成test可执行文件

?

三、分析ELF文件

3.1 ELF文件的段

ELF文件格式如下图,位于ELF Header和Section Header Table 之间的都是段(Section)。一个典型的ELF文件包含下面几个段:

·text:已编译程序的指令代码段。
·rodata:ro 代表 read only,即只读数据(譬如常数 const)。
·data:已初始化的 C 程序全局变量和静态局部变量。
·bss:未初始化的 C 程序全局变量和静态局部变量。
·debug:调试符号表,调试器用此段的信息帮助调试。
ELF

可以使用readelf -S test查看test可执行文件各个section的信息如下:

There are 29 section headers, starting at offset 0x1928:

节头:
  [号] 名称              类型             地址              偏移量
       大小              全体大小          旗标   链接   信息   对齐
  [ 0]                   NULL             0000000000000000  00000000
       0000000000000000  0000000000000000           0     0     0
  [ 1] .interp           PROGBITS         0000000000000238  00000238
       000000000000001c  0000000000000000   A       0     0     1
  [ 2] .note.ABI-tag     NOTE             0000000000000254  00000254
       0000000000000020  0000000000000000   A       0     0     4
  ······
  [ 6] .dynstr           STRTAB           0000000000000360  00000360
       0000000000000082  0000000000000000   A       0     0     1
  [ 7] .gnu.version      VERSYM           00000000000003e2  000003e2
       000000000000000e  0000000000000002   A       5     0     2
  [ 8] .gnu.version_r    VERNEED          00000000000003f0  000003f0
       0000000000000020  0000000000000000   A       6     1     8
  [ 9] .rela.dyn         RELA             0000000000000410  00000410
       00000000000000c0  0000000000000018   A       5     0     8
  ······
  [13] .plt.got          PROGBITS         0000000000000520  00000520
       0000000000000008  0000000000000008  AX       0     0     8
  [14] .text             PROGBITS         0000000000000530  00000530
       00000000000001a2  0000000000000000  AX       0     0     16
  [15] .fini             PROGBITS         00000000000006d4  000006d4
       0000000000000009  0000000000000000  AX       0     0     4
  
  ······
  [22] .got              PROGBITS         0000000000200fb8  00000fb8
       0000000000000048  0000000000000008  WA       0     0     8
  [23] .data             PROGBITS         0000000000201000  00001000
       0000000000000010  0000000000000000  WA       0     0     8
  ······
  [26] .symtab           SYMTAB           0000000000000000  00001040
       00000000000005e8  0000000000000018          27    43     8
  [27] .strtab           STRTAB           0000000000000000  00001628
       0000000000000202  0000000000000000           0     0     1
  [28] .shstrtab         STRTAB           0000000000000000  0000182a
       00000000000000fe  0000000000000000           0     0     1
Key to Flags:
  W (write), A (alloc), X (execute), M (merge), S (strings), I (info),
  L (link order), O (extra OS processing required), G (group), T (TLS),
  C (compressed), x (unknown), o (OS specific), E (exclude),
  l (large), p (processor specific)

?3.2 反汇编ELF

由于ELF文件无法被当做普通文本文件打开,如果希望直接查看一个 ELF文件包含的指令和数据,需要使用反汇编的方法。

使用objdump -D test对其进行反汇编如下:

test:     文件格式 elf64-x86-64


Disassembly of section .interp:

0000000000000238 <.interp>:
 238:	2f                   	(bad)  
 239:	6c                   	insb   (%dx),%es:(%rdi)
 23a:	69 62 36 34 2f 6c 64 	imul   $0x646c2f34,0x36(%rdx),%esp
 241:	2d 6c 69 6e 75       	sub    $0x756e696c,%eax
 246:	78 2d                	js     275 <_init-0x273>
 248:	78 38                	js     282 <_init-0x266>
 24a:	36 2d 36 34 2e 73    	ss sub $0x732e3436,%eax
 250:	6f                   	outsl  %ds:(%rsi),(%dx)
 251:	2e 32 00             	xor    %cs:(%rax),%al
······

Disassembly of section .comment:

0000000000000000 <.comment>:
   0:	47                   	rex.RXB
   1:	43                   	rex.XB
   2:	43 3a 20             	rex.XB cmp (%r8),%spl
   5:	28 55 62             	sub    %dl,0x62(%rbp)
   8:	75 6e                	jne    78 <_init-0x470>
   a:	74 75                	je     81 <_init-0x467>
   c:	20 37                	and    %dh,(%rdi)
   e:	2e 35 2e 30 2d 33    	cs xor $0x332d302e,%eax
  14:	75 62                	jne    78 <_init-0x470>
  16:	75 6e                	jne    86 <_init-0x462>
  18:	74 75                	je     8f <_init-0x459>
  1a:	31 7e 31             	xor    %edi,0x31(%rsi)
  1d:	38 2e                	cmp    %ch,(%rsi)
  1f:	30 34 29             	xor    %dh,(%rcx,%rbp,1)
  22:	20 37                	and    %dh,(%rdi)
  24:	2e                   	cs
  25:	35                   	.byte 0x35
  26:	2e 30 00             	xor    %al,%cs:(%rax)

使用objdump -S将其反汇编并且将其C语言源代码混合显示出来:

执行命令gcc -o test -g test.c再执行objdump -S test

得到如下结果:

test:     文件格式 elf64-x86-64


Disassembly of section .init:

00000000000004e8 <_init>:
 4e8:	48 83 ec 08          	sub    $0x8,%rsp
 4ec:	48 8b 05 f5 0a 20 00 	mov    0x200af5(%rip),%rax        # 200fe8 <__gmon_start__>
 4f3:	48 85 c0             	test   %rax,%rax
 4f6:	74 02                	je     4fa <_init+0x12>
 4f8:	ff d0                	callq  *%rax
 4fa:	48 83 c4 08          	add    $0x8,%rsp
 4fe:	c3                   	retq   

······
xchg   %ax,%ax

Disassembly of section .text:

0000000000000530 <_start>:
 530:	31 ed                	xor    %ebp,%ebp
 532:	49 89 d1             	mov    %rdx,%r9
 535:	5e                   	pop    %rsi
 536:	48 89 e2             	mov    %rsp,%rdx
 539:	48 83 e4 f0          	and    $0xfffffffffffffff0,%rsp
 53d:	50                   	push   %rax
 53e:	54                   	push   %rsp
 53f:	4c 8d 05 8a 01 00 00 	lea    0x18a(%rip),%r8        # 6d0 <__libc_csu_fini>
 546:	48 8d 0d 13 01 00 00 	lea    0x113(%rip),%rcx        # 660 <__libc_csu_init>
 54d:	48 8d 3d e6 00 00 00 	lea    0xe6(%rip),%rdi        # 63a <main>
 ······
00000000000006d0 <__libc_csu_fini>:
 6d0:	f3 c3                	repz retq 

Disassembly of section .fini:

00000000000006d4 <_fini>:
 6d4:	48 83 ec 08          	sub    $0x8,%rsp
 6d8:	48 83 c4 08          	add    $0x8,%rsp
 6dc:	c3                   	retq   

?

  C++知识库 最新文章
【C++】友元、嵌套类、异常、RTTI、类型转换
通讯录的思路与实现(C语言)
C++PrimerPlus 第七章 函数-C++的编程模块(
Problem C: 算法9-9~9-12:平衡二叉树的基本
MSVC C++ UTF-8编程
C++进阶 多态原理
简单string类c++实现
我的年度总结
【C语言】以深厚地基筑伟岸高楼-基础篇(六
c语言常见错误合集
上一篇文章      下一篇文章      查看所有文章
加:2021-10-06 12:00:37  更:2021-10-06 12:01:13 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年5日历 -2024/5/19 22:19:05-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码