linux编程笔记(1)-内存管理介绍
来源:互联网 发布:c如何定义一维数组 编辑:程序博客网 时间:2024/06/06 06:44
内存管理主要分为以下几个层次:
- 硬件层次:内存结构管理
- 内核层次:内存映射/堆扩展
- 语言层次:c(malloc)/c++(new)
c语言用malloc依次申请4个字节空间的代码:
#include<stdio.h>#include<stdlib.h>int main(){ int *p1 = malloc(4); int *p2 = malloc(4); int *p3 = malloc(4); int *p4 = malloc(4); printf("p1 = %p\n",p1); printf("p2 = %p\n",p2); printf("p3 = %p\n",p3); printf("p4 = %p\n",p4); return 0;}
打印输出:
p1 = 0x11ca010
p2 = 0x11ca030
p3 = 0x11ca050
p4 = 0x11ca070
#include<stdio.h> #include<stdlib.h> #include<iostream> int main() { int *p1 = new int; int *p2 = new int; int *p3 = new int; int *p4 = new int; printf("p1 = %p\n",p1); printf("p2 = %p\n",p2); printf("p3 = %p\n",p3); printf("p4 = %p\n",p4); return 0; }
p1 = 0x1794c20
p2 = 0x1794c40
p3 = 0x1794c60
p4 = 0x1794c80
malloc怎么分配空间?
new 与malloc的关系?
linux对内存的结构描述
在linux系统中,/proc/${pid}/目录下存放进程运行时所有的信息,包括内存结构。进程结束,该目录会清除。运行下面这段代码:
int main(){ while(1){ };}查看该该进程的运行目录如下图:
其中:
exe:指向执行进程的文件
cwd:指向执行进程所在的目录
fd:为进程打开的所有文件
cpuset:是cpu的信息
maps:保存了程序运行的所有内存结构
任何程序的内存空间被分为4个基本部分:
- 代码区
- 全局栈区
- 堆
- 局部栈
include<stdio.h>#include<stdlib.h>#include<unistd.h>int add(int a,int b){ return a+b;}int a1 = 1;static int a2 = 2;const int a3 = 3;int main(){ int b1 = 4; static int b2 =5; const int b3 = 6; int *p1 = malloc(4); printf("a1=%p\n",&a1); printf("a2=%p\n",&a2); printf("a3=%p\n",&a3); printf("b1=%p\n",&b1); printf("b2=%p\n",&b2); printf("b3=%p\n",&b3); printf("p1=%p\n",p1); printf("main=%p",main); printf("add=%p",add); printf("pid=%d",getpid()); while(1); return 0;}
运行结果为:
a1=0x601050 全局区
a2=0x601054 全局区
a3=0x400774 全局常量在代码区
b1=0x7ffc8f8e4698 局部栈区
b2=0x601058
b3=0x7ffc8f8e469c 局部常量放在局部栈区
p1=0x15ee010
main=0x4005ea
add=0x4005d6
pid=2456
查看该进程的maps文件如下图:
函数调用栈空间的分配与释放
#include<stdio.h>int add(int a,int b){ return a+b;}int main(){ int (*func)(int) =(int(*)(int)) add; int ret = func(20); //只传入一个参数 printf("ret = %d\n",ret); int ret2 = func(10,20,30); //传入三个参数,第三个参数没用,能正常得到结果 return 0;}//代码能编译通过,执行的结果是错误的。
函数执行的时候,函数拥有自己的临时栈。函数的就在临时栈中,如果函数传递实参,则用来临时参数变量。
__stdcall,__cdecl,__fastcall
1.决定函数栈压栈的参数顺序
2.决定函数栈的清空方式
3.决定了的名字转换方式
虚拟内存的分配
栈:编译器自动的生成代码来负责维护
堆:地址是否映射?,映射空间是否被管理?
1.brk/sbrk 内存映射函数
分配释放函数:
int brk(void* end); //分配空间,释放空间void *sbrk(int size); //返回空间地址
应用:
- 使用sbrk分配空间
- 使用sbrk得到没有映射的虚拟地址(sbrk(0))
- 使用brk分配空间
- 使用brk释放空间
sbrk(int):如果是第一次调用,则返回没有映射的虚拟地址空间首地址,同时产生一个数据,指向地址。
int main(){ int *p = sbrk(4); //分配4字节的空间 *p =8888; printf("%d\n",*p); return 0;}
- linux编程笔记(1)-内存管理介绍
- Linux系统编程学习笔记(七)内存管理
- linux内存管理介绍
- linux内存管理介绍
- Linux内存管理介绍
- linux 内存管理笔记
- linux内存管理笔记
- Linux内存管理学习笔记(一)
- Linux内存管理--笔记(转载)
- linux网络编程-内存管理
- Linux系统编程学习笔记(五)进程管理1
- linux内存管理学习笔记
- linux内存管理学习笔记
- linux kernel内存管理 笔记
- linux内存管理伙伴算法(一:基本概念介绍)
- linux内存管理伙伴算法(一:基本概念介绍)
- arm-linux内存管理学习笔记(1)-内存页表的硬件原理
- 【linux编程】C++内存管理详解(一)
- nginx 设置匿名http正向代理
- 3831: [Poi2014]Little Bird|DP|单调队列
- 你经常需要的功能——Android篇(不断更新中...)
- 我读Mongoose源码----程序框架
- Java BIO、NIO、AIO 学习
- linux编程笔记(1)-内存管理介绍
- 020 小记一次网络故障处理
- 奕新集团RAC 11g 生产库环境(待完善无图)
- setInterval() 使用注意的地方
- linux常用命令
- 河南第六届ACM省赛(Adjacent Bit Counts)
- java中的list、set与map
- linux 挂载 windows下的分区
- Android逆向笔记(4)--- santoku安装方法