Articles of 堆栈

为什么堆栈必须是页面alignment的?

在Linux中,我试过(只是为了好玩)在process.c中修改内核源代码。创build一个具有更多熵的堆栈地址,即: sp -= get_random_int() % 8192; 当我改变太多,内核停止或我得到一些看似不明确的行为。 我猜这会导致PAGE_ALIGN()以某种方式失败? 我并不关心为什么PAGE_ALIGN()特别是失败,或者说内核中的哪一段代码失败了(尽pipe这也是很好的事情)。 我更感兴趣的是为什么堆栈必须驻留在特定的区域。 这背后的build筑理由和动机是什么? 这与GDT / LDT如何在保护模式下工作有关系吗? 只是为了弄清楚我在问什么: 为什么堆栈的forms必须是0xbfXXXXXX(在32位上)? 为什么堆栈不能是例如0xaaXXXXXX或其他值?

gcc -mpreferred-stack-boundary选项

我想知道GNU编译器在编译过程中使用了-mpreferred-stack-boundary选项。 我查过了文档,但是我的解释没有了。 有人可以解释一下吗?

程序栈的增长方向究竟是什么?

我正在阅读理查德·布鲁姆(Richard Blum)的专业汇编语言 ( Professional Assembly Language) ,我对本书的不一致感到困惑,我想知道程序堆栈的增长方向到底是什么? 这是从第312页的图片,这是build议程序堆栈成长。 但是,当我到达第322页时,我看到另一个版本,这表明程序堆栈增长缓慢。 和这个

每个进程是否存在内核堆栈?

是否存在每个用户空间进程的内核堆栈和用户空间堆栈? 如果两个堆栈都存在,那么每个用户空间进程应该有两个堆栈指针?

溢出的缓冲区数据不会连续存储

我有以下代码来模拟缓冲区溢出。 编辑:我错过了下面的代码中的重要一步。 随着讨论的进行,variablesc得到了修改。 void function (int fd, int e) { int i = 0; int n; char c; char s[44]; . . c = getchar(fd); . //Some check on c s[i++] = c; . //Some more local variables and some operations on them. } 我想通过发送更多的input> 4字节溢出缓冲区,以查看如何本地variables和EBP和RET和参数得到修改。 但是,当我在GDB中debugging以查看堆栈帧时,此缓冲区溢出,溢出的数据似乎不会被分配连续的内存位置。 缓冲区基址:0xbfff fdb3 C地址:0xbfff fddf地址:0xbfff fde0 正如你所看到的,我的inputstring包含了大量的NOP(\ x90),然后大量的A(\ x41)。 […]

有什么方法可以在运行时确定可用的堆栈空间吗?

我知道堆栈大小是固定的。 所以我们不能在堆栈上存储大对象,我们转移到dynamic分配(例如malloc)。 另外,当函数调用嵌套时,栈被使用,所以我们也避免了recursion函数。 在运行时是否有任何方法来确定目前使用了多less堆栈内存以及剩余多less内存? 在这里,我假设Linux环境(gcc编译器)与x86架构。

理解由一个简单的C程序生成的汇编代码

我试图通过使用gdb的反汇编器来检查一个简单的C程序的组件级代码。 以下是C代码: #include <stdio.h> void function(int a, int b, int c) { char buffer1[5]; char buffer2[10]; } void main() { function(1,2,3); } 以下是main和function的反汇编代码 gdb) disass main Dump of assembler code for function main: 0x08048428 <main+0>: push %ebp 0x08048429 <main+1>: mov %esp,%ebp 0x0804842b <main+3>: and $0xfffffff0,%esp 0x0804842e <main+6>: sub $0x10,%esp 0x08048431 <main+9>: movl $0x3,0x8(%esp) 0x08048439 <main+17>: […]

Interrupt Handler使用哪个堆栈 – Linux

在多任务系统中,当任何硬件对特定的CPU产生中断时,除非CPU已经在服务ISR,否则CPU可以执行以下任一种情况: 用户模式进程正在CPU上执行 内核模式进程正在CPU上执行 想知道在以上两种情况下哪个堆栈被中断处理程序使用,为什么?

有没有比使用backtrace()更便宜的方法来find调用堆栈的深度?

我的日志logging代码使用backtrace()的返回值来确定当前的堆栈深度(用于漂亮的打印目的),但从分析中可以看出这是一个相当昂贵的调用。 我不认为有这样做的更便宜的方法? 请注意,我不关心帧地址,只是其中有多less。 编辑:这些日志loggingfunction遍布大型代码库,所以手动跟踪堆栈深度并不是一个真正的select。

如何在Linux上对clone()系统调用进行mmap映射?

Linux上的clone()系统调用需要一个指向堆栈的参数,供新创build的线程使用。 做到这一点的显而易见的方法是简单地malloc一些空间,并通过它,但是你必须确保你已经malloc'd尽可能多的堆栈空间,因为该线程将使用(很难预测)。 我记得使用pthreads时,我不必这样做,所以我很好奇它做了什么。 我遇到这个网站 ,它解释说:“Linux pthreads实现使用的最好的解决scheme是使用mmap分配内存,标记指定了使用时分配的内存区域,这样内存分配给如果系统不能分配额外的内存,则会发生分段违规。 我曾经听过mmap用过的唯一的上下文是将文件映射到内存中,并且确实读取了mmap手册页,它使用文件描述符。 这怎么可以用来分配一个dynamic长度的堆栈给clone()? 这个网站是疯了吗? ;) 无论哪种情况,内核都不需要知道如何为新的堆栈find一堆免费的内存,因为这是用户启动新进程时必须要做的事情。 为什么一个堆栈指针甚至需要首先指定,如果内核已经可以解决这个问题呢?