DAY01AM
一、约定
1.作业完成
2.50-200lines codes.
二、课程体系
语言
C
C++
算法
算法
数据结构
基础(系统核心(Kernel)编程)
Linux/Unix Window MacOSX
PC机服务器 ARM
设备驱动、进程管理、内存管理、文件目录系统管理、IO
内存管理
文件管理
IO
进程管理
进程创建
进程控制
进程通信
进程同步
线程管理
线程创建
线程同步
线程通信
应用
网络
数据库(pro*c/c++)
UI
shell
XML处理
分布式与中间件(Tuxedo/Corba/MQ)
webservice
OpenGL
定位:提供编程的能力,为设备驱动与Windows应用奠定基础
三、内存管理
硬件层次
内存结构管理
内核层次
内存映射
堆扩展
语言层次
c:malloc
c++:new
数据结构层次
STL
智能指针
1.问题:
malloc怎么分配内存空间?
malloc与new的关系?
2.Linux对内存的结构描述
1./proc/${pid}/存放进程运行时候所有的信息(包括内存结构)
结论:
任何程序的内存空间分成4个基本部分
1.代码区
2.全局栈区(全局变量)
3.堆
4.局部栈
任何一个程序都有一个自加载器 /lib/ld-linux.so.2 (0x005ff000)
负责将执行程序拷贝到代码空间同时将指针指向main()
执行程序的另一种方式是 /lib/ld-linux.so.2 ./可执行文件
Unix标准头文件是 #include<unistd.h>
进程查看 ps aue#a所有的 #u用户 #e有效进程
2.理解程序的变量与内存空间的关系
结论:
1.内存分四个区
2.各种变量对应存放区
3.堆栈是一种管理内存的数据结构
4.查看一个程序的内存地址
3.理解malloc的工作的原理
malloc使用一个数据结构(链表)来维护分配的空间
链表的构成:分配的空间、上一个空间数据、下一个空间、空间大小等信息
对malloc分配的空间不要越界访问。因为容易破坏后台的一个维护结构。导致malloc、free、calloc、realloc不正常工作
4.C++的new与malloc的关系
malloc new new[]
realloc new() //定位分配
calloc new[]
free delete delete[]
结论:
new的实现使用的是malloc来实现的。
区别:new使用malloc后,还要初始化空间。
基本类型:直接初始化成默认值。
复合类型(UDT-userdefine type用户定义类型) 调用指定的构造器
delete调用free实现。
区别:delete负责调用析构器。然后在调用free
new与new[]区别
new值调用一个构造器初始化。
new[]循环对每个区域调用构造器
delete与delete[]
deletep 与 delete[] p 都能释放p指向的第一个对象
Malloc.c |
#include<stdio.h> #include<stdlib.h> main() { int *p1 = malloc(4); int *p2 = malloc(4); int *p3 = malloc(4); int *p4 = malloc(4); int *p5 = malloc(4);
printf("%p\n",p1); printf("%p\n",p2); printf("%p\n",p3); printf("%p\n",p4); printf("%p\n",p5);
} |
Malloc.cpp |
#include<stdio.h> #include<stdlib.h> int main() { int *p1 = new int; int *p2 = new int; int *p3 = new int; int *p4 = new int; int *p5 = new int;
printf("%p\n",p1); printf("%p\n",p2); printf("%p\n",p3); printf("%p\n",p4); printf("%p\n",p5);
return 0; } |
找到进程目录 cd /proc |
查看进程 ps -aue |
可以根据需要进入相应的进程目录
cd PID |
程序运行的时候存在这个目录3378 ,当结束的时候就消失
ls –l exe 指向执行程序 |
cwd 指向当前目录 |
cat maps 程序运行的所有内存结构 |
程序理论上内存应该从08048000开始
十六进制1000代表4k (在Linux叫做1页)
代码空间 代码空间产生的全局栈 堆 局部栈 |
任何一个程序都有一个自加载器 /lib/ld-linux.so.2 (0x005ff000) 负责将执行程序拷贝到代码空间同时将指针指向main() |
执行程序的另一种方式是 /lib/ld-linux.so.2 ./可执行文件#include<unistd.h> |
#include<unistd.h> #include<stdio.h>
main() { printf("%d\n", getpid()); while(1) ; } |
代码var1.c |
#include<stdio.h> #include<stdlib.h> #include<unistd.h>
int add(int a, int b) { return a + b; }
int a1 = 1; //全局变量前面不能加auto(auto是自动) static a2 = 2; const int a3 = 3;
main() { int b1 = 4; static b2 = 5; const 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\n", main); printf("add: %p\n", add);
printf("%d\n", getpid()); while(1);
} |
执行结果 |
|
【vdso】:visual device shell object 代码区:只有代码区是有执行权限的 全局区:是大小可变的 堆: 栈: 栈: |
代码:stackleap.c |
#include<stdio.h> #include<stdlib.h> #include<unistd.h>
int main() { int a1 = 10; int a2 = 20; int a3 = 30;
int *p1 = malloc(4) int *p2 = malloc(4); int *p3 = malloc(4);
printf("%p\n", &a1); printf("%p\n", &a2); printf("%p\n", &a3); printf("%p\n", p1); printf("%p\n", p2); printf("%p\n", p3);
printf("%d\n", getpid(); while(1); } |
执行结果 |
观察可知: 变量在栈中每两个间隔是4,依次减小。 指针是在堆中,间隔是16,依次增大 |
代码mallocstruct.c |
#include<stdio.h> #include<stdlib.h> #include<unistd.h>
int main() { int *p1 = malloc(4); int *p2 = malloc(4); int *p3 = malloc(4);
*p1 = 1; *(p1+1) = 2; *(p1+2) = 3; *(p1+3) = 4; *(p1+4) = 5; *(p1+5) = 6; *(p1+5) = 6; *(p1+6) = 7; *(p1+7) = 8;
printf("%d\n",*p2); printf("%d\n", getpid(); while(1); } |
执行结果 |
代码mallocstruct2.c |
#include<stdio.h> #include<stdlib.h> #include<unistd.h>
int main() { int *p1 = malloc(4); int *p2 = malloc(4); int *p3 = malloc(4);
*p1 = 1; *(p1+1) = 2; *(p1+2) = 3; *(p1+3) = 4; *(p1+4) = 5; *(p1+5) = 6; *(p1+5) = 6; *(p1+6) = 7; *(p1+7) = 8;
free(p1);
printf("%d\n",*p2); printf("%d\n", getpid(); while(1); } |
执行结果: |
堆:malloc实际上是由链表来维护的。
当前内存 |
后继结点 |
前驱结点 |
当前区域大小 |
代码newmalloc.cpp |
#include<stdio.h> #include<stdlib.h> #include<unistd.h>
int main() { int *p1 = (int*)malloc(4); int *p2 = new int; int *p3 = (int*)malloc(4); int *p4 = new int; int *p5 = new int; int *p6 = new int;
printf("%d\n",*p1); printf("%d\n",*p2); printf("%d\n",*p3); printf("%d\n",*p4); printf("%d\n",*p5); printf("%d\n",*p6);
return 0; } |
执行结果 |
|
#include<stdio.h> #include<stdlib.h> #include<unistd.h> #include<new>
int main() { char 1[20]; int *p = new(a) int;
return 0; } |
DAY01PM
Funcproblem.c |
#include<stdio.h>
int add(int a, int b) { return a + b; }
int main() { int (*fun)(int) = add int r = fun(20); printf("%d\n", r); } |
#include<stdio.h>
int add(int a, int b) { return a + b; }
int main() { //int (*fun)(int) = (int(*)(int))&add typedef int(*fun)(int) fun f = (fun)add;
int r = f(20); printf("%d\n", r); } |