美文网首页
2019-05-30

2019-05-30

作者: Xindolia_Ring | 来源:发表于2019-05-31 00:17 被阅读0次

https://blog.csdn.net/u013580497/article/details/50360689
Linux当new一个新内存空间的时候操作系统如何分配

首先尝试申请一个128MB空间,观察maps和status文件的变化。

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str, s);
    char l[8] = {"/maps"};
    strcat(str, l);
    cout << str << endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str, s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout << str << endl;
    system(str);
}
 
int main(){
    int *p[8];
    char s[8];
    int pid = getpid();
    sprintf(s, "%d", pid);
    cout << "分配内存前的maps和status情况" << endl;
    maps(s);
    status(s);
    cout << "先分配1个128MB的内存" << endl;
    p[1] = new int[33554432];
    maps(s);
    status(s);
    delete[] p[1];
    return 0;
}

连续申请分配六个128MB空间(记为1~6号),然后释放第2、3、5号的128MB空间。

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/maps"};
    strcat(str, l);
    cout << str << endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout << str << endl;
    system(str);
}
 
int main(){
    int *p[8];
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    cout << "分配内存前的maps和status情况" << endl;
    maps(s);
    status(s);
    cout << "先分配6个128MB的内存,然后删除235号" << endl;
    
    p[0] = new int[33554432];
    p[1] = new int[33554432];
    p[2] = new int[33554432];
    p[3] = new int[33554432];
    p[4] = new int[33554432];
    p[5] = new int[33554432];
    
    delete[] p[1];
    delete[] p[2];
    delete[] p[4];
    
    maps(s);
    status(s);
    
    delete[] p[0];
    delete[] p[3];
    delete[] p[5];
    return 0;
}

连续申请分配六个128MB空间(记为1~6号),释放第2、3、5号的128MB空间,然后再分配1024MB。

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str, s);
    char l[8] = {"/maps"};
    strcat(str, l);
    cout << str << endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str, s);
    char l[8] = {"/status"};
    strcat(str, l);
    cout<<str<<endl;
    system(str);
}
 
int main(){
    int *p[8];
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    cout<<"分配内存前的maps和status情况"<<endl;
    maps(s);
    status(s);
    cout<<"先分配6个128MB的内存,然后删除235号"<<endl;
    p[0] = new int[33554432];
    p[1] = new int[33554432];
    p[2] = new int[33554432];
    p[3] = new int[33554432];
    p[4] = new int[33554432];
    p[5] = new int[33554432];
    delete[] p[1];
    delete[] p[2];
    delete[] p[4];
    //1024MB = 128MB * 8
    cout<<"分配一个1024MB内存..."<<endl;
    p[6] = new int[33554432*8];
    
    maps(s);
    status(s);
    
    delete[] p[0];
    delete[] p[3];
    delete[] p[5];
    delete[] p[6];
    return 0;
}

连续申请分配六个128MB空间(记为1~6号),释放第2、3、5号的128MB空间,分配1024MB。再分配64M内存。

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/maps"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
int main(){
    int *p[8];
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    cout<<"分配内存前的maps和status情况"<<endl;
    maps(s);
    status(s);
    cout<<"先分配6个128MB的内存,然后删除235号"<<endl;
    //一个int占4个字节
    //128MB = 128 * 1024 KB = 131072 KB
    //128MB = 128 * 1024 * 1024 字节(byte) = 134217728 Byte
    //int数组长度为 128 * 1024 * 1024 / 4
    p[0] = new int[33554432];
    p[1] = new int[33554432];
    p[2] = new int[33554432];
    p[3] = new int[33554432];
    p[4] = new int[33554432];
    p[5] = new int[33554432];
    delete[] p[1];
    delete[] p[2];
    delete[] p[4];
    //1024MB = 128MB * 8
    cout<<"分配一个1024MB内存..."<<endl;
    p[6] = new int[33554432*8];
    //64MB = 128MB / 2
    cout<<"分配一个64MB的内存..."<<endl;
    p[7] = new int[33554432/2];
    maps(s);
    status(s);
    delete[] p[0];
    delete[] p[3];
    delete[] p[5];
    delete[] p[6];
    delete[] p[7];
    return 0;
}

设计一个程序测试出你的系统单个进程所能分配到的最大虚拟内存空间为多大。

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/maps"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
 
int main(){
    int *p[10000] = { NULL };
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    cout<<"分配内存前的maps和status情况"<<endl;
    maps(s);
    status(s);
    int i = 0;
    try{
        do{
            p[i] = new int[33554432];
        }while(i<10000 && p[i++]!=NULL);
    }
    catch(std::bad_alloc&){
        cout<<"耗光虚拟内存后的maps和status情况 "<<i<<endl;
        maps(s);
        status(s);
        int max = i-1;
        for(i=-1;++i<max;){
            delete[]p[i];
        }
    }
    return 0;
}

编写一个程序,分配256MB内存空间(或其他足够大的空间),检查分配前后/proc/pid/status文件中关于虚拟内存和物理内存的使用情况,然后每隔4KB间隔将相应地址进行读操作,再次检查/proc/pid/status文件中关于内存的情况,对比前后两次内存情况,说明所分配物理内存(物理内存块)的变化。然后重复上面操作,不过此时为写操作,再观察其变化。

读操作

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/maps"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
 
int main(){
    int *p;
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    //一个int占4个字节
    //128MB = 128 * 1024 KB = 131072 KB
    //128MB = 128 * 1024 * 1024 字节(byte) = 134217728 Byte
    //int数组长度为 128 * 1024 * 1024 / 4
    //256MB = 128M * 2
    cout<<"分配256MB内存,看maps和status的情况..."<<endl;
    int sum = 33554432 * 2;
    p = new int[sum];
    status(s);
    cout<<"进行读操作"<<endl;
    //相隔4KB进行读写就是相隔1024个int进行读写
    int i  = 0;
    for(;i<sum;i += 1024){
        p[i];
    }
    cout<<endl;
    status(s);
    delete[] p;
    return 0;
}

写操作

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/maps"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
 
int main(){
    int *p;
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    //一个int占4个字节
    //128MB = 128 * 1024 KB = 131072 KB
    //128MB = 128 * 1024 * 1024 字节(byte) = 134217728 Byte
    //int数组长度为 128 * 1024 * 1024 / 4
    //256MB = 128M * 2
    cout<<"分配256MB内存,看maps和status的情况..."<<endl;
    int sum = 33554432 * 2;
    p = new int[sum];
    status(s);
    cout<<"进行写操作"<<endl;
    //相隔4KB进行读写就是相隔1024个int进行读写
    int i  = 0;
    for(;i<sum;i += 1024){
        p[i] = i;
    }
    cout<<endl;
    status(s);
    delete[] p;
    return 0;
}

添加以下代码:

void statusvmHWM(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[] = {"/status | grep VmRSS"};
    strcat(str,l);
    system(str);
}

修改成以下代码:

int i  = 0;
    for(;i<sum;i+=1024){
        p[i] = 1;
        statusvmHWM(s);
        sleep(1);
}

编写并运行(在第5步的程序未退出前)另一进程,分配等于或大于物理内存的空间,然后每隔4KB间隔将相应地址的字节数值增1,此时再查看前一个程序的物理内存变化,观察两个进程竞争物理内存的现象。

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <time.h>
using namespace std;
 
//命令 cat /proc/pid/maps
void maps(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/maps"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
//命令 cat /proc/pid/status
void status(char s[8]){
    char str[100] = {"cat /proc/"};
    strcat(str,s);
    char l[8] = {"/status"};
    strcat(str,l);
    cout<<str<<endl;
    system(str);
}
 
 
void statusvmHWM(char s[8]){
    char str[100] = {"echo '('$(date +%H:%M:%S)')' $(cat /proc/"};
    strcat(str,s);
    char l[] = {"/status | grep VmHWM)"};
    strcat(str,l);
    system(str);
}
 
 
int main(){
    int *p;
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    int sum = 2.74 * 1024 * 1024 * 1024 / 4;
    p = new int[sum];
    //相隔4KB进行读写就是相隔1024个int进行读写
    int i  = 0;
    for(;i<sum;i += 1024){
        p[i]++;
    }
    delete[] p;
    return 0;
}

分配足够大的内存空间,其容量超过系统现有的空闲物理内存的大小,1)按4KB的间隔逐个单元进行写操作,重复访问数遍(使得程序运行时间可测量);2)与前面访问总量和次数不变,但是将访问分成16个连续页为一组,逐组完成访问,记录运行时间。观察系统的状态,比较两者运行时间,给出判断和解释。

代码一、

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <sys/time.h>
#include <unistd.h>
using namespace std;
 
int main(){
    timeval starttime, endtime;
    int *p;
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    int sum = 2.74 * 1024 * 1024 * 1024 / 4;
    p = new int[sum];
    //相隔4KB进行读写就是相隔1024个int进行读写
    int i,j;
    gettimeofday(&starttime,0);
    for(i=0;i<sum;i += 1024){
        p[i]++;
    }
    gettimeofday(&endtime,0);
    double timeuse = 1000000*(endtime.tv_sec - starttime.tv_sec) + endtime.tv_usec - starttime.tv_usec;
    timeuse /=1000;//ms
    cout<<timeuse<<"ms"<<" = "<<timeuse/1000<<"s"<<endl;
    delete[] p;
    return 0;
}

代码二、

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <pthread.h>
#include <sys/time.h>
#include <unistd.h>
using namespace std;
 
int sum = 2.74 * 1024 * 1024 * 1024 / 4;
int *p  = new int[sum];
int a = 0;
void* visit(void* arg){
    int i = *(int *)arg;
    int end = i + sum/16;
    for(;i < end;i += 1024){
        ++p[i];
    }
    ++a;
}
 
 
int main(){
    timeval starttime, endtime;
    pthread_t id[16];
    int i,ret;
    int pc[16];
    int x = sum /16;
    for(i=-1;++i<16;){
        pc[i] = i * x;
    }
    char s[8];
    int pid = getpid();
    sprintf(s,"%d",pid);
    cout<<"进入计时状态"<<endl;
    gettimeofday(&starttime,0);
    for(i=-1;++i<16;){ 
        ret=pthread_create(&id[i],NULL,visit,&pc[i]);
    }
    while(a!=16){}
    gettimeofday(&endtime,0);
    cout<<"结束计时状态"<<endl;
    double timeuse = 1000000*(endtime.tv_sec - starttime.tv_sec) + endtime.tv_usec - starttime.tv_usec;
    timeuse /=1000;//ms
    cout<<timeuse<<"ms"<<" = "<<timeuse/1000<<"s"<<endl;
    delete[] p;
    return 0;
}

相关文章

网友评论

      本文标题:2019-05-30

      本文链接:https://www.haomeiwen.com/subject/wdhitctx.html