免费注册 查看新帖 |

Chinaunix

广告
  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 3774 | 回复: 6
打印 上一主题 下一主题

[C++] 用mmap共享内存 进行进程间通信出现问题 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2008-12-30 00:58 |只看该作者 |倒序浏览
fd_map=open(path, O_CREAT|O_RDWR|O_TRUNC, 00777);
write(fd_map," ", sizeof(CPipegData));

pmap = (CPipeData*) mmap( NULL,sizeof(CPipeMsgData), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0 );


pMsg->dwPduLenth = pmap->Msgdata.msgLenth;
if(pmap->Msgdata.pMsgData && pMsg->dwPduLenth != 0)

{
    pMsg->pMsgBuf = new unsigned char[pMsg->dwPduLenth + 1];
    memcpy(pMsg->pMsgBuf, pmap->Msgdata.pMsgData, pMsg->dwPduLenth);
    pMsg->pMsgBuf[pMsg->dwPduLenth] = '\0';
}



我的问题:
1、为什么要加上write(p_msg_map," ", sizeof(CPipeMsgData));进程才能对内存进行写操作?
2、还有我的代码把数据用memcpy到一个对象的成员中,然后把pMsg 的指针的指针保存到msgTempList中,这样push_back多个后,一次性把msgTempList中的数据全部取得,到另外一个跟msgTempList同样类型的list中,在对单个数据操作,把pmsgBuf
指向一个unsigned char* 指针,就出现段错误,但是我确定memcpy(pMsg->pMsgBuf, pmap->Msgdata.pMsgData, pMsg->dwPduLenth);中的pmap->Msgdata.pMsgData 是有数据的啊, 请各位帮我看看!谢谢

论坛徽章:
0
2 [报告]
发表于 2008-12-30 11:11 |只看该作者

回复 #1 datastreamcn 的帖子

->fd_map=open(path, O_CREAT|O_RDWR|O_TRUNC, 00777);
path是啥?普通文件?已经存在了?
->write(fd_map," ", sizeof(CPipegData));
有问题," "才一个字节,sizeof(CPipegData)是多少?
第二个问题太长了,看了眼花...,你先仔细man mmap看看帮助吧。

论坛徽章:
0
3 [报告]
发表于 2008-12-30 15:59 |只看该作者
先谢谢楼上兄弟,
1、 path是普通文件,我认为存在与否应该没有关系。
  write是要写上数据。

  2、我的第二个问题我确认是在对stl 中的list操作问题上,就是先把数据 添加到一个CMSGLIST list1,list2, 然后从list1中取出数据到list2中来,然后对里面的数据进行访问就失败,查看是NULL。
我能确定memcpy(pMsg->pMsgBuf, pmap->Msgdata.pMsgData, pMsg->dwPduLenth);  中的pmap->Msgdata.pMsgData是有数据的,操作后,
  (1)在addMsg(pmsg) 函数中 list1.push_back(pMsg )   添加
   (2)在getAll(CMSGLIST & list2)  中把list1中的数据拷贝到list2中,然后访问list2中第一个元素的pMsgBuf ,段错误,pMsgBuf为NULL。

附注:

class CMsg
{
     ..........
     int    dwPduLenth;
     unsigned char *pMsgBuf;
}
typedef std::list<CMsg *>  CMSGLIST;


请各位不吝指教?谢谢

论坛徽章:
0
4 [报告]
发表于 2008-12-30 17:22 |只看该作者
谢谢各位兄弟了!
问题2已经解决,是我自己不小心,没有赋值。

  对于问题1,

CPipegData msgData;
fd_map=open(path, O_CREAT|O_RDWR|O_TRUNC, 00777);
write(fd_map, (void*)&msgData, sizeof(CPipegData));  

pmap = (CPipeData*) mmap( NULL,sizeof(CPipeMsgData), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0 );



我也看了mmap的Manual上的,感觉还是不怎么清楚, 我写了个小测试程序,如果屏蔽掉write 语句,就会报总线错误?
还有点不怎么明白?为什么要加上这条语句了,或者还有其他什么办法不加write语句没?

   请各位兄弟姐妹指点指点,本人在刚做linux开发,以前是在windows 下开发,再此感谢!

论坛徽章:
0
5 [报告]
发表于 2008-12-30 17:37 |只看该作者
扩大文件大小啊。或者用ftruncate来扩充你的文件。。去看看UNIX网络编程第二卷,讲得很详细了

论坛徽章:
0
6 [报告]
发表于 2008-12-30 18:23 |只看该作者
1.write函数可以预先分配sizeof(CPipeMsgData)这么大的一个文件,这样才能mmap映射上去.

论坛徽章:
0
7 [报告]
发表于 2008-12-31 00:26 |只看该作者
谢谢各位了!

因为我看到apue上面在用mmap的时候没有要write一下,还有看了帮助认为mmap函数中的第二个参数就可以直接为文件分配len长的文件。呵呵,看来以后要很仔细的看帮助文档,呵呵!
  
再次谢谢各位了!
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP