用进程开辟物理内存

http://blog.csdn.net/jnu_simba/article/details/8917076

进程地址空间和物理地址

http://www.kerneltravel.net/journal/v/mem.htm

linux内存管理

 

top命令解释

http://wenku.baidu.com/view/d1727f0c76c66137ee061981.html

 

内存映射(mmap)是Linux操作系统的一个很大特色,它可以将系统内存映射到一个文件(设备)上,以便可以通过访问文件内容来达到访问内存的目的。

mmap将一个文件或者其它对象映射进内存。

munmap(解除内存映射)
 
 

http://www.ibm.com/developerworks/cn/linux/l-ipc/part5/index1.html

得到映射普通文件的大小介于一个页面与两个页面之间(大小为:pagesize*2-99),版本1的被映射部分是整个文件

的基础上,

思考  在父子进程 通过mmap匿名映射,实验共享的时候最多可以打开多大空间,修改程序fork.cpp

得到结果

access page 1 over
access page 1 edge over, now begin to access page 2
access page 2 over
access page 2 over
access page 2 edge over, now begin to access page 3
access page 3 over
access page 3 over
access page 3 edge over, now begin to access page 4
access page 4 over
access page 4 over
access page 4 edge over, now begin to access page 5
access page 5 over
access page 5 over
access page 5 edge over, now begin to access page 6
娈甸敊璇?
          [root@localhost yis]# child read: the 1 people's age is 20
child read: the 2 people's age is 21
child read: the 3 people's age is 22
child read: the 4 people's age is 23
child read: the 5 people's age is 24
child read: 1 people's age is 100
child  page 1 read over
child read: 2 people's age is 100
child  page 2 read over
child read: 3 people's age is 100
child  page 3 read over
child read: 4 people's age is 100
child  page 4 read over
child read: 5 people's age is 100
child  page 5 read over

得到,开辟空间的大小介于4个页面与5个页面之间(大小为:pagesize*5-99),

24k左右的空间,内存不受影响

key_t ftok( const char * fname, int id )

系统建立IPC通讯 (消息队列信号量共享内存) 时必须指定一个ID值。通常情况下,该id值通过ftok函数得到。

 

 程序a .cpp  b.cpp产生进程间的通信

 http://blog.csdn.net/muge0913/article/details/7342653

 

 shmget 共享内存

http://blog.csdn.net/icechenbing/article/details/7715472

 系统V共享内存是随内核持续的,即使所有访问共享内存的进程都已经正常终止,共享内存区仍然存在(除非显式删

      除共享内存),在内核重新引导之前,对该共享内存区域的任何改写操作都将一直保留。

MemControl.h

#include <sys/ipc.h>
#include <sys/shm.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <vector>
#include <iostream>
using namespace std;

#define IPCKEY 0x366378
#define MEMSIZE 1024*1024  //MEMSIZE要随IPCKEY一同改变
#define MEMNUM  150 //开辟空间的块数
 
typedef struct
{
 int file_no;
 char agen[10];
} st_setting;

class MemControl
{
    public:
    vector < int >  m_OnlyNum;      //存储唯一的一串数字
    vector < int > m_VecShm_id;      //唯一数字对应的id
    vector < st_setting * > m_VecPSetting;  //存储共享空间在当前进程,每一块的首地址
    bool GetNum();                 //用ftok获取的一串唯一数字
    bool Init();               //开辟空间,如果空间已经开辟就获取id和地址
    bool WriteMem();                 //在空间位置写数据
    bool ReadMem( );                    //读取空间数据
    bool ClearMem();                     //清除空间
   
};

MemControl.cpp

#include "MemControl.h"

//MemControl::MemControl()
//{}
//MemControl::~MemControl()
//{}
bool
MemControl::GetNum()
{
   
    for(int i=1;i<=MEMNUM;i++)
    {  
        //int var;
       // var=ftok(".",i);
        m_OnlyNum.push_back( IPCKEY+i );
   
    }
    return true;
}
bool
MemControl::Init( )
{   GetNum();
    int shm_id;
    st_setting * p_setting;
    for( vector<int>::iterator iter=m_OnlyNum.begin();iter!=m_OnlyNum.end();++iter)
    {
        shm_id=shmget( *iter ,MEMSIZE,0640|IPC_CREAT );
        if( shm_id==-1 )
        {
            printf("shmget error,please change the IPCKEY \n");
            return false;
        }
         p_setting=(st_setting*)shmat(shm_id,NULL,0);
        
         m_VecPSetting.push_back(p_setting);
         m_VecShm_id.push_back(shm_id);
    }
     return true;
}
bool
MemControl::WriteMem()
{
  int a=0;
  string b;
    for( vector<st_setting*>::iterator iter=m_VecPSetting.begin(); iter!=m_VecPSetting.end(); ++iter )
    {  a=a+1;
        cout<<a<<"=="<<endl;
        if(1==a)
         b="yis A ";
        else if(2==a)
           b="yis B";
     
            else if(3==a)
                      b="yis C";
               else if(4 ==a)
                      b="yis D";
               else if(5==a)
                      b="yis E";
                  else if(6==a)
                      b="yis F";
                  else  if(7==a )
                      b="yis G";
                     else if(8==a)
                      b="yis H";
                  else if(9==a)
                      b="yis I";
                    else if(10==a)
                      b="yis J";
                else
                b="数值大于10";
   
        for(   int i=0;i< (MEMSIZE)/sizeof(st_setting) ;  i++)
       {                
                 // (*iter+i)->agen =  b; //这样赋值会错误?
                cout<<"===="<<b<<endl;
                  strncpy((*iter+i)->agen,b.c_str() ,10);
                  cout<< "写入的agen: "<<( *iter+i )->agen <<endl;
                  (*iter+i)->file_no = i;  
                //  sleep(1);
                 printf( "file_no:%d\n",( *iter+i )->file_no );
                    printf("当前地址%d\n",(*iter+i) );
        } 
    }
   
 return true;
}

bool
MemControl::ReadMem()
{   
       for( vector<st_setting *>::iterator iter=m_VecPSetting.begin(); iter!=m_VecPSetting.end(); ++iter )
    {
    
         for(int i=0;i<(MEMSIZE)/sizeof(st_setting);i++)
        {
          printf("The value is  :%d\n",( *iter+i )->file_no);
          printf("当前地址%d\n",(*iter+i) );
          cout<<( *iter+i )->agen<<endl;
        // sleep(1);
        }
    }
   

     return true;
}
bool
MemControl::ClearMem()
{
    for( vector<st_setting *>::iterator iter=m_VecPSetting.begin(); iter!=m_VecPSetting.end(); ++iter )
    {
     if(shmdt(*iter) == -1)
        {
            return false;
            perror(" detach error ");
         }
     }    
  //  删除共享内存
      for( vector<int>::iterator iter=m_VecShm_id.begin(); iter!=m_VecShm_id.end(); ++iter )
     {
     if (shmctl( *iter , IPC_RMID , NULL ) == -1)
        {
         perror(" delete error ");  
         return false;
        }
     }
      return true;

}

writetest.cpp

#include "MemControl.h"
int main()
{
    MemControl A;
     A.Init();
    A.WriteMem(); 
    
}

readtest.cpp

#include "MemControl.h"
int main()
{
    MemControl A;
   A.Init();
    A.ReadMem(); 
    
}

 

clearmem.cpp

#include "MemControl.h"
int main()
{
    MemControl A;
     A.Init();
    A.ClearMem(); 
    
}

 

以上是用shm相关函数来控制内存,读写进程共享内存,达到128M的空间

 

1、系统V共享内存中的数据,从来不写入到实际磁盘文件中去;而通过mmap()映射普通文件实现的共享内存通信可以

     指定何时将数据写入磁盘文件中。 注:系统V共享内存机制实际是通过shm文件系统中的文件

     实现的,shm文件系统的安装点在交换分区上,系统重新引导后,所有的内容都丢失。


2、系统V共享内存是随内核持续的,即使所有访问共享内存的进程都已经正常终止,共享内存区仍然存在(除非显式删

      除共享内存),在内核重新引导之前,对该共享内存区域的任何改写操作都将一直保留。


3、通过调用mmap()映射普通文件进行进程间通信时,一定要注意考虑进程何时终止对通信的影响。而通过系统V共享

     内存实现通信的进程则不然。

以上是 http://blog.csdn.net/icechenbing/article/details/7715472

的总结

 

dev/shm/是linux下一个非常有用的目录,因为这个目录不在硬盘上,而是在内存里。因此在linux下,就不需要大费周折去建 ramdisk,直接使用/dev/shm/就可达到很好的优化效果。/dev /shm/需要注意的一个是容量问题,在linux下,它默认最大为内存的一半大小,使用df -h命令可以看到。但它并不会真正的占用这块内存,如果/dev/shm/下没有任何文件,它占用的内存实际上就是0字节;如果它最大为1G,里头放有 100M文件,那剩余的900M仍然可为其它应用程序所使用,但它所占用的100M内存,是绝不会被系统回收重新划分的,否则谁还敢往里头存文件呢?

 

默认系统就会加载/dev/shm ,它就是所谓的tmpfs,有人说跟ramdisk(虚拟磁盘),但不一样。象虚拟磁盘一样,tmpfs 可以使用您的 RAM,但它也可以使用您的交换分区来存储。而且传统的虚拟磁盘是个块设备,并需要一个 mkfs 之类的命令才能真正地使用它,tmpfs 是一个文件系统,而不是块设备;您只是安装它,它就可以使用了。

tmpfs有以下优势:

1,动态文件系统的大小。
2,tmpfs 的另一个主要的好处是它闪电般的速度。因为典型的 tmpfs 文件系统会完全驻留在 RAM 中,读写几乎可以是瞬间的。
3,tmpfs 数据在重新启动之后不会保留,因为虚拟内存本质上就是易失的。所以有必要做一些脚本做诸如加载,绑定的操作。

其他详细tmpfs操作:http://www.oschina.net/question/12_79565


 

 

 

 

 

 

 

 

 

http://blog.163.com/qimo601@126/blog/static/15822093201332755551363/

QSystemSemaphore使用  

 

 

 

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值