ASLR 和 PIE

2024-02-27 01:28
文章标签 pie aslr

本文主要是介绍ASLR 和 PIE,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

前言

ASLR(Address Space Layout Randomization,地址空间随机化)是一种内存攻击缓解技术,是一种操作系统用来抵御缓冲区溢出攻击的内存保护机制。这种技术使得系统上运行的进程的内存地址无法被预测,使得与这些进程有关的漏洞变得更加难以利用。
它最早于 2001 年出现在 PaX 项目中,于 2005 年正式成为 Linux 的一部分,如今已经广泛使用在各类操作系统中。

在 Linux 上,ASLR 的全局配置 /proc/sys/kernel/randomize_va_space 有三种情况:
0 表示关闭 ASLR;
1 表示部分开启(将 mmap 的基址、stack 和 vdso 页面随机化);
2 表示完全开启(在部分开启的基础上增加 heap 的随机化)
在这里插入图片描述

实例

环境:ARM Linux 32bit,qemu

test.c

#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>int main()
{int stack;int *heap;void *libc;heap = malloc(sizeof(int));libc = dlopen("libc.so.6", RTLD_NOW | RTLD_GLOBAL);printf("executable : %p\n", &main);printf("system@plt : %p\n", &system);printf("heap       : %p\n", heap);printf("stack      : %p\n", &stack);printf("1ibc       : %p\n", libc);free(heap);return 0;
}

Makefile

TARGET=testCC=/home/liyongjun/project/board/buildroot/Vexpress_2/host/bin/arm-linux-gccall:${CC} ${TARGET}.c -o ${TARGET}.out -Wall -no-piecp:cp ${TARGET}.out ~/tftp/clean:rm *.out

注意,编译时使用 -no-pie 选项关闭了 PIE,因为开启 PIE 会影响 heap 随机化(原因未追查)。

测试

从 host 机下载 test.out 到 ARM Linux 系统,然后针对 ASLR 不同配置,进行测试对比
一、关闭 ASLR

# tftp -gr test.out 192.168.31.223
# echo 0 > /proc/sys/kernel/randomize_va_space
# ./test.out 
executable : 0x105ac
system@plt : 0x10484
heap       : 0x13190
stack      : 0x7efffcf0
1ibc       : 0x76fd7380
# ./test.out 
executable : 0x105ac
system@plt : 0x10484
heap       : 0x13190
stack      : 0x7efffcf0
1ibc       : 0x76fd7380

发现两次执行 test.out,程序执行时所有地址都是不变化的

二、部分开启 ASLR

# echo 1 > /proc/sys/kernel/randomize_va_space
# ./test.out 
executable : 0x105ac
system@plt : 0x10484
heap       : 0x13190
stack      : 0x7ed35cf0
1ibc       : 0x76f68380
# ./test.out 
executable : 0x105ac
system@plt : 0x10484
heap       : 0x13190
stack      : 0x7e81ccf0
1ibc       : 0x76ee1380

两次执行 test.out,只有 stack、动态库地址随机化

三、完全开启 ASLR

# echo 2 > /proc/sys/kernel/randomize_va_space
# ./test.out 
executable : 0x105ac
system@plt : 0x10484
heap       : 0x1828190
stack      : 0x7ec97cf0
1ibc       : 0x76f4d380
# ./test.out 
executable : 0x105ac
system@plt : 0x10484
heap       : 0x1724190
stack      : 0x7ec41cf0
1ibc       : 0x76efe380

增加了 heap 地址随机化

PIE

由于 ASLR 是一种操作系统层面的技术,而二进制程序本身是不支持地址随机化加载的,便出现了一些绕过方式,例如 ret2plt、GOT 劫持、地址爆破等。于是,在 2003 年引入了位置无关可执行文件(Position-Independent Executable, PIE),它在应用层的编译器上实现,通过将程序编译为位置无关代码(Position-Independent Code, PIC),使程序可以被加载到任意位置运行,就像是一个特殊的共享库
在 PIE 和 ASLR 同时开启的情况下,攻击者将对程序的内存布局一无所知,大大增加了利用难度。当然凡事有利也有弊,在增加安全性的同时,PIE 也会一定程度上影响性能,因此在大多数操作系统上 PIE 仅用于一些对安全性要求比较高的程序。

gcc 支持的 PIE 选项如下所示,-fpie 是代码生成选项,其生成的位置无关代码可以被 -pie 选项链接到可执行文件中。

  • -fpic,为共享库生成位置无关代码
  • -pie,生成动态链接的位置无关可执行文件,通常需要同时指定 -fpie
  • -no-pie,不生成动态链接的位置无关可执行文件
  • -fpie,类似于 -fpic,但生成的位置无关代码只能用于可执行文件,通常同时指定 -pie
  • -fno-pie,不生成位置无关代码

修改 Makefile 文件

TARGET=testCC=/home/liyongjun/project/board/buildroot/Vexpress_2/host/bin/arm-linux-gccall:${CC} ${TARGET}.c -o ${TARGET}.out -Wall -pie -fpiecp:cp ${TARGET}.out ~/tftp/clean:rm *.out

重新编译、下载、执行

# tftp -gr test.out 192.168.31.223
# ./test.out 
executable : 0x49c6dc
system@plt : 0x76e8fc40
heap       : 0xb7f190
stack      : 0x7ee06ce8
1ibc       : 0x76f90380
# ./test.out 
executable : 0x4436dc
system@plt : 0x76de8c40
heap       : 0x17db190
stack      : 0x7ea81ce8
1ibc       : 0x76ee9380

发现程序运行的所有地址都随机化了

EXEC & DYN

如何查看一个二进制程序是 pie 的,还是 no-pie 的?使用 readelf 工具查看 ELF 文件类型

no-pie:

$ readelf -h test.out | grep TypeType:                              EXEC (Executable file)

pie:

$ readelf -h test.out | grep TypeType:                              DYN (Shared object file)

关闭 ASLR 的几种方法

在调试程序时,开启 ASLR 会增加调试难度,下面是几种临时关闭 ASLR 的方法
一、修改 /proc/sys/kernel/randomize_va_space

# echo 0 > /proc/sys/kernel/randomize_va_space
# ./test.out 
executable : 0x4006dc
system@plt : 0x76ed6c40
heap       : 0x403190
stack      : 0x7efffce8
1ibc       : 0x76fd7380
# ./test.out 
executable : 0x4006dc
system@plt : 0x76ed6c40
heap       : 0x403190
stack      : 0x7efffce8
1ibc       : 0x76fd7380

二、使用 setarch 命令
-R 选项即为关闭地址空间随机化

# setarch --help
BusyBox v1.36.1 (2024-01-04 00:19:02 CST) multi-call binary.Usage: setarch PERSONALITY [-R] PROG ARGSPERSONALITY may be:linux32	Set 32bit uname emulationlinux64	Set 64bit uname emulation-R	Disable address space randomization
# setarch linux32 -R ./test.out
executable : 0x4006dc
system@plt : 0x76ed6c40
heap       : 0x403190
stack      : 0x7efffce8
1ibc       : 0x76fd7380
# setarch linux32 -R ./test.out
executable : 0x4006dc
system@plt : 0x76ed6c40
heap       : 0x403190
stack      : 0x7efffce8
1ibc       : 0x76fd7380

三、gdb
在 gdb 场景下,使用 set disable-randomization on 命令关闭地址随机化
不过,很明显,在我的测试环境中,该方案没起作用。(有知道内幕的小伙伴请在评论区告知)

# gdb test.out 
GNU gdb (GDB) 12.1
Copyright (C) 2022 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "arm-buildroot-linux-gnueabihf".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<https://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:<http://www.gnu.org/software/gdb/documentation/>.For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from test.out...
(No debugging symbols found in test.out)
(gdb) set disable-randomization on
(gdb) show disable-randomization
Disabling randomization of debuggee's virtual address space is on.
(gdb) run
Starting program: /root/test.out 
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/libthread_db.so.1".
executable : 0x4c46dc
system@plt : 0x76e9fc40
heap       : 0x8e5190
stack      : 0x7eee0cc8
1ibc       : 0x76fa0380
[Inferior 1 (process 254) exited normally]
(gdb) run
Starting program: /root/test.out 
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/libthread_db.so.1".
executable : 0x4066dc
system@plt : 0x76e9cc40
heap       : 0x12aa190
stack      : 0x7e8eecc8
1ibc       : 0x76f9d380
[Inferior 1 (process 256) exited normally]
(gdb) 

总结

ASLR 不负责代码段以及数据段的随机化工作,这项工作由 PIE 负责。但是只有在开启 ASLR 之后,PIE 才会生效。
无论是 ASLR 还是 PIE,由于颗粒度问题,被随机化的都只是某个对象的起始地址,而在该对象的内部依然保持原来的结构,也就是说相对偏移是不会变的。

附录

Documentation/admin-guide/sysctl/kernel.rst

randomize_va_space
==================This option can be used to select the type of process address
space randomization that is used in the system, for architectures
that support this feature.==  ===========================================================================
0   Turn the process address space randomization off.  This is thedefault for architectures that do not support this feature anyways,and kernels that are booted with the "norandmaps" parameter.1   Make the addresses of mmap base, stack and VDSO page randomized.This, among other things, implies that shared libraries will beloaded to random addresses.  Also for PIE-linked binaries, thelocation of code start is randomized.  This is the default if the``CONFIG_COMPAT_BRK`` option is enabled.2   Additionally enable heap randomization.  This is the default if``CONFIG_COMPAT_BRK`` is disabled.There are a few legacy applications out there (such as some ancientversions of libc.so.5 from 1996) that assume that brk area startsjust after the end of the code+bss.  These applications break whenstart of the brk area is randomized.  There are however no knownnon-legacy applications that would be broken this way, so for mostsystems it is safe to choose full randomization.Systems with ancient and/or broken binaries should be configuredwith ``CONFIG_COMPAT_BRK`` enabled, which excludes the heap from processaddress space randomization.
==  ===========================================================================

这篇关于ASLR 和 PIE的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/750796

相关文章

Matlab_learning_2(Pie‘s source code饼状图源码)

一、源代码 function hh = pie(varargin)%PIE Pie chart.% PIE(X) draws a pie plot of the data in the vector X. The values in X% are normalized via X/SUM(X) to determine the area of each slice of p

HDU 1969 Pie (二分查找)

题目链接:click here~~ 题目大意:n块馅饼分给m+1个人,每个人的馅饼必须是整块的,馅饼可以被切开,但不能组合,也不一定要全部分完,问你每个人最大能分到多大体积的馅饼面积。 【解题思路】:二分,对于每个V值,我们枚举对应情况下人数P的多少,发现是单调递减的,因此二分查找区间,初始值left=0,right=inf;然后judge函数判断当前mid值能否使得p>=m,因此累计ans

coco2dx新建项目报错,ld: -pie can only be used when targeting iOS 4.2 or later clang: error: linker command

在新建cocos2d-x以后,运行发现以下错误: ld: -pie can only be used when targeting iOS 4.2 or later clang: error: linker command failed with exit code 1 (use -v to see invocation) 如图所示: 这时候,选中左上角

PIE原则——编程要表达出意图

PIE 英文:Program Intently and Expressively 中文:编程要表达出意图 是什么 在写代码时,明确表达意图十分重要,这与写诗、写随笔、写博客和写信是一个道理。 这是因为代码是写给人看的,而不是写给编译器看的。 因此,在写代码的时候要在表达上多花心思,将软件运行方式直接地传送给阅读代码的人。 为什么 代码是我们正确、完整地了解软件运行方式的唯一线索。

driftingblues9 - 溢出ASLR(内存地址随机化机制)

Site Unreachable driftingblues9easyaPphp GETSHELL、searchsploit使用、凭据收集、gdb使用、缓冲区溢出漏洞(难)、pattern_create.rb、pattern_offset.rb 使用 主机发现 ┌──(kali㉿kali)-[~/桌面/OSCP]└─$ sudo netdiscover -i eth0 -r 192.168

Android报表库aChartEngine-pie chart

1、pie chart介绍 aChartEngine中的pie Chart其实就是一个饼状图,是数据显示的一种。效果如图:   2、如何使用pie chart。 其实aChartEngine是使用是非常简单的,不同的chart的使用方式都是一样的,并不需要我们根据不同的chart调用不同的接口,接口都是统一的。那么我们应该如何使用呢?总结了一下分为两步: ①获取数据da

UVA - 12097 Pie

题意:有F+1个人来分N个圆派,每个人得到的必须是一整块派,而不是几块拼在一起,且面积要相同,求每个人最多能得到多大面积的派(不必是圆形) 思路:二分答案,因为派是不能拼起来的,所以一个半径r的派只能切出[pir^2/x]个派。向下取整, #include <iostream>#include <cstdio>#include <cstring>#include <cmath>#i

uvalive 3635 - Pie(二分搜索)

题目连接:3635 - Pie 题目大意: 有m个派, 要分给n + 1个人, 要求每个人拿到的大小相同, 并且每个人的派必须是一整块, 不能说分别从两个派切出一块凑成。 现在给出m个派的半径(派均为圆柱,高为1),输出每人可以拿到的最大派的体积。 解题思路:二分查找。 #include <stdio.h>#include <string.h>#include <m

Linux内核地址空间随机化ASLR的几种实现方法

ASLR(Address Space Layout Randomization)在2005年被引入到Linux内核kernel 2.6.12中。地址空间随机化在内核中有多种实现和表现方式,下面分别介绍。 堆栈随机化 堆栈随机化是一项安全增强,它允许对系统调用发生时,内核使用的堆栈添加一个随机偏移。这给基于stack的攻击增加了难度,因为stack攻击通常要求stack有个固定的layout。现

【转】Android 9 Pie 兼容性常见问题及注意事项

应用不兼容的常见原因 使用了系统的 ClassLoader 加载 org.apache.http.* 的库 Android M 就已经开始移除对 Apache HTTP client 的支持。而 Android P 的系统 ClassLoader 已经不支持加载 org.apache.http.包 (抛出 NoClassDefFoundError),应用必须用自定义的 ClassLoader