hacktricks/binary-exploitation/integer-overflow.md

6.3 KiB
Raw Blame History

整数溢出

{% hint style="success" %} 学习并练习 AWS 黑客技术:HackTricks 培训 AWS 红队专家 (ARTE)
学习并练习 GCP 黑客技术:HackTricks 培训 GCP 红队专家 (GRTE)

支持 HackTricks
{% endhint %}

基本信息

整数溢出的核心是计算机编程中数据类型的大小限制和数据的解释

例如,一个8位无符号整数可以表示从0到255的值。如果尝试将值256存储在8位无符号整数中由于其存储容量的限制它会回绕到0。同样对于一个16位无符号整数,它可以保存从0到65,535的值将65,535加1会将值回绕到0。

此外,一个8位有符号整数可以表示从**-128到127的值。这是因为一个比特用于表示符号正或负剩下的7位用于表示大小。最负数表示为-128**(二进制 10000000),最正数为127(二进制 01111111)。

最大值

对于潜在的网络漏洞,了解最大支持的值非常有趣:

{% tabs %} {% tab title="Rust" %}

fn main() {

let mut quantity = 2147483647;

let (mul_result, _) = i32::overflowing_mul(32767, quantity);
let (add_result, _) = i32::overflowing_add(1, quantity);

println!("{}", mul_result);
println!("{}", add_result);
}

{% endtab %}

{% tab title="C" %} 整数溢出是一种常见的安全漏洞,发生在对整数进行算术运算时,结果超出了该整数类型所能表示的范围。这可能导致未预期的行为,如数据损坏、程序崩溃或甚至远程代码执行。在 C 语言中,整数溢出是一种常见的问题,因为 C 不会自动检查整数运算是否会导致溢出。为了防止整数溢出,开发人员应该谨慎设计他们的代码,确保在进行整数运算时考虑到可能的溢出情况。 {% endtab %}

#include <stdio.h>
#include <limits.h>

int main() {
int a = INT_MAX;
int b = 0;
int c = 0;

b = a * 100;
c = a + 1;

printf("%d\n", INT_MAX);
printf("%d\n", b);
printf("%d\n", c);
return 0;
}

例子

纯溢出

打印结果将为0因为我们溢出了char

#include <stdio.h>

int main() {
unsigned char max = 255; // 8-bit unsigned integer
unsigned char result = max + 1;
printf("Result: %d\n", result); // Expected to overflow
return 0;
}

有符号转无符号转换

考虑这样一种情况:从用户输入中读取一个有符号整数,然后在一个将其视为无符号整数的上下文中使用,但没有进行适当的验证:

#include <stdio.h>

int main() {
int userInput; // Signed integer
printf("Enter a number: ");
scanf("%d", &userInput);

// Treating the signed input as unsigned without validation
unsigned int processedInput = (unsigned int)userInput;

// A condition that might not work as intended if userInput is negative
if (processedInput > 1000) {
printf("Processed Input is large: %u\n", processedInput);
} else {
printf("Processed Input is within range: %u\n", processedInput);
}

return 0;
}

在这个例子中,如果用户输入一个负数,由于二进制值的解释方式,它将被解释为一个大的无符号整数,可能导致意外行为。

其他示例

(((argv[1] * 0x1064deadbeef4601) & 0xffffffffffffffff) == 0xD1038D2E07B42569)

ARM64

这在ARM64中没有改变,如您可以在这篇博客文章中看到的。

{% hint style="success" %} 学习并练习AWS HackingHackTricks Training AWS Red Team Expert (ARTE)
学习并练习GCP HackingHackTricks Training GCP Red Team Expert (GRTE)

支持 HackTricks
{% endhint %}