C++ 如何在linux中保护堆内存?

C++ 如何在linux中保护堆内存?,c++,linux,memory-management,C++,Linux,Memory Management,我想将堆内存设为只读。为此,我尝试了使用memalign()和mprotect()。但是从memalignment中我可以得到什么,memalign从进程堆中分配内存 我想将堆的某些部分设置为只读。有什么帮助吗 malloc()->mmap()->mprotect()一个假设的想法,但不确定这是否有帮助。。。上面有实现的示例代码吗 我需要保护堆中的内存地址。使用malloc()时,我得到的地址大约为0x10012008,而使用mmap()时,它是0xf7ec9000。我的目的是使heap meo

我想将堆内存设为只读。为此,我尝试了使用
memalign()
mprotect()
。但是从memalignment中我可以得到什么,memalign从进程堆中分配内存

我想将堆的某些部分设置为只读。有什么帮助吗

malloc()->mmap()->mprotect()
一个假设的想法,但不确定这是否有帮助。。。上面有实现的示例代码吗


我需要保护堆中的内存地址。使用malloc()时,我得到的地址大约为0x10012008,而使用mmap()时,它是0xf7ec9000。我的目的是使heap meory的一部分成为只读的,以捕获可能试图通过该堆运行的任何trampler

是的,mmap和mprotect是正确的功能。我不明白您当前的方法有什么问题,也就是说,您所说的“为此,我尝试了使用memalign()和mprotect()。但是从memalign中我可以得到什么,memalign将内存从进程堆中分配出去。”

下面是如何创建写保护内存区域的示例:

#include <fcntl.h>  
#include <signal.h>
#include <stdio.h>
#include <string.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>

static int alloc_size;
static char* memory;

void segv_handler (int signal_number)  {
 printf ("memory accessed!\n");
 mprotect (memory, alloc_size, PROT_READ | PROT_WRITE);
} 

int main () {
 int fd;
 struct sigaction sa;

 /* Install segv_handler as the handler for SIGSEGV. */
 memset (&sa, 0, sizeof (sa));
  sa.sa_handler = &segv_handler;
 sigaction (SIGSEGV, &sa, NULL);

 /* Allocate one page of memory by mapping /dev/zero. Map the memory
 as write-only, initially. */
  alloc_size = getpagesize ();
 fd = open ("/dev/zero", O_RDONLY);
  memory = mmap (NULL, alloc_size, PROT_WRITE, MAP_PRIVATE, fd, 0);
  close (fd);
  /* Write to the page to obtain a private copy. */
  memory[0] = 0;
 /* Make the memory unwritable. */
  mprotect (memory, alloc_size, PROT_NONE);

 /* Write to the allocated memory region. */
 memory[0] = 1;

  /* All done; unmap the memory. */
 printf ("all done\n");
 munmap (memory, alloc_size);
 return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
静态内部分配大小;
静态字符*存储器;
无效segv_处理器(内部信号_编号){
printf(“已访问内存!\n”);
mprotect(内存、分配大小、保护读取、保护写入);
} 
int main(){
int-fd;
struct-sigaction-sa;
/*安装segv_处理程序作为SIGSEGV的处理程序*/
memset(&sa,0,sizeof(sa));
sa.sa_handler=&segv_handler;
sigaction(SIGSEGV,&sa,NULL);
/*通过映射/dev/zero分配一页内存
最初是只写*/
alloc_size=getpagesize();
fd=打开(“/dev/zero”,仅适用于);
内存=mmap(NULL,alloc_size,PROT_WRITE,MAP_PRIVATE,fd,0);
关闭(fd);
/*写入页面以获取私人副本*/
内存[0]=0;
/*使记忆无法书写*/
mprotect(内存、分配大小、保护无);
/*写入分配的内存区域*/
内存[0]=1;
/*全部完成;取消映射内存*/
printf(“全部完成”\n);
munmap(内存、分配大小);
返回0;
}
您应该直接使用
mmap()
并完全删除
malloc()
。而且,根据您的需要,您可能根本不需要
mprotect()

ptr = mmap(NULL, length, PROT_READ, MAP_PRIVATE | MAP_ANONYMOUS, 0, 0);

在最近的内核和libc实现中,这将使用指定的保护模式分配请求的内存量——在这种情况下,分配的内存区域只能读取,不能写入。如果你只需要一堆零页,那就可以了。否则,生成的区域将正确对齐,您可以使用
mprotect()
以受控方式在短时间内取消对其的保护…

我是否可以建议使用
MAP\u ANONYMOUS
并避免整个
fopen()
e.t.c.古怪?细微的挑剔:
printf
不是吗